Center SubViews in ParentView in Objective-C - ios

I have the following code:
UIView *parentView = [[UIView alloc] init];
parentView.frame = CGRectMake(0, 0, 100, 100);
parentView.center = self.view.center;
parentView.backgroundColor = [UIColor greenColor];
UIView *subView = [[UIView alloc] init];
subView.backgroundColor = [UIColor redColor];
subView.frame = CGRectMake(0, 0, 50, 50);
subView.center = parentView.center;
[parentView addSubview:subView];
[self.view addSubview:parentView];
Which produces the following result:
Why is the red view not centered in the green view since they have the same center?

The Apple UIView documentation states for the center property:
The center is specified within the coordinate system of its superview and is measured in points. Setting this property changes the values of the frame properties accordingly.
That means the parentView center will be relative to its superview (the white background view by the looks of your screenshot).
To get the desired result you need to do something like this:
subview.center = CGPointMake(CGRectGetMidX(parentView.bounds),
CGRectGetMidY(parentView.bounds));
But you should really be using autolayout for this type of thing.

You are setting the green view to be the center of it's superview, but you are setting the red view to be in the center of it's superview's superview...
The way to fix that with the smallest amount of code change would be to change the red view's superview.
[self.view addSubview:parentView];
[self.view addSubview:subView];
EDIT: To explain a little further what is going on. Say when you set the center of your green view it gets set to (500,500). That's inside it's superview, so it gets set to the middle of the screen. Then you set your red view's center to the same value as the green view's center, (500,500). But it's parent that it is relative to is the red view, so it gets placed (500,500) from the origin point of the green view. It gets placed near the bottom right of the screen.

You are Doing Like this
UIView *parentView = [[UIView alloc] init];
parentView.frame = CGRectMake(0, 0, 100, 100);
parentView.center = self.view.center;
parentView.backgroundColor = [UIColor greenColor];
UIView *subView = [[UIView alloc] init];
subView.backgroundColor = [UIColor redColor];
CGFloat SubviewX = (parentView.frame.size.width - 50)/2;
CGFloat SubviewY = (parentView.frame.size.height - 50)/2;
subView.frame = CGRectMake(SubviewX, SubviewY, 50, 50);
[parentView addSubview:subView];
[self.view addSubview:parentView];

The best way to center a view, and maintain it that way even if the view changes its view frame is using constraints:
UIView *parentView = [[UIView alloc] init];
parentView.translatesAutoresizingMaskIntoConstraints = NO;
// You might want to add constraints for the view's size
parentView.frame = CGRectMake(0, 0, 100, 100);
parentView.backgroundColor = [UIColor greenColor];
[self.view addSubview:parentView];
NSContraint *xContraint = [NSLayoutConstraint constraintWithItem:parentView
attribute:NSLayoutAttributeCenterX
relatedBy:NSLayoutRelationEqual
toItem:self.view
attribute:NSLayoutAttributeCenterX
multiplier:1.0
constant:0.0];
[self.view addConstraint:xContraint];
NSContraint *yContraint = [NSLayoutConstraint constraintWithItem:parentView
attribute:NSLayoutAttributeCenterY
relatedBy:NSLayoutRelationEqual
toItem:self.view
attribute:NSLayoutAttributeCenterY
multiplier:1.0
constant:0.0];
[self.view addConstraint:yContraint];
UIView *subView = [[UIView alloc] init];
subView.translatesAutoresizingMaskIntoConstraints = NO;
// You might want to add constraints for the view's size
subView.frame = CGRectMake(0, 0, 50, 50);
subView.backgroundColor = [UIColor redColor];
[parentView addSubview:subView];
NSContraint *xSubContraint = [NSLayoutConstraint constraintWithItem:subView
attribute:NSLayoutAttributeCenterX
relatedBy:NSLayoutRelationEqual
toItem:parentView
attribute:NSLayoutAttributeCenterX
multiplier:1.0
constant:0.0];
[parentView addConstraint:xSubContraint];
NSContraint *ySubContraint = [NSLayoutConstraint constraintWithItem:subView
attribute:NSLayoutAttributeCenterY
relatedBy:NSLayoutRelationEqual
toItem:parentView
attribute:NSLayoutAttributeCenterY
multiplier:1.0
constant:0.0];
[parentView addConstraint:ySubContraint];

Related

how to make rectangle for imageView frame as a subview in objective c

