Displaying new subview once created

Discussion in 'iPhone/iPad Programming' started by l0uismustdie, Aug 19, 2010.

  1. macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #1
    Hello, I am trying to display a new subview in my app. I have already created the subview and added it to the UIWindow. This is inside my appDelegate:[and as a side note if i comment out the second line the resultsController.view will display]

    Code:
    [window addSubview:resultsController.view];
    [window addSubview:viewController.view];
    [window makeKeyAndVisible];
    
    (resultsController.view is what I am trying to display). Once I have these views added I am trying to display resultsController.view when a button is pressed in viewController.view. Currently the button runs a function inside of the appDelegate. I have tried a number of things including:
    Code:
    -(IBAction)buttonPressed:(id)sender
    {	
    	vmAppDelegate *delegate=[vmAppDelegate new];
    	
    	NSLog(@"buttonpressed");
    	[delegate.window addSubview:delegate.resultsController.view];	
    	[delegate connectToProject:URLField.text];
    }
    
    Code:
    -(void)displayNewView:(UIView*)viewToDisplay
    {
    	NSLog(@"displaynewview");
    	[UIView beginAnimations:nil context:NULL];
    	[UIView setAnimationDuration:1.0];
    	[UIView setAnimationTransition:UIViewAnimationTransitionCurlUp forView:window cache:YES];
    	[window bringSubviewToFront:viewToDisplay];	
    	[UIView commitAnimations];	
    }
    
    And then calling this function from inside the function called when the button is pressed. Along with a number of other ideas like adding the subview once the button has been pressed, removing the other subview when the button is pressed, etc etc... There is something I am obviously missing here and no amount of google search will discover what it is.

    Thanks,
    Josh
     
  2. macrumors 603

    Joined:
    Jul 29, 2003
    Location:
    Silicon Valley
    #2
    Code:
    vmAppDelegate *delegate=[vmAppDelegate new];
    
    This creates a new object. All the window and views inside it will be nil. Why do you want to play with nil objects?
     
  3. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #3
    Well obviously I don't want to "play with nil objects" that is what I am trying to learn how to change by posting my question to this forum.
     
  4. Moderator emeritus

    robbieduncan

    Joined:
    Jul 24, 2002
    Location:
    London
    #4
    Don't use new. Seriously. Look at any sample code. It always uses alloc/init. Never new.
     
  5. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #5
    Well I have looked at plenty of sample code in order to fix this problem and others I have encountered in the process. I think perhaps if you aren't going to post a constructive reply it would be more beneficial if you didn't post a reply at all. From the last post I changed the line:
    Code:
    vmAppDelegate *delegate=[vmAppDelegate new];
    
    to
    Code:
    vmAppDelegate *delegate=[[vmAppDelegate alloc]init];
    
    This is, I suppose, not the answer. So, to reiterate sort of exactly what I'm trying to do. I have created two views(vmViewController.view and vmController.view) in my appDelegate and added them as subviews to my UIWindow. vmViewController.view has a button that calls a function in the appDelegate and I am trying to get the second view to become the top view once that function is called.

    Thanks again
     
  6. Moderator emeritus

    robbieduncan

    Joined:
    Jul 24, 2002
    Location:
    London
    #6
    No, that's what you think you've done. What you are really doing is creating a new instance of the app delegate class instead of using the already existing one. This is why it's not working. Which is what you were told in the first reply.
     
  7. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #7
    Also, the usual approaches to showing a new view are either presenting it modally or pushing it onto a navigation stack.

    I guess I will channel chown33 here and ask what is your experience level with iPhone programming and programming in general? What books or tutorials have you already learned from? Be specific.
     
  8. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #8
    Well you've made your point...I don't know how to solve this problem. But that's why I posted here. I am not sure how to use the already existing instance of the app delegate without creating one. This is the next idea that I've tried:
    Code:
    vmAppDelegate *appDelegate=[[UIApplication sharedApplication]delegate];
    [appDelegate connectToProject:URLField.text];
    
     
  9. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #9
    ...and?... what was the result?
     
  10. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #10
    Haha, sorry. Figured you would sense my lack of enthusiasm. This still doesn't allow me to pull the subview to the front when the button is pushed. Additionally the second view is loading (viewDidLoad is running) it is just not being displayed. The two lines I am running are:
    Code:
    [viewController.view removeFromSuperview];
    [window addSubview:resultsController.view];
    
    I have also tried this without the removeFromSuperview and still have not been able to display the view.
     
  11. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #11
    Bringing a subview to the front (aside: are you even sure you want a subview at this point; see my previous post on showing new views) is something quite different from adding a subview, which you are actually doing twice for resultsController.view (once in applicationDidFinishLaunching, I'm guessing, and again in buttonPressed:).

    Where have you learned about showing new views?
     
  12. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #12
    The only thing I really know about views I have gathered from assorted internet sites. This is the last portion of a project I have been working on all summer and I am pretty far away from an OO programmer. I spend most of my time at as low of a level as I can be. All I really need to do is create a welcome screen that allows the user to type in a URL (which I have done) and then once they click the connect button switch to a new view where I can just display some information as things are happening throughout my program. As for adding the view twice I had actually commented out the first one (applicationDidFinishLaunching:) and placed it in the function the button is calling. As for your last post it is a modal window I am looking for because at this stage I don't care if the user can get back to the "welcome screen". In my program, in order:
    Code:
    - (void)applicationDidFinishLaunching:(UIApplication *)application
    {       
        [window addSubview:viewController.view];
        [window makeKeyAndVisible];
    }
    
    Code:
    -(IBAction)buttonPressed:(id)sender
    {	
    	vmAppDelegate *appDelegate=[[UIApplication sharedApplication]delegate];
    	[appDelegate connectToProject:URLField.text];	
    }
    
    Code:
    -(void)connectToProject:(NSString *)URL
    {	NSLog(@"urlField,%@",URL);
    	[window addSubview:resultsController.view];
    	while(1) ;
    }
    
    It is inside of this function I have been doing most of my experimenting. This is obviously where I want the next view (resultsController.view) to be displayed.
     
  13. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #13
    So, you should now have enough hints to begin searching around for how to present a modal view from within your desired method.

    P.S. What's with the while(1) ; ?
     
  14. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #14
    What I am still confused on is why in applicationDidFinishLoading: can I write
    Code:
    [window addSubview:resultsController.view];
    [window addSubview:viewController.view];
    [window makeKeyAndVisible];
    [window bringSubviewToFront:resultsController.view];
    
    and see the resultsController.view but I can't do this same thing in a later function in the same class? That seems the easiest solution to the problem.
     
  15. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #15
    Is your connectToProject: still just adding the subview or is it now calling bringSubviewToFront: ?

    P.S. I still think, based on your requirements, you should pursue the modal presentation approach.
     
  16. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #16
    You are probably right that I should take that approach. I just don't understand why this approach doesn't work the way I think it should. my connectToProject: has used a number of different techniques including adding the subView and then bringing it to the front and removing the previous subView. I have also tried this function I found someone use for this particular idea:
    Code:
    -(void)displayNewView:(UIView*)viewToDisplay
    {
    	NSLog(@"displaynewview");
    	[UIView beginAnimations:nil context:NULL];
    	[UIView setAnimationDuration:1.0];
    	[UIView setAnimationTransition:UIViewAnimationTransitionCurlUp forView:window cache:YES];
    	[window bringSubviewToFront:viewToDisplay];	
    	[UIView commitAnimations];	
    }
    
    Additionally I have now tried this line (commented out all the others) in connectToProject:
    Code:
    [viewController presentModalViewController:resultsController animated:YES];
    
     
  17. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #17
    So, I'm guessing (again!) that none of these attempts is working. And by "not working", I mean: compiles fine, no warnings or errors, runs okay (other than not doing what you want), no run-time errors or crashes. Is that right? And you're certain connectToProject: is being called and resultsController is non-nil and hasn't been released?
     
  18. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #18
    That's right...the results haven't changed. In response to your last post though I tried three changes, the first being sending a retain message to responseController inside of applicationDidFinishLaunching
    Following that I tried (inside of connectToProject:):
    Code:
    [viewController presentModalViewController:resultsController animated:YES];
    
    Code:
    [window addSubview:resultsController.view];
    
    and
    Code:
    [window addSubview:resultsController.view];
    [window bringSubviewToFront:resultsController.view];
    
    I am certain that connectToProject: is being called as for resultController I am also certain (simple did a NSLog("%@",resultsController) inside of connectToProject: and it is still around) [Side note: Is there a way to check a variable's retain count during execution?]
     
  19. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #19
    So, resultsController is non-nil, viewController is non-nil, you call presentModalViewController:animated: and nothings happens? Something screwy is going on in your project!

    Anyways, how is resultsController declared and where is it instantiated?
     
  20. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #20
    Yeah I am with you there. I have done everything the same between viewController and resultsController. It was created with a xib file. Here is how everything is declared:
    Code:
    @interface vmAppDelegate : NSObject <UIApplicationDelegate> 
    {
    	UIWindow				*window;
    	vmViewController		*viewController;
    	vmController			*resultsController;
    	NSString				*dataFile,*r,*savedURL;
    }
    @property(nonatomic,retain)IBOutlet	vmController	 *resultsController;
    @property(nonatomic,retain)IBOutlet	vmViewController *viewController;
    
    Its next appearance in the program (same as with viewController) is when they are added as subViews to window.

    Also, I sincerely appreciate your help today.
     
  21. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #21
    How did you connect resultsController to the IBOutlet?

    Which is totally unnecessary, IMHO. Here's what I would do:
    Code:
    -(void)connectToProject:(NSString *)URL
    {	NSLog(@"urlField,%@",URL);
    	ResultsController *resultsController = [[ResultsController alloc] init];
    	// do something with URL here probably
    	[viewController presentModalViewController:resultsController animated:YES];
    	[resultsController release];
    }
    
    No property, no ivar, no adding to subview, just a simple alloc/init when needed and use right away.
     
  22. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #22
    Excellent. I think we are heading on the right track. I have implemented what you suggested and still have no luck. So here are some ideas. I am certain the view is loading (NSLog(@"viewDidLoad") inside of viewDidLoad: ) After that a function inside of vmController.h gets called. Well maybe this is easier...here is the code:
    Code:
    - (void)viewDidLoad 
    {
        [super viewDidLoad];
    	NSLog(@"vmControllerDidLoad");
    	[self setuptextView];
    }
    -(void)setuptextView
    {
    	NSLog(@"set up text view");
    	self.textView = [[[UITextView alloc] initWithFrame:self.view.frame] autorelease];
    	self.textView.textColor = [UIColor blackColor];
    	self.textView.font = [UIFont fontWithName:@"Arial" size:18];
    	self.textView.delegate = self;
    	self.textView.backgroundColor = [UIColor whiteColor];
    	
    	self.textView.text = @"This is the text view example,we can edit , delete, add content in the text view.";
    	self.textView.returnKeyType = UIReturnKeyDefault;
    	self.textView.keyboardType = UIKeyboardTypeDefault;
    	self.textView.scrollEnabled = YES;
    	
    	
    	self.textView.autoresizingMask = UIViewAutoresizingFlexibleHeight;
    	[self.view addSubview: self.textView];  
    }
    
    and here is vmController.h
    Code:
    @interface vmController : UIViewController <UITextViewDelegate>
    {
    	IBOutlet UITextView		*eventView;
    	UITextView				*textView;
    }
    @property(nonatomic,retain)UITextView	*textView;
    
    -(void)setuptextView;
    
     
  23. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #23
    What exactly happens / are you seeing when you click the button?

    Your code works fine in my test project, attached:
     

    Attached Files:

  24. thread starter macrumors regular

    Joined:
    Nov 30, 2009
    Location:
    Edinburgh, UK
    #24
    When the button is clicked nothing happens really. The NSLog() events are printed and then the program hits the while(1) ; loop. Yours does work though so I am examining some differences. Just out of curiosity what type of project did you create? View based?
     
  25. Moderator

    dejo

    Staff Member

    Joined:
    Sep 2, 2004
    Location:
    The Centennial State
    #25
    Ah, well, there's your problem! What the heck is that supposed to be doing (other than blocking the UI loop)? Get rid of it!

    Maybe we could've gotten to the issue earlier, if you had responded to my query about it when I asked. :)
     

Share This Page