Ocultar teclado al desplazarse UITableView


134

En mi aplicación, quiero ocultar el teclado cuando empiezo a desplazar UITableView. Busco sobre esto en Internet, y la mayoría de las respuestas son subclases UITableView (http://stackoverflow.com/questions/3499810/tapping-a-uiscrollview-to-hide-the-keyboard).

Hice una subclase pero no funciona.

#import <UIKit/UIKit.h>

@protocol MyUITableViewDelegate <NSObject>
@optional
- (void)myUITableViewTouchesBegan;
@end

@interface MyUITableView : UITableView <UITableViewDelegate, UIScrollViewDelegate> {
    id<MyUITableViewDelegate> delegate;
}
@end

archivo .m

#import "MyUITableView.h"

@implementation MyUITableView

- (void)scrollViewDidScroll:(UIScrollView *)scrollView{
    NSLog(@"delegate scrollView"); //this is dont'work
    [super scrollViewDidScroll:scrollView];
}

- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event {
    NSLog(@"delegate myUITableViewTouchesBegan"); // work only here
    [delegate myUITableViewTouchesBegan];
    [super touchesBegan:touches withEvent:event];

}

- (void)dealloc {
...

Yo uso esta clase como esta. Pero la función delegar myUITableViewTouchesBegan no funciona en ViewController

.h

#import <UIKit/UIKit.h>
#import "MyUITableView.h"

@interface FirstViewController : UIViewController <UITableViewDelegate, UISearchBarDelegate, MyUITableViewDelegate> {
    MyUITableView *myTableView;
    UISearchBar *searchBar; 
}

@property(nonatomic,retain) IBOutlet MyUITableView *myTableView;
...

.metro

- (void) myUITableViewTouchesBegan{
    NSLog(@"myUITableViewTouchesBegan");
    [searchBar resignFirstResponder];
}

Tengo algunos problemas con esta implementación:
1) myUITableViewTouchesBegan no funciona en ViewController
2) NSLog de MyUITableView.m - NSLog (@ "delegar myUITableViewTouchesBegan"); funciona solo cuando toco la mesa. ¿Cómo funciona también cuando empiezo a desplazarme?
Intento anular scrollViewDidScroll pero el comiler dijo que MyUITableVIew puede no responder en esta cadena [super scrollViewDidScroll: scrollView];

Respuestas:


144

No estoy seguro de por qué necesita subclasificar UITableView para esto.

En el controlador de vista que contiene el UITableView simple, intente agregar esto:

- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView
{
    [searchBar resignFirstResponder];
}

418

Aquí está la forma más limpia de lograr esto en iOS 7.0 y superior:

tableView.keyboardDismissMode = UIScrollViewKeyboardDismissModeOnDrag;

O descartar interactivamente al tocar:

tableView.keyboardDismissMode = UIScrollViewKeyboardDismissModeInteractive;

O en Swift:

tableView.keyboardDismissMode = .onDrag

Para descartar de forma interactiva:

tableView.keyboardDismissMode = .interactive

21
Por supuesto, este atributo también se puede establecer en el inspector de atributos para aquellos que usan plumillas y guiones gráficos.
JuJoDi

1
Amigo, enloquecí por completo, perdí esto como una actualización, todavía estaba usando la forma antigua con el protocolo que scrollview se desplazó ... ¡Gracias, amigo!
Tomás Sykora

3
Para aquellos que se olvidan, aún debe hacer que UITextfield renuncie al primer respondedor.
skyline75489

1
He estado haciendo desarrollo de iOS desde hace 3 años y no sabía sobre esto hasta ahora ... irreal.
Jacob King

¿Cómo extraño estas cosas, genial!
trampero

129

Puede hacerlo directamente en Interface Builder. Seleccione su UITableViewy abra el Inspector de atributos. En la sección Vista de desplazamiento, configure el campo Teclado en Descartar al arrastrar .

ingrese la descripción de la imagen aquí


¡Gracias, me salvaste la vida!
Sabobin

41

Solo para agregar una actualización a las respuestas anteriores. Lo siguiente funcionó para mí en Swift 1.2

tableView.keyboardDismissMode = UIScrollViewKeyboardDismissMode.OnDrag

o

tableView.keyboardDismissMode = UIScrollViewKeyboardDismissMode.Interactive

2

Con Swift 5

Para ocultar el teclado al desplazarse por TableView y detener la edición correctamente, aún necesitamos combinar dos tipos de respuestas:

  1. Configure el modo de descarte del teclado en IB (como explicó Kyle ) o en ViewDidLoad()código (como explicó Pei ) por ejemplo:
tableView.keyboardDismissMode = .onDrag
  1. Forzar el campo de texto actual a renunciar como primer respondedor (como en la respuesta de Vasily ). Solo necesitamos agregar lo siguiente a nuestra UITableViewControllerclase
    override func scrollViewDidScroll(_ scrollView: UIScrollView) {
        if !tableView.isDecelerating {
            view.endEditing(true)
        }
    }

1

Solución de trabajo sin escribir una sola línea de código en su controlador:

Como su pregunta es manejar el teclado oculto con una sola condición (en desplazamiento). Pero aquí estoy recomendando una solución para manejar el campo de texto y el teclado juntos que funciona de maravilla para UIViewController, UITableView y UIScrollView. El hecho interesante es que no necesita escribir una sola línea de código.

Aquí tienes: TPKeyboardAvoiding: una solución increíble para manejar el teclado y el desplazamiento


0

Tarea

