rubyxmacro 0.0.7

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore ADDED
@@ -0,0 +1,39 @@
1
+ tmp/*
2
+ pkg/*
3
+ *.swp
4
+ *.gem
5
+
6
+ # Compiled source #
7
+ ###################
8
+ *.com
9
+ *.class
10
+ *.dll
11
+ *.exe
12
+ *.o
13
+ *.so
14
+
15
+ # Packages #
16
+ ############
17
+ # it's better to unpack these files and commit the raw source
18
+ # git has its own built in compression methods
19
+ *.7z
20
+ *.dmg
21
+ *.gz
22
+ *.iso
23
+ *.jar
24
+ *.rar
25
+ *.tar
26
+ *.zip
27
+
28
+ # Logs and databases #
29
+ ######################
30
+ *.log
31
+ *.sql
32
+ *.sqlite
33
+
34
+ # OS generated files #
35
+ ######################
36
+ .DS_Store?
37
+ ehthumbs.db
38
+ Icon?
39
+ Thumbs.db
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in rubyxmacro.gemspec
4
+ gemspec
data/README.markdown ADDED
@@ -0,0 +1,56 @@
1
+ # RubyXMacro
2
+
3
+ ## A ruby gem to automate the mouse and keyboard in X Windows.
4
+
5
+ Rubyxmacro allows you to automate mouse and keyboard movements on Linux with Ruby. It was created in order to test flash websites, but it could be used for many other purposes.
6
+
7
+ The project is hosted on github at [http://github.com/mattddowney/rubyxmacro](http://github.com/mattddowney/rubyxmacro)
8
+
9
+ ## Install
10
+
11
+ Your system needs to have the Xtst library installed.
12
+ On Ubuntu, this is as easy as:
13
+ sudo apt-get install libxtst-dev
14
+ On Fedora, try:
15
+ yum install libXtst-devel
16
+
17
+ Then, just install with rubygems:
18
+
19
+ gem install rubyxmacro
20
+
21
+ ## Usage
22
+
23
+ Create a display:
24
+
25
+ require 'rubyxmacro'
26
+ d = RubyXMacro::Display.new
27
+
28
+ Move the mouse:
29
+
30
+ d.moveMouse(100,100)
31
+
32
+ Click the mouse:
33
+
34
+ d.click
35
+ d.rightClick
36
+
37
+ Type a string of keys:
38
+
39
+ d.sendKeys('Hello World!')
40
+
41
+ Other methods:
42
+
43
+ d.mouseDown #press and hold the mouse button down until mouseUp
44
+ d.mouseUp #release the mouse button
45
+ d.rightMouseDown #press and hold the right mouse button down until rightMouseUp
46
+ d.rightMouseUp #release the right mouse button
47
+
48
+ d.keyPress #press a key, only supports letters and numerals
49
+ d.keycodePress(keycodeNum) #press a key based on it's keycode
50
+ d.keycodeShiftPress(keycodeNum) #hold down shift, then press key
51
+ d.keycodeDown(keycodeNum) #press and hold down key with the specified keycode
52
+ d.keycodeUp(keycodeNum) #release the key with the specified keycode
53
+
54
+ ## Author
55
+
56
+ Matthew Downey - [http://www.writehack.com](http://www.writehack.com)
data/Rakefile ADDED
@@ -0,0 +1,16 @@
1
+ require "rubygems"
2
+ require "rake"
3
+ require "bundler"
4
+ require "rake/extensiontask"
5
+
6
+ Rake::ExtensionTask.new("rubyxmacro") do |extension|
7
+ extension.lib_dir = "lib/rubyxmacro"
8
+ end
9
+
10
+ task :chmod do
11
+ File.chmod(0775, 'lib/rubyxmacro/rubyxmacro.so')
12
+ end
13
+
14
+ task :build => [:clean, :compile, :chmod]
15
+
16
+ Bundler::GemHelper.install_tasks
@@ -0,0 +1,199 @@
1
+ /*****************************************************************************
2
+ *
3
+ * controlx.h
4
+ * Copyright (C) 2010 Matthew Downey <mattddowney@gmail*NOSPAM*.com>
5
+ *
6
+ * This program is free software: you can redistribute it and/or modify
7
+ * it under the terms of the GNU General Public License as published by
8
+ * the Free Software Foundation, either version 3 of the License, or
9
+ * (at your option) any later version.
10
+ *
11
+ * This program is distributed in the hope that it will be useful,
12
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
+ * GNU General Public License for more details.
15
+ *
16
+ * You should have received a copy of the GNU General Public License
17
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
18
+ *
19
+ ****************************************************************************/
20
+
21
+ #include "opendisplay.h"
22
+
23
+ /* Globals */
24
+ Display * display;
25
+ const int DELAY = 10;
26
+ const int LEFT_MOUSE_BUTTON = 1;
27
+ const int RIGHT_MOUSE_BUTTON = 3;
28
+ const int SHIFT_KEYCODE = 50;
29
+
30
+ /* Open the default display.
31
+ * The default display is contained in the $DISPLAY environment variable. */
32
+ void openDefaultDisplay() {
33
+ display = openDisplay(getenv("DISPLAY"));
34
+ return;
35
+ }
36
+
37
+ /*****************
38
+ * *
39
+ * Mouse Related *
40
+ * *
41
+ *****************/
42
+
43
+ /* push a button down on the mouse */
44
+ void buttonDown(int buttonNum) {
45
+ XTestFakeButtonEvent(display, buttonNum, 1, DELAY);
46
+ XFlush(display); /* flush the buffer to actually make the change */
47
+ return;
48
+ }
49
+
50
+ /* release a button on the mouse */
51
+ void buttonUp(int buttonNum) {
52
+ XTestFakeButtonEvent(display, buttonNum, 0, DELAY);
53
+ XFlush(display); /* flush the buffer to actually make the change */
54
+ return;
55
+ }
56
+
57
+ /* click a button on the mouse */
58
+ void buttonClick(int buttonNum) {
59
+ buttonDown(buttonNum);
60
+ buttonUp(buttonNum);
61
+ return;
62
+ }
63
+
64
+ /* Move the mouse pointer to position (x,y). */
65
+ void moveMouse(int x, int y)
66
+ {
67
+ XTestFakeMotionEvent(display, -1, x, y, DELAY);
68
+ XFlush(display); /* flush the buffer to actually make the change */
69
+ return;
70
+ }
71
+
72
+ /* Left-click the mouse. */
73
+ void click()
74
+ {
75
+ buttonClick(LEFT_MOUSE_BUTTON);
76
+ return;
77
+ }
78
+
79
+ /* Hold the left mouse button down until mouseUp. */
80
+ void mouseDown()
81
+ {
82
+ buttonDown(LEFT_MOUSE_BUTTON);
83
+ return;
84
+ }
85
+
86
+ /* Release the left mouse button. Usually used after mouseDown. */
87
+ void mouseUp()
88
+ {
89
+ buttonUp(LEFT_MOUSE_BUTTON);
90
+ return;
91
+ }
92
+
93
+ /* Right-click the mouse. */
94
+ void rightClick()
95
+ {
96
+ buttonClick(RIGHT_MOUSE_BUTTON);
97
+ return;
98
+ }
99
+
100
+ /* Hold the right mouse button down until rightMouseUp. */
101
+ void rightMouseDown()
102
+ {
103
+ buttonDown(RIGHT_MOUSE_BUTTON);
104
+ return;
105
+ }
106
+
107
+ /* Release the right mouse button. Usually used after rightMouseDown. */
108
+ void rightMouseUp()
109
+ {
110
+ buttonUp(RIGHT_MOUSE_BUTTON);
111
+ return;
112
+ }
113
+
114
+ /********************
115
+ * *
116
+ * Keyboard Related *
117
+ * *
118
+ ********************/
119
+
120
+ /* Hold down the key with the value keycode until keycodeUp. */
121
+ void keycodeDown(int keycode)
122
+ {
123
+ XTestFakeKeyEvent(display, keycode, 1, DELAY);
124
+ XFlush(display); /* flush the buffer to actually make the change */
125
+ return;
126
+ }
127
+
128
+ /* Release the key with the value keycode. Usually used after keycodeDown. */
129
+ void keycodeUp(int keycode)
130
+ {
131
+ XTestFakeKeyEvent(display, keycode, 0, DELAY);
132
+ XFlush(display); /* flush the buffer to actually make the change */
133
+ return;
134
+ }
135
+
136
+ /* Press and release the key with the value keycode. */
137
+ void keycodePress(int keycode)
138
+ {
139
+ keycodeDown(keycode);
140
+ keycodeUp(keycode);
141
+ return;
142
+ }
143
+
144
+ /* Hold down shift, then press and release the key with the value keycode. */
145
+ void keycodeShiftPress(int keycode)
146
+ {
147
+ keycodeDown(SHIFT_KEYCODE);
148
+ keycodePress(keycode);
149
+ keycodeUp(SHIFT_KEYCODE);
150
+ return;
151
+ }
152
+
153
+ /* Convert a string to it's keycode. */
154
+ int stringToKeycode(char * key)
155
+ {
156
+ KeySym keyS;
157
+ KeyCode keyC;
158
+
159
+ keyS = XStringToKeysym(key);
160
+
161
+ if((keyC = XKeysymToKeycode(display, keyS)) == 0)
162
+ {
163
+ fprintf(stderr, "Could not get keycode for %s", key);
164
+ return;
165
+ }
166
+ else
167
+ return ((int)keyC);
168
+ }
169
+
170
+ /* Hold down the key until keyUp. */
171
+ void keyDown(char * key)
172
+ {
173
+ keycodeDown(stringToKeycode(key));
174
+ return;
175
+ }
176
+
177
+ /* Release the key. Usually used after keyDown. */
178
+ void keyUp(char * key)
179
+ {
180
+ keycodeUp(stringToKeycode(key));
181
+ return;
182
+ }
183
+
184
+ /* Press and release the key. */
185
+ /* needs work to handle special characters */
186
+ void keyPress(char * key)
187
+ {
188
+ KeySym keyS, lowercase, uppercase;
189
+
190
+ keyS = XStringToKeysym(key);
191
+ XConvertCase(keyS, &lowercase, &uppercase);
192
+
193
+ if (keyS == lowercase)
194
+ keycodePress(stringToKeycode(key));
195
+ else /* uppercase */
196
+ keycodeShiftPress(stringToKeycode(key));
197
+
198
+ return;
199
+ }
@@ -0,0 +1,23 @@
1
+ # extconf.rb
2
+ # Copyright (C) 2010 Matthew Downey <mattddowney@gmail-NOSPAM-.com>
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+ require 'mkmf'
18
+ if have_library("Xtst") then
19
+ create_makefile("rubyxmacro/rubyxmacro")
20
+ else
21
+ puts "Cannot find Xtst library."
22
+ puts "Try apt-get install libxtst-dev"
23
+ end
@@ -0,0 +1,66 @@
1
+ /*****************************************************************************
2
+ *
3
+ * opendisplay.h - a function to open an X11 display.
4
+ * Portions Copyright (C) 2010 Matthew Downey <mattddowney@gmail-NOSPAM-.com>
5
+ *
6
+ * This code was copied and modified from:
7
+ * xmacro (http://xmacro.sourceforge.net/) which is:
8
+ * Copyright (C) 2000 Gabor Keresztfalvi <keresztg@mail.com>
9
+ *
10
+ * Which was based heavily on:
11
+ * xremote (http://infa.abo.fi/~chakie/xremote/) which is:
12
+ * Copyright (C) 2000 Jan Ekholm <chakie@infa.abo.fi>
13
+ *
14
+ * This program is free software: you can redistribute it and/or modify
15
+ * it under the terms of the GNU General Public License as published by
16
+ * the Free Software Foundation, either version 3 of the License, or
17
+ * (at your option) any later version.
18
+ *
19
+ * This program is distributed in the hope that it will be useful,
20
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
21
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22
+ * GNU General Public License for more details.
23
+ *
24
+ * You should have received a copy of the GNU General Public License
25
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
26
+ *
27
+ ****************************************************************************/
28
+
29
+ #include <X11/extensions/XTest.h>
30
+
31
+ // open the X11 display
32
+ Display * openDisplay (const char * displayName) {
33
+ int event, error, major, minor;
34
+
35
+ // open the display
36
+ Display * xDisplay = XOpenDisplay(displayName);
37
+
38
+ // did we get it?
39
+ if(!xDisplay) {
40
+ // nope, so show error and abort
41
+ fprintf(stderr, "could not open display \"%s\", aborting.\n", XDisplayName(displayName));
42
+ exit(EXIT_FAILURE);
43
+ }
44
+
45
+ // does the remote display have the Xtest-extension?
46
+ if(!XTestQueryExtension(xDisplay, &event, &error, &major, &minor)) {
47
+ // nope, extension not supported
48
+ fprintf(stderr, "XTest extension not supported on server \"%s\", aborting.\n", DisplayString(xDisplay));
49
+
50
+ // close the display and go away
51
+ XCloseDisplay(xDisplay);
52
+ exit(EXIT_FAILURE);
53
+ }
54
+
55
+ // take control of the server
56
+ XTestGrabControl(xDisplay, 1);
57
+
58
+ // sync the server
59
+ XSync(xDisplay, 1);
60
+
61
+ // discard all events
62
+ XTestDiscard (xDisplay);
63
+
64
+ // return the display
65
+ return xDisplay;
66
+ }
@@ -0,0 +1,267 @@
1
+ /*****************************************************************************
2
+ *
3
+ * rubyxmacro.c
4
+ * Copyright (C) 2010 Matthew Downey <mattddowney@gmail*NOSPAM*.com>
5
+ *
6
+ * This program is free software: you can redistribute it and/or modify
7
+ * it under the terms of the GNU General Public License as published by
8
+ * the Free Software Foundation, either version 3 of the License, or
9
+ * (at your option) any later version.
10
+ *
11
+ * This program is distributed in the hope that it will be useful,
12
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
13
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
+ * GNU General Public License for more details.
15
+ *
16
+ * You should have received a copy of the GNU General Public License
17
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
18
+ *
19
+ ****************************************************************************/
20
+
21
+ #include "ruby.h"
22
+ #include "controlx.h"
23
+
24
+ /*****************************
25
+ * *
26
+ * Methods Exposed to Ruby *
27
+ * *
28
+ *****************************/
29
+
30
+ /*
31
+ * Document-method: initialize
32
+ *
33
+ * Get a RubyXMacro object with the default display.
34
+ * The default display is stored in the $DISPLAY environment variable.
35
+ *
36
+ * display = RubyXMacro.new
37
+ */
38
+ static VALUE init(VALUE self)
39
+ {
40
+ openDefaultDisplay();
41
+ return Qnil;
42
+ }
43
+
44
+ /*******************
45
+ * *
46
+ * Mouse Related *
47
+ * *
48
+ *******************/
49
+
50
+ /*
51
+ * Document-method: move
52
+ *
53
+ * Move the mouse pointer to position (x,y).
54
+ *
55
+ * display.move(int_x, int_y)
56
+ */
57
+ static VALUE method_moveMouse(VALUE self, VALUE x, VALUE y)
58
+ {
59
+ moveMouse(NUM2INT(x), NUM2INT(y));
60
+ return Qnil;
61
+ }
62
+
63
+ /*
64
+ * Document-method: click
65
+ *
66
+ * Left-click the mouse.
67
+ *
68
+ * display.click
69
+ */
70
+ static VALUE method_click(VALUE self)
71
+ {
72
+ click();
73
+ return Qnil;
74
+ }
75
+
76
+ /*
77
+ * Document-method: mouseDown
78
+ *
79
+ * Hold the left mouse button down until mouseUp.
80
+ *
81
+ * display.mouseDown
82
+ */
83
+ static VALUE method_mouseDown(VALUE self)
84
+ {
85
+ mouseDown();
86
+ return Qnil;
87
+ }
88
+
89
+ /*
90
+ * Document-method: mouseUp
91
+ *
92
+ * Release the left mouse button. Usually used after mouseDown.
93
+ *
94
+ * display.mouseUp
95
+ */
96
+ static VALUE method_mouseUp(VALUE self)
97
+ {
98
+ mouseUp();
99
+ return Qnil;
100
+ }
101
+
102
+ /*
103
+ * Document-method: rightClick
104
+ *
105
+ * Right-click the mouse.
106
+ *
107
+ * display.rightClick
108
+ */
109
+ static VALUE method_rightClick(VALUE self)
110
+ {
111
+ rightClick();
112
+ return Qnil;
113
+ }
114
+
115
+ /*
116
+ * Document-method: rightMouseDown
117
+ *
118
+ * Hold the right mouse button down until rightMouseUp.
119
+ *
120
+ * display.rightMouseDown
121
+ */
122
+ static VALUE method_rightMouseDown(VALUE self)
123
+ {
124
+ rightMouseDown();
125
+ return Qnil;
126
+ }
127
+
128
+ /*
129
+ * Document-method: rightMouseUp
130
+ *
131
+ * Release the right mouse button. Usually used after rightMouseDown.
132
+ *
133
+ * display.rightMouseUp
134
+ */
135
+ static VALUE method_rightMouseUp(VALUE self)
136
+ {
137
+ rightMouseUp();
138
+ return Qnil;
139
+ }
140
+
141
+ /**********************
142
+ * *
143
+ * Keyboard Related *
144
+ * *
145
+ **********************/
146
+
147
+ /*
148
+ * Document-method: keycodeDown
149
+ *
150
+ * Hold down the key with the value keycode until keycodeUp.
151
+ *
152
+ * display.keycodeDown(int_keycode)
153
+ */
154
+ static VALUE method_keycodeDown(VALUE self, VALUE keycode)
155
+ {
156
+ keycodeDown(NUM2INT(keycode));
157
+ return Qnil;
158
+ }
159
+
160
+ /*
161
+ * Document-method: keycodeUp
162
+ *
163
+ * Release the key with the value keycode. Usually used after keycodeDown.
164
+ *
165
+ * display.keycodeUp(int_keycode)
166
+ */
167
+ static VALUE method_keycodeUp(VALUE self, VALUE keycode)
168
+ {
169
+ keycodeUp(NUM2INT(keycode));
170
+ return Qnil;
171
+ }
172
+
173
+ /*
174
+ * Document-method: keycodePress
175
+ *
176
+ * Press and release the key with the value keycode.
177
+ *
178
+ * display.keycodePress(int_keycode)
179
+ */
180
+ static VALUE method_keycodePress(VALUE self, VALUE keycode)
181
+ {
182
+ keycodePress(NUM2INT(keycode));
183
+ return Qnil;
184
+ }
185
+
186
+ /*
187
+ * Document-method: keycodeShiftPress
188
+ *
189
+ * Hold down shift, then press and release the key with the value keycode.
190
+ *
191
+ * display.keycodeShiftPress(int_keycode)
192
+ */
193
+ static VALUE method_keycodeShiftPress(VALUE self, VALUE keycode)
194
+ {
195
+ keycodeShiftPress(NUM2INT(keycode));
196
+ return Qnil;
197
+ }
198
+
199
+ /*
200
+ * Document-method: keyDown
201
+ *
202
+ * Hold down the key until keyUp.
203
+ *
204
+ * display.keyDown(str_key)
205
+ */
206
+ static VALUE method_keyDown(VALUE self, VALUE keycode)
207
+ {
208
+ keyDown(StringValuePtr(keycode));
209
+ return Qnil;
210
+ }
211
+
212
+ /*
213
+ * Document-method: keyUp
214
+ *
215
+ * Release the key. Usually used after keyDown.
216
+ *
217
+ * display.keyUp(str_key)
218
+ */
219
+ static VALUE method_keyUp(VALUE self, VALUE keycode)
220
+ {
221
+ keyUp(StringValuePtr(keycode));
222
+ return Qnil;
223
+ }
224
+
225
+ /*
226
+ * Document-method: keyPress
227
+ *
228
+ * Press and release the key.
229
+ *
230
+ * display.keyPress(str_key)
231
+ */
232
+ static VALUE method_keyPress(VALUE self, VALUE key)
233
+ {
234
+ keyPress(StringValuePtr(key));
235
+ return Qnil;
236
+ }
237
+
238
+ /******************
239
+ * *
240
+ * Ruby Related *
241
+ * *
242
+ ******************/
243
+
244
+ VALUE rubyXMacro;
245
+ VALUE displayClass;
246
+
247
+ /* Automate the mouse and keyboard in X. */
248
+ void Init_rubyxmacro()
249
+ {
250
+ rubyXMacro = rb_define_module("RubyXMacro");
251
+ displayClass = rb_define_class_under(rubyXMacro, "Display", rb_cObject);
252
+ rb_define_method(displayClass, "initialize", init, 0);
253
+ rb_define_method(displayClass, "moveMouse", method_moveMouse, 2);
254
+ rb_define_method(displayClass, "click", method_click, 0);
255
+ rb_define_method(displayClass, "mouseDown", method_mouseDown, 0);
256
+ rb_define_method(displayClass, "mouseUp", method_mouseUp, 0);
257
+ rb_define_method(displayClass, "rightClick", method_rightClick, 0);
258
+ rb_define_method(displayClass, "rightMouseDown", method_rightMouseDown, 0);
259
+ rb_define_method(displayClass, "rightMouseUp", method_rightMouseUp, 0);
260
+ rb_define_method(displayClass, "keycodeDown", method_keycodeDown, 1);
261
+ rb_define_method(displayClass, "keycodeUp", method_keycodeUp, 1);
262
+ rb_define_method(displayClass, "keycodePress", method_keycodePress, 1);
263
+ rb_define_method(displayClass, "keycodeShiftPress", method_keycodeShiftPress, 1);
264
+ rb_define_method(displayClass, "keyDown", method_keyDown, 1);
265
+ rb_define_method(displayClass, "keyUp", method_keyUp, 1);
266
+ rb_define_method(displayClass, "keyPress", method_keyPress, 1);;
267
+ }
data/lib/keycodes.rb ADDED
@@ -0,0 +1,90 @@
1
+ module RubyXMacro
2
+ SPECIAL_KEYCODES = {
3
+ 'BACKSPACE' => 22,
4
+ 'BS' => 22,
5
+ 'BKSP' => 22,
6
+ 'BREAK' => 127,
7
+ 'CAPSLOCK' => 66,
8
+ 'DELETE' => 119,
9
+ 'DEL' => 119,
10
+ 'DOWN' => 116,
11
+ 'END' => 115,
12
+ 'ENTER' => 36,
13
+ 'ESC' => 9,
14
+ #'HELP' =>
15
+ 'HOME' => 110,
16
+ 'INSERT' => 118,
17
+ 'INS' => 118,
18
+ 'LEFT' => 113,
19
+ 'NUMLOCK' => 77,
20
+ 'PGDN' => 117,
21
+ 'PGUP' => 112,
22
+ #'PRTSC' =>
23
+ 'RIGHT' => 114,
24
+ #'SCROLLLOCK' =>
25
+ 'TAB' => 23,
26
+ 'UP' => 111,
27
+ 'F1' => 67,
28
+ 'F2' => 68,
29
+ 'F3' => 69,
30
+ 'F4' => 70,
31
+ 'F5' => 71,
32
+ 'F6' => 72,
33
+ 'F7' => 73,
34
+ 'F8' => 74,
35
+ 'F9' => 75,
36
+ 'F10' => 76,
37
+ 'F11' => 95,
38
+ 'F12' => 96
39
+ #'F13' =>
40
+ #'F14' =>
41
+ #'F15' =>
42
+ #'F16' =>
43
+ }
44
+
45
+ KEYCODES = {
46
+ ' ' => '65l',
47
+ '`' => '49l',
48
+ '~' => '49u',
49
+ '1' => '10l',
50
+ '!' => '10u',
51
+ '2' => '11l',
52
+ '@' => '11u',
53
+ '3' => '12l',
54
+ '#' => '12u',
55
+ '4' => '13l',
56
+ '$' => '13u',
57
+ '5' => '14l',
58
+ '%' => '14u',
59
+ '6' => '15l',
60
+ '^' => '15u',
61
+ '7' => '16l',
62
+ '&' => '16u',
63
+ '8' => '17l',
64
+ '*' => '17u',
65
+ '9' => '18l',
66
+ '(' => '18u',
67
+ '0' => '19l',
68
+ ')' => '19u',
69
+ '-' => '20l',
70
+ '_' => '20u',
71
+ '=' => '21l',
72
+ '+' => '21u',
73
+ '[' => '34l',
74
+ '{' => '34u',
75
+ ']' => '35l',
76
+ '}' => '35u',
77
+ '\\' => '51l',
78
+ '|' => '51u',
79
+ ';' => '47l',
80
+ ':' => '47u',
81
+ "'" => '48l',
82
+ '"' => '48u',
83
+ ',' => '59l',
84
+ '<' => '59u',
85
+ '.' => '60l',
86
+ '>' => '60u',
87
+ '/' => '61l',
88
+ '?' => '61u'
89
+ }
90
+ end
@@ -0,0 +1,3 @@
1
+ module RubyXMacro
2
+ VERSION = "0.0.7"
3
+ end
data/lib/rubyxmacro.rb ADDED
@@ -0,0 +1,37 @@
1
+ require 'rubyxmacro/rubyxmacro'
2
+ require 'keycodes'
3
+
4
+ module RubyXMacro
5
+ class Display
6
+ # Press and release a string of keys.
7
+ def sendKeys(keyString)
8
+ while keyString.length > 0 do
9
+ keyStringArray = keyString.partition(/\{(.*?)\}/)
10
+ keyString = keyStringArray[0]
11
+
12
+ keyString.each_char do |key|
13
+ if RubyXMacro::KEYCODES[key] == nil then
14
+ self.keyPress(key)
15
+ else
16
+ keycode = RubyXMacro::KEYCODES[key]
17
+ keyCase = keycode[-1]
18
+ keycode = keycode.chop.to_i
19
+ if keyCase == 'l' then
20
+ keycodePress(keycode)
21
+ else
22
+ keycodeShiftPress(keycode)
23
+ end
24
+ end
25
+ end
26
+
27
+ specialKey = keyStringArray[1].slice(1..(keyStringArray[1].length - 2))
28
+ if specialKey != nil && specialKey.length > 0 then
29
+ specialKey.upcase!
30
+ keycodePress(RubyXMacro::SPECIAL_KEYCODES[specialKey])
31
+ end
32
+
33
+ keyString = keyStringArray[2]
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,23 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "rubyxmacro/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "rubyxmacro"
7
+ s.version = RubyXMacro::VERSION
8
+ s.platform = Gem::Platform::RUBY
9
+ s.authors = ["Matthew Downey"]
10
+ s.email = ["mattddowney@gmail.com"]
11
+ s.homepage = "http://www.github.com/mattddowney/rubyxmacro"
12
+ s.summary = "Automate the mouse and keyboard in X"
13
+ s.description = "A ruby C extension to automate the mouse and keyboard in X Windows"
14
+
15
+ #s.rubyforge_project = "rubyxmacro"
16
+
17
+ s.files = `git ls-files`.split("\n") #<< "lib/rubyxmacro/rubyxmacro.so"
18
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
19
+ # s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
20
+ s.require_paths = ["lib", "ext/rubyxmacro"]
21
+ s.extensions = ["ext/rubyxmacro/extconf.rb"]
22
+ #s.executables = ["rubyxmacro"]
23
+ end
data/test/test.rb ADDED
@@ -0,0 +1,29 @@
1
+ require 'rubyxmacro'
2
+ require 'test/unit'
3
+
4
+ class TestRubyXMacro < Test::Unit::TestCase
5
+
6
+ def setup
7
+ @d = RubyXMacro::Display.new
8
+ end
9
+
10
+ def test_display
11
+ assert_instance_of(RubyXMacro::Display, @d)
12
+ end
13
+
14
+ def test_mouse_1
15
+ assert_nil(@d.moveMouse(100,200))
16
+ assert_nil(@d.click)
17
+ sleep 0.1
18
+ end
19
+
20
+ def test_special
21
+ assert_nil(@d.sendKeys '~!@#$%^&*()_+{}|:"<>?{ENTER}')
22
+ assert_nil(@d.sendKeys "`1234567890-=[]\;',./{ENTER}")
23
+ assert_nil(@d.sendKeys "This text should be highlighted")
24
+ 3.times do
25
+ assert_nil(@d.click)
26
+ end
27
+ end
28
+
29
+ end
metadata ADDED
@@ -0,0 +1,60 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: rubyxmacro
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.7
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Matthew Downey
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2012-03-20 00:00:00.000000000Z
13
+ dependencies: []
14
+ description: A ruby C extension to automate the mouse and keyboard in X Windows
15
+ email:
16
+ - mattddowney@gmail.com
17
+ executables: []
18
+ extensions:
19
+ - ext/rubyxmacro/extconf.rb
20
+ extra_rdoc_files: []
21
+ files:
22
+ - .gitignore
23
+ - Gemfile
24
+ - README.markdown
25
+ - Rakefile
26
+ - ext/rubyxmacro/controlx.h
27
+ - ext/rubyxmacro/extconf.rb
28
+ - ext/rubyxmacro/opendisplay.h
29
+ - ext/rubyxmacro/rubyxmacro.c
30
+ - lib/keycodes.rb
31
+ - lib/rubyxmacro.rb
32
+ - lib/rubyxmacro/version.rb
33
+ - rubyxmacro.gemspec
34
+ - test/test.rb
35
+ homepage: http://www.github.com/mattddowney/rubyxmacro
36
+ licenses: []
37
+ post_install_message:
38
+ rdoc_options: []
39
+ require_paths:
40
+ - lib
41
+ - ext/rubyxmacro
42
+ required_ruby_version: !ruby/object:Gem::Requirement
43
+ none: false
44
+ requirements:
45
+ - - ! '>='
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ required_rubygems_version: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
54
+ requirements: []
55
+ rubyforge_project:
56
+ rubygems_version: 1.8.6
57
+ signing_key:
58
+ specification_version: 3
59
+ summary: Automate the mouse and keyboard in X
60
+ test_files: []