ViewController and SegmentedControl - iphone

I have ViewCtrl1, and StartBtn:
-(IBAction)startbtn
{
ViewCtrl2 *vc2 = [[ViewCtrl2 alloc]init];
[self presentModalViewController:vc2 animated:YES];
}
I have also ViewCtrl2, UISegmentedControl, and ExitBtn:
- (IBAction)exitIt {
[self dismissModalViewControllerAnimated:YES];
}
If in ViewCtrl2 i select segment 2, or 3. When I press ExitBtn, will show ViewCtrl1, and if I press StartBtn from ViewCtrl1, my ViewCtrl2 shows default selected segment, not changes that i made recently.
How can i fix it?

You creating new vc2 each time and of course it shows default values. Initialise it once and reuse.

Related

iOS: Navigation bar item disappearing and reappearing

Trying to add and remove navigation Bar Items on the navigation bar, some bar items disappear.
When I run the codes below at viewDidLoad, they work fine.
-(void) resetNavigationBarRearrangeMode {
NSArray*rightBarItems = [[NSArray alloc] initWithObjects:actionCancel, actionSave, actionAddItem, actionRearrange, nil];
self.navBar.topItem.rightBarButtonItems = rightBarItems;
}
When I try to remove some of the bar button items, it appears fine.
- (IBAction)cancelClicked:(id)sender {
NSArray*rightBarItems = [[NSArray alloc] initWithObjects:actionRearrange, nil];
self.navBar.topItem.rightBarButtonItems = rightBarItems;
Log(#"running cancel");
}
But when I clicked rearrange to run the below code, this doesn't work.
- (IBAction)rearrangeClicked:(id)sender {
[self resetNavigationBarRearrangeMode];
}
Anyone know what's wrong? thanks in advance.
The barButtonItems are overlapped each and every time you call the method. You need to reset the barButtonItems by setting it as nil before calling the method for rearranging.
- (IBAction)rearrangeClicked:(id)sender {
self.navigationItem.rightBarButtonItem = nil;
[self resetNavigationBarRearrangeMode];
}
It would work. Refer this link for further assistance.

PopViewController in Tabbar application

I am working on a Tab-bar application.
TAB-BAR CONTROLLER
|
_______________________________________________________
| | | |
View 1 View 2 View 3 View 4
| |
SearchingON Detail View
Problem 1 :I have a button (Let say Sign Out), On click of The button which is on View 4, I want to pop the Detail view of View 2.
So that after new login new user should not reach to detail veiw.
I have tried :
if ([[NSUserDefaults standardUserDefaults] valueForKey:#"IsChattingON"])
{
ChatDetail *chat = [[ChatDetail alloc] initWithNibName:#"ChatDetail" bundle:nil];
[chat BackButtonClicked:nil];
}
and in Detail View back Button my code is :
-(IBAction)BackButtonClicked:(id)sender
{
[[NSUserDefaults standardUserDefaults] setBool:NO forKey:#"IsChattingON"];
[self.navigationController popViewControllerAnimated:YES];
}
Here User Defaults having Bool value whether Detail View is open or not.
Problem 2 : I am applying Search on View 1's Table View and want to remove Search if View 4 SignOut button is clicked. I want to refresh my View 1 if Signout button of View 4 is clicked.
For removing Search I have done this code but not getting the desired results.
PeopleController *People = [[PeopleController alloc] initWithNibName:#"PeopleController" bundle:nil];
People.isSearchingRecords = NO;
I have Searched so far about popViewControllers but cant find this scene. Pls let me know how can I achieve this functionality.
You should not allocate a new view controller when the user taps on logout,
instead you should do the following
- (void) logOut
{
//get the view 2
//you should have a way to access view 2
[view2 closeChatView];
}
//On view 2 maintain a reference of chat detail controller
- (void) closeChatView
{
[[NSUserDefaults standardUserDefaults] setBool:NO forKey:#"IsChattingON"];
//chat is the reference to the chat details controller
[chat.navigationController popViewControllerAnimated:YES];
}
I assume that you keep instance of navigation controllers in appDelegate then you can try this:
NSArray *viewNavStack = appDelegate.viewNavController.viewControllers;
if ([viewNavStack count] > 1) {
[appDelegate.overviewNavController popToRootViewControllerAnimated:NO];
}
Finally I got solution for Problem 2 :
I am setting a NSUserDefault BOOL to NO, and in ViewWillAppear I am getting that UserDefaults value whether searching is ON or not.
On click of Signout Button :
[[NSUserDefaults standardUserDefaults]setBool:NO forKey:#"SearchingON"];
and on View 1 :
isSearchingRecords = [[NSUserDefaults standardUserDefaults] boolForKey: #"SearchingON"];
if (isSearchingRecords)
{
self.btnSearchCancel.hidden = NO;
}else
{
self.btnSearchCancel.hidden = YES;
}
But cant find the solution of Problem 1 - to pop the view by another tab, if any one have any idea pls let me know !!

perpareForSegue - Passing image name - Blank at First

I have a thumbnail view controller with two thumbnails. Each have an IBAction setting the image name. The next view should display the full image.
The first time I select a button, the new view opens but is completely blank. I go back to the previous screen (navigation controller) and select the button again and the full image screen shows with the correct full image.
Back out, select the second button and the full image of the first button is displayed.
It appears that the full image is off by one iteration.
Below are some code snippets.
thumbnailViewController.M
- (void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
fullImageViewController *targetVC = (fullImageViewController*)segue.destinationViewController;
targetVC.fullImageName = _imageName;
}
- (IBAction)running1 {
_imageName = #"img_running1.png";
}
- (IBAction)running2 {
_imageName = #"img_running2.png";
}
fullImageViewController.m
- (void)viewDidLoad
{
[super viewDidLoad];
_fullImage.image = [UIImage imageNamed: _fullImageName];
}
Any suggestions.
I'm guessing that you have both the IBAction and the Segue hooked up to your buttons? If so this is your issue. The segue occurs before the IBAction. The solution is instead of having the button hooked up to the segue have the IBAction perform it.
- (IBAction)running1 {
_imageName = #"img_running1.png";
[self performSegueWithIdentifier:#"yourSegue" sender:self];
}
This will correct the order by giving you control. otherwise I believe its segue then action.

UIPopoverController memory question

I'm creating a UIPopoverController and setting "Editor1" as the content view controller.
When the caller receives the didDismissPopover I'm releasing the UIPopoverController.
This is the code:
- (IBAction)open1:(id)sender {
Editor1 *editor = [[Editor1 alloc] initWithNibName:#"Editor1" bundle:nil];
_popoverController = [[UIPopoverController alloc] initWithContentViewController:editor];
_popoverController.delegate = self;
[editor release];
[self.popOverController presentPopoverFromRect:self.open1Button.bounds inView:self.open1Button permittedArrowDirections:UIPopoverArrowDirectionAny animated:NO];
}
- (BOOL)popoverControllerShouldDismissPopover:(UIPopoverController *)popoverController{
NSLog(#"popoverControllerShouldDismissPopover");
return YES;
}
- (void)popoverControllerDidDismissPopover:(UIPopoverController *)popoverController{
NSLog(#"popvoerControllerDidDismissPopover");
[_popoverController release];
}
In my editor I have a UITextField where the user changes text and I save it when I get the message "editingDidEnd"
- (IBAction)editingDidEnd:(id)sender {
NSLog(#"Editing did End");
// SAVE PROCEDURE
}
My question regards the order in which the methods get called.
The order is:
2011-09-07 12:35:21.628 iosTest[1967:b603] popoverControllerShouldDismissPopover
2011-09-07 12:35:21.629 iosTest[1967:b603] popvoerControllerDidDismissPopover
2011-09-07 12:35:21.983 iosTest[1967:b603] Editing did End
2011-09-07 12:35:21.985 iosTest[1967:b603] viewWill Disappear
As you can see the popoverControllerDidDismissPopover gets called before editingDidEnd:, so this means I'm releasing the popover before I do my save procedure. This could bring me a crash problem.
Also, in my save procedure I need to ask the user for confirmation in some cases. I'm using a UIAlertView for this.
Do you have any recommendations?
Usually views are well-behaved and don't send events after they're off-screen. You can check for potential problems by enabling zombies (set the environment variable NSZombieEnabled=YES).
If there is a crash, the correct place to fix it is in -[Editor1 dealloc] (and possibly -viewDidUnload): just do textField.delegate = nil and you should stop receiving callbacks. This is not usually necessary except for web views and scroll views where it seems to be problematic (the scroll animation continues even if the VC is off-screen).
In your case, you can probably make saving happen in -popoverControllerShouldDismissPopover:, returning NO if you need to display a UIAlertView (and dismissing the popover when the button is pressed).
it seems, that _popoverController is the instance-property. in this case you can release it in viewDidUnload method of parent-controller.
Why don't you use UITextFieldDelegate protocol? Usage:
aTextField.delegate = self;
(...)
- (void)textFieldDidEndEditing:(UITextField *)textField {
NSLog(#"Editing did End");
// SAVE PROCEDURE
}
Read the documentation for more info.

Is it possible to select a row in a **previous** UITableview

Is it possible to select a row in a previous UITableview.
I provided image samples to get a more clear picture of what is happening exactly.
http://img186.imageshack.us/img186/933/picture8a.png
http://img405.imageshack.us/img405/9327/picture9d.png
http://img200.imageshack.us/img200/5386/picture10thm.png
At the morning workout screen , one can select a row and behind it so it will play a Movie.
If the movie plays you can press the secondbutton and it will take you to the final table.
If you press the backbutton you will simply return to the previous screen.
Now here is where my problem lies.
If i'm in my final screen after pressing the secondbutton and I press on the backbutton it would be great if it could play the previous video( in other words the video connected to the previously selected cell)
So if it's possible for me to create a function or some sort of action that can actually select the previously selected row from the first field ( for instance Lunge Forward in this example ).
perhaps with some like
previousRow = [ self.tableView indexPathForSelectedRow];
[self tableView:[self tableView] didSelectRowAtIndexPath:previousRow];
just doing something there
Even if it's not possible I would appreciate it if someone would let me know.
edit:
Here is some code behind the cell when it's going to play a video
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
//Get the dictionary of the selected data source.
NSDictionary *dictionary = [self.tableDataSource objectAtIndex:indexPath.row];
//check to see if video must be played
NSString *playVids = [dictionary objectForKey:#"playVids"];
finalscreen = [dictionary objectForKey:#"finalScreen"];
if(playVids == nil )
{
if(CurrentLevel != 0 )
{
if( finalscreen == nil )
{
NSString *movies = [dictionary objectForKey:#"movieID"];
NSURL *movie = [NSURL fileURLWithPath:[[NSBundle mainBundle] pathForResource:movies ofType:#"m4v"]];
theMovie = [[MPMoviePlayerController alloc] initWithContentURL:movie];
[theMovie setOrientation:UIDeviceOrientationPortrait animated:NO];
[theMovie setScalingMode:MPMovieScalingModeAspectFit];
theMovie.backgroundColor = [ UIColor whiteColor];
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(myMovieFinishedCallback:)
name:MPMoviePlayerPlaybackDidFinishNotification
object:theMovie];
[theMovie play];
[self getToolBarStuff];
lblTitle.text = [dictionary objectForKey:#"Title"];
[[[UIApplication sharedApplication]keyWindow]addSubview:toolbar2];
[[[UIApplication sharedApplication]keyWindow]addSubview:imageView];
[[UIApplication sharedApplication]keyWindow]addSubview:lblTitle];
}
}
else
{
WebViewController *web = [[WebViewController alloc] initWithNibName:#"WebView" bundle:[NSBundle mainBundle]];
[self.navigationController pushViewController:web animated:YES];
[web release];
}
}
else {
//Prepare to tableview.
rvController = [[RootViewController alloc] initWithNibName:#"RootViewController" bundle:[NSBundle mainBundle]];
//Increment the Current View
rvController.CurrentLevel += 1;
//Set the title;
rvController.CurrentTitle = [dictionary objectForKey:#"Title"];
//Push the new table view on the stack
[self.navigationController pushViewController:rvController animated:YES];
rvController.tableDataSource = Children;
[rvController release];
}
}
I get my info/feeds from a dictionaryfile and also different tags in my dictionary tell my tableview when to play the video and when not( playVids ).
so to be exact I have a start screen which brings you to a second screen and that one brings you to the morning workout screen and from there if you click a cell it will play a (different with every cell) video. I can't use the standard design from apple(with the backbutton above) since this assignment specifically asks to use their own design.
That's the reason why i created my own tabbar and backbutton.
My backbutton looks like this
-(void)back_clicked:(id)sender
{
[self.navigationController popViewControllerAnimated:YES];
CurrentLevel--;
switch( CurrentLevel ) {
case 0;
[toolbar removeFromSuperView];
default:
break;
}
}
So if I'm in the last screen I just pop that screen to return to my previous one( the morning workout). And what actually has to be done is pop that screen and play the last video. I thought I could do that by popping the last screen and then selecting the previously clicked cell in morning workout.
Any thoughts on that.
I am not sure I understand your problem exactly here. Can you show a bit more code? You have 3 view controllers, right? Are you using a standard navigation controller pattern with push/pop to get from one to the other? It looks like maybe you aren't since the buttons are in an odd layout.
If you are then pressing the back button can just pop view 3 and go back to view 2 naturally (it will still be there, so the video should still be playable) so I don't see why you need to mess with the table in view 1 in order to find that and make it show again. You should just be able to hook into viewWillAppear and do the same thing you did when coming from view 1.
And if you aren't using a standard navigation controller pattern then maybe this is the problem. From a UI perspective you probably should do that anyway - people will expect a standard back button in the title bar.
I am pretty sure your problem is soluble anyhow - you can always pass object references from one view to the other when creating them for example - but I don't think you need to resort to the method you have in mind.
edit: reading the additional detail I see you are indeed using push/pop. So you have a stack of views, and when one is popped it uncovers the one beneath it, right? It should therefore be possible to do what you want by implementing the viewWillAppear or viewDidAppear methods in your controller. When your final screen is popped, if I understand correctly it will uncover the view which is able to play the movie. Your viewcontroller will get the viewWillAppear / viewDidAppear messages in that case - by maintaining state and receiving those messages you can then implement logic to decide whether or not you need to play the movie. Rather than call the didSelectRow. method again you could perhaps put the movie play stuff in its own method so you can call from either viewDidAppear or didSelectRow...
I also am not sure that I fully understand your question either but it sounds similar to a problem I was working on recently. Check out this post on using up down arrows to move through the parent table while in a detail view. My app was based on the same sample code so you should be able to get this to work without much trouble.
Up/down arrows in nav bar of detail view to page through objects in parent table