Ocultar el teclado mediante programación cuando se desplaza UITableView en Swift 3

Detalles

xCode 8.2.1, swift 3

Solución

func scrollViewDidScroll(_ scrollView: UIScrollView) {
    if !tableView.isDecelerating {
        view.endEditing(true)
    }
}

Muestra completa

ViewController

import UIKit

class ViewController: UIViewController {

    @IBOutlet weak var tableView: UITableView!
    @IBOutlet weak var searchBar: UISearchBar!


    override func viewDidLoad() {
        super.viewDidLoad()
        tableView.dataSource = self
        tableView.delegate = self
    }
}

// MARK: - UITableViewDataSource

extension ViewController: UITableViewDataSource {

    func numberOfSections(in tableView: UITableView) -> Int {
        return 1
    }

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return 100
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell =  UITableViewCell(style: .subtitle, reuseIdentifier: nil)
        cell.textLabel?.text = "Title"
        cell.detailTextLabel?.text = "\(indexPath)"
        return cell
    }
}

// MARK: - UITableViewDelegate

extension ViewController: UITableViewDelegate {

    func scrollViewDidScroll(_ scrollView: UIScrollView) {
        if !tableView.isDecelerating {
            view.endEditing(true)
        }
    }
}

StoryBoard

<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="11762" systemVersion="16D32" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" colorMatched="YES" initialViewController="BYZ-38-t0r">
    <device id="retina4_7" orientation="portrait">
        <adaptation id="fullscreen"/>
    </device>
    <dependencies>
        <deployment identifier="iOS"/>
        <plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="11757"/>
        <capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
    </dependencies>
    <scenes>
        <!--View Controller-->
        <scene sceneID="tne-QT-ifu">
            <objects>
                <viewController id="BYZ-38-t0r" customClass="ViewController" customModule="stackoverflow_4399357" customModuleProvider="target" sceneMemberID="viewController">
                    <layoutGuides>
                        <viewControllerLayoutGuide type="top" id="y3c-jy-aDJ"/>
                        <viewControllerLayoutGuide type="bottom" id="wfy-db-euE"/>
                    </layoutGuides>
                    <view key="view" contentMode="scaleToFill" id="8bC-Xf-vdC">
                        <rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
                        <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
                        <subviews>
                            <searchBar contentMode="redraw" translatesAutoresizingMaskIntoConstraints="NO" id="wU1-dV-ueB">
                                <rect key="frame" x="0.0" y="20" width="375" height="44"/>
                                <textInputTraits key="textInputTraits"/>
                            </searchBar>
                            <tableView clipsSubviews="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" keyboardDismissMode="interactive" dataMode="prototypes" style="plain" separatorStyle="default" rowHeight="44" sectionHeaderHeight="28" sectionFooterHeight="28" translatesAutoresizingMaskIntoConstraints="NO" id="L52-4c-UtT">
                                <rect key="frame" x="0.0" y="64" width="375" height="603"/>
                                <color key="backgroundColor" white="1" alpha="1" colorSpace="calibratedWhite"/>
                            </tableView>
                        </subviews>
                        <color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
                        <constraints>
                            <constraint firstItem="wU1-dV-ueB" firstAttribute="bottom" secondItem="L52-4c-UtT" secondAttribute="top" id="0WF-07-qY1"/>
                            <constraint firstAttribute="trailing" secondItem="wU1-dV-ueB" secondAttribute="trailing" id="3Mj-h0-IvO"/>
                            <constraint firstItem="wU1-dV-ueB" firstAttribute="leading" secondItem="L52-4c-UtT" secondAttribute="leading" id="8W5-9j-2Rg"/>
                            <constraint firstItem="wU1-dV-ueB" firstAttribute="trailing" secondItem="L52-4c-UtT" secondAttribute="trailing" id="crK-dR-UYf"/>
                            <constraint firstItem="wU1-dV-ueB" firstAttribute="leading" secondItem="8bC-Xf-vdC" secondAttribute="leading" id="mPe-bp-Dxw"/>
                            <constraint firstItem="L52-4c-UtT" firstAttribute="bottom" secondItem="wfy-db-euE" secondAttribute="top" id="oIo-DI-vLh"/>
                            <constraint firstItem="wU1-dV-ueB" firstAttribute="top" secondItem="y3c-jy-aDJ" secondAttribute="bottom" id="tVC-UR-PA4"/>
                        </constraints>
                    </view>
                    <connections>
                        <outlet property="searchBar" destination="wU1-dV-ueB" id="xJf-bq-4t9"/>
                        <outlet property="tableView" destination="L52-4c-UtT" id="F0T-yb-h5r"/>
                    </connections>
                </viewController>
                <placeholder placeholderIdentifier="IBFirstResponder" id="dkx-z0-nzr" sceneMemberID="firstResponder"/>
            </objects>
            <point key="canvasLocation" x="-79.200000000000003" y="137.18140929535232"/>
        </scene>
    </scenes>
</document>

Resultado

ingrese la descripción de la imagen aquí


0

Después de iOS 7, puedes usar la propiedad tableview

Swift 3.0+

myTableView.keyboardDismissMode = UIScrollViewKeyboardDismissMode.OnDrag

C objetivo

myTableView.keyboardDismissMode = UIScrollViewKeyboardDismissModeOnDrag;

Para versiones anteriores, la implementación del delegado de vista de desplazamiento podría funcionar.

func scrollViewDidScroll(_ scrollView: UIScrollView) {
        view.endEditing(true)
}
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.