robobot 0.0.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/.gitignore +17 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +45 -0
- data/Rakefile +1 -0
- data/examples/build.sh +6 -0
- data/examples/test.rb +61 -0
- data/lib/robobot.rb +6 -0
- data/lib/robobot/keyboard.rb +52 -0
- data/lib/robobot/mouse.rb +71 -0
- data/lib/robobot/notification.rb +57 -0
- data/lib/robobot/version.rb +3 -0
- data/lib/robobot/window.rb +103 -0
- data/lib/robobot/workspaces.rb +38 -0
- data/robobot.gemspec +20 -0
- metadata +61 -0
data/.gitignore
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2014 Roman Pramberger
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following 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 OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
# Robobot
|
2
|
+
|
3
|
+
TODO: Write a gem description
|
4
|
+
|
5
|
+
**This gem works only on linux!**
|
6
|
+
|
7
|
+
## Installation
|
8
|
+
|
9
|
+
Add this line to your application's Gemfile:
|
10
|
+
|
11
|
+
gem 'robobot'
|
12
|
+
|
13
|
+
And then execute:
|
14
|
+
|
15
|
+
$ bundle
|
16
|
+
|
17
|
+
Or install it yourself as:
|
18
|
+
|
19
|
+
$ gem install robobot
|
20
|
+
|
21
|
+
## Depencies
|
22
|
+
|
23
|
+
You need to have xdotool installed
|
24
|
+
|
25
|
+
$ sudo apt-get install xdotool
|
26
|
+
|
27
|
+
If you like notifications you need libnotify as well:
|
28
|
+
|
29
|
+
$ sudo apt-get install libnotify-bin
|
30
|
+
|
31
|
+
And if you want to use the beep functions you need to:
|
32
|
+
|
33
|
+
$ modprobe pcspkr
|
34
|
+
|
35
|
+
## Usage
|
36
|
+
|
37
|
+
TODO: Write usage instructions here
|
38
|
+
|
39
|
+
## Contributing
|
40
|
+
|
41
|
+
1. Fork it
|
42
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
43
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
44
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
45
|
+
5. Create new Pull Request
|
data/Rakefile
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
require "bundler/gem_tasks"
|
data/examples/build.sh
ADDED
data/examples/test.rb
ADDED
@@ -0,0 +1,61 @@
|
|
1
|
+
require 'robobot'
|
2
|
+
require "robobot/window"
|
3
|
+
require "robobot/notification"
|
4
|
+
require "robobot/keyboard"
|
5
|
+
require "robobot/mouse"
|
6
|
+
require "robobot/workspaces"
|
7
|
+
|
8
|
+
Robobot.debug = true
|
9
|
+
|
10
|
+
Robobot::Notification.show "Select a window", :timeout => 500
|
11
|
+
Robobot::Notification.beep :frequency => 150, :length => 100
|
12
|
+
|
13
|
+
window = Robobot::Window.new :click
|
14
|
+
puts "Window name:\t#{window.name}"
|
15
|
+
puts "Window geo :\t#{window.geometry}"
|
16
|
+
|
17
|
+
# set size may bugs if not hidden
|
18
|
+
window.hide
|
19
|
+
window.set_size 1920, 500
|
20
|
+
window.show
|
21
|
+
window.set_position 0, 0
|
22
|
+
window.raise
|
23
|
+
window.focus
|
24
|
+
# window.kill
|
25
|
+
|
26
|
+
# Test keyboard
|
27
|
+
keyboard = Robobot::Keyboard.new window
|
28
|
+
10.times do
|
29
|
+
keyboard.key "space"
|
30
|
+
end
|
31
|
+
|
32
|
+
# Test mouse
|
33
|
+
mouse = Robobot::Mouse.new window
|
34
|
+
mouse.click
|
35
|
+
sleep 1
|
36
|
+
mouse.move 100, 100
|
37
|
+
mouse.click 3
|
38
|
+
sleep 0.5
|
39
|
+
mouse.move 80, 80
|
40
|
+
mouse.down
|
41
|
+
sleep 0.2
|
42
|
+
mouse.up
|
43
|
+
mouse.click
|
44
|
+
|
45
|
+
# Test workspaces
|
46
|
+
puts "Workspaces: #{Robobot::Workspaces.count}"
|
47
|
+
Robobot::Workspaces.count 4
|
48
|
+
puts "Workspaces: #{Robobot::Workspaces.count}"
|
49
|
+
|
50
|
+
puts "Current: #{Robobot::Workspaces.current}"
|
51
|
+
Robobot::Workspaces.current 2
|
52
|
+
sleep 0.5
|
53
|
+
|
54
|
+
puts "Window is on: #{Robobot::Workspaces.get_workspace(window)}"
|
55
|
+
Robobot::Workspaces.move window, 2
|
56
|
+
puts "Window is now on: #{Robobot::Workspaces.get_workspace(window)}"
|
57
|
+
|
58
|
+
window.focus
|
59
|
+
sleep 1
|
60
|
+
Robobot::Workspaces.move window, 0
|
61
|
+
window.focus
|
data/lib/robobot.rb
ADDED
@@ -0,0 +1,52 @@
|
|
1
|
+
# This class controls the keyboard
|
2
|
+
|
3
|
+
# Author:: Roman Pramberger (mailto:roman@pramberger.ch)
|
4
|
+
# License:: MIT
|
5
|
+
|
6
|
+
module Robobot
|
7
|
+
class Keyboard
|
8
|
+
|
9
|
+
# Initialize keyboard
|
10
|
+
def initialize window = nil
|
11
|
+
@window = window
|
12
|
+
end
|
13
|
+
|
14
|
+
# Press key
|
15
|
+
#
|
16
|
+
# You may use any Syntax like:
|
17
|
+
# space, Control+a, A, up, alt+r,
|
18
|
+
# BackSpace, Control, Control_R, shift, super, ...
|
19
|
+
#
|
20
|
+
def key key
|
21
|
+
cmd "key #{key}"
|
22
|
+
end
|
23
|
+
|
24
|
+
# Key down only
|
25
|
+
def keydown key
|
26
|
+
cmd "keydown #{key}"
|
27
|
+
end
|
28
|
+
|
29
|
+
# Key up
|
30
|
+
def keyup key
|
31
|
+
cmd "keyup #{key}"
|
32
|
+
end
|
33
|
+
|
34
|
+
# type text
|
35
|
+
def type text
|
36
|
+
cmd "type \"#{text}\""
|
37
|
+
end
|
38
|
+
|
39
|
+
private
|
40
|
+
|
41
|
+
# Command generator (add window if set)
|
42
|
+
def cmd command
|
43
|
+
command = command.split(" ",2)
|
44
|
+
cmd = "xdotool #{command[0]}"
|
45
|
+
cmd += " --window #{@window.id}" if @window
|
46
|
+
cmd += " #{command[1]}"
|
47
|
+
puts "#{cmd}"
|
48
|
+
`#{cmd}`
|
49
|
+
end
|
50
|
+
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,71 @@
|
|
1
|
+
# This class controls the mouse
|
2
|
+
|
3
|
+
# Author:: Roman Pramberger (mailto:roman@pramberger.ch)
|
4
|
+
# License:: MIT
|
5
|
+
|
6
|
+
module Robobot
|
7
|
+
class Mouse
|
8
|
+
|
9
|
+
# Initialize mouse
|
10
|
+
def initialize window = nil
|
11
|
+
@window = window
|
12
|
+
end
|
13
|
+
|
14
|
+
# Move mouse to x,y
|
15
|
+
def move x,y
|
16
|
+
cmd "mousemove --sync #{x} #{y}"
|
17
|
+
end
|
18
|
+
|
19
|
+
# Move relative to current position
|
20
|
+
def move_relative x,y
|
21
|
+
cmd "mousemove_relative --sync #{x} #{y}"
|
22
|
+
end
|
23
|
+
|
24
|
+
# Click
|
25
|
+
#
|
26
|
+
# Buttons:
|
27
|
+
# 1 = Left
|
28
|
+
# 2 = Middle
|
29
|
+
# 3 = Right
|
30
|
+
# 4 = Wheel up
|
31
|
+
# 5 = Wheel down
|
32
|
+
#
|
33
|
+
def click button = "1"
|
34
|
+
cmd "click #{button}"
|
35
|
+
end
|
36
|
+
|
37
|
+
# Mouse down (see Click)
|
38
|
+
def down button = "1"
|
39
|
+
cmd = "mousedown #{button}"
|
40
|
+
end
|
41
|
+
|
42
|
+
# Mouse up (see Click)
|
43
|
+
def up button = "1"
|
44
|
+
cmd = "mousedown #{button}"
|
45
|
+
end
|
46
|
+
|
47
|
+
# Get location
|
48
|
+
def location
|
49
|
+
location = `xdotool getmouselocation --shell`.split("\n")
|
50
|
+
return {
|
51
|
+
:x => location[0].split("=")[1],
|
52
|
+
:y => location[1].split("=")[1],
|
53
|
+
:screen => location[2].split("=")[1],
|
54
|
+
:window => location[3].split("=")[1]
|
55
|
+
}
|
56
|
+
end
|
57
|
+
|
58
|
+
private
|
59
|
+
|
60
|
+
# Command generator (add window if set)
|
61
|
+
def cmd command
|
62
|
+
command = command.split(" ",2)
|
63
|
+
cmd = "xdotool #{command[0]}"
|
64
|
+
cmd += " --window #{@window.id}" if @window
|
65
|
+
cmd += " #{command[1]}"
|
66
|
+
puts "#{cmd}"
|
67
|
+
`#{cmd}`
|
68
|
+
end
|
69
|
+
|
70
|
+
end
|
71
|
+
end
|
@@ -0,0 +1,57 @@
|
|
1
|
+
# Notifications help to show results and information to the user
|
2
|
+
# It uses: libnotify
|
3
|
+
|
4
|
+
# Author:: Roman Pramberger (mailto:roman@pramberger.ch)
|
5
|
+
# License:: MIT
|
6
|
+
|
7
|
+
module Robobot
|
8
|
+
module Notification
|
9
|
+
|
10
|
+
# show a notification
|
11
|
+
# you must define a title
|
12
|
+
#
|
13
|
+
# Parameter
|
14
|
+
# title: required title
|
15
|
+
# options: see below
|
16
|
+
#
|
17
|
+
# Options
|
18
|
+
# :msg optional message
|
19
|
+
# :icon icon path
|
20
|
+
# :urgency low, normal or critical
|
21
|
+
# :time time in milliseconds
|
22
|
+
#
|
23
|
+
def self.show title, options
|
24
|
+
cmd = "notify-send \"#{title}\""
|
25
|
+
cmd += " \"#{options[:msg]}\"" if !options[:msg].nil?
|
26
|
+
cmd += " -i #{options[:icon]}" if !options[:icon].nil?
|
27
|
+
cmd += " -u #{options[:urgency]}" if !options[:urgency].nil?
|
28
|
+
cmd += " -t #{options[:timeout]}" if !options[:timeout].nil?
|
29
|
+
`#{cmd}`
|
30
|
+
puts cmd if Robobot.debug
|
31
|
+
end
|
32
|
+
|
33
|
+
# beeping :)
|
34
|
+
# in order to make it work you have to:
|
35
|
+
# modprobe pcspkr
|
36
|
+
#
|
37
|
+
# Parameter
|
38
|
+
# options: see below
|
39
|
+
#
|
40
|
+
# Options
|
41
|
+
# :frequency
|
42
|
+
# :length
|
43
|
+
# :repeat
|
44
|
+
# :delay
|
45
|
+
#
|
46
|
+
def self.beep options
|
47
|
+
cmd = "beep"
|
48
|
+
cmd += " -f #{options[:frequency]}" if !options[:frequency].nil?
|
49
|
+
cmd += " -l #{options[:length]}" if !options[:length].nil?
|
50
|
+
cmd += " -r #{options[:repeat]}" if !options[:repeat].nil?
|
51
|
+
cmd += " -D #{options[:delay]}" if !options[:delay].nil?
|
52
|
+
`beep`
|
53
|
+
puts cmd if Robobot.debug
|
54
|
+
end
|
55
|
+
|
56
|
+
end
|
57
|
+
end
|
@@ -0,0 +1,103 @@
|
|
1
|
+
# This class handles the window on which the commands are used
|
2
|
+
# Its fully optional, if now window is defined it will use
|
3
|
+
# the current active one.
|
4
|
+
|
5
|
+
# Author:: Roman Pramberger (mailto:roman@pramberger.ch)
|
6
|
+
# License:: MIT
|
7
|
+
|
8
|
+
module Robobot
|
9
|
+
class Window
|
10
|
+
require 'RMagick'
|
11
|
+
@window
|
12
|
+
@img
|
13
|
+
|
14
|
+
# Gets a window by process name (string) or process id (integer)
|
15
|
+
# you may also use :current to use the current active one
|
16
|
+
# or use :click to request clicking the window
|
17
|
+
def initialize name_or_pid
|
18
|
+
if name_or_pid == :current
|
19
|
+
@window = `xdotool getwindowfocus`.chomp
|
20
|
+
elsif name_or_pid == :click
|
21
|
+
@window = `xdotool selectwindow`.chomp
|
22
|
+
elsif name_or_pid.is_a? String
|
23
|
+
@window = `xdotool search #{name_or_pid} | head -1`.chomp
|
24
|
+
elsif name_or_pid.is_a? Integer
|
25
|
+
@window = `xdotool search --pid #{name_or_pid}`.chomp
|
26
|
+
else
|
27
|
+
raise 'Not a valid window value'
|
28
|
+
end
|
29
|
+
if Robobot.debug
|
30
|
+
puts "Window selected: #{@window}"
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
# Return window id
|
35
|
+
def id
|
36
|
+
@window
|
37
|
+
end
|
38
|
+
|
39
|
+
# Return a windows name
|
40
|
+
def name
|
41
|
+
return `xdotool getwindowname #{@window}`.chomp
|
42
|
+
end
|
43
|
+
|
44
|
+
# Return window geometry
|
45
|
+
def geometry
|
46
|
+
geo = `xdotool getwindowgeometry #{@window}`.chomp.split("\n")
|
47
|
+
xy = geo[1].split(": ")[1].split(" ")[0].split(",")
|
48
|
+
screen = geo[1].split("(")[1].split(": ")[1].split(")")[0]
|
49
|
+
wh = geo[2].split(": ")[1].chomp.split("x")
|
50
|
+
out = {
|
51
|
+
:x => xy[0].to_i,
|
52
|
+
:y => xy[1].to_i,
|
53
|
+
:screen => screen.to_i,
|
54
|
+
:width => wh[0].to_i,
|
55
|
+
:height => wh[1].to_i
|
56
|
+
}
|
57
|
+
return out
|
58
|
+
end
|
59
|
+
|
60
|
+
# Set window size
|
61
|
+
def set_size width, height
|
62
|
+
`xdotool windowsize #{@window} #{width} #{height}`
|
63
|
+
puts "xdotool windowsize #{@window} #{width} #{height}" if Robobot.debug
|
64
|
+
end
|
65
|
+
|
66
|
+
# Set window position
|
67
|
+
def set_position x, y
|
68
|
+
`xdotool windowmove #{@window} #{x} #{y}`
|
69
|
+
puts "xdotool windowmove #{@window} #{x} #{y}" if Robobot.debug
|
70
|
+
end
|
71
|
+
|
72
|
+
# Hide window
|
73
|
+
def hide
|
74
|
+
`xdotool windowunmap #{@window}`
|
75
|
+
puts "xdotool windowunmap #{@window}" if Robobot.debug
|
76
|
+
end
|
77
|
+
|
78
|
+
# Show window
|
79
|
+
def show
|
80
|
+
`xdotool windowmap #{@window}`
|
81
|
+
puts "xdotool windowmap #{@window}" if Robobot.debug
|
82
|
+
end
|
83
|
+
|
84
|
+
# Raise window to the front
|
85
|
+
def raise
|
86
|
+
`xdotool windowraise #{@window}`
|
87
|
+
puts "xdotool windowraise #{@window}" if Robobot.debug
|
88
|
+
end
|
89
|
+
|
90
|
+
# Focus the window
|
91
|
+
def focus
|
92
|
+
# may work better than windowfocus, also switches workspaces
|
93
|
+
`xdotool windowactivate --sync #{@window}`
|
94
|
+
puts "xdotool windowactivate --sync #{@window}" if Robobot.debug
|
95
|
+
end
|
96
|
+
|
97
|
+
# Kill window
|
98
|
+
def kill
|
99
|
+
`xdotool windowkill #{@window}`
|
100
|
+
puts "xdotool windowkill #{@window}" if Robobot.debug
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
# This module helps controling workspaces
|
2
|
+
|
3
|
+
# Author:: Roman Pramberger (mailto:roman@pramberger.ch)
|
4
|
+
# License:: MIT
|
5
|
+
|
6
|
+
module Robobot
|
7
|
+
module Workspaces
|
8
|
+
|
9
|
+
# Get or Set current workspace count
|
10
|
+
def self.count num = nil
|
11
|
+
if num.nil?
|
12
|
+
return `xdotool get_num_desktops`
|
13
|
+
else
|
14
|
+
`xdotool set_num_desktops #{num}`
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
# Get or Set current workspace
|
19
|
+
def self.current workspace = nil
|
20
|
+
if workspace.nil?
|
21
|
+
return `xdotool get_desktop`
|
22
|
+
else
|
23
|
+
`xdotool set_desktop #{workspace}`
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
# Move window to workspace
|
28
|
+
def self.move window, workspace
|
29
|
+
`xdotool set_desktop_for_window #{window.id} #{workspace}`
|
30
|
+
end
|
31
|
+
|
32
|
+
# Get workspace of window
|
33
|
+
def self.get_workspace window
|
34
|
+
`xdotool get_desktop_for_window #{window.id}`
|
35
|
+
end
|
36
|
+
|
37
|
+
end
|
38
|
+
end
|
data/robobot.gemspec
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'robobot/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |gem|
|
7
|
+
gem.name = "robobot"
|
8
|
+
gem.version = Robobot::VERSION
|
9
|
+
gem.authors = ["Roman Pramberger"]
|
10
|
+
gem.email = ["roman@pramberger.ch"]
|
11
|
+
gem.description = %q{Automate tasks with mouse and keyboard inputs.}
|
12
|
+
gem.summary = %q{Automate tasks with mouse and keyboard inputs.}
|
13
|
+
gem.homepage = ""
|
14
|
+
gem.license = "MIT"
|
15
|
+
|
16
|
+
gem.files = `git ls-files`.split($/)
|
17
|
+
gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
|
18
|
+
gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
|
19
|
+
gem.require_paths = ["lib"]
|
20
|
+
end
|
metadata
ADDED
@@ -0,0 +1,61 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: robobot
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Roman Pramberger
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2014-05-25 00:00:00.000000000 Z
|
13
|
+
dependencies: []
|
14
|
+
description: Automate tasks with mouse and keyboard inputs.
|
15
|
+
email:
|
16
|
+
- roman@pramberger.ch
|
17
|
+
executables: []
|
18
|
+
extensions: []
|
19
|
+
extra_rdoc_files: []
|
20
|
+
files:
|
21
|
+
- .gitignore
|
22
|
+
- Gemfile
|
23
|
+
- LICENSE.txt
|
24
|
+
- README.md
|
25
|
+
- Rakefile
|
26
|
+
- examples/build.sh
|
27
|
+
- examples/test.rb
|
28
|
+
- lib/robobot.rb
|
29
|
+
- lib/robobot/keyboard.rb
|
30
|
+
- lib/robobot/mouse.rb
|
31
|
+
- lib/robobot/notification.rb
|
32
|
+
- lib/robobot/version.rb
|
33
|
+
- lib/robobot/window.rb
|
34
|
+
- lib/robobot/workspaces.rb
|
35
|
+
- robobot.gemspec
|
36
|
+
homepage: ''
|
37
|
+
licenses:
|
38
|
+
- MIT
|
39
|
+
post_install_message:
|
40
|
+
rdoc_options: []
|
41
|
+
require_paths:
|
42
|
+
- lib
|
43
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
44
|
+
none: false
|
45
|
+
requirements:
|
46
|
+
- - ! '>='
|
47
|
+
- !ruby/object:Gem::Version
|
48
|
+
version: '0'
|
49
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ! '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
requirements: []
|
56
|
+
rubyforge_project:
|
57
|
+
rubygems_version: 1.8.23
|
58
|
+
signing_key:
|
59
|
+
specification_version: 3
|
60
|
+
summary: Automate tasks with mouse and keyboard inputs.
|
61
|
+
test_files: []
|