cura 0.0.3 → 0.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,62 @@
1
+ require "cura"
2
+ require "cura/termbox/adapter"
3
+ require "faker"
4
+ require "pry"
5
+
6
+ class ScrollWindowApp < Cura::Application
7
+ on_event(:key_down) do |event|
8
+ stop if event.control? && event.name == :C # CTRL+C
9
+
10
+ @listbox.add_child(:label, text: Faker::Hipster.sentence)
11
+ end
12
+
13
+ def initialize(attributes={})
14
+ super
15
+
16
+ window = Cura::Window.new
17
+ add_window(window)
18
+
19
+ window.root = Cura::Component::Pack.new(width: window.width, height: window.height, fill: true)
20
+
21
+ @listbox = window.add_child(:listbox, height: window.height-1, background: Cura::Color.red)
22
+
23
+ line_pack = window.add_child(:pack, orientation: :horizontal)
24
+
25
+ @prompt = line_pack.add_child(:label, text: ">", margin: { right: 1 })
26
+ @input = line_pack.add_child(:textbox, width: window.width - @prompt.width)
27
+
28
+ @input.focus
29
+ end
30
+ end
31
+
32
+
33
+
34
+ require "ruby-prof"
35
+
36
+ RubyProf.start
37
+
38
+ app = ScrollWindowApp.new
39
+
40
+ Thread.new do
41
+ sleep 5
42
+
43
+ letters = ("A".."Z").to_a + ("a".."z").to_a
44
+ letters.each do |letter|
45
+ app.dispatch_event(:key_down, name: letter)
46
+ sleep 0.25
47
+ end
48
+ app.stop
49
+ end
50
+ app.run
51
+
52
+
53
+ result = RubyProf.stop
54
+
55
+ path = Pathname.new(__FILE__).join("..", "..", "doc", "coverage").expand_path
56
+ path.mkpath
57
+
58
+ printer = RubyProf::CallStackPrinter.new(result)
59
+ path.join("call_stack.html").open("w+") { |file| printer.print(file) }
60
+
61
+ printer = RubyProf::GraphHtmlPrinter.new(result)
62
+ path.join("graph.html").open("w+") { |file| printer.print(file) }
@@ -0,0 +1 @@
1
+ # Logfile created on 2016-06-24 22:52:31 -0400 by logger.rb/53141
@@ -95,7 +95,10 @@ module Cura
95
95
 
96
96
  self
97
97
  ensure
98
- @adapter.cleanup
98
+ unless @cleaned
99
+ @adapter.cleanup
100
+ @cleaned = true
101
+ end
99
102
  end
100
103
 
101
104
  # Stop the application after the current run cycle.
@@ -111,8 +114,10 @@ module Cura
111
114
  #
112
115
  # @return [Application] This application.
113
116
  def stop!
114
- stop
117
+ @running = false
118
+
115
119
  @adapter.cleanup
120
+ @cleaned = true
116
121
 
117
122
  self
118
123
  end
@@ -45,11 +45,16 @@ module Cura
45
45
  # A Symbol representing the child component type or a {Component::Base} instance.
46
46
  # When a Symbol is given, a new child component will be initialized of that type. See {Component::Base.type}.
47
47
  # @param [#to_h] attributes
48
+ # When component_or_type is a Class, then these attributes will be used to initialize the child component.
48
49
  # When component_or_type is a Symbol, then these attributes will be used to initialize the child component.
49
50
  # When component_or_type is a {Component::Base}, then these attributes will be used to update the child component.
50
51
  # @return [Component]
51
52
  def add_child(component_or_type, attributes={})
52
- component = if component_or_type.respond_to?(:to_sym)
53
+ component = if component_or_type.is_a?(Class)
54
+ raise Error::InvalidComponent unless component_or_type < Component::Base
55
+
56
+ component_or_type.new
57
+ elsif component_or_type.respond_to?(:to_sym)
53
58
  type = component_or_type.to_sym
54
59
  component_class = Component.find_by_type(type)
55
60
 
@@ -100,6 +105,7 @@ module Cura
100
105
  # @return [Group]
