IOS/Objective-C: Animate Image Change in UIBarButtonItem - ios

I am trying to create an effect where a custom image in a UIBarButtonItem changes to another image. So far, I have been able to get the first image to dissolve with the following code. Can anyone suggest how I could get the second image to fade in at the same time?
//Create barbuttonitem in viewwillappear
UIButton *b = [UIButton buttonWithType:UIButtonTypeCustom];
[b setFrame:CGRectMake(12, 0, 22, 22)];
[b addTarget:self action:#selector(menuButtonPressed:) forControlEvents:UIControlEventTouchUpInside];
[b setImage:[UIImage imageNamed:#"firstimage.png"] forState:UIControlStateNormal];
UIBarButtonItem * myBarButton = [[UIBarButtonItem alloc] initWithCustomView:b];
//Animate in viewDidAppaer
[UIView animateWithDuration:1.0
delay:1.0
options:UIViewAnimationOptionCurveEaseIn
animations:^{
self.myBarButton.customView.alpha = 0;
}
completion:^(BOOL finished) {
UIImage *secondImage = [UIImage imageNamed:#"menu2.png"];
[self.myBarButton setImage:secondImage];//THis does not change image
self.myBarButton.customView.alpha = 1;//no animation
}];

You can use something like this
[UIView transitionWithView:self.myBarButton
duration:0.3
options:UIViewAnimationOptionTransitionCrossDissolve
animations:^{ [self.myBarButton setImage:secondImage];}
completion:nil];

Try this code
#interface ViewController ()
{
UIBarButtonItem * myBarButton;
NSTimer *time;
UIButton *b;
}
#end
#implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
b = [UIButton buttonWithType:UIButtonTypeCustom];
[b setFrame:CGRectMake(12, 0, 22, 22)];
[b addTarget:self action:#selector(menuButtonPressed:) forControlEvents:UIControlEventTouchUpInside];
[b setImage:[UIImage imageNamed:#"AddPlus_Yellow.png"] forState:UIControlStateNormal];
myBarButton = [[UIBarButtonItem alloc] initWithCustomView:b];
self.navigationItem.rightBarButtonItem=myBarButton;
time = [NSTimer scheduledTimerWithTimeInterval: 2.0 target: self selector:#selector(onTick:) userInfo: nil repeats:NO];
// Do any additional setup after loading the view, typically from a nib.
}
-(void)onTick:(NSTimer *)timer {
[b setImage:[UIImage imageNamed:#"filter.png"] forState:UIControlStateNormal];
[time invalidate];
}

Related

How to remove UIBarButtonItem tintColor animation on iOS?

I have a BarButtonItem animation here:
[UIView animateWithDuration:AnimDurationTintColorHint delay:0 options:UIViewAnimationOptionRepeat | UIViewAnimationOptionAutoreverse animations:^{
[view performSelector:#selector(setTintColor:) withObject:UIColor.blackColor];
} completion:^(BOOL finished) {
........
}];
because UIBarButtonItem has no layer property, I can't use .layer removeAllAnimations to stop the endless animation assigned.
How to remove that?
You have to take leftBarButtonItem or rightBarButtonItem and then set enabled property of UIBarButtonItem to NO.
UIImage *img = [UIImage imageNamed:#"your image"];
UIButton *btnMenu = [UIButton buttonWithType:UIButtonTypeCustom];
btnMenu.frame = CGRectMake( 10, 0, img.size.width, img.size.height);
[btnMenu addTarget:self action:#selector(handleBack:) forControlEvents:UIControlEventTouchUpInside];
[btnMenu setImage:img forState:UIControlStateNormal];
UIBarButtonItem *backButton = [[UIBarButtonItem alloc] initWithCustomView:btnMenu];
self.navigationItem.leftBarButtonItem = backButton;
self.navigationItem.leftBarButtonItem.enabled = NO;

Show a UIViewController as Alert View in iOS

I'm trying to create a custom Alert View similar to this
I want to use a View Controller as the alert because the 'X' button on the top left corner must be there, and neither a regular UIAlertController or any pod I found can help me with that.
How can I achieve this?
Thank you.
For showing viewController as UIAlertView try this
SecondViewController *secondViewController = [[UIStoryboard storyboardWithName:#"Main" bundle:[NSBundle mainBundle]] instantiateViewControllerWithIdentifier:#"SecondViewController"];
secondViewController.view.frame = self.view.frame;
[self.view addSubview:secondViewController.view];
secondViewController.view.transform = CGAffineTransformMakeScale(0.01, 0.01);
[UIView animateWithDuration:0.2 delay:0 options:UIViewAnimationOptionCurveEaseOut animations:^{
secondViewController.view.transform = CGAffineTransformIdentity;
} completion:^(BOOL finished){
}];
try this..
#interface alertViewController ()
{
UILabel *labelTitle;
UIView *viewToShow,*viewAlert;
}
#end
#implementation alertViewController
- (void)viewDidLoad
{
[super viewDidLoad];
viewToShow = [[UIView alloc]initWithFrame:CGRectMake(0,0, 165*2, 400)];
[viewToShow setBackgroundColor:[UIColor whiteColor]];
[viewToShow setOpaque:NO];
[self.navigationController.view addSubview:viewToShow];
labelTitle = [[UILabel alloc]initWithFrame:CGRectMake(10, 10, 165*2, 30)];
[[labelTitle layer] setCornerRadius:14];
labelTitle.text=#"TITLE";
[labelTitle setTextAlignment:NSTextAlignmentCenter];
[viewToShow addSubview:labelTitle];
UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[button addTarget:self
action:#selector(cancelButtonAction:)
forControlEvents:UIControlEventTouchUpInside];
[button setTitle:#"X" forState:UIControlStateNormal];
[button.titleLabel setFont:[UIFont fontWithName:#"helvetica-neue" size:20]];
button.frame = CGRectMake(5,5,30, 40.0);
[viewToShow addSubview:button];
UITextView *textView=[[UITextView alloc]initWithFrame:CGRectMake(10, 60,viewToShow.frame.size.width-20, 250)];
[textView setBackgroundColor:[UIColor lightGrayColor]];
[viewToShow addSubview:textView];
UIButton *button1 = [UIButton buttonWithType:UIButtonTypeRoundedRect];
[button1 addTarget:self
action:#selector(cancelButtonAction:)
forControlEvents:UIControlEventTouchUpInside];
[button1 setTitle:#"Continue" forState:UIControlStateNormal];
button1.frame = CGRectMake((viewToShow.frame.size.width/2)-40,viewToShow.frame.size.height-40,80,40);
[viewToShow addSubview:button1];
[[viewToShow layer] setCornerRadius:14];
CGPoint centerForCustomExportView;
if (UIDeviceOrientationIsLandscape((UIDeviceOrientation)[[UIApplication sharedApplication] statusBarOrientation]))
{
centerForCustomExportView = CGPointMake(([[UIScreen mainScreen]bounds].size.height>[[UIScreen mainScreen]bounds].size.width?[[UIScreen mainScreen]bounds].size.height:[[UIScreen mainScreen]bounds].size.width)/2, (([[UIScreen mainScreen]bounds].size.height>[[UIScreen mainScreen]bounds].size.width?[[UIScreen mainScreen]bounds].size.width:[[UIScreen mainScreen]bounds].size.height)/2));
}
else
{
centerForCustomExportView = CGPointMake([[UIScreen mainScreen]bounds].size.width/2, ([[UIScreen mainScreen]bounds].size.height-self.navigationController.navigationBar.frame.size.height)/2);
}
viewToShow.center = centerForCustomExportView;
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(deviceRotated:)name:UIDeviceOrientationDidChangeNotification object:nil];
}
try this.....
- (void)show
{
NSLog(#"show");
isShown = YES;
self.transform = CGAffineTransformMakeScale(0.1, 0.1);
self.alpha = 0;
[UIView beginAnimations:#"showAlert" context:nil];
[UIView setAnimationDelegate:self];
self.transform = CGAffineTransformMakeScale(1.1, 1.1);
self.alpha = 1;
[UIView commitAnimations];
}

Change image in UIImageView when UIButton is pressed programmatically

I am trying to change the image inside an imageview when a UIButton is pressed. I need at least three or 4 clicks before the image is changed. What is wrong ?
Here is the code I am using
#interface ARViewController ()
#property (nonatomic, strong) NSMutableArray *pepsiPhotos;
#property (nonatomic, strong) UIImageView *imageView;
#end
#implementation ARViewController
{
IBOutlet UIView *overlayView;
int currentImageIndex;
}
#synthesize imageView;
- (void)viewDidLoad
{
[super viewDidLoad];
_pepsiPhotos = [NSMutableArray arrayWithObjects:#"pepsican.jpeg",
#"pepsilight.jpeg", #"7up.jpeg", #"mirinda.jpeg", nil];
overlayView = [[UIView alloc] initWithFrame:CGRectMake(50.f, 80.f, 240.f, 275.f)];
[overlayView setHidden:YES];
imageView = [[UIImageView alloc] initWithFrame:CGRectMake(10.f, 20.f, 200.f, 150.f)];
[overlayView addSubview:imageView];
[self.view addSubview:overlayView];
currentImageIndex = 0;
[self showImages];
}
-(void) showImages
{
//
[overlayView setHidden:NO];
[overlayView setBackgroundColor:[UIColor clearColor]];
[overlayView setUserInteractionEnabled:YES];
UIButton *nextButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
nextButton.frame = CGRectMake(165.f, 260.f, 40.f, 40.f);
[nextButton setTitle:#"Next" forState:UIControlStateNormal];
[nextButton addTarget:self action:#selector(nextButtonPressed:) forControlEvents:UIControlEventTouchDown];
[nextButton setUserInteractionEnabled:YES];
[overlayView addSubview:nextButton];
[overlayView bringSubviewToFront:nextButton];
UIButton *previousButton = [UIButton buttonWithType:UIButtonTypeRoundedRect];
previousButton.frame = CGRectMake(0, 260.f, 40.f, 40.f);
[previousButton setTitle:#"Last" forState:UIControlStateNormal];
[previousButton addTarget:self action:#selector(previousButtonPressed:) forControlEvents:UIControlEventTouchDown];
[previousButton setUserInteractionEnabled:YES];
[overlayView addSubview:previousButton];
[imageView setImage:[UIImage imageNamed:[_pepsiPhotos objectAtIndex:currentImageIndex]]];
[overlayView addSubview:imageView];
[self.view addSubview:overlayView];
}
-(IBAction)nextButtonPressed:(id)sender
{
if (currentImageIndex < [_pepsiPhotos count] -1)
{
currentImageIndex++;
[self performSelectorOnMainThread:#selector(showNextImage) withObject:nil waitUntilDone:NO];
}
}
-(IBAction)previousButtonPressed:(id)sender
{
if (currentImageIndex > 0)
{
currentImageIndex--;
[self performSelectorOnMainThread:#selector(showNextImage) withObject:nil waitUntilDone:NO];
}
}
-(void)showNextImage
{
[imageView setImage:[UIImage imageNamed:[_pepsiPhotos objectAtIndex:currentImageIndex]]];
[overlayView addSubview:imageView];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
One problem is that you are saying performSelectorOnMainThread:. If this is an action method from your button, you are on the main thread. Just respond however you want to respond.
Saying performSelectorOnMainThread: when you are already on the main thread can actually cause a delay, because now we have to wait for the main thread to become free before we can run the code.

Why isn't my button working?

I have created a UIButton; actually, a few buttons, and I have initialized them and set them up in the
-(void)viewDidLoad
method. My issue now, is connecting them to the method that I have created. I have created a typedef enum to replace the numbers for the tags of my buttons with names to certain situations. I do not know if this is the issue or what, but I am confused on why when I press the button(s), they are not working. My code is below.
My enum:
typedef enum {
DiseasesStrepThroat = 1,
DiseasesFlu = 2,
DiseasesChickenPox = 3,
DiseasesSmallPox = 4,
DiseasesMeasels = 5,
DiseasesCommonCold = 6
} DiseasesTagNumber;
I have initialized all of the UIButton objects; as well as my IBAction in my .h file already, so I don't have to worry about that part.
Here is my view did load
// Implement viewDidLoad to do additional setup after loading the view, typically from a nib.
- (void)viewDidLoad {
[super viewDidLoad];
scrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, 700, 768, 125)];
scrollView.contentSize = CGSizeMake(1000, 125);
scrollView.backgroundColor = [UIColor darkGrayColor];
scrollView.showsHorizontalScrollIndicator = YES;
scrollView.indicatorStyle = UIScrollViewIndicatorStyleWhite;
scrollView.autoresizesSubviews = NO;
[self.view addSubview:scrollView];
//////////////////////////////////////////
// //
// creating all the buttons //
// //
//////////////////////////////////////////
// strep throat
strep = [UIButton buttonWithType:UIButtonTypeRoundedRect];
strep.frame = CGRectMake(10, 10, 110, 100);
[strep setTitle:#"Strep" forState:UIControlStateNormal];
[strep setTag:DiseasesStrepThroat];
[scrollView addSubview:strep];
// the flu
flu = [UIButton buttonWithType:UIButtonTypeRoundedRect];
flu.frame = CGRectMake(130, 10, 110, 100);
[flu setTitle:#"Flu" forState:UIControlStateNormal];
[flu setTag:DiseasesFlu];
[scrollView addSubview:flu];
// chicken pox
chickenPox = [UIButton buttonWithType:UIButtonTypeRoundedRect];
chickenPox.frame = CGRectMake(250, 10, 110, 100);
[chickenPox setTitle:#"Chicken Pox" forState:UIControlStateNormal];
[chickenPox setTag:DiseasesChickenPox];
[scrollView addSubview:chickenPox];
// small pox
smallPox = [UIButton buttonWithType:UIButtonTypeRoundedRect];
smallPox.frame = CGRectMake(370, 10, 110, 100);
[smallPox setTitle:#"Small Pox" forState:UIControlStateNormal];
[smallPox setTag:DiseasesSmallPox];
[scrollView addSubview:smallPox];
// measels
measels = [UIButton buttonWithType:UIButtonTypeRoundedRect];
measels.frame = CGRectMake(490, 10, 110, 100);
[measels setTitle:#"Measels" forState:UIControlStateNormal];
[measels setTag:DiseasesMeasels];
[scrollView addSubview:measels];
// common cold
commonCold = [UIButton buttonWithType:UIButtonTypeRoundedRect];
commonCold.frame = CGRectMake(610, 10, 110, 100);
[commonCold setTitle:#"Common Cold" forState:UIControlStateNormal];
[commonCold setTag:DiseasesCommonCold];
[scrollView addSubview:commonCold];
NSArray *array = [[NSArray alloc] initWithObjects:strep, flu, chickenPox, smallPox, measels, commonCold, nil];
for(UIButton *b in array) {
b.showsTouchWhenHighlighted = YES;
}
//&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//
// //
// CREATING ALL THE TARGETS //
// //
//&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&//
[strep addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
[flu addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
[chickenPox addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
[smallPox addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
[measels addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
[commonCold addTarget:self action:#selector(showDiseasesWithTag:) forControlEvents:UIControlEventTouchUpInside];
}
and now my IBAction method
- (IBAction) showDiseasesWithTag:(NSInteger)senderTag {
switch (senderTag) {
case DiseasesStrepThroat:
a = [[UIAlertView alloc]
initWithTitle:#"H"
message:#"yo"
delegate:self
cancelButtonTitle:nil
otherButtonTitles:nil];
[a show];
break;
case DiseasesFlu:
[UIView animateWithDuration:1.0 animations:^ {
}completion:^(BOOL finished) {
}];
break;
case DiseasesChickenPox:
[UIView animateWithDuration:1.0 animations:^ {
}completion:^(BOOL finished) {
}];
break;
case DiseasesSmallPox:
[UIView animateWithDuration:1.0 animations:^ {
}completion:^(BOOL finished) {
}];
break;
case DiseasesMeasels:
[UIView animateWithDuration:1.0 animations:^ {
}completion:^(BOOL finished) {
}];
break;
case DiseasesCommonCold:
[UIView animateWithDuration:1.0 animations:^ {
}completion:^(BOOL finished) {
}];
break;
}
}
To clear anything up, all the UIView animation and completion blocks are not completed. I am mainly focused on the first case. Is it because I have the first case as a 1? When I had it set to 0, it still did nothing.
The actual issue with everything, is when i press the first UIButton in my UIScrollView, I am able to press it, but what happens is the button does nothing regarding the IBAction method. It doesn't seem to be calling it at all.
Any help is appreciated.
OK, you are simply using the wrong argument to the action method. It should be:
- (IBAction) showDiseasesWithTag:(id)sender {
NSInteger senderTag = [sender tag];
switch (senderTag) {
...
}
}
Under iOS the target method can have one of three different signatures:
- (IBAction)actionMethod;
- (IBAction)actionMethod:(id)sender;
- (IBAction)actionMethod:(id)sender forEvent:(UIEvent *)event;
but never:
- (IBAction)actionMethod:(NSInteger)senderTag;

iOS Subview with buttons not responding to touches.

I have a UIView Subclass that has a frame/image with buttons in it. I'm trying to add it to my view controller however when I do it shows up but none of the buttons will register ANY touches.
Here is my UIView Subclass.
#import "ControlView.h"
#implementation ControlView
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
CGRect slideFrame = CGRectMake(0, 402, 320, 82);
slider = [[UIView alloc] initWithFrame:slideFrame];
slider.backgroundColor = [[UIColor alloc] initWithPatternImage:[UIImage imageNamed:#"shelf.png"]];
[self addSubview:slider];
UIImage *btnImage = [UIImage imageNamed:#"NavBar_01.png"];
UIImage *btnImageSelected = [UIImage imageNamed:#"NavBar_01_s.png"];
btnImage = [UIImage imageNamed:#"NavBar_01.png"];
btnImageSelected = [UIImage imageNamed:#"NavBar_01_s.png"];
btn1 = [UIButton buttonWithType:UIButtonTypeCustom];
btn1.frame = CGRectMake(12, 28, 70, 50);
[btn1 setBackgroundImage:btnImage forState:UIControlStateNormal];
[btn1 setBackgroundImage:btnImageSelected forState:UIControlStateSelected];
[slider addSubview:btn1];
[slider bringSubviewToFront:btn1];
[btn1 addTarget:self action:#selector(home) forControlEvents:UIControlEventTouchUpInside];
btnImage = [UIImage imageNamed:#"NavBar_02.png"];
btnImageSelected = [UIImage imageNamed:#"NavBar_02_s.png"];
btn2 = [UIButton buttonWithType:UIButtonTypeCustom];
btn2.frame = CGRectMake(87, 28, 70, 50);
[btn2 setBackgroundImage:btnImage forState:UIControlStateNormal];
[btn2 setBackgroundImage:btnImageSelected forState:UIControlStateSelected];
[slider addSubview:btn2];
[slider bringSubviewToFront:btn2];
// [btn2 addTarget:self action:#selector() forControlEvents:UIControlEventTouchUpInside];
btnImage = [UIImage imageNamed:#"NavBar_03.png"];
btnImageSelected = [UIImage imageNamed:#"NavBar_03_s.png"];
btn3 = [UIButton buttonWithType:UIButtonTypeCustom];
btn3.frame = CGRectMake(162, 28, 70, 50);
[btn3 setBackgroundImage:btnImage forState:UIControlStateNormal];
[btn3 setBackgroundImage:btnImageSelected forState:UIControlStateSelected];
[slider addSubview:btn3];
[slider bringSubviewToFront:btn3];
// [btn3 addTarget:self action:#selector() forControlEvents:UIControlEventTouchUpInside];
btnImage = [UIImage imageNamed:#"NavBar_04.png"];
btnImageSelected = [UIImage imageNamed:#"NavBar_04_s.png"];
btn4 = [UIButton buttonWithType:UIButtonTypeCustom];
btn4.frame = CGRectMake(237, 28, 70, 50);
[btn4 setBackgroundImage:btnImage forState:UIControlStateNormal];
[btn4 setBackgroundImage:btnImageSelected forState:UIControlStateSelected];
[slider addSubview:btn4];
[slider bringSubviewToFront:btn4];
// [btn4 addTarget:self action:#selector() forControlEvents:UIControlEventTouchUpInside];
UISwipeGestureRecognizer *recognizer;
recognizer = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:#selector(slideUp)];
[recognizer setDirection:(UISwipeGestureRecognizerDirectionUp)];
[self addGestureRecognizer:recognizer];
recognizer = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:#selector(slideDown)];
[recognizer setDirection:(UISwipeGestureRecognizerDirectionDown)];
[self addGestureRecognizer:recognizer];
}
return self;
}
-(void)slideUp
{
// Slide up based on y axis
CGRect frame = slider.frame;
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationDuration:.75];
frame.origin.y = 320;
slider.frame = frame;
[UIView commitAnimations];
}
-(void)slideDown
{
CGRect frame = slider.frame;
[UIView beginAnimations:nil context:NULL];
[UIView setAnimationDuration:.75];
frame.origin.y = 425;
slider.frame = frame;
[UIView commitAnimations];
}
/*
// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect
{
// Drawing code
}
*/
#end
And this is how I'm adding it to my ViewController.
ControlView *cont = [[ControlView alloc]init];
[homeView.view addSubview:cont];
I tried adding the same code to a ViewController and the buttons etc.. worked so I'm sure this is something simple/stupid with Delegates/Self etc.. between the subview and the ViewController however I have a mental block.
You are doing this?
ControlView *cont = [[ControlView alloc]init];
you are supposed to do
ControlView *cont = [[ControlView alloc]initWithFrame:self.view.frame];

Resources