topherfangio-lcdproc-ruby 0.1.1
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.
- data/.document +5 -0
- data/.gitignore +6 -0
- data/LICENSE +20 -0
- data/README.rdoc +9 -0
- data/Rakefile +70 -0
- data/TODO +18 -0
- data/VERSION +1 -0
- data/devices/crystalfontz/packet.rb +108 -0
- data/devices/devices.rb +41 -0
- data/examples/basic.rb +39 -0
- data/examples/clock.rb +78 -0
- data/examples/lights.rb +67 -0
- data/lcdproc.rb +43 -0
- data/lib/console.rb +39 -0
- data/lib/core_extensions/array.rb +37 -0
- data/lib/core_extensions/string.rb +37 -0
- data/lib/includes/lcdproc.rb +27 -0
- data/lib/lcdproc-ruby.rb +0 -0
- data/lib/lcdproc/client.rb +458 -0
- data/lib/lcdproc/command.rb +54 -0
- data/lib/lcdproc/errors.rb +41 -0
- data/lib/lcdproc/key_event.rb +59 -0
- data/lib/lcdproc/menu.rb +188 -0
- data/lib/lcdproc/menu_event.rb +49 -0
- data/lib/lcdproc/menu_item.rb +108 -0
- data/lib/lcdproc/menu_items/action.rb +72 -0
- data/lib/lcdproc/menu_items/alpha.rb +85 -0
- data/lib/lcdproc/menu_items/checkbox.rb +76 -0
- data/lib/lcdproc/menu_items/ip.rb +75 -0
- data/lib/lcdproc/menu_items/numeric.rb +75 -0
- data/lib/lcdproc/menu_items/ring.rb +75 -0
- data/lib/lcdproc/menu_items/slider.rb +83 -0
- data/lib/lcdproc/menu_items/submenu.rb +77 -0
- data/lib/lcdproc/response.rb +65 -0
- data/lib/lcdproc/screen.rb +283 -0
- data/lib/lcdproc/widget.rb +142 -0
- data/lib/lcdproc/widgets/graph.rb +185 -0
- data/lib/lcdproc/widgets/hbar.rb +101 -0
- data/lib/lcdproc/widgets/icon.rb +94 -0
- data/lib/lcdproc/widgets/num.rb +92 -0
- data/lib/lcdproc/widgets/scroller.rb +110 -0
- data/lib/lcdproc/widgets/string.rb +94 -0
- data/lib/lcdproc/widgets/title.rb +90 -0
- data/lib/lcdproc/widgets/vbar.rb +111 -0
- data/script/console.rb +28 -0
- data/script/telnet.rb +90 -0
- data/tasks/test/basic.rake +82 -0
- data/tasks/test/keys.rake +66 -0
- data/tasks/test/menus.rake +74 -0
- metadata +104 -0
data/lcdproc.rb
ADDED
@@ -0,0 +1,43 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
require "socket"
|
28
|
+
require "find"
|
29
|
+
|
30
|
+
fileList = []
|
31
|
+
directories = [ "lib/lcdproc", "lib/core_extensions", "devices" ]
|
32
|
+
|
33
|
+
directories.each do |directory|
|
34
|
+
Find.find( directory ) do |file|
|
35
|
+
if File.basename( file ) =~ /.rb$/
|
36
|
+
fileList << file
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
fileList.sort { |a,b| a.scan(/\//).size <=> b.scan(/\//).size }.each do |file|
|
41
|
+
require file
|
42
|
+
end
|
43
|
+
end
|
data/lib/console.rb
ADDED
@@ -0,0 +1,39 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
require 'optparse'
|
28
|
+
|
29
|
+
irb = RUBY_PLATFORM =~ /(:?mswin|mingw)/ ? 'irb.bat' : 'irb'
|
30
|
+
|
31
|
+
options = { :irb => irb }
|
32
|
+
|
33
|
+
libs = " -r irb/completion"
|
34
|
+
libs << " -r lcdproc"
|
35
|
+
libs << " -r lib/includes/lcdproc"
|
36
|
+
|
37
|
+
puts "Loading LCDProc Console Environment"
|
38
|
+
|
39
|
+
exec "#{options[:irb]} #{libs} --simple-prompt"
|
@@ -0,0 +1,37 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
class Array
|
28
|
+
|
29
|
+
def sum
|
30
|
+
inject( nil ) { |sum,x| sum ? sum + x : x }
|
31
|
+
end
|
32
|
+
|
33
|
+
def mean
|
34
|
+
sum.to_f / size
|
35
|
+
end
|
36
|
+
|
37
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
class String
|
28
|
+
|
29
|
+
def quotify
|
30
|
+
"\"#{self}\""
|
31
|
+
end
|
32
|
+
|
33
|
+
def quotify!
|
34
|
+
self.replace self.quotify
|
35
|
+
end
|
36
|
+
|
37
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
include LCDProc
|
data/lib/lcdproc-ruby.rb
ADDED
File without changes
|
@@ -0,0 +1,458 @@
|
|
1
|
+
#-------------------------------------------------------------------------------
|
2
|
+
# Copyright (c) 2008 Topher Fangio
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person
|
5
|
+
# obtaining a copy of this software and associated documentation
|
6
|
+
# files (the "Software"), to deal in the Software without
|
7
|
+
# restriction, including without limitation the rights to use,
|
8
|
+
# copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the
|
10
|
+
# Software is furnished to do so, subject to the following
|
11
|
+
# conditions:
|
12
|
+
#
|
13
|
+
# The above copyright notice and this permission notice shall be
|
14
|
+
# included in all copies or substantial portions of the Software.
|
15
|
+
#
|
16
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
|
18
|
+
# OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
|
20
|
+
# HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
21
|
+
# WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
22
|
+
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
|
23
|
+
# OTHER DEALINGS IN THE SOFTWARE.
|
24
|
+
#-------------------------------------------------------------------------------
|
25
|
+
|
26
|
+
|
27
|
+
module LCDProc
|
28
|
+
|
29
|
+
class Client
|
30
|
+
# The maximum number of messages allowed to stay in memory. This works much like a circular array with the
|
31
|
+
# oldest messages being overwritten.
|
32
|
+
MAX_MESSAGES = 512
|
33
|
+
|
34
|
+
# The number of milliseconds to wait before processing new responses.
|
35
|
+
RESPONSE_PROCESS_TIME = 25
|
36
|
+
|
37
|
+
# Whether or not debugging output should be displayed.
|
38
|
+
DEBUG = false
|
39
|
+
|
40
|
+
# The number of LCDProc-Ruby clients currently connected to the server.
|
41
|
+
@@client_count = 0
|
42
|
+
|
43
|
+
attr_reader :key_events, :commands, :name, :menu_events, :messages, :response_queue, :screens, :width, :height, :cell_width, :cell_height
|
44
|
+
attr_accessor :menu
|
45
|
+
|
46
|
+
# Create a new client.
|
47
|
+
#
|
48
|
+
# If <tt>:host</tt> is left blank, it will attempt to connect to "_localhost_" on port <i>13666</i>. You may also
|
49
|
+
# specify another port through <tt>:port</tt>.
|
50
|
+
#
|
51
|
+
# * <tt>:host</tt> - The host to which the client should attempt to connect. Defaults to "localhost".
|
52
|
+
# * <tt>:port</tt> - The port on which the client should attempt to connect. Defaults to 13666.
|
53
|
+
# * <tt>:name</tt> - The name that should be associated with this client. Defaults to "Client_" + a sequence number.
|
54
|
+
#
|
55
|
+
# Example:
|
56
|
+
#
|
57
|
+
# my_client = Client.new
|
58
|
+
#
|
59
|
+
# or
|
60
|
+
#
|
61
|
+
# my_client = Client.new( :host => "my.remote-host.com", :port => 13667, :name => 'MyGamingRig' )
|
62
|
+
def initialize( user_options = {} )
|
63
|
+
if self.respond_to?( :before_initialize ) then self.send( :before_initialize, user_options ) end
|
64
|
+
|
65
|
+
@messages = []
|
66
|
+
@commands = []
|
67
|
+
@response_queue = []
|
68
|
+
@screens = []
|
69
|
+
@menu_events = []
|
70
|
+
@global_key_events = []
|
71
|
+
@current_screen = nil
|
72
|
+
|
73
|
+
options = {}
|
74
|
+
|
75
|
+
options[:host] = "localhost"
|
76
|
+
options[:port] = 13666
|
77
|
+
options[:name] = "Client_#{@@client_count}"
|
78
|
+
|
79
|
+
# Update our defaults with anything that they passed in
|
80
|
+
options.update( user_options )
|
81
|
+
|
82
|
+
@daemon_socket = connect( options[:host], options[:port] )
|
83
|
+
|
84
|
+
if @daemon_socket.nil?
|
85
|
+
raise messages[0]
|
86
|
+
end
|
87
|
+
|
88
|
+
@thread = Thread.new do
|
89
|
+
while true do
|
90
|
+
sleep( RESPONSE_PROCESS_TIME.to_f / 1000.0 )
|
91
|
+
process_responses
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
response = send_command( Command.new( "hello" ) )
|
96
|
+
response = response.message.split(' ')
|
97
|
+
|
98
|
+
@version = response[2]
|
99
|
+
@protocol = response[4]
|
100
|
+
@width = response[7]
|
101
|
+
@height = response[9]
|
102
|
+
@cell_width = response[11]
|
103
|
+
@cell_height = response[13]
|
104
|
+
|
105
|
+
@menu = Menu.new( self )
|
106
|
+
|
107
|
+
response = send_command( Command.new( "info" ) )
|
108
|
+
driver_info = response.message
|
109
|
+
|
110
|
+
LCDProc::Devices.find_all_that_drive( driver_info ).each do |device|
|
111
|
+
LCDProc::Client.send( :include, device )
|
112
|
+
end
|
113
|
+
|
114
|
+
@name = options[:name]
|
115
|
+
|
116
|
+
response = send_command( Command.new( "client_set -name #{@name}" ) )
|
117
|
+
|
118
|
+
@@client_count += 1
|
119
|
+
|
120
|
+
if self.respond_to?( :after_initialize ) then self.send( :after_initialize, options ) end
|
121
|
+
end
|
122
|
+
|
123
|
+
|
124
|
+
# Adds a message to the client's message list. Used seperately from the responses returned by
|
125
|
+
# the LCDd server. If there are more than MAX_MESSAGES, the oldest message will be removed from
|
126
|
+
# the stack.
|
127
|
+
#
|
128
|
+
# * msg - The message to be added.
|
129
|
+
#
|
130
|
+
# Example:
|
131
|
+
#
|
132
|
+
# client.add_message( "Woah Man!!! Something is wrong!!!" )
|
133
|
+
def add_message( msg )
|
134
|
+
@messages.unshift( msg )
|
135
|
+
|
136
|
+
if @messages.length > MAX_MESSAGES
|
137
|
+
@messages.pop
|
138
|
+
end
|
139
|
+
end
|
140
|
+
|
141
|
+
|
142
|
+
# Attaches a screen to this client.
|
143
|
+
#
|
144
|
+
# * screen - Any screen which contains any number of widgets.
|
145
|
+
#
|
146
|
+
# Example:
|
147
|
+
#
|
148
|
+
# s = Screen.new( 'MyTestScreen' )
|
149
|
+
# client.attach( s )
|
150
|
+
#
|
151
|
+
# or
|
152
|
+
#
|
153
|
+
# client.attach( Screen.new( 'MyTestScreen' ) )
|
154
|
+
def attach( screen )
|
155
|
+
|
156
|
+
if @screens.select{ |s| s.id == screen.id }.empty?
|
157
|
+
if screen.attach_to( self )
|
158
|
+
@screens << screen
|
159
|
+
screen.update
|
160
|
+
return true
|
161
|
+
else
|
162
|
+
return false
|
163
|
+
end
|
164
|
+
else
|
165
|
+
return false
|
166
|
+
end
|
167
|
+
|
168
|
+
end
|
169
|
+
|
170
|
+
|
171
|
+
# Detaches a screen from the client but leaves it in memory so that it may later be attached to another
|
172
|
+
# client or re-attached to this client.
|
173
|
+
#
|
174
|
+
# * <tt>screen</tt> - Any screen currently attached to this client.
|
175
|
+
#
|
176
|
+
# Example:
|
177
|
+
#
|
178
|
+
# client.detach( 'TestScreen' )
|
179
|
+
def detach( screen )
|
180
|
+
if @screens.include? screen
|
181
|
+
|
182
|
+
if screen.detach
|
183
|
+
@screens.delete( screen )
|
184
|
+
return true
|
185
|
+
else
|
186
|
+
return false
|
187
|
+
end
|
188
|
+
|
189
|
+
else
|
190
|
+
add_message "Error: Screen '#{screen.id}' is not attached to client '#{self.name}'"
|
191
|
+
return false
|
192
|
+
end
|
193
|
+
end
|
194
|
+
|
195
|
+
|
196
|
+
# Returns the last received message from the @messages array (internally more like a circular array).
|
197
|
+
#
|
198
|
+
# Example:
|
199
|
+
#
|
200
|
+
# puts client.message
|
201
|
+
def message
|
202
|
+
@messages.first
|
203
|
+
end
|
204
|
+
|
205
|
+
|
206
|
+
# Sets the name of the client
|
207
|
+
#
|
208
|
+
# * <tt>name</tt> - The new name of the client
|
209
|
+
#
|
210
|
+
# Example:
|
211
|
+
#
|
212
|
+
# client.name = 'MyGreatClient'
|
213
|
+
def name= name
|
214
|
+
response = send_command( Command.new( "client_set -name #{name}" ) )
|
215
|
+
|
216
|
+
if response.successful?
|
217
|
+
@name = name
|
218
|
+
|
219
|
+
return @name
|
220
|
+
else
|
221
|
+
error = "Error: Failed to set client's name to '#{name}'\n\n#{response.message}".gsub( /\n/, "\n " )
|
222
|
+
add_message error
|
223
|
+
|
224
|
+
raise InvalidCommand, error
|
225
|
+
end
|
226
|
+
end
|
227
|
+
|
228
|
+
|
229
|
+
# Register a new button event for the client to process and reserves the key.
|
230
|
+
def register_key_event( key_event )
|
231
|
+
|
232
|
+
if key_event and valid_keys.include? key_event.key
|
233
|
+
response = send_command( Command.new( "client_add_key -exclusively #{key_event.key}" ) )
|
234
|
+
|
235
|
+
if response.successful?
|
236
|
+
@global_key_events << key_event
|
237
|
+
return key_event
|
238
|
+
end
|
239
|
+
end
|
240
|
+
|
241
|
+
return nil
|
242
|
+
end
|
243
|
+
|
244
|
+
|
245
|
+
# Register a new menu event for the client to process
|
246
|
+
def register_menu_event( menu_event )
|
247
|
+
|
248
|
+
if menu_event
|
249
|
+
@menu_events << menu_event
|
250
|
+
return menu_event
|
251
|
+
else
|
252
|
+
return nil
|
253
|
+
end
|
254
|
+
|
255
|
+
end
|
256
|
+
|
257
|
+
|
258
|
+
# Sends a command to the server and returns a Response object. This is generally used for internal
|
259
|
+
# purposes, but has been opened to the public API in case LCDProc changes it's behaviour or adds new
|
260
|
+
# features. You should *NOT* use this to bypass the default behaviour such as setting a client's name.
|
261
|
+
#
|
262
|
+
# * <tt>command</tt> - The Command object that you wish to send to the server.
|
263
|
+
#
|
264
|
+
# Example:
|
265
|
+
#
|
266
|
+
# client.send_command( Command.new( 'info' ) )
|
267
|
+
def send_command( command )
|
268
|
+
|
269
|
+
puts "Command: " + command.message unless not DEBUG
|
270
|
+
if command.message.kind_of? String
|
271
|
+
|
272
|
+
@daemon_socket.write( command.message )
|
273
|
+
@commands << command
|
274
|
+
|
275
|
+
# NOTE: This extra get_response is here because LCDd will get confused if sent two messages very
|
276
|
+
# quickly when trying to add menu items to a menu. Hopefully it will be removed when they have their
|
277
|
+
# commands queued properly.
|
278
|
+
if command.message =~ /^menu_add_item/
|
279
|
+
r1 = get_response
|
280
|
+
|
281
|
+
if r1.message =~ /^success/
|
282
|
+
get_response
|
283
|
+
end
|
284
|
+
|
285
|
+
return r1
|
286
|
+
else
|
287
|
+
return get_response
|
288
|
+
end
|
289
|
+
|
290
|
+
elsif command.message.kind_of? Array
|
291
|
+
|
292
|
+
@daemon_socket.write( command.message.join("\n") )
|
293
|
+
@commands << command
|
294
|
+
return get_response( command.message.length )
|
295
|
+
|
296
|
+
end
|
297
|
+
end
|
298
|
+
|
299
|
+
|
300
|
+
# Unregisters a button event from the client
|
301
|
+
def unregister_key_event( key_event )
|
302
|
+
if @global_key_events.include? key_event
|
303
|
+
@global_key_events.delete key_event
|
304
|
+
return key_event
|
305
|
+
else
|
306
|
+
return nil
|
307
|
+
end
|
308
|
+
end
|
309
|
+
|
310
|
+
|
311
|
+
# Register a new menu event for the client to process
|
312
|
+
def unregister_menu_event( menu_event )
|
313
|
+
|
314
|
+
if @menu_events.include? menu_event
|
315
|
+
@menu_events.delete( menu_event )
|
316
|
+
return menu_event
|
317
|
+
else
|
318
|
+
return nil
|
319
|
+
end
|
320
|
+
end
|
321
|
+
|
322
|
+
|
323
|
+
# Returns the keys that may be registered for the client
|
324
|
+
def valid_keys
|
325
|
+
if VALID_KEYS
|
326
|
+
VALID_KEYS
|
327
|
+
else
|
328
|
+
[]
|
329
|
+
end
|
330
|
+
end
|
331
|
+
|
332
|
+
|
333
|
+
private
|
334
|
+
# Connects this client to a remote (or local) LCDd server.
|
335
|
+
#
|
336
|
+
# * <tt>:host</tt> - The remote host to which you wish to connect. Defaults to <i>"localhost"</i>.
|
337
|
+
# * <tt>:port</tt> - The port on which the TCP socket should be opened. Defaults to <i>13666</i>.
|
338
|
+
def connect( host, port )
|
339
|
+
daemon_socket = nil
|
340
|
+
|
341
|
+
begin
|
342
|
+
daemon_socket = TCPSocket.new( host, port )
|
343
|
+
rescue Errno::ECONNREFUSED
|
344
|
+
add_message "Connection to '#{host}':#{port} was refused"
|
345
|
+
end
|
346
|
+
|
347
|
+
return daemon_socket
|
348
|
+
end
|
349
|
+
|
350
|
+
|
351
|
+
# Blocks until a message is entered into the response queue, creates a new Response object
|
352
|
+
# and returns it to the requester.
|
353
|
+
def get_response( number_of_responses = 1 )
|
354
|
+
|
355
|
+
responses = []
|
356
|
+
|
357
|
+
1.upto( number_of_responses ) do |i|
|
358
|
+
response = @response_queue.pop
|
359
|
+
|
360
|
+
while response.nil?
|
361
|
+
Thread.pass
|
362
|
+
|
363
|
+
response = @response_queue.pop
|
364
|
+
end
|
365
|
+
|
366
|
+
puts "Q: #{@response_queue}, #{response}" unless not DEBUG
|
367
|
+
|
368
|
+
responses << response
|
369
|
+
end
|
370
|
+
|
371
|
+
if responses.length == 1
|
372
|
+
puts "returning one response" unless not DEBUG
|
373
|
+
|
374
|
+
return Response.new( responses[0] )
|
375
|
+
else
|
376
|
+
puts "returning multiple response: #{responses.length}" unless not DEBUG
|
377
|
+
|
378
|
+
return Response.new( responses )
|
379
|
+
end
|
380
|
+
end
|
381
|
+
|
382
|
+
|
383
|
+
# Controls processing the responses received from the LCDd server. This includes
|
384
|
+
# <tt>listen</tt> and <tt>ignore</tt> messages as well as button presses and responses to
|
385
|
+
# commands. Takes no arguments.
|
386
|
+
#
|
387
|
+
# This should be called via a thread in the client at least twice every second (currently
|
388
|
+
# set to fifty (50) times a second).
|
389
|
+
def process_responses
|
390
|
+
data = @daemon_socket.recv( 1024 )
|
391
|
+
|
392
|
+
puts "Data: " + data unless not DEBUG
|
393
|
+
array = data.split( "\n" )
|
394
|
+
|
395
|
+
puts "Array: #{array.inspect}" unless not DEBUG
|
396
|
+
|
397
|
+
array.each do |response|
|
398
|
+
puts "response: #{response} about to be processed" unless not DEBUG
|
399
|
+
|
400
|
+
# Process the listen event
|
401
|
+
if response =~ /^listen .*$/
|
402
|
+
|
403
|
+
@current_screen = @screens.find{ |s| s.id == response.split(' ').last }
|
404
|
+
puts " ! processing listen..." unless not DEBUG
|
405
|
+
|
406
|
+
|
407
|
+
|
408
|
+
# Process the ignore event
|
409
|
+
elsif response =~ /^ignore .*$/
|
410
|
+
|
411
|
+
puts " ! processing ignore..." unless not DEBUG
|
412
|
+
|
413
|
+
|
414
|
+
|
415
|
+
# Process menu events
|
416
|
+
elsif response =~ /^menuevent .*$/
|
417
|
+
|
418
|
+
puts " ! processing a menu event: #{response}" unless not DEBUG
|
419
|
+
|
420
|
+
@menu_events.each do |me|
|
421
|
+
if response =~ /^menuevent #{me.menu_item.lcdproc_event_type} #{me.menu_item.id}/
|
422
|
+
if me.block
|
423
|
+
me.block.call( response )
|
424
|
+
end
|
425
|
+
end
|
426
|
+
end
|
427
|
+
|
428
|
+
|
429
|
+
|
430
|
+
# Process key events
|
431
|
+
elsif response =~ /^key .*$/
|
432
|
+
key = response.split(' ').last
|
433
|
+
|
434
|
+
puts "Processing key #{key} in Client" unless not DEBUG
|
435
|
+
|
436
|
+
@global_key_events.each do |gbe|
|
437
|
+
if ( key == gbe.key ) and ( gbe.block )
|
438
|
+
gbe.block.call
|
439
|
+
end
|
440
|
+
end
|
441
|
+
|
442
|
+
@current_screen.process_key( key )
|
443
|
+
|
444
|
+
|
445
|
+
|
446
|
+
# Otherwise stick it in the queue
|
447
|
+
else
|
448
|
+
# If we don't know how to process it, assume that it is a response to a command
|
449
|
+
@response_queue << response
|
450
|
+
puts "response: #{response} added to queue" unless not DEBUG
|
451
|
+
end
|
452
|
+
end
|
453
|
+
|
454
|
+
end
|
455
|
+
|
456
|
+
end
|
457
|
+
|
458
|
+
end
|