slithernix-cdk 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
data/lib/cdk/screen.rb ADDED
@@ -0,0 +1,281 @@
1
+ module CDK
2
+ class SCREEN
3
+ attr_accessor :object_focus, :object_count, :object_limit, :object, :window
4
+ attr_accessor :exit_status
5
+
6
+ NOEXIT = 0
7
+ EXITOK = 1
8
+ EXITCANCEL = 2
9
+
10
+ def initialize (window)
11
+ Curses.curs_set(0)
12
+ # initialization for the first time
13
+ if CDK::ALL_SCREENS.size == 0
14
+ # Set up basic curses settings.
15
+ # #ifdef HAVE_SETLOCALE
16
+ # setlocale (LC_ALL, "");
17
+ # #endif
18
+
19
+ Curses.noecho
20
+ Curses.cbreak
21
+ end
22
+
23
+ CDK::ALL_SCREENS << self
24
+ @object_count = 0
25
+ @object_limit = 2
26
+ @object = Array.new(@object_limit, nil)
27
+ @window = window
28
+ @object_focus = 0
29
+ end
30
+
31
+ # This registers a CDK object with a screen.
32
+ def register(cdktype, object)
33
+ if @object_count + 1 >= @object_limit
34
+ @object_limit += 2
35
+ @object_limit *= 2
36
+ @object.concat(Array.new(@object_limit - @object.size, nil))
37
+ end
38
+
39
+ if object.validObjType(cdktype)
40
+ self.setScreenIndex(@object_count, object)
41
+ @object_count += 1
42
+ end
43
+ end
44
+
45
+ # This removes an object from the CDK screen.
46
+ def self.unregister(cdktype, object)
47
+ if object.validObjType(cdktype) && object.screen_index >= 0
48
+ screen = object.screen
49
+
50
+ unless screen.nil?
51
+ index = object.screen_index
52
+ object.screen_index = -1
53
+
54
+ # Resequence the objects
55
+ (index...screen.object_count - 1).each do |x|
56
+ screen.setScreenIndex(x, screen.object[x+1])
57
+ end
58
+
59
+ if screen.object_count <= 1
60
+ # if no more objects, remove the array
61
+ screen.object = []
62
+ screen.object_count = 0
63
+ screen.object_limit = 0
64
+ else
65
+ screen.object[screen.object_count] = nil
66
+ screen.object_count -= 1
67
+
68
+ # Update the object-focus
69
+ if screen.object_focus == index
70
+ screen.object_focus -= 1
71
+ Traverse.setCDKFocusNext(screen)
72
+ elsif screen.object_focus > index
73
+ screen.object_focus -= 1
74
+ end
75
+ end
76
+ end
77
+ end
78
+ end
79
+
80
+ def setScreenIndex(number, obj)
81
+ obj.screen_index = number
82
+ obj.screen = self
83
+ @object[number] = obj
84
+ end
85
+
86
+ def validIndex(n)
87
+ n >= 0 && n < @object_count
88
+ end
89
+
90
+ def swapCDKIndices(n1, n2)
91
+ if n1 != n2 && self.validIndex(n1) && self.validIndex(n2)
92
+ o1 = @object[n1]
93
+ o2 = @object[n2]
94
+ self.setScreenIndex(n1, o2)
95
+ self.setScreenIndex(n2, o1)
96
+
97
+ if @object_focus == n1
98
+ @object_focus = n2
99
+ elsif @object_focus == n2
100
+ @object_focus = n1
101
+ end
102
+ end
103
+ end
104
+
105
+ # This 'brings' a CDK object to the top of the stack.
106
+ def self.raiseCDKObject(cdktype, object)
107
+ if object.validObjType(cdktype)
108
+ screen = object.screen
109
+ screen.swapCDKIndices(object.screen_index, screen.object_count - 1)
110
+ end
111
+ end
112
+
113
+ # This 'lowers' an object.
114
+ def self.lowerCDKObject(cdktype, object)
115
+ if object.validObjType(cdktype)
116
+ object.screen.swapCDKIndices(object.screen_index, 0)
117
+ end
118
+ end
119
+
120
+ # This pops up a message.
121
+ def popupLabel(mesg, count)
122
+ #Create the label.
123
+ popup = CDK::LABEL.new(self, CENTER, CENTER, mesg, count, true, false)
124
+
125
+ old_state = Curses.curs_set(0)
126
+ #Draw it on the screen
127
+ popup.draw(true)
128
+
129
+ # Wait for some input.
130
+ popup.win.keypad(true)
131
+ popup.getch([])
132
+
133
+ # Kill it.
134
+ popup.destroy
135
+
136
+ # Clean the screen.
137
+ Curses.curs_set(old_state)
138
+ self.erase
139
+ self.refresh
140
+ end
141
+
142
+ # This pops up a message
143
+ def popupLabelAttrib(mesg, count, attrib)
144
+ # Create the label.
145
+ popup = CDK::LABEL.new(self, CENTER, CENTER, mesg, count, true, false)
146
+ popup.setBackgroundAttrib
147
+
148
+ old_state = Curses.curs_set(0)
149
+ # Draw it on the screen)
150
+ popup.draw(true)
151
+
152
+ # Wait for some input
153
+ popup.win.keypad(true)
154
+ popup.getch([])
155
+
156
+ # Kill it.
157
+ popup.destroy
158
+
159
+ # Clean the screen.
160
+ Curses.curs_set(old_state)
161
+ screen.erase
162
+ screen.refresh
163
+ end
164
+
165
+ # This pops up a dialog box.
166
+ def popupDialog(mesg, mesg_count, buttons, button_count)
167
+ # Create the dialog box.
168
+ popup = CDK::DIALOG.new(self, CDK::CENTER, CDK::CENTER,
169
+ mesg, mesg_count, buttons, button_count, Curses::A_REVERSE,
170
+ true, true, false)
171
+
172
+ # Activate the dialog box
173
+ popup.draw(true)
174
+
175
+ # Get the choice
176
+ choice = popup.activate('')
177
+
178
+ # Destroy the dialog box
179
+ popup.destroy
180
+
181
+ # Clean the screen.
182
+ self.erase
183
+ self.refresh
184
+
185
+ return choice
186
+ end
187
+
188
+ # This calls SCREEN.refresh, (made consistent with widgets)
189
+ def draw
190
+ self.refresh
191
+ end
192
+
193
+ # Refresh one CDK window.
194
+ # FIXME(original): this should be rewritten to use the panel library, so
195
+ # it would not be necessary to touch the window to ensure that it covers
196
+ # other windows.
197
+ def SCREEN.refreshCDKWindow(win)
198
+ win.touch
199
+ win.refresh
200
+ end
201
+
202
+ # This refreshes all the objects in the screen.
203
+ def refresh
204
+ focused = -1
205
+ visible = -1
206
+
207
+ CDK::SCREEN.refreshCDKWindow(@window)
208
+
209
+ # We erase all the invisible objects, then only draw it all back, so
210
+ # that the objects can overlap, and the visible ones will always be
211
+ # drawn after all the invisible ones are erased
212
+ (0...@object_count).each do |x|
213
+ obj = @object[x]
214
+ if obj.validObjType(obj.object_type)
215
+ if obj.is_visible
216
+ if visible < 0
217
+ visible = x
218
+ end
219
+ if obj.has_focus && focused < 0
220
+ focused = x
221
+ end
222
+ else
223
+ obj.erase
224
+ end
225
+ end
226
+ end
227
+
228
+ (0...@object_count).each do |x|
229
+ obj = @object[x]
230
+
231
+ if obj.validObjType(obj.object_type)
232
+ obj.has_focus = (x == focused)
233
+
234
+ if obj.is_visible
235
+ obj.draw(obj.box)
236
+ end
237
+ end
238
+ end
239
+ end
240
+
241
+ # This clears all the objects in the screen
242
+ def erase
243
+ # We just call the object erase function
244
+ (0...@object_count).each do |x|
245
+ obj = @object[x]
246
+ if obj.validObjType(obj.object_type)
247
+ obj.erase
248
+ end
249
+ end
250
+
251
+ # Refresh the screen.
252
+ @window.refresh
253
+ end
254
+
255
+ # Destroy all the objects on a screen
256
+ def destroyCDKScreenObjects
257
+ (0...@object_count).each do |x|
258
+ obj = @object[x]
259
+ before = @object_count
260
+
261
+ if obj.validObjType(obj.object_type)
262
+ obj.erase
263
+ obj.destroy
264
+ x -= (@object_count - before)
265
+ end
266
+ end
267
+ end
268
+
269
+ # This destroys a CDK screen.
270
+ def destroy
271
+ CDK::ALL_SCREENS.delete(self)
272
+ end
273
+
274
+ # This is added to remain consistent
275
+ def self.endCDK
276
+ Curses.echo
277
+ Curses.nocbreak
278
+ Curses.close_screen
279
+ end
280
+ end
281
+ end