how to make rectangle for imageView frame as a subview in objective c?
inside view controller i've a view , inside that view i want to put an imageView , and imageView frame should be less than the frame of the view frame and imageView should be in the centre of the view frame.
Firstly, set the imageView's size, secondary, set the imageView's coordinates, here is code:
UIView *container = [[UIView alloc] initWithFrame:CGRectMake(100, 100, 200, 200)];
container.backgroundColor = [UIColor blueColor];
[self.view addSubview:container];
UIImageView *imageView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)];
imageView.backgroundColor = [UIColor redColor];
[container addSubview:imageView];
CGRect f = imageView.frame;
f.origin.x = CGRectGetWidth(container.bounds) / 2.0f - CGRectGetWidth(f) / 2.0;
f.origin.y = CGRectGetHeight(container.bounds) / 2.0f - CGRectGetHeight(f) / 2.0f;
imageView.frame = f;
or set the imageView's center(Alert! The imageView add to the self.view!)
UIView *container = [[UIView alloc] initWithFrame:CGRectMake(100, 100, 200, 200)];
container.backgroundColor = [UIColor blueColor];
[self.view addSubview:container];
UIImageView *imageView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 100, 100)];
imageView.backgroundColor = [UIColor redColor];
[self.view addSubview:imageView];
imageView.center = container.center;
Also, you can use autolayout, like this:
UIView *container = [[UIView alloc] initWithFrame:CGRectMake(100, 100, 200, 200)];
container.backgroundColor = [UIColor blueColor];
[self.view addSubview:container];
UIImageView *imageView = [[UIImageView alloc] init];
imageView.backgroundColor = [UIColor redColor];
[container addSubview:imageView];
imageView.translatesAutoresizingMaskIntoConstraints = NO;
NSLayoutConstraint *c1 = [NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1 constant:100];
NSLayoutConstraint *c2 = [NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1 constant:100];
NSLayoutConstraint *c3 = [NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:container attribute:NSLayoutAttributeCenterX multiplier:1 constant:0];
NSLayoutConstraint *c4 = [NSLayoutConstraint constraintWithItem:imageView attribute:NSLayoutAttributeCenterY relatedBy:NSLayoutRelationEqual toItem:container attribute:NSLayoutAttributeCenterY multiplier:1 constant:0];
c1.active = YES;
c2.active = YES;
c3.active = YES;
c4.active = YES;
All of the solutions above will put the imageView at the center of container

Objective-C add more UIButton horizontally