101
106
  def delete_children
102
107
  (0...@children.count).to_a.reverse_each { |index| delete_child_at(index) } # TODO: Why reverse?
108
+
103
109
  self
104
110
  end
105
111
 
@@ -8,6 +8,7 @@ module Cura
8
8
  module Attributes
9
9
  # Adds the `root` attribute to an object, which defaults to a Component::Group.
10
10
  module HasRoot
11
+
11
12
  include Attributes::HasAttributes
12
13
 
13
14
  def initialize(attributes={})
@@ -16,20 +17,23 @@ module Cura
16
17
  super
17
18
  end
18
19
 
19
- # @method root
20
20
  # Get root component for this object.
21
21
  #
22
22
  # @return [Component::Group]
23
+ attr_reader :root
23
24
 
24
- # @method root=(component)
25
25
  # Set root component for this object.
26
26
  #
27
27
  # @param [Component::Group] component
28
28
  # @return [Component::Group]
29
+ def root=(value)
30
+ raise TypeError, "root must be a Component::Group" unless value.is_a?(Component::Group)
29
31
 
30
- attribute(:root) { |component| set_root(component) }
32
+ @root = value
33
+ end
31
34
 
32
35
  # Delegates -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
36
+ # TODO: Use Forwardable
33
37
 
34
38
  # Get the children of this object.
35
39
  #
@@ -89,17 +93,6 @@ module Cura
89
93
  @root.children?
90
94
  end
91
95
 
92
- protected
93
-
94
- def set_root(component)
95
- raise TypeError, "root must be a Component::Group" unless component.is_a?(Component::Group)
96
-
97
- @root.parent = nil unless @root.nil?
98
- @root = component
99
- @root.parent = self
100
-
101
- @root
102
- end
103
96
  end
104
97
  end
105
98
  end
@@ -40,6 +40,8 @@ module Cura
40
40
  end
41
41
  end
42
42
 
43
+ RGB_TO_LAB_CACHE = {}
44
+
43
45
  def initialize(r=0, g=0, b=0, a=255)
44
46
  if r.respond_to?(:to_h)
45
47
  super(r.to_h)
@@ -50,7 +52,10 @@ module Cura
50
52
  @alpha = a
51
53
  end
52
54
 
53
- @lab = rgb_to_lab([@red, @green, @blue]) # TODO: Update on rgb setters?
55
+ # TODO: Update on rgb setters?
56
+ rgb = [@red, @green, @blue]
57
+ @lab = (RGB_TO_LAB_CACHE[rgb] ||= rgb_to_lab(rgb))
58
+ # @lab = rgb_to_lab(rgb)
54
59
  end
55
60
 
56
61
  # @method red
@@ -7,7 +7,9 @@ if Kernel.respond_to?(:require)
7
7
  require "cura/attributes/has_offsets"
8
8
  require "cura/attributes/has_relative_coordinates"
9
9
  require "cura/attributes/has_visibility"
10
+ require "cura/helpers/component/drawing"
10
11
  require "cura/component"
12
+ require "cura/window"
11
13
  end
12
14
 
13
15
  module Cura
@@ -17,9 +19,12 @@ module Cura
17
19
  # All components use a box model similar to CSS.
18
20
  # Margins, borders, paddings, then content.
19
21
  class Base
22
+
20
23
  class << self
21
24
  # On subclass hook.
22
25
  def inherited(subclass)
26
+ super
27
+
23
28
  Component.all << subclass
24
29
  end
25
30
 
@@ -47,6 +52,8 @@ module Cura
47
52
  include Attributes::HasRelativeCoordinates
48
53
  include Attributes::HasVisibility
49
54
 
55
+ include Helpers::Component::Drawing
56
+
50
57
  # Get the cursor for this application.
51
58
  # TODO: Delegate something like: def_delegate(:cursor) { application }
52
59
  #
@@ -72,6 +79,17 @@ module Cura
72
79
  parent.application
73
80
  end
74
81
 
