motion-prime 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (65) hide show
  1. data/.gitignore +17 -0
  2. data/Gemfile +13 -0
  3. data/Gemfile.lock +83 -0
  4. data/README.md +67 -0
  5. data/Rakefile +23 -0
  6. data/app/app_delegate.rb +5 -0
  7. data/doc/SECTION.md +7 -0
  8. data/doc/STYLE.md +39 -0
  9. data/files/Gemfile +3 -0
  10. data/files/Rakefile +16 -0
  11. data/files/app/app_delegate.rb +4 -0
  12. data/files/app/screens/application_screen.rb +3 -0
  13. data/lib/motion-prime.rb +14 -0
  14. data/lib/view_styler.rb +141 -0
  15. data/motion-prime.gemspec +27 -0
  16. data/motion-prime/app_delegate.rb +56 -0
  17. data/motion-prime/elements/base.rb +94 -0
  18. data/motion-prime/elements/button.rb +7 -0
  19. data/motion-prime/elements/draw.rb +56 -0
  20. data/motion-prime/elements/draw/image.rb +43 -0
  21. data/motion-prime/elements/draw/label.rb +13 -0
  22. data/motion-prime/elements/image.rb +14 -0
  23. data/motion-prime/elements/label.rb +20 -0
  24. data/motion-prime/elements/text_field.rb +7 -0
  25. data/motion-prime/elements/text_view.rb +7 -0
  26. data/motion-prime/helpers/has_authorization.rb +10 -0
  27. data/motion-prime/helpers/has_search_bar.rb +25 -0
  28. data/motion-prime/models/base.rb +220 -0
  29. data/motion-prime/screens/_aliases_mixin.rb +32 -0
  30. data/motion-prime/screens/_base_mixin.rb +119 -0
  31. data/motion-prime/screens/_navigation_bar_mixin.rb +57 -0
  32. data/motion-prime/screens/_navigation_mixin.rb +118 -0
  33. data/motion-prime/screens/_orientations_mixin.rb +39 -0
  34. data/motion-prime/screens/base_screen.rb +22 -0
  35. data/motion-prime/screens/sidebar_container_screen.rb +58 -0
  36. data/motion-prime/sections/base.rb +101 -0
  37. data/motion-prime/sections/draw.rb +62 -0
  38. data/motion-prime/sections/form.rb +103 -0
  39. data/motion-prime/sections/form/base_field_section.rb +26 -0
  40. data/motion-prime/sections/form/password_field_section.rb +33 -0
  41. data/motion-prime/sections/form/select_field_section.rb +40 -0
  42. data/motion-prime/sections/form/string_field_section.rb +32 -0
  43. data/motion-prime/sections/form/submit_field_section.rb +20 -0
  44. data/motion-prime/sections/form/text_field_section.rb +33 -0
  45. data/motion-prime/sections/table.rb +97 -0
  46. data/motion-prime/sections/table/refresh_mixin.rb +13 -0
  47. data/motion-prime/styles/forms.rb +93 -0
  48. data/motion-prime/support/_key_value_store.rb +10 -0
  49. data/motion-prime/support/dm_button.rb +22 -0
  50. data/motion-prime/support/dm_cell_with_section.rb +12 -0
  51. data/motion-prime/support/dm_text_field.rb +30 -0
  52. data/motion-prime/support/dm_text_view.rb +93 -0
  53. data/motion-prime/support/dm_view_controller.rb +50 -0
  54. data/motion-prime/support/dm_view_with_section.rb +11 -0
  55. data/motion-prime/support/navigation_controller.rb +4 -0
  56. data/motion-prime/support/ui_search_bar_custom.rb +10 -0
  57. data/motion-prime/support/ui_view.rb +59 -0
  58. data/motion-prime/version.rb +3 -0
  59. data/motion-prime/views/layout.rb +45 -0
  60. data/motion-prime/views/styles.rb +44 -0
  61. data/motion-prime/views/view_builder.rb +80 -0
  62. data/motion-prime/views/view_styler.rb +141 -0
  63. data/resources/Default-568h@2x.png +0 -0
  64. data/spec/main_spec.rb +9 -0
  65. metadata +245 -0
