I have A and B UIViewController. A controller has button and textview and click this button it goes to B controller. Then I click the B controller I come back to A controller. But when I come back from B controller I need to hide textview from A controller.
B controller:
-(void)A{
[self.navigationController popToRootViewController animated:YES];
}
You are using poptoviewcontroller method so after going back to previous controller the data still persists. So, before navigating to B controller from A controller hide the textview, so that when navigation view pops to main view, the textview will be hidden
Try to use like this...
There are two solution
1.
- (void)viewDidLoad
{
[super viewDidLoad];
textview.hideen = NO;
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
textview.hidden = YES;
}
2 . Use a key in NSUserDefaults for status . I mean check it is coming from B Controller or not.
There are many options for this:
Before navigating to the next view hide the textview.
Hide the textview in the viewwilldisappear method.
Use a key with NSUserDefaults and check whether it is coming from B controller.
Declare a variable in appdelegate and change its value in B controller check the value in a controller hide the textview based on result.
You can navigate to another page by declaring a view controller and setting it to naviagation controller before that you can set the properties of that controller.
->write code in controller A
- (void)viewDidLoad
{
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(hideTextview) name:#“hidetextview” object:nil];
}
- (void) hideTextview{
textview.hidden = YES;
}
->in controller B
(void)viewWillDisappear:(BOOL)animated{
[[NSNotificationCenter defaultCenter] postNotificationName:#"hidetextview" object:nil userInfo:nil];
}
The simplest thing you could do is hide the text view in viewcontroller A before you navigate to view controller B so the code needs to be added in the
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
textview.hidden = YES;
}
OR
- (void)navigateToBController{
VCB *b = [[VCB alloc]init];
[self.navigationController pushviewController:b];
textview.hidden = YES;
}
If you are navigating from A -> B -> C and then in viewcontroller C you navigate to root view controller i.e A then in this case what i would suggest is to maintain a variable in NSUSerDefault which would inform you from which viewcontroller it has popped so that you could show / hide your textview.
Related
I am newbie working on objective C. I am facing one problem .
I have tab bar controller containing three view controllers out of which I am concerned about only two VCs named "Setting" and "BBVC" . "BBVC" has a UIButton and "Setting" has a UISwitch (Please see below image).
When button "B" is pressed, in tab bar view controller below code gets executed :
- (void)centerButtonTapped:(id __unused)sender {
BBVC *vc = [[BBVC alloc] init];
UINavigationController *nc = [[UINavigationController alloc] initWithRootViewController:vc];
[self presentViewController:nc animated:YES completion:nil];
}
BBVC gets loaded as pop UP
My aim is I want to change the value of "UISwitch" based on "UIButton" action event.
Case 1 : Not On setting View
In this case after pressing the UIButton, when I am on
"Setting" VC, the aim can be achieved by using viewWillappear and UserDefault as shown below :
- (void)viewWillAppear:(BOOL)animated
{
NSLog(#"viewWillAppear");
[super viewWillAppear:animated];
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
[Switch setOn:[defaults boolForKey:#"EnableLIVE"] animated:YES];
}
Case 2 :
In this case I am already on "Settings" VC (i.e. setting view is already loaded) and when button "B" from tab bar is pressed, it gets loaded as a pop up as shown in below image. I am trying to achieve my aim but its not working.
Attempt 1 :
In Setting VC, I updated the code in "viewDidAppear" method but while debugging I got to know after closing BBVC, method "viewDidAppear" is not getting called.
-(void)viewDidDisappear:(BOOL)animated
{
NSLog(#"viewDidDisappear");
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
[Switch setOn:[defaults boolForKey:#"EnableLIVE"] animated:YES];
}
Attempt 2 :
Use Delegate and Protocols :
I have used delegate and protocols which is working fine but in this case address of UISwitch is nil. Please see below image
Note : UISwitch is created programmatically.
I am clueless here. Any kind of help is appreciated.
Thank you.
If i'm interpreting your question correctly, it sounds like the main problem you're experiencing currently is updating the live switch on the settings VC when it's already displaying, but the BBVC is displaying modally overtop (and it's button is pressed).
You can listen for a notification of changes to user defaults within your settings controller when it loads up, and remove it as an observer once deallocated -- then adjust the switch to the appropriate value once the notification of user defaults changing comes in. Something along these lines:
- (void)viewDidLoad {
[super viewDidLoad];
[[NSNotificationCenter defaultCenter] addObserver:self selector:#selector(userDefaultsDidChange:) name:NSUserDefaultsDidChangeNotification object:nil];
}
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
[self.liveSwitch setOn:[[NSUserDefaults standardUserDefaults] boolForKey:#"EnableLIVE"]];
}
- (void)userDefaultsDidChange:(NSNotification *)notification {
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
[self.liveSwitch setOn:[[notification object] boolForKey:#"EnableLIVE"]];
}];
}
- (void)dealloc {
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
https://developer.apple.com/documentation/foundation/nsuserdefaultsdidchangenotification?language=objc
Scenario:
I need to show 3 or more popups one after the other on button click in each popup. I have created a different viewcontroller and xib files for each popup. So for displaying each popup I have used presentViewController instead of pushViewController.
That is, I have used this:
[self presentPopupViewController:searchPopUpView animationType:0];
instead of
[self.navigationController pushViewController:searchPopUpView animated:YES];
For dismissing a popup, the following code has been written:
[self dismissPopupViewControllerWithanimationType:0];
Issue:
The popups are displaying perfectly, but the background gets darker and darker whenever a popup shows up. After all popups have been dismissed I have to finally click on the blank screen to remove those darker parts. How to overcome this issue?
I think you are using MJPopupViewController to show pop-up.
If it is so, Then try this.
Suppose there is a controllerA from which you want to show a pop-up controller popupControllerB.
Then in your controllerA add Notifications Observer
Code to write in controllerA :
// Add Notification Observer when your view initialise.
[[NSNotificationCenter defaultCenter]addObserver:self selector:#selector(dismissPopup) name:#"DISMISS_POPUP" object:nil];
In viewWillDisappear remove the notifications observer
- (void)viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
This method will be called when you Post-notification from your popupControllerB
-(void)dismissPopup {
[self dismissPopupViewControllerWithanimationType:MJPopupViewAnimationFade];
}
And In popupControllerB, Where you want to dismiss the Pop-up, write this code.
[[NSNotificationCenter defaultCenter] postNotificationName:#"DISMISS_POPUP" object:nil];
Above line of code will call a method written in your controllerA and dismiss the pop-up properly.
If you want to dismiss presented UIViewControllers you can use this code. I have used this approach to dismiss presentedViewControllers. It will dismiss all your presentedViewControllers on your rootViewController.
UIViewController* presVC = self.window.rootViewController;
while (presVC) {
UIViewController* temp = vc.presentingViewController;
if (!temp.presentedViewController) {
[vc dismissViewControllerAnimated:NO completion:^{}];
break;
}
vc = temp;
}
I have three view controllers that are connected to a tab bar controller, which I thought should automatically set the presentingViewController/presentedViewController. However, when I toggle between my view controllers and I log [self presentingViewController], it logs null. I put the log in my viewDidAppear methods in each of the view controllers.
-(void)viewDidAppear:(BOOL)animated {
[super viewDidAppear:YES];
NSLog(#" my presenting view controller is %#", [self presentingViewController]);
}
Output:
my presenting view controller is (null)
If you want to know which tab you came from, then you should subclass the tab bar controller, and set it as its own delegate. Create an integer property, oldIndex which you can set before the tab switch in the delegate method, tabBarController:shouldSelectViewController:.
#interface RDTBC () <UITabBarControllerDelegate>
#end
#implementation RDTBC
- (void)viewDidLoad {
[super viewDidLoad];
self.delegate = self;
}
- (BOOL)tabBarController:(UITabBarController *)tabBarController shouldSelectViewController:(UIViewController *)viewController {
self.oldIndex = self.selectedIndex;
return YES;
}
Then in your view controller, you can get it like this,
-(void)viewDidAppear:(BOOL)animated {
[super viewDidAppear:animated];
NSLog(#"%ld",[(RDTBC *)self.tabBarController oldIndex]);
}
It's probably not a good idea to make one tab's behavior dependent on what tab was last shown. Tabs are designed to function independently.
I've two view controller A and B.
A contains a table view and when the user taps on a row, B is pushed.
B has a UIToolbar self.navigationController.toolbarHidden = NO; and the problem is when I pop from B to A: the toolbar remains even on A and I have no idea how to remove.
It's happening because you does not hide toolBar when you pop from B to A viewController.
Use/write following code in B viewController
#pragma mark -
#pragma mark - viewWillDisappear Methods
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
self.navigationController.toolbarHidden = YES;
}
So, your toolBar hide whenever you pop from B to A viewController.
You Also should try with another option, use same code on viewWillAppear method of A viewController.
Say I have UIViewController A and B.
User navigates from A to B with a push segue.
Than user presses back button and comes to A.
Now viewWillAppear of A is called. Can I know in the code here that I came from back button (navigationController popTo...) and not by another way? And without writing special code in the B view controller.
hm, maybe you can use self.isMovingToParentViewController in viewWillAppear, see docs, if it is NO then it means the current view controller is already on the navigation stack.
I like to do the following in view controller A:
- (void) viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
if (_popping) {
_popping = false;
NSLog(#"BECAUSE OF POPPING");
} else {
NSLog(#"APPEARING ANOTHER WAY");
}
//keep stack size updated
_stackSize = self.navigationController.viewControllers.count;
....
}
- (void) viewWillDisappear:(BOOL)animated {
[super viewWillDisappear:animated];
_popping = self.navigationController.viewControllers.count > _stackSize;
....
}
What you are doing is keeping track of whether your view controller (A) is disappearing because a view controller (B) is being pushed or for another reason. Then (if you did not modify the child view controller order) it should accurately tell you if (A) is appearing because of a pop on the navigation controller.
Add a BOOL property to UIViewController A:
#property (nonatomic) BOOL alreadyAppeared;
Then in your viewWillAppear: method, add:
if (!self.alreadyAppeared) {
self.alreadyAppeared = YES;
// Do here the stuff you wanted to do on first appear
}