I am using a open source UIAlertView.View is
I want to add more button like horizontally, one in left side and another in right of BYE button, like this one
my using source-code are bellow
-(void)popUPView{
UIView* contentView = [[UIView alloc] init];
contentView.translatesAutoresizingMaskIntoConstraints = NO;
contentView.backgroundColor = [UIColor klcLightGreenColor];
contentView.layer.cornerRadius = 12.0;
UILabel* dismissLabel = [[UILabel alloc] init];
dismissLabel.translatesAutoresizingMaskIntoConstraints = NO;
dismissLabel.backgroundColor = [UIColor clearColor];
dismissLabel.textColor = [UIColor whiteColor];
dismissLabel.font = [UIFont boldSystemFontOfSize:32.0];
dismissLabel.text = #"Hi.";
UIButton* dismissButton = [UIButton buttonWithType:UIButtonTypeCustom];
dismissButton.translatesAutoresizingMaskIntoConstraints = NO;
dismissButton.contentEdgeInsets = UIEdgeInsetsMake(10, 20, 10, 20);
dismissButton.backgroundColor = [UIColor klcGreenColor];
[dismissButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[dismissButton setTitleColor:[[dismissButton titleColorForState:UIControlStateNormal] colorWithAlphaComponent:0.5] forState:UIControlStateHighlighted];
dismissButton.titleLabel.font = [UIFont boldSystemFontOfSize:16.0];
[dismissButton setTitle:#"Bye" forState:UIControlStateNormal];
dismissButton.layer.cornerRadius = 6.0;
[contentView addSubview:dismissLabel];
[contentView addSubview:dismissButton];
NSDictionary* views = NSDictionaryOfVariableBindings(contentView, dismissButton, dismissLabel);
[contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:#"V:|-(16)-[dismissLabel]-(10)-[dismissButton]-(24)-|"
options:NSLayoutFormatAlignAllCenterX
metrics:nil
views:views]];
[contentView addConstraints:
[NSLayoutConstraint constraintsWithVisualFormat:#"H:|-(36)-[dismissLabel]-(36)-|"
options:0
metrics:nil
views:views]];
KLCPopup *popup = [KLCPopup popupWithContentView:contentView
showType:KLCPopupShowTypeShrinkIn
dismissType:KLCPopupDismissTypeShrinkOut
maskType:KLCPopupMaskTypeDimmed
dismissOnBackgroundTouch:TRUE
dismissOnContentTouch:FALSE];
[popup show];
}
would you kindly help me how to solve this problem . Thanks is advance
For this you must set proper leading/trailing values ,
leftView.trailing = rightView.leading
for example if you want to align a new view to the right , you would do something like this
UIView *viewToAllign = yourView;
UIView *view = [[UIView alloc] init];
imageViewOn.translatesAutoresizingMaskIntoConstraints = NO;
[self.view addSubview:view];
NSLayoutConstraint *leading = [NSLayoutConstraint constraintWithItem:view
attribute:NSLayoutAttributeLeading
relatedBy:NSLayoutRelationEqual
toItem:viewToAllign
attribute:NSLayoutAttributeTrailing
multiplier:1
constant:SPACING_BETWEEN_VIEWS];
or if you want to align something on the left , just switch layout attributes
UIView *viewToAllign = yourView;
UIView *view = [[UIView alloc] init];
imageViewOn.translatesAutoresizingMaskIntoConstraints = NO;
[self.view addSubview:view];
NSLayoutConstraint *leading = [NSLayoutConstraint constraintWithItem:view
attribute:NSLayoutAttributeTrailing
relatedBy:NSLayoutRelationEqual
toItem:viewToAllign
attribute:NSLayoutAttributeLeading
multiplier:1
constant:SPACING_BETWEEN_VIEWS];
then you have to create other constraints ( height , width , top and bottom )
after this , you can add constraints to your container view

UILabel is not centered in my UIView

I'm adding a UILabel to a UIView on initialization and the label will not center itself. I've tried centering it is layoutSubviews and adding constraints programmatically with no luck. When it appears it is about 200 pixels to the left of the center. Here is my code. Thanks in advance.
- (instancetype)initWithTitle:(NSString *)title andBody:(NSString *)body Andwidth:(CGFloat)width {
self = [super initWithFrame:CGRectMake(0, 0, width, 60)];
if (self) {
UIView *containerView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, width, 60)];
containerView.backgroundColor = [UIColor orangeColor];
[self addSubview:containerView];
self.winningLabel = [[UILabel alloc] initWithFrame:CGRectMake(0,0, 300, 40)];
self.winningLabel.textColor = [UIColor whiteColor];
self.winningLabel.font = [UIFont fontWithName:#"Avenir" size:30];
self.winningLabel.backgroundColor = [UIColor clearColor];
self.winningLabel.lineBreakMode = NSLineBreakByTruncatingTail;
self.winningLabel.numberOfLines = 2;
self.winningLabel.text = #"YOU WIN";
self.winningLabel.hidden = YES;
[containerView addSubview:self.winningLabel];
NSLayoutConstraint *xCenterConstraint = [NSLayoutConstraint constraintWithItem:self.winningLabel attribute:NSLayoutAttributeCenterX relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterX multiplier:1.0 constant:0];
[self addConstraint:xCenterConstraint];
NSLayoutConstraint *yCenterConstraint = [NSLayoutConstraint constraintWithItem:self.winningLabel attribute:NSLayoutAttributeCenterY relatedBy:NSLayoutRelationEqual toItem:self attribute:NSLayoutAttributeCenterY multiplier:1.0 constant:0];
[self addConstraint:yCenterConstraint];
}
return self;
}
- (void)layoutSubviews {
[self.winningLabel setCenter:self.center];
}
I think you forget the text alignment. By default the text in a label is aligned to the left. If you want it to be in the center, you should specify it explicitly.
self.winningLabel.textAlignment = NSTextAlignmentCenter;

how to set subview of UIScrollView using autolayout