82
+ # Get the window of this object.
83
+ #
84
+ # @return [Application]
85
+ def window
86
+ return nil if parent.nil?
87
+ return nil if parent.is_a?(Cura::Application)
88
+ return parent if parent.is_a?(Cura::Window)
89
+
90
+ parent.window
91
+ end
92
+
75
93
  # Focus on this component.
76
94
  #
77
95
  # @return [Component]
@@ -116,6 +134,8 @@ module Cura
116
134
  #
117
135
  # @return [Component]
118
136
  def update
137
+ @draw = true
138
+
119
139
  self
120
140
  end
121
141
 
@@ -123,14 +143,27 @@ module Cura
123
143
  #
124
144
  # @return [Component]
125
145
  def draw
126
- if @visible
127
- draw_background
128
- draw_border
129
- end
146
+ return self unless @visible
147
+ return self unless draw?
148
+
149
+ draw_background
150
+ draw_border
130
151
 
131
152
  self
132
153
  end
133
154
 
155
+ # @method draw?
156
+ # Get whether this component should be drawn.
157
+ #
158
+ # @return [Boolean]
159
+
160
+ # @method draw=
161
+ # Set whether this component should be drawn.
162
+ #
163
+ # @param [Boolean] value
164
+ # @return [Boolean]
165
+ attribute(:draw, query: true)
166
+
134
167
  # Instance inspection.
135
168
  #
136
169
  # @return [String]
@@ -138,56 +171,6 @@ module Cura
138
171
  "#<#{self.class}:0x#{__id__.to_s(16)} x=#{x} y=#{y} absolute_x=#{absolute_x} absolute_y=#{absolute_y} w=#{width} h=#{height} parent=#{@parent.class}:0x#{@parent.__id__.to_s(16)}>"
139
172
  end
140
173
 
141
- protected
142
-
143
- # Draw a point.
144
- def draw_point(x, y, color=Cura::Color.black)
145
- x = absolute_x + @offsets.left + x
146
- y = absolute_y + @offsets.top + y
147
-
148
- pencil.draw_point(x, y, color)
149
- end
150
-
151
- # Draw a rectangle.
152
- # TODO: filled argument
153
- def draw_rectangle(x, y, width, height, color=Cura::Color.black)
154
- x = absolute_x + @offsets.left + x
155
- y = absolute_y + @offsets.top + y
156
-
157
- pencil.draw_rectangle(x, y, width, height, color)
158
- end
159
-
160
- # Draw a single character.
161
- def draw_character(x, y, character, foreground=Cura::Color.black, background=Cura::Color.white, bold=false, underline=false)
162
- x = absolute_x + @offsets.left + x
163
- y = absolute_y + @offsets.top + y
164
-
165
- pencil.draw_character(x, y, character, foreground, background, bold, underline)
166
- end
167
-
168
- # Draw text.
169
- def draw_text(x, y, text, foreground=Cura::Color.black, background=Cura::Color.white, bold=false, underline=false)
170
- x = absolute_x + @offsets.left + x
171
- y = absolute_y + @offsets.top + y
172
-
173
- pencil.draw_text(x, y, text, foreground, background, bold, underline)
174
- end
175
-
176
- # Draw the background of this component.
177
- def draw_background
178
- x = absolute_x + @margin.left + @border.left
179
- y = absolute_y + @margin.top + @border.top
180
- width = self.width + @padding.width
181
- height = self.height + @padding.height
182
- color = background
183
-
184
- pencil.draw_rectangle(x, y, width, height, color)
185
- end
186
-
187
- # Draw the border of this component.
188
- def draw_border # TODO
189
- end
190
-
191
174
  def get_or_inherit_color(name, default)
192
175
  value = instance_variable_get("@#{name}")
193
176
 
@@ -82,6 +82,7 @@ module Cura
82
82
  # TODO: If the dimensions of this group of this group are less than the computed dimensions, the drawing will be clipped.
83
83
  def draw
84
84
  super
85
+ return self unless @draw
85
86
 
86
87
  draw_children
87
88
  end
@@ -131,6 +131,7 @@ module Cura
131
131
 
132
132
  def draw
133
133
  super
134
+ return self unless @draw
134
135
 
