2015-08-15 16:05:48 -05:00
|
|
|
// 15 august 2015
|
|
|
|
#import "uipriv_darwin.h"
|
|
|
|
|
2016-04-30 16:14:14 -05:00
|
|
|
NSLayoutConstraint *mkConstraint(id view1, NSLayoutAttribute attr1, NSLayoutRelation relation, id view2, NSLayoutAttribute attr2, CGFloat multiplier, CGFloat c, NSString *desc)
|
2015-08-15 16:05:48 -05:00
|
|
|
{
|
2016-04-30 17:07:36 -05:00
|
|
|
NSLayoutConstraint *constraint;
|
2015-08-15 16:05:48 -05:00
|
|
|
|
2016-04-30 17:07:36 -05:00
|
|
|
constraint = [NSLayoutConstraint constraintWithItem:view1
|
2016-04-30 16:14:14 -05:00
|
|
|
attribute:attr1
|
|
|
|
relatedBy:relation
|
|
|
|
toItem:view2
|
|
|
|
attribute:attr2
|
|
|
|
multiplier:multiplier
|
|
|
|
constant:c];
|
|
|
|
// apparently only added in 10.9
|
2016-04-30 17:07:36 -05:00
|
|
|
if ([constraint respondsToSelector:@selector(setIdentifier:)])
|
|
|
|
[((id) constraint) setIdentifier:desc];
|
|
|
|
return constraint;
|
2015-08-15 16:05:48 -05:00
|
|
|
}
|
2016-05-11 17:06:29 -05:00
|
|
|
|
2016-05-26 20:25:32 -05:00
|
|
|
CGFloat uiDarwinMarginAmount(void *reserved)
|
|
|
|
{
|
|
|
|
return 20.0;
|
|
|
|
}
|
|
|
|
|
|
|
|
CGFloat uiDarwinPaddingAmount(void *reserved)
|
|
|
|
{
|
|
|
|
return 8.0;
|
|
|
|
}
|
|
|
|
|
2016-05-12 19:18:22 -05:00
|
|
|
// this is needed for NSSplitView to work properly; see http://stackoverflow.com/questions/34574478/how-can-i-set-the-position-of-a-nssplitview-nowadays-setpositionofdivideratind (stal in irc.freenode.net/#macdev came up with the exact combination)
|
2016-05-12 19:20:39 -05:00
|
|
|
// turns out it also works on NSTabView and NSBox too, possibly others!
|
|
|
|
// and for bonus points, it even seems to fix unsatisfiable-constraint-autoresizing-mask issues with NSTabView and NSBox too!!! this is nuts
|
2016-05-12 19:18:22 -05:00
|
|
|
void jiggleViewLayout(NSView *view)
|
|
|
|
{
|
|
|
|
[view setNeedsLayout:YES];
|
|
|
|
[view layoutSubtreeIfNeeded];
|
|
|
|
}
|
|
|
|
|
2016-05-11 17:06:29 -05:00
|
|
|
static CGFloat margins(int margined)
|
|
|
|
{
|
|
|
|
if (!margined)
|
|
|
|
return 0.0;
|
2016-05-26 20:25:32 -05:00
|
|
|
return uiDarwinMarginAmount(NULL);
|
2016-05-11 17:06:29 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
void singleChildConstraintsEstablish(struct singleChildConstraints *c, NSView *contentView, NSView *childView, BOOL hugsTrailing, BOOL hugsBottom, int margined, NSString *desc)
|
|
|
|
{
|
|
|
|
CGFloat margin;
|
|
|
|
|
|
|
|
margin = margins(margined);
|
|
|
|
|
|
|
|
c->leadingConstraint = mkConstraint(contentView, NSLayoutAttributeLeading,
|
|
|
|
NSLayoutRelationEqual,
|
|
|
|
childView, NSLayoutAttributeLeading,
|
2016-05-12 00:49:00 -05:00
|
|
|
1, -margin,
|
2016-05-11 17:06:29 -05:00
|
|
|
[desc stringByAppendingString:@" leading constraint"]);
|
|
|
|
[contentView addConstraint:c->leadingConstraint];
|
2016-05-13 12:08:00 -05:00
|
|
|
[c->leadingConstraint retain];
|
2016-05-11 17:06:29 -05:00
|
|
|
|
|
|
|
c->topConstraint = mkConstraint(contentView, NSLayoutAttributeTop,
|
|
|
|
NSLayoutRelationEqual,
|
|
|
|
childView, NSLayoutAttributeTop,
|
2016-05-12 00:49:00 -05:00
|
|
|
1, -margin,
|
2016-05-11 17:06:29 -05:00
|
|
|
[desc stringByAppendingString:@" top constraint"]);
|
|
|
|
[contentView addConstraint:c->topConstraint];
|
2016-05-13 12:08:00 -05:00
|
|
|
[c->topConstraint retain];
|
2016-05-11 17:06:29 -05:00
|
|
|
|
2016-05-13 12:08:00 -05:00
|
|
|
c->trailingConstraintGreater = mkConstraint(contentView, NSLayoutAttributeTrailing,
|
|
|
|
NSLayoutRelationGreaterThanOrEqual,
|
|
|
|
childView, NSLayoutAttributeTrailing,
|
|
|
|
1, margin,
|
|
|
|
[desc stringByAppendingString:@" trailing >= constraint"]);
|
2016-05-11 17:06:29 -05:00
|
|
|
if (hugsTrailing)
|
2016-05-13 12:08:00 -05:00
|
|
|
[c->trailingConstraintGreater setPriority:NSLayoutPriorityDefaultLow];
|
|
|
|
[contentView addConstraint:c->trailingConstraintGreater];
|
|
|
|
[c->trailingConstraintGreater retain];
|
|
|
|
|
|
|
|
c->trailingConstraintEqual = mkConstraint(contentView, NSLayoutAttributeTrailing,
|
|
|
|
NSLayoutRelationEqual,
|
2016-05-11 17:06:29 -05:00
|
|
|
childView, NSLayoutAttributeTrailing,
|
2016-05-12 00:49:00 -05:00
|
|
|
1, margin,
|
2016-05-13 12:08:00 -05:00
|
|
|
[desc stringByAppendingString:@" trailing == constraint"]);
|
|
|
|
if (!hugsTrailing)
|
|
|
|
[c->trailingConstraintEqual setPriority:NSLayoutPriorityDefaultLow];
|
|
|
|
[contentView addConstraint:c->trailingConstraintEqual];
|
|
|
|
[c->trailingConstraintEqual retain];
|
2016-05-11 17:06:29 -05:00
|
|
|
|
2016-05-13 12:08:00 -05:00
|
|
|
c->bottomConstraintGreater = mkConstraint(contentView, NSLayoutAttributeBottom,
|
|
|
|
NSLayoutRelationGreaterThanOrEqual,
|
|
|
|
childView, NSLayoutAttributeBottom,
|
|
|
|
1, margin,
|
|
|
|
[desc stringByAppendingString:@" bottom >= constraint"]);
|
2016-05-11 17:06:29 -05:00
|
|
|
if (hugsBottom)
|
2016-05-13 12:08:00 -05:00
|
|
|
[c->bottomConstraintGreater setPriority:NSLayoutPriorityDefaultLow];
|
|
|
|
[contentView addConstraint:c->bottomConstraintGreater];
|
|
|
|
[c->bottomConstraintGreater retain];
|
|
|
|
|
|
|
|
c->bottomConstraintEqual = mkConstraint(contentView, NSLayoutAttributeBottom,
|
|
|
|
NSLayoutRelationEqual,
|
2016-05-11 17:06:29 -05:00
|
|
|
childView, NSLayoutAttributeBottom,
|
2016-05-12 00:49:00 -05:00
|
|
|
1, margin,
|
2016-05-13 12:08:00 -05:00
|
|
|
[desc stringByAppendingString:@" bottom == constraint"]);
|
|
|
|
if (!hugsBottom)
|
|
|
|
[c->bottomConstraintEqual setPriority:NSLayoutPriorityDefaultLow];
|
|
|
|
[contentView addConstraint:c->bottomConstraintEqual];
|
|
|
|
[c->bottomConstraintEqual retain];
|
2016-05-11 17:06:29 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
void singleChildConstraintsRemove(struct singleChildConstraints *c, NSView *cv)
|
|
|
|
{
|
|
|
|
if (c->leadingConstraint != nil) {
|
|
|
|
[cv removeConstraint:c->leadingConstraint];
|
|
|
|
[c->leadingConstraint release];
|
|
|
|
c->leadingConstraint = nil;
|
|
|
|
}
|
|
|
|
if (c->topConstraint != nil) {
|
|
|
|
[cv removeConstraint:c->topConstraint];
|
|
|
|
[c->topConstraint release];
|
|
|
|
c->topConstraint = nil;
|
|
|
|
}
|
2016-05-13 12:08:00 -05:00
|
|
|
if (c->trailingConstraintGreater != nil) {
|
|
|
|
[cv removeConstraint:c->trailingConstraintGreater];
|
|
|
|
[c->trailingConstraintGreater release];
|
|
|
|
c->trailingConstraintGreater = nil;
|
|
|
|
}
|
|
|
|
if (c->trailingConstraintEqual != nil) {
|
|
|
|
[cv removeConstraint:c->trailingConstraintEqual];
|
|
|
|
[c->trailingConstraintEqual release];
|
|
|
|
c->trailingConstraintEqual = nil;
|
|
|
|
}
|
|
|
|
if (c->bottomConstraintGreater != nil) {
|
|
|
|
[cv removeConstraint:c->bottomConstraintGreater];
|
|
|
|
[c->bottomConstraintGreater release];
|
|
|
|
c->bottomConstraintGreater = nil;
|
2016-05-11 17:06:29 -05:00
|
|
|
}
|
2016-05-13 12:08:00 -05:00
|
|
|
if (c->bottomConstraintEqual != nil) {
|
|
|
|
[cv removeConstraint:c->bottomConstraintEqual];
|
|
|
|
[c->bottomConstraintEqual release];
|
|
|
|
c->bottomConstraintEqual = nil;
|
2016-05-11 17:06:29 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void singleChildConstraintsSetMargined(struct singleChildConstraints *c, int margined)
|
|
|
|
{
|
|
|
|
CGFloat margin;
|
|
|
|
|
|
|
|
margin = margins(margined);
|
|
|
|
if (c->leadingConstraint != nil)
|
2016-05-12 00:49:00 -05:00
|
|
|
[c->leadingConstraint setConstant:-margin];
|
2016-05-11 17:06:29 -05:00
|
|
|
if (c->topConstraint != nil)
|
2016-05-12 00:49:00 -05:00
|
|
|
[c->topConstraint setConstant:-margin];
|
2016-05-13 12:08:00 -05:00
|
|
|
if (c->trailingConstraintGreater != nil)
|
|
|
|
[c->trailingConstraintGreater setConstant:margin];
|
|
|
|
if (c->trailingConstraintEqual != nil)
|
|
|
|
[c->trailingConstraintEqual setConstant:margin];
|
|
|
|
if (c->bottomConstraintGreater != nil)
|
|
|
|
[c->bottomConstraintGreater setConstant:margin];
|
|
|
|
if (c->bottomConstraintEqual != nil)
|
|
|
|
[c->bottomConstraintEqual setConstant:margin];
|
2016-05-11 17:06:29 -05:00
|
|
|
}
|