i am trying to implement Horizontal scrollview with ten views.
its working fine in portrait mode but i want same scenario in landscape too.
can anyone help me by which constraint i can achieve this?
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
self.title=#"Demo.....";
self.myScrollView.pagingEnabled = YES;
NSInteger numberOfViews = 10;
for (int i = 0; i < numberOfViews; i++) {
CGFloat myOrigin = i * self.view.frame.size.width;
UIView *myView = [[UIView alloc] initWithFrame:CGRectMake(myOrigin, 0, self.view.frame.size.width, self.view.frame.size.height)];
myView.backgroundColor = [UIColor purpleColor];
CGRect myFrame = CGRectMake(10.0f, 70.0f, 200.0f, 25.0f);
UILabel *myLabel = [[UILabel alloc] initWithFrame:myFrame];
myLabel.translatesAutoresizingMaskIntoConstraints = NO;
myLabel.text = [NSString stringWithFormat:#"This is page number %d", i];
myLabel.font = [UIFont boldSystemFontOfSize:16.0f];
myLabel.textAlignment = NSTextAlignmentLeft;
[myView addSubview:myLabel];
//set the scroll view delegate to self so that we can listen for changes
self.myScrollView.delegate = self;
//add the subview to the scroll view
[self.myScrollView addSubview:myView];
NSLayoutConstraint *constraintLeft = [NSLayoutConstraint constraintWithItem:myView
attribute:NSLayoutAttributeLeft
relatedBy:NSLayoutRelationEqual
toItem:self.myScrollView
attribute:NSLayoutAttributeLeft
multiplier:1.0
constant:0.0];
// 0px to the right of the UIScrollView
NSLayoutConstraint *constraintRight = [NSLayoutConstraint constraintWithItem:myView
attribute:NSLayoutAttributeRight
relatedBy:NSLayoutRelationEqual
toItem:self.myScrollView
attribute:NSLayoutAttributeRight
multiplier:1.0
constant:0.0];
[self.myScrollView addConstraint:constraintLeft];
[self.myScrollView addConstraint:constraintRight];
}
//set the content size of the scroll view, we keep the height same so it will only
//scroll horizontally
self.myScrollView.contentSize = CGSizeMake(self.view.frame.size.width * numberOfViews,
self.view.frame.size.height);
//we set the origin to the 3rd page
CGPoint scrollPoint = CGPointMake(self.view.frame.size.width * 2, 0);
//change the scroll view offset the the 3rd page so it will start from there
[myScrollView setContentOffset:scrollPoint animated:YES];
[self.view addSubview:self.myScrollView];
}
in my above code,
ten view is completely added into scrollview and working fine in portrait mode but when i change the orientation to horizontal it will not resize and not scrolled.
You need to tie subviews width constraint equal to scrollView width
for (UIView *subView in subViews)
{
NSLayoutConstraint *constraintEqualWidth = [NSLayoutConstraint constraintWithItem:subView
attribute:NSLayoutAttributeWidth
relatedBy:NSLayoutRelationEqual
toItem:self.myScrollView
attribute:NSLayoutAttributeWidth
multiplier:1.0
constant:0.0];
[subView addConstraint:constraintEqualWidth];
}

how content inset affects layout

While working with UIScrollView, I noticed some weird behavior about auto layout and content inset; take the following code for example:
- (void) loadView
{
UIScrollView * scroller = [[UIScrollView alloc] init];
scroller.backgroundColor = [UIColor orangeColor];
UILabel * label = [[UILabel alloc] init];
label.backgroundColor = [UIColor blueColor];
label.translatesAutoresizingMaskIntoConstraints = NO;
[scroller addSubview:label];
[scroller addConstraint: [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeLeft relatedBy:NSLayoutRelationEqual toItem:scroller attribute:NSLayoutAttributeLeft multiplier:1.0 constant:40]];
[scroller addConstraint: [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeTop relatedBy:NSLayoutRelationEqual toItem:scroller attribute:NSLayoutAttributeTop multiplier:1.0 constant:20]];
[scroller addConstraint: [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeWidth relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1.0 constant:240]];
[scroller addConstraint: [NSLayoutConstraint constraintWithItem:label attribute:NSLayoutAttributeHeight relatedBy:NSLayoutRelationEqual toItem:nil attribute:NSLayoutAttributeNotAnAttribute multiplier:1.0 constant:44]];
self.view = scroller;
scroller.contentInset = UIEdgeInsetsMake(44, 0, 0, 0); //this is the game changer
}
Without the last line that changes the content inset, the UILabel is at (40, 20) as expected. When altering the content inset, the label moved to (40, 108), instead of (40, 64); the top content inset is somehow doubled.
If the UILabel is created with set frame and without those constraints as:
- (void) loadView
{
UIScrollView * scroller = [[UIScrollView alloc] init];
scroller.backgroundColor = [UIColor orangeColor];
CGRect frame = CGRectMake(40, 20, 240, 44);
UILabel * label = [[UILabel alloc] initWithFrame:frame];
label.backgroundColor = [UIColor blueColor];
[scroller addSubview:label];
self.view = scroller;
scroller.contentInset = UIEdgeInsetsMake(44, 0, 0, 0);
}
Then it behave as expected (40, 20) and (40, 64) depending on the content inset.
I checked with the documents and tried flipping some switches, but still can't figure out why.
BTW, that was the result from the IOS(6) simulator, I did not try it on device yet.
P.S.
Things appear as expected on simulator with IOS7, except the difference of the new status bar behavior.

Resources