135
136
  draw_text unless text.empty?
136
137
  end
@@ -81,6 +81,19 @@ module Cura
81
81
  @children[@selected_index]
82
82
  end
83
83
 
84
+ # Set the selected child.
85
+ #
86
+ # @param [Component] child
87
+ # @return [Component]
88
+ def selected_child=(child)
89
+ index = @children.index(child)
90
+
91
+ return nil if index.nil? # TODO: Raise error?
92
+ self.selected_index = index
93
+
94
+ selected_child
95
+ end
96
+
84
97
  # Add a child to this group.
85
98
  #
86
99
  # @param [#to_sym, Component] component_or_type
@@ -113,7 +113,7 @@ module Cura
113
113
  #
114
114
  # @return [Pack]
115
115
  def draw
116
- pack_children
116
+ pack_children # TODO: Should be in #update?
117
117
 
118
118
  super
119
119
  end
@@ -88,7 +88,7 @@ module Cura
88
88
  other == to_h
89
89
  end
90
90
 
91
- # Dispatches this event directly to it's target.
91
+ # Dispatches this event directly to it's target, if it has an application.
92
92
  #
93
93
  # @return [Event::Base] This event.
94
94
  def dispatch
@@ -9,6 +9,11 @@ module Cura
9
9
  # @param [#to_h] options
10
10
  # @option options [Event::Base] :event
11
11
  def call(options={})
12
+ # TODO: !!!! Refactor
13
+ return nil if options[:event].nil?
14
+ return nil if options[:event].target.nil?
15
+ return nil if !options[:event].target.is_a?(Application) && options[:event].target.application.nil? # TODO: Check if orphaned, maybe log this?
16
+
12
17
  options[:dispatch_queue] << options[:event]
13
18
  end
14
19
  end
@@ -0,0 +1,66 @@
1
+ if Kernel.respond_to?(:require)
2
+ require "cura/color"
3
+ end
4
+
5
+ module Cura
6
+ module Helpers
7
+ module Component
8
+
9
+ # Helpers for drawing within components.
10
+ module Drawing
11
+
12
+ protected
13
+
14
+ # Draw a point.
15
+ def draw_point(x, y, color=Cura::Color.black)
16
+ x = absolute_x + @offsets.left + x
17
+ y = absolute_y + @offsets.top + y
18
+
19
+ pencil.draw_point(x, y, color)
20
+ end
21
+
22
+ # Draw a rectangle.
23
+ # TODO: filled argument
24
+ def draw_rectangle(x, y, width, height, color=Cura::Color.black)
25
+ x = absolute_x + @offsets.left + x
26
+ y = absolute_y + @offsets.top + y
27
+
28
+ pencil.draw_rectangle(x, y, width, height, color)
29
+ end
30
+
31
+ # Draw a single character.
32
+ def draw_character(x, y, character, foreground=Cura::Color.black, background=Cura::Color.white, bold=false, underline=false)
33
+ x = absolute_x + @offsets.left + x
34
+ y = absolute_y + @offsets.top + y
35
+
36
+ pencil.draw_character(x, y, character, foreground, background, bold, underline)
37
+ end
38
+
39
+ # Draw text.
40
+ def draw_text(x, y, text, foreground=Cura::Color.black, background=Cura::Color.white, bold=false, underline=false)
41
+ x = absolute_x + @offsets.left + x
42
+ y = absolute_y + @offsets.top + y
43
+
44
+ pencil.draw_text(x, y, text, foreground, background, bold, underline)
45
+ end
46
+
47
+ # Draw the background of this component.
48
+ def draw_background
49
+ x = absolute_x + @margin.left + @border.left
50
+ y = absolute_y + @margin.top + @border.top
51
+ width = self.width + @padding.width
52
+ height = self.height + @padding.height
53
+ color = background
54
+
55
+ pencil.draw_rectangle(x, y, width, height, color)
56
+ end
57
+
58
+ # Draw the border of this component.
59
+ def draw_border # TODO
60
+ end
61
+
62
+ end
63
+
64
+ end
65
+ end
66
+ end