UIButton selected state change image - ios

I know this should be very simple but since I really have looked around here and on google without getting my code to work I will ask. Yes, I have checked related questions and they does not work...
I simply want to change the image of the button when it is pressed.
This is my header file:
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController
#property (strong, nonatomic) IBOutlet UIButton *myButton;
#end
And my implementation file:
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
[self.myButton setImage:[UIImage imageNamed:#"normal.png"] forState:UIControlStateNormal];
[self.myButton setImage:[UIImage imageNamed:#"selected.png"] forState:UIControlStateSelected];
}
#end
The button is built and connected in Main.storyBoard and I have also tried to do it in the attributes inspector but neither way worked!
Please note that I am not looking for how to do highlighted state but selected.

I believe what you need to do is set the button's state to selected when the button is tapped. Probably something like this:
-(IBAction)buttonTapped:(id)sender {
if(self.myButton.selected)
[self.mybytton setSelected:NO];
else
[self.mybutton setSelected:YES];
}

You need to set the image for each state from your interface builder and you don't need to add a code if you want :
Select the State Config to Default and then choose an image
Select the State Config to Selected and then choose an image
And now to test each state of the button:
You can do the same for background image just select the parameter "Background"

Change to whatever image you need in the IB builder in the State Config and add an action to that button and in that add this line of code as said by #Aladin.
#IBAction func btnPressed (_ sender: UIButton) {
// If you want to change it for selected state when tapped.
sender.isSelected = !sender.isSelected
}

Do you have a method for when the button is clicked? If yes, put this below lines in there:
[self.myButton setSelected:YES];
[self.myButton setImage:[UIImage imageNamed:#"selected.png"] forState:UIControlStateSelected];

Why not try to set background image default to "normal.png";
[self.mybutton setBackgroundImage:[UIImage imageNamed:#"normal.png"]];
And switch to "selected.png" when perform the button.
[self.mybutton setBackgroundImage:[UIImage imageNamed:#"selected.png"]];

Related

Changing button text of different button on button click

I have 3 buttons in my storyboard and ViewController that are working as expected:
- (IBAction)button0:(id)sender {
[sender setTitle:#"btn0 pressed" forState:UIControlStateNormal];
}
- (IBAction)button1:(id)sender {
[sender setTitle:#"btn1 pressed" forState:UIControlStateNormal];
}
- (IBAction)button2:(id)sender {
[sender setTitle:#"btn2 pressed" forState:UIControlStateNormal];
}
I have a fourth button that, when pressed, I would like to change the displayed text of button0-2 to an empty string.
- (IBAction)resetAllButtons:(id)sender {
//In Android this code would be something like:
//Button btn0 = (Button) findViewById(R.id.button0);
//btn0.setText(" ");
}
How do I do this? I've found many ways to change the button text, but only of the current button being pressed. Can I target all the buttons by id somehow?
Figured it out (although still not clear on why it works?)
I connected button0 as an IBOutlet in my ViewController.h file.
#property (weak, nonatomic) IBOutlet UIButton *button0;
From there I was able to reference it in my ViewController.m file using
[self.button0 setTitle:#" " forState:UIControlStateNormal];
But why am I able to do that? I thought that if I declared
- (IBAction)button0:(id)sender;
in my ViewControler.h file that I couldn't also have an outlet connected to the same object? Thanks for reading either way.

Alternative option of UIButton addTarget:action:forControlEvents: method in IOS

I know that this question has been asked so many times but i want to pass a custom object as an argument on clicking a button.
UIButton addTarget:action:forControlEvents: doesn't allow us to do that but it is important for me so I can do further on the basis of custom objects.
If an alternative for add target is possible, so please give the solution.
The code is like this:
Custom Object:
HeaderData *cell ;
Button:
_forward =[UIButton buttonWithType:UIButtonTypeRoundedRect];
[_forward setTitle:#"F" forState:UIControlStateNormal];
_forward.frame = CGRectMake(300, (_CELL_HEIGHT-_LABEL_HEIGHT)/2, 10 ,_LABEL_HEIGHT);]
[_forward addTarget:web action:#selector(functionName:) forControlEvents:UIControlEventTouchUpInside];
and the function which is called on clicking the UIButton _forward is:
-(void)functionName:(UIButton *)sender{
//code for further programming on the basis of cell.
}
You could make a custom subclass of UIButton:
#interface CustomDataButton : UIButton
#property (nonatomic, strong) id userData;
#end
Then in functionName, you can pull the data back out:
-(void)functionName:(UIButton *)sender
{
if ([sender isKindOfClass:[CustomDataButton class]])
{
id customData = ((CustomDataButton *) sender).userData;
}
}
caveat: written without an IDE. Watch out for typos etc.

objective-c how to modify button text of a button different than the button pressed

This is what I would use to change the text if it were the same method but I want to change it from a different method.
-(IBAction)StartTimer:(id)sender {
[sender setTitle:#"Stop" forState:UIControlStateNormal];
}
-(IBAction)ResetAllData:(id)sender {
[(NEED THIS PIECE) setTitle:#"Start" forState:UIControlStateNormal];
}
There are several ways of doing it. Perhaps the simplest one is to make an IBOutlet for the other button, give it a name (say, anotherButton), attach it in the storyboard, and call it directly, like this:
-(IBAction)ResetAllData:(id)sender {
[anotherButton setTitle:#"Start" forState:UIControlStateNormal];
}
An alternative would be to add a tag * to the button in question (say, 123), and then reference it by its numeric tag, like this:
-(IBAction)ResetAllData:(id)sender {
[[self viewWithTag:123] setTitle:#"Start" forState:UIControlStateNormal];
}
* To add a tag, select the button in the interface builder, open its properties, find the tag, and type in the desired value in the text field.
Make the UIButton you want to change the title of a property of the class, then you will have direct access to it. For example, the following could be put in your ViewController's .m file.
#interface ViewController ()
#property (nonatomic) UIButton *otherButton;
#end
Then in your first IBAction, just set the title of otherButton.
-(IBAction)ResetAllData:(id)sender {
[self.otherButton setTitle:#"Start" forState:UIControlStateNormal];
}

iOS >> Why isn't it Possible to Set UIControls Properties Directly in Code When Approaching Them via "sender"?

Let's say that I wish to approach a certain UIControl in a certain method that it triggers - I can send the method a pointer to the UIControl using "sender". but then, for some reason, I cannot approach sender's properties directly and have to use the setX:forState: methods. If I approach the properties directly, I get no error or warning; it simply does nothing...
Here's an example:
h. file...
#interface MYViewController : UIViewController
#property (weak, nonatomic) IBOutlet UIButton *dButton; //connected to a UIButton in IB
-(IBAction)dButtonClick:(UIButton*)sender; //connected to the same UIButton in IB
#end
then...
m. file...
- (void)viewDidLoad
{
[super viewDidLoad];
self.dButton.titleLabel.textColor = [UIColor greenColor]; //this is working...
}
-(IBAction)dButtonClick:(UIButton*)sender
{
sender.titleLabel.textColor = [UIColor redColor]; //this is not working...
self.dButton.titleLabel.textColor = [UIColor redColor]; //this is also not working...
[sender setTitleColor:[UIColor redColor] forState:UIControlStateNormal]; //only this is working.
//But why?!?!?
}
I tried to search for some info about the way these items work, but couldn't find anything that explains the logic behind it clear enough.
Any help would be... well... helpful...
This:
sender.titleLabel.textColor
And this:
[sender setTitleColor:[UIColor redColor] forState:UIControlStateNormal];
Are different not just because of the dot notation but also because of the state. The button has different colours for each state so any colour set directly will be overridden by the colour for the state.
This line:
self.dButton.titleLabel.textColor = [UIColor redColor];
Could be the same issue or you may just not have connected the outlet.

How to Reference UIImageView (Xcode iOS)

I've just started learning the basics of Xcode and Objective C and I am making a basic torch app as a starting point.
I've already picked up most of the basics of things, but I don't know how to make a reference to another element from an separate action (I have no idea if this terminology is correct).
For example:
- (IBAction)screenButtonClicked:(id)sender {
UIButton *button = (UIButton *)sender;
if (_ScreenOnOff) {
[self.view setBackgroundColor:[UIColor blackColor]];
[button setTitle:#"Screen (Off)" forState: UIControlStateNormal];
}
else {
[self.view setBackgroundColor:[UIColor whiteColor]];
[button setTitle:#"Screen (On)" forState: UIControlStateNormal];
}
_ScreenOnOff = !_ScreenOnOff;
}
I have a button on the storyboard which is linked to that, and I have a UIImageView which I want to show and hide (depending on the if's).
I've looked everywhere about how to do this and put it as many ways as I can into Google, but no luck.
This might be a baby step in Objective C, but please help as it will teach me.
Thanks in advance.
Declare an IBOutlet for the UIImageView in the header file:
#property (weak) IBOutlet UIImageView *myImageView;
After that, connect the UIImageView to this IBOutlet in Interface Builder.
Then, you can reference (and hide it) like:
self.myImageView.hidden = _ScreenOnOff;
in your implementation file.
See also: Creating and Connecting an Outlet
This action is probably owned by your view controller. If your view controller has a UIImageView property named 'imageView' you can access it from inside your action just like you're doing with the _ScreenOnOff.
To hide your image view you could do something like this:
self.imageView.hidden = YES;
Note that it is important to use self.imageView and self.ScreenOnOff instead of accessing directly the property by _imageView. When you declare a property in your class (be it an IBOutlet or not) the compiler synthesizes accessor methods to that property (get and sets). So when you call self.ScreenOnOff it would be the similar of doing [self ScreenOnOff].
The only places where you will access the property directly by '_' is inside init and dealloc methods. '- (void) viewDidLoad' is on type of init method. I guess you want something like this:
- (IBAction)screenButtonClicked:(id)sender {
UIButton *button = (UIButton *)sender;
if (self.ScreenOnOff) {
[self.view setBackgroundColor:[UIColor blackColor]];
[button setTitle:#"Screen (Off)" forState: UIControlStateNormal];
self.imageView.hidden = YES;
}
else {
[self.view setBackgroundColor:[UIColor whiteColor]];
[button setTitle:#"Screen (On)" forState: UIControlStateNormal];
self.imageView.hidden = NO;
}
self.ScreenOnOff = !self.ScreenOnOff;
}
I hope that helps.

Resources