Handling Touch Event in UILabel and hooking it up to an IBAction
Solution 1
Check it out:
UILabel *label = ...
label.userInteractionEnabled = YES;
UITapGestureRecognizer *tapGesture =
[[UITapGestureRecognizer alloc] initWithTarget:self
action:@selector(labelTap)];
[label addGestureRecognizer:tapGesture];
The trick is to enable user interaction.
Solution 2
UILabel inherits from UIView which inherits from UIResponder. All UIresponder objects can handle touch events. So in your class file which knows about your view (which contains the UIlabel) implement:
-(void)touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event;
In interface builder set the UILabel's tag value. when touches occur in your touchesBegan method, check the tag value of the view to which the tag belongs:
UITouch *touch = [touches anyObject];
if(touch.view.tag == MY_TAG_VAL)
label.text = @"new text";
You connect your code in your class file with the UILabel object in interface builder by declaring your UILabel instance variable with the IBOutlet prefix:
IBOutlet UILabel *label;
Then in interface builder you can connect them up.
Solution 3
You can use a UIButton, make it transparent, i.e. custom type without an image, and add a UILabel on it (centered). Then wire up the normal button events.
Solution 4
Swift 3
You have an IBOutlet
@IBOutlet var label: UILabel!
In which you enable user interaction and add a gesture recognizer
label.isUserInteractionEnabled = true
let tapGesture = UITapGestureRecognizer(target: self, action: #selector(userDidTapLabel(tapGestureRecognizer:)))
label.addGestureRecognizer(tapGesture)
And finally, handle the tap
func userDidTapLabel(tapGestureRecognizer: UITapGestureRecognizer) {
// Your code goes here
}
Related videos on Youtube
wfbarksdale
Updated on May 22, 2020Comments
-
wfbarksdale almost 4 years
Ok, so I have a
UILabel
created in interface builder that displays some some default text of "tap to begin".When the user taps the
UILabel
I want it to trigger an IBAction method:-(IBAction)next;
which updates the text on the label to say something new.
It would be really convenient if this allowed me to simply drag a connection from my method to my label and then select touch up inside, as with a button. but alas, no cigar.so anyways, I guess my question is, am I going to have to subclass
UILabel
to get this to work? Or is there some way I can drag a button over the label, but make it 0% opaque. Or is there a simpler solution I'm missing? -
stitz almost 14 yearsI agree, the custom button type should give you a UILabel type user experience.
-
midas06 almost 14 yearsOne note, you have to make sure you check "User Interaction Enabled" in interface builder, or this won't work.
-
midas06 almost 14 yearsI hit one problem with this method. It worked fine when the view controller was loaded directly, but when i created a nav controller, pushed the controller containing the label to the nav controller and then displaying it, the touches don't seem to get to the label anymore. Any Ideas?
-
Remover almost 14 yearsif it's the same view controller class that you're pushing it should work. sounds like there may be some other little problem. maybe start another question and post some code
-
Brian Moeskau over 13 years+1, nice and simple. I had tried this before by setting a normal button to opactiy 0 which did not work, but the tip to change the type to custom worked perfectly.
-
Eiko over 13 yearsThe opacity will effect the button and all of its subviews, so opacity=0 will make the whole thing invisible.
-
Defragged over 12 yearsA similar method that doesn't require tags is to simply check if touch.view is equal to the outlet you set for the label. I prefer this, as it means I don't have to keep track of the tags.
-
James Boutcher over 11 yearsYikes. This is a hack compared to the other solutions in this thread. Use a tap gesture recognizer on a label if you want to recognize a tap gesture on a label. (See how it reads like it was meant for this?)
-
kevinl almost 11 yearsgreat solution. I recommend that you don't set any tag to be 0 because clicking anywhere else has a tag value of 0. This is because your view will most likely have a tag value of 0. Otherwise, you can set the tag of your view to something like -1 and then you can use the tag value of 0 somewhere else i.e. a button
-
learner almost 10 yearsWhat if I have multiple labels? how might I differentiate which one was tapped?
-
thedjaney almost 10 years@learner try the tag property. make sure to use labelTap: instead of labelTap. and use - (void) labelTap:(id)sender;.
-
h4labs about 9 years@thedjaney The sender is the UITapGestureRecognizer, not the UILabel
-
Admin almost 8 yearsTapGestureRecognizer is not the same as touch up inside, and loses human interface conformance and accessibility.
-
Admin almost 8 yearsThis is a far, far better solution because buttons handle touchupinside rather than just taps (begin).
-
Eiko almost 8 years@JamesBoutcher Look at the date of this question. UIGestureRecognizer was brand new (on the iPhone a few days). If you wanted to target anything older, it was not available. Today, I consider it a valid alternative. Just use the method that shows the intents best - if it really behaves like a button, use a button; if it's just some "text with a custom action not meant to be clicked regularly" take a gesture recognizer.
-
DJTano almost 8 years@h4labs you can use UITapGestureRecognizer *tapGesture = sender; then get the label tag with tapGesture.view.tag
-
POSIX-compliant over 5 yearsI had to add @objc to userDidTapLabel to get this to work. Might be a swift 4 thing.