@@ -0,0 +1,32 @@
1
+ module MotionPrime
2
+ module ScreenAliasesMixin
3
+ def view_did_load; end
4
+ def view_will_appear(animated)
5
+ self.will_appear
6
+ end
7
+ def will_appear; end
8
+
9
+ def view_did_appear(animated)
10
+ self.on_appear
11
+ end
12
+ def on_appear; end
13
+
14
+ def view_will_disappear(animated)
15
+ self.will_disappear
16
+ end
17
+ def will_disappear; end
18
+
19
+ def view_did_disappear(animated)
20
+ self.on_disappear
21
+ end
22
+ def on_disappear; end
23
+
24
+ def will_rotate(orientation, duration); end
25
+
26
+ def should_autorotate
27
+ true
28
+ end
29
+
30
+ def on_rotate; end;
31
+ end
32
+ end
@@ -0,0 +1,119 @@
1
+ motion_require "./_aliases_mixin"
2
+ motion_require "./_orientations_mixin"
3
+ motion_require "./_navigation_mixin"
4
+ motion_require "./_navigation_bar_mixin"
5
+ module MotionPrime
6
+ module ScreenBaseMixin
7
+ extend ::MotionSupport::Concern
8
+
9
+ include ::MotionSupport::Callbacks
10
+ include MotionPrime::ScreenAliasesMixin
11
+ include MotionPrime::ScreenOrientationsMixin
12
+ include MotionPrime::ScreenNavigationMixin
13
+ include MotionPrime::ScreenNavigationBarMixin
14
+
15
+ attr_accessor :parent_screen, :modal, :params, :main_section
16
+ class_attribute :current_screen
17
+
18
+ included do
19
+ define_callbacks :load
20
+ end
21
+
22
+ def on_load; end
23
+
24
+ def on_screen_load
25
+ run_callbacks :load do
26
+ on_load
27
+ end
28
+ end
29
+
30
+ def on_create(args = {})
31
+ unless self.is_a?(UIViewController)
32
+ raise StandardError.new("ERROR: Screens must extend UIViewController.")
33
+ end
34
+
35
+ self.params = args[:params] || {}
36
+ args.each do |k, v|
37
+ self.send("#{k}=", v) if self.respond_to?("#{k}=")
38
+ end
39
+
40
+ self.add_navigation_controller if args[:navigation]
41
+ self.on_init if respond_to?(:on_init)
42
+ self
43
+ end
44
+
45
+ def modal?
46
+ !!self.modal
47
+ end
48
+
49
+ def has_navigation?
50
+ !navigation_controller.nil?
51
+ end
52
+
53
+ def navigation_controller
54
+ @navigation_controller ||= self.navigationController
55
+ end
56
+
57
+ def navigation_controller=(val)
58
+ @navigation_controller = val
59
+ end
60
+
61
+ def add_navigation_controller
62
+ self.navigation_controller = NavigationController.alloc.initWithRootViewController(self)
63
+ end
64
+
65
+ def title
66
+ title = self.class.title
67
+ title = self.instance_eval(&title) if title.is_a?(Proc)
68
+ title
69
+ end
70
+
71
+ def title=(new_title)
72
+ self.class.title(new_title)
73
+ super
74
+ end
75
+
76
+ def main_controller
77
+ has_navigation? ? navigation_controller : self
78
+ end
79
+
80
+ # ACTIVITY INDICATOR
81
+ # ---------------------
82
+
83
+ def show_activity_indicator
84
+ if @activity_indicator_view.nil?
85
+ @activity_indicator_view = UIActivityIndicatorView.gray
86
+ @activity_indicator_view.center = CGPointMake(view.center.x, view.center.y - 50)
87
+ view.addSubview @activity_indicator_view
88
+ end
89
+ @activity_indicator_view.startAnimating
90
+ end
91
+
92
+ def hide_activity_indicator
93
+ return unless @activity_indicator_view
94
+ @activity_indicator_view.stopAnimating
95
+ end
96
+
97
+ def show_notice(message, time = 1.0)
98
+ MBHUDView.hudWithBody message,
99
+ type: MBAlertViewHUDTypeCheckmark, hidesAfter: time, show: true
100
+ end
101
+
102
+ def refresh
103
+ main_section.reload_data
104
+ end
105
+
106
+ # Class methods
107
+ module ClassMethods
108
+ def title(t = nil)
109
+ t ? @title = t : @title ||= self.to_s
110
+ end
111
+ def before_load(method_name)
112
+ set_callback :load, :before, method_name
113
+ end
114
+ def after_load(method_name)
115
+ set_callback :load, :after, method_name
116
+ end
117
+ end
118
+ end
119
+ end
@@ -0,0 +1,57 @@
1
+ module MotionPrime
2
+ module ScreenNavigationBarMixin
3
+ def navigation_right_button
4
+ navigationItem.rightBarButtonItem
5
+ end
6
+
7
+ def navigation_left_button
8
+ navigationItem.leftBarButtonItem
9
+ end
10
+
11
+ def set_navigation_right_button(title, args = {})
12
+ navigationItem.rightBarButtonItem = create_navigation_button(title, args)
13
+ end
14
+
15
+ def set_navigation_left_button(title, args = {})
16
+ navigationItem.leftBarButtonItem = create_navigation_button(title, args)
17
+ end
18
+
19
+ def set_navigation_back_button(title, args = {})
20
+ navigationItem.leftBarButtonItem = create_navigation_button(title, {action: :back}.merge(args))
21
+ end
22
+
23
+ def create_navigation_button(title, args = {})
24
+ args[:style] ||= UIBarButtonItemStylePlain
25
+ args[:target] ||= self
26
+ args[:action] ||= nil
27
+
28
+ # TODO: Find better place for this code, may be just create custom control
29
+ if args[:image]
30
+ image = args[:image].uiimage
31
+ face = UIButton.buttonWithType UIButtonTypeCustom
32
+ face.bounds = CGRectMake(0, 0, image.size.width, image.size.height)
33
+ face.setImage image, forState: UIControlStateNormal
34
+ face.on :touch do
35
+ args[:action].to_proc.call(self)
36
+ end
37
+ button = UIBarButtonItem.alloc.initWithCustomView(face)
38
+ button
39
+ elsif args[:icon]
40
+ image = args[:icon].uiimage
41
+ face = UIButton.buttonWithType UIButtonTypeCustom
42
+ face.setImage(image, forState: UIControlStateNormal)
43
+ face.setTitle(title, forState: UIControlStateNormal)
44
+ face.bounds = CGRectMake(0, 0, 100, 60)
45
+ face.setContentHorizontalAlignment UIControlContentHorizontalAlignmentLeft
46
+ face.on :touch do
47
+ args[:action].to_proc.call(self)
48
+ end
49
+ button = UIBarButtonItem.alloc.initWithCustomView(face)
50
+ button
51
+ else
52
+ UIBarButtonItem.alloc.initWithTitle(title,
53
+ style: args[:style], target: args[:target], action: args[:action])
54
+ end
55
+ end
56
+ end
57
+ end
@@ -0,0 +1,118 @@
1
+ module MotionPrime
2
+ module ScreenNavigationMixin
3
+ def app_delegate
4
+ UIApplication.sharedApplication.delegate
5
+ end
6
+
7
+ def open_screen(screen, args = {})
8
+ # Apply properties to instance
9
+ screen = setup_screen_for_open(screen, args)
10
+ ensure_wrapper_controller_in_place(screen, args)
11
+ screen.send(:on_screen_load) if screen.respond_to?(:on_screen_load)
12
+ if args[:modal]
13
+ present_modal_view_controller screen, (args[:animated] || true)
14
+ elsif has_navigation?
15
+ push_view_controller screen
16
+ else
17
+ app_delegate.open_screen(screen.main_controller)
18
+ end
19
+ end
20
+
21
+ def open_root_screen(screen)
22
+ app_delegate.open_root_screen(screen)
23
+ end
24
+
25
+ def show_sidebar
26
+ app_delegate.show_sidebar
27
+ end
28
+
29
+ def hide_sidebar
30
+ app_delegate.hide_sidebar
31
+ end
32
+
33
+ def close_screen(args = {})
34
+ args ||= {}
35
+ args[:animated] ||= true
36
+ # Pop current view, maybe with arguments, if in navigation controller
37
+ if modal?
38
+ close_modal_screen args
39
+ elsif has_navigation?
40
+ close_navigation args
41
+ send_on_return(args)
42
+ end
43
+ end
44
+
45
+ def back
46
+ close_screen
47
+ end
48
+
49
+ def send_on_return(args = {})
50
+ if parent_screen && parent_screen.respond_to?(:on_return)
51
+ parent_screen.send(:on_return)
52
+ end
53
+ end
54
+
55
+ def push_view_controller(vc)
56
+ navigation_controller.pushViewController(vc, animated: true)
57
+ end
58
+
59
+ protected
60
+
61
+ def setup_screen_for_open(screen, args = {})
62
+ # Instantiate screen if given a class
63
+ screen = screen.new if screen.respond_to?(:new)
64
+
65
+ # Set parent, title & modal properties
66
+ screen.parent_screen = self if screen.respond_to?("parent_screen=")
67
+ screen.title = args[:title] if args[:title] && screen.respond_to?("title=")
68
+ screen.modal = args[:modal] if args[:modal] && screen.respond_to?("modal=")
69
+
70
+ # Wrap in a NavigationController?
71
+ screen.add_navigation if args[:navigation] && screen.respond_to?(:add_navigation)
72
+
73
+ # Return modified screen instance
74
+ screen
75
+ end
76
+
77
+ def ensure_wrapper_controller_in_place(screen, args={})
78
+ if !args[:modal] && screen.respond_to?(:navigation_controller=)
79
+ screen.navigation_controller ||= navigation_controller
80
+ end
81
+ end
82
+
83
+ def present_modal_view_controller(screen, animated)
84
+ self.presentModalViewController(screen.main_controller, animated: animated)
85
+ end
86
+
87
+ def close_modal_screen(args = {})
88
+ parent_screen.dismissViewControllerAnimated(args[:animated], completion: lambda {
89
+ send_on_return(args)
90
+ })
91
+ end
92
+
93
+ def close_navigation(args = {})
94
+ if args[:to_screen] && args[:to_screen].is_a?(UIViewController)
95
+ self.parent_screen = args[:to_screen]
96
+ self.navigation_controller.popToViewController(args[:to_screen], animated: args[:animated])
97
+ else
98
+ self.navigation_controller.popViewControllerAnimated(args[:animated])
99
+ end
100
+ end
101
+
102
+ def has_navigation?
103
+ !navigation_controller.nil?
104
+ end
105
+
106
+ def navigation_controller
107
+ @navigation_controller ||= self.navigationController
108
+ end
109
+
110
+ def navigation_controller=(val)
111
+ @navigation_controller = val
112
+ end
113
+
114
+ def add_navigation_controller
115
+ self.navigation_controller = NavigationController.alloc.initWithRootViewController(self)
116
+ end
117
+ end
118
+ end
@@ -0,0 +1,39 @@
1
+ module MotionPrime
2
+ module ScreenOrientationsMixin
3
+ def should_rotate(orientation)
4
+ case orientation
5
+ when UIInterfaceOrientationPortrait
6
+ return supported_orientation?("UIInterfaceOrientationPortrait")
7
+ when UIInterfaceOrientationLandscapeLeft
8
+ return supported_orientation?("UIInterfaceOrientationLandscapeLeft")
9
+ when UIInterfaceOrientationLandscapeRight
10
+ return supported_orientation?("UIInterfaceOrientationLandscapeRight")
11
+ when UIInterfaceOrientationPortraitUpsideDown
12
+ return supported_orientation?("UIInterfaceOrientationPortraitUpsideDown")
13
+ else
14
+ false
15
+ end
16
+ end
17
+
18
+ def supported_orientation?(orientation)
19
+ NSBundle.mainBundle.infoDictionary["UISupportedInterfaceOrientations"].include?(orientation)
20
+ end
21
+
22
+ def supported_orientations
23
+ ors = 0
24
+ NSBundle.mainBundle.infoDictionary["UISupportedInterfaceOrientations"].each do |ori|
25
+ case ori
26
+ when "UIInterfaceOrientationPortrait"
27
+ ors |= UIInterfaceOrientationMaskPortrait
28
+ when "UIInterfaceOrientationLandscapeLeft"
29
+ ors |= UIInterfaceOrientationMaskLandscapeLeft
30
+ when "UIInterfaceOrientationLandscapeRight"
31
+ ors |= UIInterfaceOrientationMaskLandscapeRight
32
+ when "UIInterfaceOrientationPortraitUpsideDown"
33
+ ors |= UIInterfaceOrientationMaskPortraitUpsideDown
34
+ end
35
+ end
36
+ ors
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,22 @@
1
+ motion_require '../support/dm_view_controller.rb'
2
+ motion_require '../views/layout.rb'
3
+ motion_require '../screens/_base_mixin.rb'
4
+ motion_require '../helpers/has_authorization'
5
+ motion_require '../helpers/has_search_bar'
6
+ module MotionPrime
7
+ class BaseScreen < DMViewController
8
+ include Layout
9
+ include ScreenBaseMixin
10
+ include HasAuthorization
11
+ include HasSearchBar
12
+
13
+ def render
14
+ end
15
+
16
+ def on_load
17
+ setup view, styles: [:base_screen, self.class.name.underscore.to_sym] do
18
+ render
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,58 @@
1
+ module MotionPrime
2
+ class SidebarContainerScreen < PKRevealController
3
+
4
+ include ::MotionPrime::ScreenBaseMixin
5
+
6
+ def self.new(menu, content, options={})
7
+ screen = self.revealControllerWithFrontViewController(nil, leftViewController: nil, options: nil)
8
+ screen.on_create(options) if screen.respond_to?(:on_create)
9
+ screen.menu_controller = menu unless menu.nil?
10
+ screen.content_controller = content unless content.nil?
11
+ screen
12
+ end
13
+
14
+ def show_sidebar
15
+ show_controller menu_controller
16
+ end
17
+
18
+ def hide_sidebar
19
+ show_controller content_controller
20
+ end
21
+
22
+ def menu_controller=(c)
23
+ setLeftViewController prepare_controller(c),
24
+ focusAfterChange: true, completion: default_completion_block
25
+ end
26
+
27
+ def content_controller=(c)
28
+ setFrontViewController prepare_controller(c),
29
+ focusAfterChange: true, completion: default_completion_block
30
+ end
31
+
32
+ def menu_controller
33
+ self.leftViewController
34
+ end
35
+
36
+ def content_controller
37
+ self.frontViewController
38
+ end
39
+
40
+ private
41
+
42
+ def show_controller(controller)
43
+ showViewController controller, animated: true, completion: default_completion_block
44
+ end
45
+
46
+ def prepare_controller(controller)
47
+ controller.on_screen_load if controller.respond_to?(:on_screen_load)
48
+ controller = setup_screen_for_open(controller, {})
49
+ ensure_wrapper_controller_in_place(controller, {})
50
+ controller = controller.main_controller if controller.respond_to?(:main_controller)
51
+ controller
52
+ end
53
+
54
+ def default_completion_block
55
+ -> (completed) { true }
56
+ end
57
+ end
58
+ end