Antworten:
Sie können beginnen, indem Sie die UILongPressGestureRecognizer
Instanz erstellen und an die Schaltfläche anhängen .
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(longPress:)];
[self.button addGestureRecognizer:longPress];
[longPress release];
Implementieren Sie dann die Methode, die die Geste verarbeitet
- (void)longPress:(UILongPressGestureRecognizer*)gesture {
if ( gesture.state == UIGestureRecognizerStateEnded ) {
NSLog(@"Long Press");
}
}
Dies wäre nun der grundlegende Ansatz. Sie können auch die Mindestdauer der Druckmaschine und die Toleranz für Fehler festlegen. Beachten Sie auch, dass die Methode einige Male aufgerufen wird, wenn Sie die Geste erkannt haben. Wenn Sie also am Ende etwas tun möchten, müssen Sie den Status überprüfen und damit umgehen.
if(gesture.state == UIGestureRecognizerStateBegan)
, da der Benutzer erwartet, dass etwas passiert, wenn er noch drückt (der Status Began), und nicht, wenn er loslässt (Beendet).
Als Alternative zur akzeptierten Antwort kann dies in Xcode mit Interface Builder sehr einfach durchgeführt werden.
Ziehen Sie einfach einen Gestenerkenner für langes Drücken aus der Objektbibliothek und legen Sie ihn oben auf der Schaltfläche ab, auf der Sie die Aktion für langes Drücken ausführen möchten.
Verbinden Sie als Nächstes eine Aktion aus dem gerade hinzugefügten Long Press Gesture Recognizer mit Ihrem Ansichts-Controller und wählen Sie den Absender aus, der vom Typ sein soll UILongPressGestureRecognizer
. IBAction
Verwenden Sie im Code dieses Codes Folgendes, das dem in der akzeptierten Antwort vorgeschlagenen Code sehr ähnlich ist:
In Ziel-C :
if ( sender.state == UIGestureRecognizerStateEnded ) {
// Do your stuff here
}
Oder in Swift :
if sender.state == .Ended {
// Do your stuff here
}
Aber ich muss zugeben, dass ich nach dem Versuch den Vorschlag von @shengbinmeng als Kommentar der akzeptierten Antwort vorziehe, die verwendet werden sollte:
In Ziel-C :
if ( sender.state == UIGestureRecognizerStateBegan ) {
// Do your stuff here
}
Oder in Swift :
if sender.state == .Began {
// Do your stuff here
}
Der Unterschied besteht darin, dass Ended
Sie beim Heben des Fingers den Effekt des langen Drucks sehen. Mit sehen Began
Sie den Effekt des langen Drucks, sobald der lange Druck vom System erfasst wird, noch bevor Sie den Finger vom Bildschirm heben.
Ich habe die zusätzliche Modifikation der Verwendung vorgenommen, UIGestureRecognizerState.Began
anstatt .Ended
dass dies wahrscheinlich das ist, was die meisten Benutzer natürlich erwarten würden. Probieren Sie beide aus und überzeugen Sie sich selbst.
import UIKit
class ViewController: UIViewController {
@IBOutlet weak var button: UIButton!
override func viewDidLoad() {
super.viewDidLoad()
// add gesture recognizer
let longPress = UILongPressGestureRecognizer(target: self, action: #selector(longPress(_:)))
self.button.addGestureRecognizer(longPress)
}
func longPress(gesture: UILongPressGestureRecognizer) {
if gesture.state == UIGestureRecognizerState.began {
print("Long Press")
}
}
@IBAction func normalButtonTap(sender: UIButton) {
print("Button tapped")
}
}
Versuche dies:
Hinzufügen einer Schaltfläche viewDidLoad:
wie unten
-(void)viewDidLoad {
UIButton *btn = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[btn setTag:1]; //you can set any integer value as tag number
btn.title = @"Press Me";
[btn setFrame:CGRectMake(50.0, 50.0, 60.0, 60.0)];
// now create a long press gesture
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc]initWithTarget:self action:@selector(longPressTap:)];
[btn addGestureRecognizer:longPress];
}
Rufen Sie nun die Gestenmethode so auf
-(void)longPressTap:(id)sender {
UIGestureRecognizer *recognizer = (UIGestureRecognizer*) sender
// Recogniser have all property of button on which you have clicked
// Now you can compare button's tag with recogniser's view.tag
// View frame for getting the info on which button the click event happened
// Then compare tag like this
if(recognizer.view.tag == 1) {
// Put your button's click code here
}
// And you can also compare the frame of your button with recogniser's view
CGRect btnRect = CGRectMake(50.0, 50.0, 60.0, 60.0);
if(recogniser.view.frame == btnRect) {
//put your button's click code here
}
// Remember frame comparing is alternative method you don't need to write frame comparing code if you are matching the tag number of button
}
recognizer.view.tag
gibt mir falsches Tag von UIButton angeklickt. Irgendeine Lösung?
Ich denke du brauchst meine Lösung.
Sie sollten diesen Code für einmaliges Drücken haben
- (IBAction)buttonDidPress:(id)sender {
NSLog("buttonDidPress");
}
Fügen Sie zunächst eine lange Druckgeste zur Taste hinzu
- (void)viewWillAppear:(BOOL)animated
{
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(buttonDidLongPress:)];
[self.button addGestureRecognizer:longPress];
}
Rufen Sie dann wiederholt ein einzelnes Presseereignis auf, wenn eine lange Druckgeste erkannt wird.
- (void)buttonDidLongPress:(UILongPressGestureRecognizer*)gesture
{
switch (gesture.state) {
case UIGestureRecognizerStateBegan:
{
self.timer = [NSTimer timerWithTimeInterval:0.1 target:self selector:@selector(buttonDidPress:) userInfo:nil repeats:YES];
NSRunLoop * theRunLoop = [NSRunLoop currentRunLoop];
[theRunLoop addTimer:self.timer forMode:NSDefaultRunLoopMode];
}
break;
case UIGestureRecognizerStateEnded:
{
[self.timer invalidate];
self.timer = nil;
}
break;
default:
break;
}
}
UIGestureRecognizer
das viewWillAppear
Ereignis während des Lebenszyklus nicht hinzufügen, da bei jeder Anzeige eine weitere Gestenerkennung hinzugefügt wird. Dies sollte in einer privaten Methode erfolgen, die während der Initialisierung aufgerufen wird.
Für Swift 4 muss die "func longPress" geändert werden, damit es funktioniert:
import UIKit
class ViewController: UIViewController {
@IBOutlet weak var button: UIButton!
override func viewDidLoad() {
super.viewDidLoad()
// add guesture recognizer
let longPress = UILongPressGestureRecognizer(target: self, action: #selector(longPress(_:)))
self.button.addGestureRecognizer(longPress)
}
@objc func longPress(_ guesture: UILongPressGestureRecognizer) {
if guesture.state == UIGestureRecognizerState.began {
print("Long Press")
}
}
@IBAction func normalButtonTap(sender: UIButton) {
print("Button tapped")
}
}
Einzeilige Antwort ohne Gesten:
[btn addTarget:self action:@selector(handleTouch:) forControlEvents:UIControlEventTouchDown | UIControlEventTouchUpInside | UIControlEventTouchUpOutside];
Details:
Dies löst Ihr Ziel bei drei Ereignissen aus: 1- Sobald der Finger die Taste berührt : UIControlEventTouchDown
. Dies erfasst den Start langer Druckvorgänge. 2 & 3- Wenn der Benutzer den Finger hebt: UIControlEventTouchUpOutside
& UIControlEventTouchUpInside
. Dies erfasst das Ende der Benutzerpresse.
Hinweis: Dies funktioniert gut, wenn Sie sich nicht um die zusätzlichen Informationen kümmern, die vom Gestenerkenner bereitgestellt werden (z. B. Ort der Berührung usw.).
Sie können bei Bedarf weitere Zwischenereignisse hinzufügen. Alle finden Sie hier https://developer.apple.com/documentation/uikit/uicontrolevents?language=objc .
In Storyboard: Verbinden Sie Ihre Schaltfläche mit den 3 Ereignissen, nicht nur mit dem Standardereignis, das Storyboard auswählt (Touch Up Inside).
Ich habe einen untergeordneten UIButton für meine App, daher habe ich meine Implementierung herausgezogen. Sie können dies zu Ihrer Unterklasse hinzufügen oder es kann genauso einfach neu codiert werden wie eine UIButton-Kategorie.
Mein Ziel war es, den langen Druck auf meine Schaltfläche zu übertragen, ohne meine View Controller mit dem gesamten Code zu überladen. Ich habe beschlossen, dass die Aktion aufgerufen werden soll, wenn der Status der Gestenerkennung beginnt.
Es kommt eine Warnung heraus, die ich nie gelöst habe. Sagt, es ist ein mögliches Leck, dachte, ich habe den Code getestet und es leckt nicht.
@interface MYLongButton ()
@property (nonatomic, strong) UILongPressGestureRecognizer *gestureRecognizer;
@property (nonatomic, strong) id gestureRecognizerTarget;
@property (nonatomic, assign) SEL gestureRecognizerSelector;
@end
@implementation MYLongButton
- (void)addLongPressTarget:(CGFloat)interval target:(id)target action:(SEL)selector
{
_gestureRecognizerTarget = target;
_gestureRecognizerSelector = selector;
_gestureRecognizer = [[UILongPressGestureRecognizer alloc]initWithTarget:self action:@selector(handleLongPressGestureRecognizer:)];
_gestureRecognizer.minimumPressDuration = interval;
[self addGestureRecognizer:_gestureRecognizer];
}
- (void)handleLongPressGestureRecognizer:(UIGestureRecognizer *)gestureRecognizer
{
if (gestureRecognizer.state == UIGestureRecognizerStateBegan) {
NSAssert([_gestureRecognizerTarget respondsToSelector:_gestureRecognizerSelector], @"target does not respond to selector");
self.highlighted = NO;
// warning on possible leak -- can anybody fix it?
[_gestureRecognizerTarget performSelector:_gestureRecognizerSelector withObject:self];
}
}
Um die Aktion zuzuweisen, fügen Sie diese Zeile Ihrer viewDidLoad-Methode hinzu.
[_myLongButton addLongPressTarget:0.75 target:self selector:@selector(longPressAction:)];
Die Aktion sollte wie alle IBActions definiert werden (ohne die IBAction).
- (void)longPressAction:(id)sender {
// sender is the button
}
Keiner arbeitete daher Longpress - Code in Ich habe versucht , zu schreiben IBAction
oder Button - Klick aus storyboard
in Controller
anstelle des Schreibens inviewDidLoad
- (IBAction)btnClick:(id)sender {
tag = (int)((UIButton *)sender).tag;
// Long press here instead of in viewDidLoad
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(longPress:)];
longPress.cancelsTouchesInView = NO;
[sender addGestureRecognizer:longPress];
}