vinothp
vinothp

Reputation: 10069

How to add View below other view in ViewController in iOS?

In my app i am creating view controller with mixed of UILabel and UITextview which want to be scrollable because the text are dynamic and also exceeds vertical screen size.

I am currently having Scrollview which has subviews as below. Views are created in Xcode 4.3 Storyboard.

UILabel1(Say Heading)

UITextView1(Dynamic text which can be any size)

UILabel2(Second Heading)

UITextView2(Dynamic text which can be any size)

and so on.

The problem is

When the UITextView1 has more content then it overlaps with UILabel2 which i don't want.

I would like to have UILabel1 on top of scrollView and UITextView1 below the UILabel1. UILabel2 below UITextView1 and so on.

What i have to do to achieve this?

EDIT

In Storyboard

![enter image description here][1]

In Simulator

![enter image description here][2]

Thanks for your help guys. Much appreciated.

Code

- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.

[scrollView setScrollEnabled:YES];     
[self.view addSubview:cockTailNameLabel];
[self.view insertSubview:txtIngredients belowSubview:cockTailNameLabel];
[self.view insertSubview:scrollView belowSubview:cockTailNameLabel];
//[scrollView]

[self.cockTailNameLabel setText:self.passcockTailName];  

[_txtUse setText:self.passUse]; 
[_txtUse setEditable:NO];
[_txtUse setUserInteractionEnabled:NO];

CGRect useFrame = _txtUse.frame;
useFrame.size.height = _txtUse.contentSize.height;
_txtUse.frame = useFrame; 

[txtIngredients setText:self.passIngredients];
[txtIngredients setEditable:NO];
[txtIngredients setUserInteractionEnabled:NO];
CGRect ingredientFrame = txtIngredients.frame;
ingredientFrame.size.height = txtIngredients.contentSize.height;
txtIngredients.frame = ingredientFrame;  


[txtRecipe setText:self.passReceipe];
[txtRecipe setEditable:NO];
[txtRecipe setUserInteractionEnabled:NO];
CGRect recipeFrame = txtIngredients.frame;
recipeFrame.size.height = txtRecipe.contentSize.height;
txtRecipe.frame = recipeFrame;

[scrollView insertSubview:_txtUse belowSubview:cockTailNameLabel];
[scrollView insertSubview:titleIngredients belowSubview:_txtUse];
[scrollView insertSubview:txtIngredients belowSubview:titleIngredients];
[scrollView insertSubview:btnReceipe belowSubview:txtIngredients];
[scrollView insertSubview:btnHome belowSubview:txtIngredients];
[scrollView insertSubview:txtRecipe belowSubview:btnHome];
[scrollView insertSubview:btnfacebookShare belowSubview:txtRecipe];
[scrollView insertSubview:btnTwitterShare belowSubview:txtRecipe];



/*[scrollView addSubview:_txtUse];
[scrollView addSubview:titleIngredients];
[scrollView addSubview:txtIngredients];
[scrollView addSubview:btnReceipe];
[scrollView addSubview:btnHome];
[scrollView addSubview:txtRecipe];
[scrollView addSubview:btnfacebookShare];
[scrollView addSubview:btnTwitterShare];*/

[scrollView setContentSize:CGSizeMake(320, 1000)];

NSLog(@"RecipeName :%@ ",passcockTailName);

}

Upvotes: 5

Views: 13385

Answers (6)

Lenka Pitonakova
Lenka Pitonakova

Reputation: 1116

I think adding a transparent UI button is the fastest solution. You could add it once and then show / hide whenever you need to disable all views below the current one (assuming the "current" view, say a popup, was added last to your superview).

Declare an instance variable UIButton* _parentDisablingOverlay; in your popup view, then add this in its init or layoutSubviews method:

_parentDisablingOverlay = [[UIButton alloc] initWithFrame:CGRectMake(0,0, self.superview.frame.size.width, self.superview.frame.size.height)];
[self.superview insertSubview:_parentDisablingOverlay belowSubview:self];
_parentDisablingOverlay.hidden = true;

Later on, when you want to show the popup and disable everything below:

- (void) open {
   self.hidden = false;
   _parentDisablingOverlay.hidden = false;
}

Similarly to close and re-enable everything:

- (void) close {
    self.hidden = true;
    _parentDisablingOverlay.hidden = true;
}

Upvotes: 0

Frostmourne
Frostmourne

Reputation: 174

In my case I had to project it over the parent view, so remember there is also something,

- (void)insertSubview:(UIView *)view aboveSubview:(UIView *)siblingSubview

Upvotes: 0

Sj.
Sj.

Reputation: 1724

Your issue is labels are coming on top of the textview (Overlapped), right?

In This case, you are modifying the height of the textview dynamically. If its just for display purpose you can set the text to a UILabel with numberOfLines = 0 instead of UITextview; As its added to scrollview adding a label will be fine.

Also you need to modify the origin.y of the remaining views so that it will be properly aligned. ie, secondView.origin.y = firstView.origin.y + firstView.size.height + offset. Likewise modify the origin of the remaining views wrt the just above view. So that its origin will lie outside the previous view frame.

Upvotes: 0

frankWhite
frankWhite

Reputation: 1542

In code (in viewDidLoad):

UIScrollView *scroll =[[UIScrollView alloc] initWithFrame:CGrectMake(0,0 320, 480)];
[self.view addSubview:scroll];
// code to init your UI object
UILabel *uilabel1 = [[UIlabel alloc] initWithFrame:CGrectMake(10,10, 100, 40)]; // example 
uilabel1.font = [UIFont systemFontOfSize:10];
uilabel1.text = @"UILabel1";
uilabel1.backgroundColor = [UIColor clearColor];
//
//
UILabel *uilabel2 = [[UIlabel alloc] initWithFrame:CGrectMake(10, 10 + 10 + uilabel1.frame.origin.y, 100, 40)]; // example
uilabel2.font = [UIFont systemFontOfSize:10];
uilabel2.text = @"UILabel2";
uilabel2.backgroundColor = [UIColor clearColor];
//
//
[scroll addSubview:uilabel1];
[uilabel1 releale];
[scroll addSubview:uilabel2];
[uilabel2 releale];
//
//
// in end 
float offset = 10.0 * 2; // offset between uiobjects, N - number of objects
scroll.contentSize = CGSizeMake (0, 0, uilabel1.frame.size.height + uilabel2.frame.size.height + offset, 320);

Note that you may set frame (and other properties) of yours uiobjects and adds it in order to descend.

Upvotes: 1

Zhang
Zhang

Reputation: 11607

You can tell next view to start from the end of the first view like so:

startYOfNextView = firstView.frame.origin.y position + firstView.frame.size.height;

Do the same for the rest of the other view. If your view has variable text length, you may need to precaculate the height of the string based on a specific font e.g.:

CGSize maxSize = CGSizeMake(widthOfView, 9999999);
CGSize expectedSize = CGSizeMake(stringVar sizeWithFont:[UIFont fontWithName:@"Arial"] withMaxSize:maxSize lineBreakMode:UILineBreakModeWordWrap);

then tell your dynamic view to use the height of expectedSize variable like so:

myDynamicView = [[UILabel alloc] initWithFrame:CGRectMake(..., expectedSize.height)];

Upvotes: 0

danqing
danqing

Reputation: 3668

In Storyboard or IB you can rearrange them freely.

In code you do - (void)insertSubview:(UIView *)view belowSubview:(UIView *)siblingSubview.

Upvotes: 12

Related Questions