Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
// A view that uses Lion's auto layout code to automatically "stack" views horizontally or vertically. It optionally resizes added subviews along the non-aligned axis.
// It resizes itself based on its content.
// ##############################################################
//
// CStackView.h
// SceneKitTest
//
// Created by Jonathan Wight on 2/19/12.
// Copyright (c) 2012 toxicsoftware.com. All rights reserved.
//
#import <Cocoa/Cocoa.h>
@interface CStackView : NSView
@property (readwrite, nonatomic, assign) BOOL constrainSubviewSize;
@property (readwrite, nonatomic, assign) NSLayoutConstraintOrientation orientation;
@end
// ##############################################################
//
// CStackView.m
// SceneKitTest
//
// Created by Jonathan Wight on 2/19/12.
// Copyright (c) 2012 toxicsoftware.com. All rights reserved.
//
#import "CStackView.h"
@interface CStackView ()
@property (readwrite, nonatomic, strong) NSLayoutConstraint *endConstraint;
@end
#pragma mark -
@implementation CStackView
- (id)initWithFrame:(NSRect)inFrame
{
if ((self = [super initWithFrame:inFrame]) != NULL)
{
self.translatesAutoresizingMaskIntoConstraints = NO;
_constrainSubviewSize = YES;
_orientation = NSLayoutConstraintOrientationHorizontal;
}
return(self);
}
#if 1
- (void)drawRect:(NSRect)dirtyRect
{
[[NSColor grayColor] set];
NSRectFill(self.bounds);
}
#endif
- (void)addSubview:(NSView *)inView
{
[super addSubview:inView];
const NSLayoutAttribute theFixedDimension = self.orientation == NSLayoutConstraintOrientationHorizontal ? NSLayoutAttributeWidth : NSLayoutAttributeHeight;
const NSLayoutAttribute theDynamicDimention = self.orientation == NSLayoutConstraintOrientationHorizontal ? NSLayoutAttributeHeight : NSLayoutAttributeWidth;
const NSLayoutAttribute theNearEdge = self.orientation == NSLayoutConstraintOrientationHorizontal ? NSLayoutAttributeLeft : NSLayoutAttributeTop;
const NSLayoutAttribute theFarEdge = self.orientation == NSLayoutConstraintOrientationHorizontal ? NSLayoutAttributeRight : NSLayoutAttributeBottom;
if (self.constrainSubviewSize == YES)
{
inView.translatesAutoresizingMaskIntoConstraints = NO;
[self addConstraint:[NSLayoutConstraint constraintWithItem:inView attribute:theFixedDimension relatedBy:NSLayoutRelationEqual toItem:NULL attribute:NULL multiplier:0 constant:inView.frame.size.width]];
[self addConstraint:[NSLayoutConstraint constraintWithItem:inView attribute:theDynamicDimention relatedBy:NSLayoutRelationEqual toItem:self attribute:theDynamicDimention multiplier:1 constant:0]];
}
if (self.subviews.count == 1)
{
[self addConstraint:[NSLayoutConstraint constraintWithItem:inView attribute:theNearEdge relatedBy:NSLayoutRelationEqual toItem:self attribute:theNearEdge multiplier:1.0 constant:0.0]];
}
else
{
NSView *thePenultimateView = [self.subviews objectAtIndex:self.subviews.count - 2];
[self addConstraint:[NSLayoutConstraint constraintWithItem:inView attribute:theNearEdge relatedBy:NSLayoutRelationEqual toItem:thePenultimateView attribute:theFarEdge multiplier:1.0 constant:0.0]];
}
if (self.endConstraint != NULL)
{
[self removeConstraint:self.endConstraint];
self.endConstraint = NULL;
}
self.endConstraint = [NSLayoutConstraint constraintWithItem:self attribute:theFarEdge relatedBy:NSLayoutRelationEqual toItem:inView attribute:theFarEdge multiplier:1.0 constant:0.0];
[self addConstraint:self.endConstraint];
}
- (void)willRemoveSubview:(NSView *)subview;
{
const NSLayoutAttribute theFarEdge = self.orientation == NSLayoutConstraintOrientationHorizontal ? NSLayoutAttributeRight : NSLayoutAttributeBottom;
if (self.endConstraint != NULL)
{
[self removeConstraint:self.endConstraint];
self.endConstraint = NULL;
}
if (self.subviews.count > 1)
{
NSView *thePenultimateView = [self.subviews objectAtIndex:self.subviews.count - 2];
self.endConstraint = [NSLayoutConstraint constraintWithItem:self attribute:theFarEdge relatedBy:NSLayoutRelationEqual toItem:thePenultimateView attribute:theFarEdge multiplier:1.0 constant:0.0];
[self addConstraint:self.endConstraint];
}
}
@end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment