teacup 1.3.4 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (88) hide show
  1. data/Gemfile +1 -1
  2. data/Gemfile.lock +3 -3
  3. data/README.md +1172 -319
  4. data/Rakefile +8 -1
  5. data/app/app_delegate.rb +1 -1
  6. data/app/controllers/appearance_controller.rb +13 -0
  7. data/app/controllers/landscape_only_controller.rb +1 -1
  8. data/app/controllers/{first_controller.rb → main_controller.rb} +4 -3
  9. data/app/controllers/motion_layout_controller.rb +22 -0
  10. data/app/styles/appearance.rb +24 -0
  11. data/app/styles/main_styles.rb +8 -6
  12. data/app/views/custom_view.rb +1 -0
  13. data/lib/teacup/calculations.rb +2 -2
  14. data/lib/teacup/{z_core_extensions → core_extensions}/ca_layer.rb +0 -0
  15. data/lib/teacup/core_extensions/view_getters.rb +61 -0
  16. data/lib/teacup/handler.rb +14 -14
  17. data/lib/teacup/layout.rb +94 -17
  18. data/lib/teacup/stylesheet.rb +61 -26
  19. data/lib/teacup/stylesheet_extensions/transform.rb +88 -0
  20. data/lib/teacup/teacup_controller.rb +122 -0
  21. data/lib/teacup/teacup_util.rb +12 -7
  22. data/lib/teacup/teacup_view.rb +329 -0
  23. data/lib/teacup/version.rb +1 -1
  24. data/lib/teacup-ios/appearance.rb +96 -0
  25. data/lib/teacup-ios/core_extensions/teacup_handlers.rb +183 -0
  26. data/lib/teacup-ios/core_extensions/ui_view.rb +30 -0
  27. data/lib/teacup-ios/core_extensions/ui_view_controller.rb +110 -0
  28. data/lib/{dummy.rb → teacup-ios/dummy.rb} +2 -6
  29. data/lib/teacup-ios/handler.rb +23 -0
  30. data/lib/{teacup → teacup-ios}/style.rb +9 -10
  31. data/lib/teacup-ios/stylesheet_extensions/autoresize.rb +169 -0
  32. data/lib/{teacup/stylesheet_extensions/geometry.rb → teacup-ios/stylesheet_extensions/device.rb} +0 -0
  33. data/lib/teacup-osx/core_extensions/ns_view.rb +39 -0
  34. data/lib/teacup-osx/core_extensions/ns_view_controller.rb +21 -0
  35. data/lib/teacup-osx/core_extensions/ns_window.rb +39 -0
  36. data/lib/teacup-osx/core_extensions/ns_window_controller.rb +29 -0
  37. data/lib/{teacup/z_core_extensions/z_handlers.rb → teacup-osx/core_extensions/teacup_handlers.rb} +30 -47
  38. data/lib/teacup-osx/dummy.rb +80 -0
  39. data/lib/teacup-osx/handler.rb +16 -0
  40. data/lib/teacup-osx/style.rb +83 -0
  41. data/lib/teacup-osx/style_extensions/autoresize.rb +169 -0
  42. data/lib/teacup.rb +12 -11
  43. data/samples/Tweets/Gemfile +4 -0
  44. data/samples/Tweets/Gemfile.lock +16 -0
  45. data/samples/Tweets/README +7 -0
  46. data/samples/Tweets/Rakefile +9 -0
  47. data/samples/Tweets/app/app_delegate.rb +18 -0
  48. data/samples/Tweets/app/data_parser.rb +10 -0
  49. data/samples/Tweets/app/json_parser.rb +12 -0
  50. data/samples/Tweets/app/main_window.rb +99 -0
  51. data/samples/Tweets/app/menu.rb +108 -0
  52. data/samples/Tweets/app/stylesheet.rb +21 -0
  53. data/samples/Tweets/app/tweet.rb +11 -0
  54. data/samples/Tweets/resources/Credits.rtf +29 -0
  55. data/samples/Tweets/spec/main_spec.rb +9 -0
  56. data/samples/teacup-osx/.gitignore +1 -0
  57. data/samples/teacup-osx/Gemfile +4 -0
  58. data/samples/teacup-osx/Gemfile.lock +16 -0
  59. data/samples/teacup-osx/Rakefile +9 -0
  60. data/samples/teacup-osx/app/app_delegate.rb +23 -0
  61. data/samples/teacup-osx/app/controller.rb +11 -0
  62. data/samples/teacup-osx/app/menu.rb +108 -0
  63. data/samples/teacup-osx/app/window.rb +12 -0
  64. data/samples/teacup-osx/resources/Credits.rtf +29 -0
  65. data/samples/teacup-osx/resources/teacup.png +0 -0
  66. data/samples/teacup-osx/spec/main_spec.rb +9 -0
  67. data/spec/ios/appearance_spec.rb +18 -0
  68. data/spec/{calculations_spec.rb → ios/calculations_spec.rb} +0 -0
  69. data/spec/{constraints_spec.rb → ios/constraints_spec.rb} +0 -0
  70. data/spec/{custom_class_spec.rb → ios/custom_class_spec.rb} +0 -0
  71. data/spec/{gradient_spec.rb → ios/gradient_spec.rb} +1 -1
  72. data/spec/ios/layout_module_spec.rb +54 -0
  73. data/spec/ios/layout_spec.rb +50 -0
  74. data/spec/{main_spec.rb → ios/main_spec.rb} +52 -13
  75. data/spec/ios/motion_layout_spec.rb +44 -0
  76. data/spec/{present_modal_spec.rb → ios/present_modal_spec.rb} +0 -0
  77. data/spec/{style_spec.rb → ios/style_spec.rb} +1 -1
  78. data/spec/ios/stylesheet_extensions/autoresize_spec.rb +50 -0
  79. data/spec/{stylesheet_spec.rb → ios/stylesheet_spec.rb} +12 -0
  80. data/spec/{ui_view_getters_spec.rb → ios/ui_view_getters_spec.rb} +0 -0
  81. data/spec/{uiswitch_spec.rb → ios/uiswitch_spec.rb} +0 -0
  82. data/spec/{view_spec.rb → ios/view_spec.rb} +23 -2
  83. metadata +85 -35
  84. data/lib/teacup/stylesheet_extensions/autoresize.rb +0 -39
  85. data/lib/teacup/stylesheet_extensions/rotation.rb +0 -37
  86. data/lib/teacup/z_core_extensions/ui_view.rb +0 -262
  87. data/lib/teacup/z_core_extensions/ui_view_controller.rb +0 -263
  88. data/lib/teacup/z_core_extensions/ui_view_getters.rb +0 -58
@@ -0,0 +1,183 @@
1
+ ##|
2
+ ##| UIView.frame
3
+ ##|
4
+ Teacup.handler UIView, :left, :x do |target, x|
5
+ f = target.frame
6
+ f.origin.x = Teacup::calculate(target, :width, x)
7
+ target.frame = f
8
+ end
9
+
10
+ Teacup.handler UIView, :right do |target, r|
11
+ f = target.frame
12
+ f.origin.x = Teacup::calculate(target, :width, r) - f.size.width
13
+ target.frame = f
14
+ end
15
+
16
+ Teacup.handler UIView, :center_x, :middle_x do |target, x|
17
+ c = target.center
18
+ c.x = Teacup::calculate(target, :width, x)
19
+ target.center = c
20
+ end
21
+
22
+ Teacup.handler UIView, :top, :y do |target, y|
23
+ f = target.frame
24
+ f.origin.y = Teacup::calculate(target, :height, y)
25
+ target.frame = f
26
+ end
27
+
28
+ Teacup.handler UIView, :bottom do |target, b|
29
+ f = target.frame
30
+ f.origin.y = Teacup::calculate(target, :height, b) - f.size.height
31
+ target.frame = f
32
+ end
33
+
34
+ Teacup.handler UIView, :center_y, :middle_y do |target, y|
35
+ c = target.center
36
+ c.y = Teacup::calculate(target, :height, y)
37
+ target.center = c
38
+ end
39
+
40
+ Teacup.handler UIView, :width do |target, w|
41
+ f = target.frame
42
+ f.size.width = Teacup::calculate(target, :width, w)
43
+ target.frame = f
44
+ end
45
+
46
+ Teacup.handler UIView, :height do |target, h|
47
+ f = target.frame
48
+ f.size.height = Teacup::calculate(target, :height, h)
49
+ target.frame = f
50
+ end
51
+
52
+ Teacup.handler UIView, :size do |target, size|
53
+ f = target.frame
54
+ size_x = Teacup::calculate(target, :width, size[0])
55
+ size_y = Teacup::calculate(target, :height, size[1])
56
+ f.size = [size_x, size_y]
57
+ target.frame = f
58
+ end
59
+
60
+ Teacup.handler UIView, :origin do |target, origin|
61
+ f = target.frame
62
+ origin_x = Teacup::calculate(target, :width, origin[0])
63
+ origin_y = Teacup::calculate(target, :height, origin[1])
64
+ f.origin = [origin_x, origin_y]
65
+ target.frame = f
66
+ end
67
+
68
+ Teacup.handler UIView, :center do |target, center|
69
+ center_x = Teacup::calculate(target, :width, center[0])
70
+ center_y = Teacup::calculate(target, :height, center[1])
71
+ target.center = [center_x, center_y]
72
+ end
73
+
74
+ Teacup.handler UIView, :size do |target, size|
75
+ # odd... if I changed these to .is_a?, weird errors happen. Use ===
76
+ if Symbol === size && size == :full
77
+ if target.superview
78
+ size = target.superview.bounds.size
79
+ else
80
+ size = target.frame.size
81
+ end
82
+ elsif Array === size
83
+ size = [Teacup::calculate(target, :width, size[0]), Teacup::calculate(target, :height, size[1])]
84
+ end
85
+ f = target.frame
86
+ f.size = size
87
+ target.frame = f
88
+ end
89
+
90
+ Teacup.handler UIView, :frame do |target, frame|
91
+ # odd... if I changed these to .is_a?, weird errors happen. Use ===
92
+ if Symbol === frame && frame == :full
93
+ if target.superview
94
+ frame = target.superview.bounds
95
+ else
96
+ frame = target.frame
97
+ end
98
+ elsif Array === frame && frame.length == 4
99
+ frame = [
100
+ [Teacup::calculate(target, :width, frame[0]), Teacup::calculate(target, :height, frame[1])],
101
+ [Teacup::calculate(target, :width, frame[2]), Teacup::calculate(target, :height, frame[3])]
102
+ ]
103
+ elsif (Array === frame && frame.length == 2) || CGRect === frame
104
+ frame = [
105
+ [Teacup::calculate(target, :width, frame[0][0]), Teacup::calculate(target, :height, frame[0][1])],
106
+ [Teacup::calculate(target, :width, frame[1][0]), Teacup::calculate(target, :height, frame[1][1])]
107
+ ]
108
+ end
109
+ target.frame = frame
110
+ end
111
+
112
+ Teacup.handler UIView, :gradient do |target, gradient|
113
+ gradient_layer = target.instance_variable_get(:@teacup_gradient_layer) || begin
114
+ gradient_layer = CAGradientLayer.layer
115
+ gradient_layer.frame = target.bounds
116
+ target.layer.insertSublayer(gradient_layer, atIndex:0)
117
+ gradient_layer
118
+ end
119
+
120
+ gradient.each do |key, value|
121
+ case key.to_s
122
+ when 'colors'
123
+ colors = [value].flatten.collect { |color| color.is_a?(UIColor) ? color.CGColor : color }
124
+ gradient_layer.colors = colors
125
+ else
126
+ gradient_layer.send("#{key}=", value)
127
+ end
128
+ end
129
+
130
+ target.instance_variable_set(:@teacup_gradient_layer, gradient_layer)
131
+ end
132
+
133
+ ##|
134
+ ##| UIButton
135
+ ##|
136
+ Teacup.handler UIButton, :title do |target, title|
137
+ target.setTitle(title, forState: UIControlStateNormal)
138
+ end
139
+
140
+
141
+ Teacup.handler UIButton, :image do |target, image|
142
+ target.setImage(image, forState: UIControlStateNormal)
143
+ end
144
+
145
+
146
+ Teacup.handler UIButton, :backgroundImage do |target, background_image|
147
+ target.setBackgroundImage(background_image, forState: UIControlStateNormal)
148
+ end
149
+
150
+
151
+ Teacup.handler UIButton, :titleColor do |target, color|
152
+ target.setTitleColor(color, forState: UIControlStateNormal)
153
+ end
154
+
155
+
156
+ Teacup.handler UIButton, :titleFont, :font do |target, font|
157
+ target.titleLabel.font = font
158
+ end
159
+
160
+
161
+ ##|
162
+ ##| UINavigationBar
163
+ ##|
164
+ Teacup.handler UINavigationBar, :backgroundImage do |styles|
165
+ if styles.is_a?(UIImage)
166
+ styles = { portrait: styles }
167
+ end
168
+
169
+ styles.each do |metric, image|
170
+ case metric
171
+ when UIBarMetricsDefault, :portrait
172
+ self.setBackgroundImage(image && image.uiimage, forBarMetrics:UIBarMetricsDefault)
173
+ when UIBarMetricsLandscapePhone, :landscape
174
+ self.setBackgroundImage(image && image.uiimage, forBarMetrics:UIBarMetricsLandscapePhone)
175
+ end
176
+ end
177
+ end
178
+
179
+ # this handler lyooks redundant, but without it Teacup would treat `attrs` as a
180
+ # stylable-property (the 'nested styling' feature)
181
+ Teacup.handler UINavigationBar, :titleTextAttributes do |view, attrs|
182
+ view.titleTextAttributes = attrs
183
+ end
@@ -0,0 +1,30 @@
1
+ # Teacup's UIView extensions defines some utility functions for UIView that
2
+ # enable a lot of the magic for Teacup::Layout.
3
+ #
4
+ # Users of teacup should be able to ignore the contents of this file for
5
+ # the most part.
6
+ class UIView
7
+ include Teacup::Layout
8
+ include Teacup::View
9
+
10
+ def teacup_animation(options)
11
+ UIView.beginAnimations(nil, context: nil)
12
+ UIView.setAnimationDuration(options[:duration]) if options.key?(:duration)
13
+ UIView.setAnimationCurve(options[:curve]) if options.key?(:curve)
14
+ UIView.setAnimationDelay(options[:delay]) if options.key?(:delay)
15
+ yield
16
+ UIView.commitAnimations
17
+ end
18
+
19
+ def style(properties)
20
+ super
21
+
22
+ self.setNeedsDisplay
23
+ self.setNeedsLayout
24
+ end
25
+
26
+ def top_level_view
27
+ self
28
+ end
29
+
30
+ end
@@ -0,0 +1,110 @@
1
+ class UIViewController
2
+ include Teacup::Layout
3
+ include Teacup::Controller
4
+
5
+ def viewDidLoad
6
+ teacupDidLoad
7
+ end
8
+
9
+ # This method *used* to be useful for the `shouldAutorotateToOrientation`
10
+ # method, but the iOS 6 update deprecates that method. Instead, use the
11
+ # `supportedInterfaceOrientations` and return `autorotateMask`.
12
+ def autorotateToOrientation(orientation)
13
+ if view.stylesheet and view.stylesheet.is_a?(Teacup::Stylesheet) and view.stylename
14
+ properties = view.stylesheet.query(view.stylename, self, orientation)
15
+
16
+ # check for orientation-specific properties
17
+ case orientation
18
+ when UIInterfaceOrientationPortrait
19
+ # portrait is "on" by default, must be turned off explicitly
20
+ if properties.supports?(:portrait) == nil and properties.supports?(:upside_up) == nil
21
+ return true
22
+ end
23
+
24
+ return (properties.supports?(:portrait) or properties.supports?(:upside_up))
25
+ when UIInterfaceOrientationPortraitUpsideDown
26
+ if UIDevice.currentDevice.userInterfaceIdiom == UIUserInterfaceIdiomPhone
27
+ # iphone must have an explicit upside-down style, otherwise this returns
28
+ # false
29
+ return properties.supports?(:upside_down)
30
+ else
31
+ # ipad can just have a portrait style
32
+ return (properties.supports?(:portrait) or properties.supports?(:upside_down))
33
+ end
34
+ when UIInterfaceOrientationLandscapeLeft
35
+ return (properties.supports?(:landscape) or properties.supports?(:landscape_left))
36
+ when UIInterfaceOrientationLandscapeRight
37
+ return (properties.supports?(:landscape) or properties.supports?(:landscape_right))
38
+ end
39
+
40
+ return false
41
+ end
42
+
43
+ # returns the system default
44
+ if device == UIUserInterfaceIdiomPhone
45
+ return orientation != UIInterfaceOrientationPortraitUpsideDown
46
+ else
47
+ return true
48
+ end
49
+ end
50
+
51
+ # You can use this method in `supportedInterfaceOrientations`, and it will
52
+ # query the stylesheet for the supported orientations, based on what
53
+ # orientations are defined. At a minimum, to opt-in to this feature, you'll
54
+ # need to define styles like `style :root, landscape: true`
55
+ def autorotateMask
56
+ device = UIDevice.currentDevice.userInterfaceIdiom
57
+ if view.stylesheet and view.stylesheet.is_a?(Teacup::Stylesheet) and view.stylename
58
+ properties = view.stylesheet.query(view.stylename, self, orientation)
59
+
60
+ orientations = 0
61
+ if properties.supports?(:portrait) or properties.supports?(:upside_up)
62
+ orientations |= UIInterfaceOrientationPortrait
63
+ end
64
+
65
+ if device == UIUserInterfaceIdiomPhone
66
+ # :portrait does not imply upside_down on the iphone
67
+ if properties.supports?(:upside_down)
68
+ orientations |= UIInterfaceOrientationPortraitUpsideDown
69
+ end
70
+ else
71
+ # but does on the ipad
72
+ if properties.supports?(:portrait) or properties.supports?(:upside_down)
73
+ orientations |= UIInterfaceOrientationPortraitUpsideDown
74
+ end
75
+ end
76
+
77
+ if properties.supports?(:landscape) or properties.supports?(:landscape_left)
78
+ orientations |= UIInterfaceOrientationLandscapeLeft
79
+ end
80
+
81
+ if properties.supports?(:landscape) or properties.supports?(:landscape_right)
82
+ orientations |= UIInterfaceOrientationLandscapeRight
83
+ end
84
+
85
+ if orientations == 0
86
+ orientations |= UIInterfaceOrientationPortrait
87
+ end
88
+ return orientations
89
+ end
90
+
91
+ # returns the system default
92
+ if device == UIUserInterfaceIdiomPhone
93
+ return UIInterfaceOrientationMaskAllButUpsideDown
94
+ else
95
+ return UIInterfaceOrientationMaskAll
96
+ end
97
+ end
98
+
99
+ # restyles the view! be careful about putting styles in your stylesheet that
100
+ # you change in your controller. anything that might change over time should
101
+ # be applied in your controller using `style`
102
+ def willAnimateRotationToInterfaceOrientation(orientation, duration:duration)
103
+ view.restyle!(orientation)
104
+ end
105
+
106
+ def top_level_view
107
+ view
108
+ end
109
+
110
+ end
@@ -1,9 +1,3 @@
1
- class TeacupDummy
2
- def anyMethodName
3
- @anyobject.type = nil
4
- end
5
- end
6
-
7
1
  class DummyView < UIView
8
2
  private
9
3
  def dummy
@@ -11,6 +5,8 @@ private
11
5
  setOpaque(nil)
12
6
  setClipsToBounds(nil)
13
7
  setUserInteractionEnabled(nil)
8
+ UIView.appearanceWhenContainedIn(UIView, nil)
9
+ UIView.appearance
14
10
  end
15
11
  end
16
12
 
@@ -0,0 +1,23 @@
1
+ module Teacup
2
+ module_function
3
+
4
+ def apply_method(target, assign, setter, value)
5
+ if assign and target.respond_to?(assign)
6
+ NSLog "Setting #{key} = #{value.inspect}" if target.respond_to? :debug and target.debug
7
+ target.send(assign, value)
8
+ elsif target.respondsToSelector(setter)
9
+ NSLog "Calling target.#{setter}(#{value.inspect})" if target.respond_to? :debug and target.debug
10
+ target.send(setter, value)
11
+ elsif target.is_a?(self.AppearanceClass)
12
+ NSLog "Calling target.#{setter}(#{value.inspect})" if target.respond_to? :debug and target.debug
13
+ target.send(setter, value)
14
+ else
15
+ NSLog "TEACUP WARNING: Can't apply #{setter.inspect}#{assign and " or " + assign.inspect or ""} to #{target.inspect}"
16
+ end
17
+ end
18
+
19
+ def AppearanceClass
20
+ @appearance_klass ||= UIView.appearance.class
21
+ end
22
+
23
+ end
@@ -49,13 +49,11 @@ module Teacup
49
49
  end
50
50
 
51
51
  # first, move orientation settings into properties "base" level.
52
- if orientation
53
- Overrides[orientation].each do |orientation_key|
54
- if override = self[orientation_key]
55
- # override is first, so it takes precedence
56
- if override.is_a? Hash
57
- Teacup::merge_defaults override, properties, properties
58
- end
52
+ Overrides[orientation].each do |orientation_key|
53
+ if override = self[orientation_key]
54
+ # override is first, so it takes precedence
55
+ if override.is_a? Hash
56
+ Teacup::merge_defaults override, properties, properties
59
57
  end
60
58
  end
61
59
  end
@@ -68,8 +66,9 @@ module Teacup
68
66
  properties.delete(orientation_key)
69
67
  end
70
68
 
71
- # now we can merge extends, and importing. before merging, these will go
72
- # through the same process that we just finished on the local style
69
+ # now we can merge extends, and imported_stylesheets. before merging,
70
+ # these will go through the same process that we just finished on the
71
+ # local style
73
72
  if stylesheet && stylesheet.is_a?(Teacup::Stylesheet)
74
73
  stylesheet.imported_stylesheets.reverse.each do |stylesheet|
75
74
  imported_properties = stylesheet.query(self.stylename, target, rotation_orientation, seen)
@@ -104,7 +103,7 @@ module Teacup
104
103
  end
105
104
  end
106
105
 
107
- properties
106
+ return properties
108
107
  end
109
108
 
110
109
  end
@@ -0,0 +1,169 @@
1
+ # Example:
2
+ # Teacup::Stylesheet.new :main do
3
+ # style :root,
4
+ # # stays centered and grows in height
5
+ # autoresizingMask: autoresize.flexible_left | autoresize.flexible_right | autoresize.flexible_height
6
+ # # same, in block form
7
+ # autoresizingMask: autoresize { flexible_left | flexible_right | flexible_height }
8
+ # end
9
+ module Teacup
10
+ class Stylesheet
11
+
12
+ def autoresize &block
13
+ @@autoresize ||= Autoresize.new
14
+ if block
15
+ return @@autoresize.instance_exec &block
16
+ else
17
+ return @@autoresize
18
+ end
19
+ end
20
+
21
+ ##|
22
+ ##| DEPRECATED
23
+ ##|
24
+
25
+ def flexible_left
26
+ NSLog("The Stylesheet method `flexible_left` is deprecated, use `autoresize.flexible_left` instead")
27
+ UIViewAutoresizingFlexibleLeftMargin
28
+ end
29
+
30
+ def flexible_width
31
+ NSLog("The Stylesheet method `flexible_width` is deprecated, use `autoresize.flexible_width` instead")
32
+ UIViewAutoresizingFlexibleWidth
33
+ end
34
+
35
+ def flexible_right
36
+ NSLog("The Stylesheet method `flexible_right` is deprecated, use `autoresize.flexible_right` instead")
37
+ UIViewAutoresizingFlexibleRightMargin
38
+ end
39
+
40
+ def flexible_top
41
+ NSLog("The Stylesheet method `flexible_top` is deprecated, use `autoresize.flexible_top` instead")
42
+ UIViewAutoresizingFlexibleTopMargin
43
+ end
44
+
45
+ def flexible_height
46
+ NSLog("The Stylesheet method `flexible_height` is deprecated, use `autoresize.flexible_height` instead")
47
+ UIViewAutoresizingFlexibleHeight
48
+ end
49
+
50
+ def flexible_bottom
51
+ NSLog("The Stylesheet method `flexible_bottom` is deprecated, use `autoresize.flexible_bottom` instead")
52
+ UIViewAutoresizingFlexibleBottomMargin
53
+ end
54
+
55
+ end
56
+
57
+ class Autoresize
58
+
59
+ def none
60
+ UIViewAutoresizingNone
61
+ end
62
+
63
+ ##|
64
+ ##| FLEXIBLE
65
+ ##|
66
+
67
+ def flexible_left
68
+ UIViewAutoresizingFlexibleLeftMargin
69
+ end
70
+
71
+ def flexible_width
72
+ UIViewAutoresizingFlexibleWidth
73
+ end
74
+
75
+ def flexible_right
76
+ UIViewAutoresizingFlexibleRightMargin
77
+ end
78
+
79
+ def flexible_top
80
+ UIViewAutoresizingFlexibleTopMargin
81
+ end
82
+
83
+ def flexible_height
84
+ UIViewAutoresizingFlexibleHeight
85
+ end
86
+
87
+ def flexible_bottom
88
+ UIViewAutoresizingFlexibleBottomMargin
89
+ end
90
+
91
+ ##|
92
+ ##| FILL
93
+ ##|
94
+
95
+ def fill
96
+ flexible_width | flexible_height
97
+ end
98
+
99
+ def fill_top
100
+ flexible_width | flexible_bottom
101
+ end
102
+
103
+ def fill_bottom
104
+ flexible_width | flexible_top
105
+ end
106
+
107
+ def fill_left
108
+ flexible_height | flexible_right
109
+ end
110
+
111
+ def fill_right
112
+ flexible_height | flexible_left
113
+ end
114
+
115
+ ##|
116
+ ##| FIXED
117
+ ##|
118
+
119
+ def fixed_top_left
120
+ flexible_right | flexible_bottom
121
+ end
122
+
123
+ def fixed_top_middle
124
+ flexible_left | flexible_right | flexible_bottom
125
+ end
126
+
127
+ def fixed_top_right
128
+ flexible_left | flexible_bottom
129
+ end
130
+
131
+ def fixed_middle_left
132
+ flexible_top | flexible_bottom | flexible_right
133
+ end
134
+
135
+ def fixed_middle
136
+ flexible_top | flexible_bottom | flexible_left | flexible_right
137
+ end
138
+
139
+ def fixed_middle_right
140
+ flexible_top | flexible_bottom | flexible_left
141
+ end
142
+
143
+ def fixed_bottom_left
144
+ flexible_right | flexible_top
145
+ end
146
+
147
+ def fixed_bottom_middle
148
+ flexible_left | flexible_right | flexible_top
149
+ end
150
+
151
+ def fixed_bottom_right
152
+ flexible_left | flexible_top
153
+ end
154
+
155
+ ##|
156
+ ##| FLOAT
157
+ ##|
158
+
159
+ def float_horizontal
160
+ flexible_left | flexible_right
161
+ end
162
+
163
+ def float_vertical
164
+ flexible_top | flexible_bottom
165
+ end
166
+
167
+ end
168
+
169
+ end
@@ -0,0 +1,39 @@
1
+ # Teacup's NSView extensions defines some utility functions for NSView that
2
+ # enable a lot of the magic for Teacup::Layout.
3
+ #
4
+ # Users of teacup should be able to ignore the contents of this file for
5
+ # the most part.
6
+ class NSView
7
+ include Teacup::Layout
8
+ include Teacup::View
9
+
10
+ class << NSView
11
+ attr :teacup_is_animating
12
+ end
13
+
14
+ def teacup_animation(options)
15
+ NSAnimationContext.beginGrouping
16
+ NSAnimationContext.currentContext.setDuration(options[:duration]) if options.key?(:duration)
17
+ NSAnimationContext.currentContext.setTimingFunction(options[:timing]) if options.key?(:timing)
18
+ NSView.teacup_is_animating = true
19
+ yield
20
+ NSView.teacup_is_animating = false
21
+ NSAnimationContext.endGrouping
22
+ end
23
+
24
+ def apply_style_properties(properties)
25
+ Teacup.apply_hash((NSView.teacup_is_animating ? self.animator : self), properties)
26
+ end
27
+
28
+ def style(properties)
29
+ super
30
+
31
+ self.setNeedsDisplay(true)
32
+ self.setNeedsLayout(true)
33
+ end
34
+
35
+ def top_level_view
36
+ self
37
+ end
38
+
39
+ end
@@ -0,0 +1,21 @@
1
+ class NSViewController
2
+ include Teacup::Layout
3
+ include Teacup::Controller
4
+
5
+ alias _teacup_loadview loadView
6
+ def loadView
7
+ if nibName and nibBundle
8
+ _teacup_loadview
9
+ else
10
+ self.view = NSView.new
11
+ self.view.autoresizingMask = NSViewWidthSizable|NSViewHeightSizable
12
+ end
13
+
14
+ teacupDidLoad
15
+ end
16
+
17
+ def top_level_view
18
+ view
19
+ end
20
+
21
+ end
@@ -0,0 +1,39 @@
1
+ # Teacup's NSWindow extensions defines some utility functions for NSWindow that
2
+ # enable a lot of the magic for Teacup::Layout.
3
+ #
4
+ # Users of teacup should be able to ignore the contents of this file for the
5
+ # most part.
6
+ class NSWindow
7
+ include Teacup::Layout
8
+ include Teacup::View
9
+
10
+ class << NSWindow
11
+ attr :teacup_is_animating
12
+ end
13
+
14
+ def teacup_animation(options)
15
+ NSAnimationContext.beginGrouping
16
+ NSAnimationContext.currentContext.setDuration(options[:duration]) if options.key?(:duration)
17
+ NSAnimationContext.currentContext.setTimingFunction(options[:timing]) if options.key?(:timing)
18
+ NSWindow.teacup_is_animating = true
19
+ yield
20
+ NSWindow.teacup_is_animating = false
21
+ NSAnimationContext.endGrouping
22
+ end
23
+
24
+ def apply_style_properties(properties)
25
+ Teacup.apply_hash((NSWindow.teacup_is_animating ? self.animator : self), properties)
26
+ end
27
+
28
+ def style(properties)
29
+ super
30
+
31
+ self.setNeedsDisplay(true)
32
+ self.setNeedsLayout(true)
33
+ end
34
+
35
+ def top_level_view
36
+ contentView
37
+ end
38
+
39
+ end