Class: Melomel::Bridge
- Defined in:
- lib/melomel/bridge.rb,
lib/melomel/bridge/ui.rb,
lib/melomel/bridge/messaging.rb
Instance Attribute Summary collapse
-
#host ⇒ Object
Returns the value of attribute host.
-
#port ⇒ Object
Returns the value of attribute port.
Instance Method Summary collapse
-
#busy! ⇒ Object
Checks if the Flash virtual machine is currently busy.
-
#click(component, properties = {}) ⇒ Object
Imitates a click on a component.
-
#connect ⇒ Object
Opens a socket connection to listen for incoming bridge connections.
-
#create_object(class_name) ⇒ Object
Creates an object in the Flash virtual machine and returns the reference to it.
-
#create_object!(class_name) ⇒ Object
Same as ‘create_object` except that an error is thrown if the class is not found.
-
#disconnect ⇒ Object
Closes any open connection to a Flash virtual machine.
-
#double_click(component, properties = {}) ⇒ Object
Imitates a double click on a component.
-
#find(class_name, root = {}, properties = {}) ⇒ Object
Finds the first display object matching a class and hash of properties.
- #find!(class_name, root = {}, properties = {}) ⇒ Object
-
#find_all(class_name, root = {}, properties = {}) ⇒ Object
Finds a list of display objects matching a class and hash of properties.
- #find_all!(class_name, root = {}, properties = {}) ⇒ Object
-
#find_labeled(class_name, label_text, root = {}, properties = {}) ⇒ Object
Finds a component based on the label of a nearby component.
- #find_labeled!(class_name, label_text, root = {}, properties = {}) ⇒ Object
-
#format_message_value(xml, value) ⇒ Object
Formats a Ruby value into an XML message.
-
#get_class(class_name) ⇒ Object
Retrieves a reference to a class in the Flash virtual machine.
-
#get_class!(class_name) ⇒ Object
Same as ‘get_class` except that an error is thrown if the class is not found.
-
#get_property(proxy_id, property) ⇒ Object
Retrieves a property of an object in the Flash virtual machine.
-
#get_property!(proxy_id, property) ⇒ Object
Same as ‘get_property` except that an error is thrown if the property does not exist.
-
#initialize(host = '127.0.0.1', port = 10101) ⇒ Bridge
constructor
A new instance of Bridge.
-
#invoke_function(function_name, *args) ⇒ Object
Invokes a package level function in the Flash virtual machine.
-
#invoke_function!(function_name, *args) ⇒ Object
Same as ‘invoke_function` except that an error is thrown if the method does not exist.
-
#invoke_method(proxy_id, method_name, *args) ⇒ Object
Invokes a method on an object in the Flash virtual machine.
-
#invoke_method!(proxy_id, method_name, *args) ⇒ Object
Same as ‘invoke_method` except that an error is thrown if the method does not exist.
-
#items_to_labels!(component, data) ⇒ Object
Generates a list of labels created by a data control or column based on a data set.
-
#key_down(component, char, properties = {}) ⇒ Object
Imitates a key down on a component.
-
#key_press(component, char, properties = {}) ⇒ Object
Imitates a key press on a component.
-
#key_up(component, char, properties = {}) ⇒ Object
Imitates a key up on a component.
-
#parse_message_value(xml) ⇒ Object
Parses a return message and converts it into an appropriate type.
-
#receive ⇒ Object
Receives a message from the Flash bridge.
-
#send(message) ⇒ Object
Sends a message over to the Flash bridge.
-
#set_property(proxy_id, property, value) ⇒ Object
Sets a property on an object in the Flash virtual machine.
-
#set_property!(proxy_id, property, value) ⇒ Object
Same as ‘set_property` except that an error is thrown if the property does not exist.
-
#wait ⇒ Object
Blocks until Melomel.busy in the Flash virtual machine is false.
Constructor Details
#initialize(host = '127.0.0.1', port = 10101) ⇒ Bridge
Returns a new instance of Bridge.
11 12 13 14 15 |
# File 'lib/melomel/bridge.rb', line 11 def initialize(host='127.0.0.1', port=10101) self.host = host self.port = port server, @socket = nil, nil end |
Instance Attribute Details
#host ⇒ Object
Returns the value of attribute host.
9 10 11 |
# File 'lib/melomel/bridge.rb', line 9 def host @host end |
#port ⇒ Object
Returns the value of attribute port.
9 10 11 |
# File 'lib/melomel/bridge.rb', line 9 def port @port end |
Instance Method Details
#busy! ⇒ Object
Checks if the Flash virtual machine is currently busy. See Melomel#busy in the Melomel asdocs for more information.
Returns true if the Flash virtual machine is busy. Otherwise returns false.
19 20 21 |
# File 'lib/melomel/bridge/ui.rb', line 19 def busy! get_class!('Melomel').busy! end |
#click(component, properties = {}) ⇒ Object
Imitates a click on a component
118 119 120 |
# File 'lib/melomel/bridge/ui.rb', line 118 def click(component, properties={}) get_class('melomel.core.UI').click(component, properties) end |
#connect ⇒ Object
Opens a socket connection to listen for incoming bridge connections. This method automatically handles requests for the policy file.
19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
# File 'lib/melomel/bridge.rb', line 19 def connect() disconnect() # Listen for connections server = TCPServer.open(host, port) # Retrieve socket and check for initial handshake while(@socket.nil?) do socket = server.accept() data = socket.gets("\x00").chomp("\x00") # Send policy file if requested. if(data == '<policy-file-request/>') send_policy_file(socket) # Otherwise open connection and continue elsif(data == '<connect/>') @socket = socket end end server.close(); end |
#create_object(class_name) ⇒ Object
Creates an object in the Flash virtual machine and returns the reference to it.
class_name - The name of the class to instantiate.
Returns an instance of the class if the class is found. Otherwise, nil.
18 19 20 |
# File 'lib/melomel/bridge/messaging.rb', line 18 def create_object(class_name) send_create_object(class_name, false) end |
#create_object!(class_name) ⇒ Object
Same as ‘create_object` except that an error is thrown if the class is not found.
24 25 26 |
# File 'lib/melomel/bridge/messaging.rb', line 24 def create_object!(class_name) send_create_object(class_name, true) end |
#disconnect ⇒ Object
Closes any open connection to a Flash virtual machine.
43 44 45 46 47 48 49 50 |
# File 'lib/melomel/bridge.rb', line 43 def disconnect() begin @socket.close() rescue end @socket = nil end |
#double_click(component, properties = {}) ⇒ Object
Imitates a double click on a component
123 124 125 |
# File 'lib/melomel/bridge/ui.rb', line 123 def double_click(component, properties={}) get_class('melomel.core.UI').doubleClick(component, properties) end |
#find(class_name, root = {}, properties = {}) ⇒ Object
Finds the first display object matching a class and hash of properties.
class_name - The type of object to search for. root - The object to start searching from. (Defaults to the stage). properties - A list of properties to match on the object.
Example:
bridge.find('mx.controls.Button', :label => 'Click me')
# => <Melomel::ObjectProxy>
Returns the first display object contained by root that matches the properties and class specified.
66 67 68 69 70 71 72 73 74 75 |
# File 'lib/melomel/bridge/ui.rb', line 66 def find(class_name, root={}, properties={}) # Merge hashes if no root is specified if root.is_a?(Hash) properties.merge!(root) root = nil end # Retrieve object get_class('melomel.core.UI').find(class_name, root, properties) end |
#find!(class_name, root = {}, properties = {}) ⇒ Object
77 78 79 80 81 |
# File 'lib/melomel/bridge/ui.rb', line 77 def find!(class_name, root={}, properties={}) object = find(class_name, root, properties) raise MelomelError.new("No object found") if object.nil? return object end |
#find_all(class_name, root = {}, properties = {}) ⇒ Object
Finds a list of display objects matching a class and hash of properties.
class_name - The type of objects to search for. root - The object to start searching from. (Defaults to the stage). properties - A list of properties to match on each object.
Example:
bridge.find_all('mx.controls.Button', :label => 'Click me')
# => [<Melomel::ObjectProxy>, <Melomel::ObjectProxy>]
Returns a list of display objects contained by root that match the properties and class specified.
36 37 38 39 40 41 42 43 44 45 |
# File 'lib/melomel/bridge/ui.rb', line 36 def find_all(class_name, root={}, properties={}) # Merge hashes if no root is specified if root.is_a?(Hash) properties.merge!(root) root = nil end # Retrieve object get_class('melomel.core.UI').findAll(class_name, root, properties) end |
#find_all!(class_name, root = {}, properties = {}) ⇒ Object
47 48 49 50 51 |
# File 'lib/melomel/bridge/ui.rb', line 47 def find_all!(class_name, root={}, properties={}) objects = find_all(class_name, root, properties) raise MelomelError.new("No objects found") if objects.empty? return objects end |
#find_labeled(class_name, label_text, root = {}, properties = {}) ⇒ Object
Finds a component based on the label of a nearby component. This works by first finding a Halo or Spark label component and then recursively searching the label’s parent’s children for a component of a given class.
class_name - The type of object to search for. label_text - The label text to search for. root - The object to start searching from. (Defaults to the stage). properties - A list of properties to match on the object.
Example:
bridge.find_labeled('mx.controls.TextInput', 'First Name')
# => <Melomel::ObjectProxy>
Returns the first display object which is inside the parent of a given label.
99 100 101 102 103 104 105 106 107 108 |
# File 'lib/melomel/bridge/ui.rb', line 99 def find_labeled(class_name, label_text, root={}, properties={}) # Merge hashes if no root is specified if root.is_a?(Hash) properties.merge!(root) root = nil end # Retrieve object get_class('melomel.core.UI').findLabeled(class_name, label_text, root, properties) end |
#find_labeled!(class_name, label_text, root = {}, properties = {}) ⇒ Object
110 111 112 113 114 |
# File 'lib/melomel/bridge/ui.rb', line 110 def find_labeled!(class_name, label_text, root={}, properties={}) object = find_labeled(class_name, label_text, root, properties) raise MelomelError.new("No object found") if object.nil? return object end |
#format_message_value(xml, value) ⇒ Object
Formats a Ruby value into an XML message
117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 |
# File 'lib/melomel/bridge/messaging.rb', line 117 def (xml, value) # Automatically convert simple objects to proxies. value = value.to_object_proxy(self) unless value.nil? if value.nil? xml['dataType'] = 'null' elsif value.class == Fixnum || value.class == Bignum xml['value'] = value.to_s xml['dataType'] = 'int' elsif value.class == Float xml['value'] = value.to_s xml['dataType'] = 'float' elsif value == true || value == false xml['value'] = value.to_s xml['dataType'] = 'boolean' elsif value.class == Melomel::ObjectProxy xml['value'] = value.proxy_id.to_s xml['dataType'] = 'object' elsif value.class == String xml['value'] = value xml['dataType'] = 'string' end end |
#get_class(class_name) ⇒ Object
Retrieves a reference to a class in the Flash virtual machine.
class_name - The name of the class to retrieve a reference to.
Returns a reference to the class if it exists. Otherwise, nil.
33 34 35 |
# File 'lib/melomel/bridge/messaging.rb', line 33 def get_class(class_name) send_get_class(class_name, false) end |
#get_class!(class_name) ⇒ Object
Same as ‘get_class` except that an error is thrown if the class is not found.
39 40 41 |
# File 'lib/melomel/bridge/messaging.rb', line 39 def get_class!(class_name) send_get_class(class_name, true) end |
#get_property(proxy_id, property) ⇒ Object
Retrieves a property of an object in the Flash virtual machine
proxy_id - The identifier for the object proxy. property - The name of the property to access.
Returns the value of the property if it exists. Otherwise, nil.
49 50 51 |
# File 'lib/melomel/bridge/messaging.rb', line 49 def get_property(proxy_id, property) send_get_property(proxy_id, property, false) end |
#get_property!(proxy_id, property) ⇒ Object
Same as ‘get_property` except that an error is thrown if the property does not exist.
55 56 57 |
# File 'lib/melomel/bridge/messaging.rb', line 55 def get_property!(proxy_id, property) send_get_property(proxy_id, property, true) end |
#invoke_function(function_name, *args) ⇒ Object
Invokes a package level function in the Flash virtual machine
function_name - The fully qualified name of the function to invoke. *args - List of arguments passed to the function.
Returns the return value of the Flash function.
99 100 101 |
# File 'lib/melomel/bridge/messaging.rb', line 99 def invoke_function(function_name, *args) send_invoke_function(function_name, args, false) end |
#invoke_function!(function_name, *args) ⇒ Object
Same as ‘invoke_function` except that an error is thrown if the method does not exist.
105 106 107 |
# File 'lib/melomel/bridge/messaging.rb', line 105 def invoke_function!(function_name, *args) send_invoke_function(function_name, args, true) end |
#invoke_method(proxy_id, method_name, *args) ⇒ Object
Invokes a method on an object in the Flash virtual machine
proxy_id - The identifier of the object proxy. method_name - The name of the method to invoke. *args - List of arguments passed to the method.
Returns the value returned from the Flash method.
83 84 85 |
# File 'lib/melomel/bridge/messaging.rb', line 83 def invoke_method(proxy_id, method_name, *args) send_invoke_method(proxy_id, method_name, args, false) end |
#invoke_method!(proxy_id, method_name, *args) ⇒ Object
Same as ‘invoke_method` except that an error is thrown if the method does not exist.
89 90 91 |
# File 'lib/melomel/bridge/messaging.rb', line 89 def invoke_method!(proxy_id, method_name, *args) send_invoke_method(proxy_id, method_name, args, true) end |
#items_to_labels!(component, data) ⇒ Object
Generates a list of labels created by a data control or column based on a data set.
component - The control or column which has an itemToLabel() method. data - The data set to generate labels from.
Returns a Ruby array of labels.
151 152 153 |
# File 'lib/melomel/bridge/ui.rb', line 151 def items_to_labels!(component, data) get_class('melomel.core.UI').itemsToLabels!(component, data) end |
#key_down(component, char, properties = {}) ⇒ Object
Imitates a key down on a component
129 130 131 |
# File 'lib/melomel/bridge/ui.rb', line 129 def key_down(component, char, properties={}) get_class('melomel.core.UI').keyDown(component, char, properties) end |
#key_press(component, char, properties = {}) ⇒ Object
Imitates a key press on a component
139 140 141 |
# File 'lib/melomel/bridge/ui.rb', line 139 def key_press(component, char, properties={}) get_class('melomel.core.UI').keyPress(component, char, properties) end |
#key_up(component, char, properties = {}) ⇒ Object
Imitates a key up on a component
134 135 136 |
# File 'lib/melomel/bridge/ui.rb', line 134 def key_up(component, char, properties={}) get_class('melomel.core.UI').keyUp(component, char, properties) end |
#parse_message_value(xml) ⇒ Object
Parses a return message and converts it into an appropriate type
142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 |
# File 'lib/melomel/bridge/messaging.rb', line 142 def (xml) name = xml.name() # If we receive an error back then raise it in the Ruby VM. if name == 'error' stack_trace_xml = xml.at_xpath('stack-trace') object = Melomel::ObjectProxy.new(self, xml['proxyId'].to_i) error_id = xml['errorId'].to_i = xml['message'] name = xml['name'] stack_trace = stack_trace_xml ? stack_trace_xml.to_str : nil $stderr.puts(stack_trace) raise Melomel::Error.new(object, error_id, , name, stack_trace), # Otherwise we have a return value so we should parse it. else value = xml['value'] data_type = xml['dataType'] if data_type == 'null' return nil elsif data_type == 'int' return value.to_i elsif data_type == 'float' return value.to_f elsif data_type == 'boolean' return value == 'true' elsif data_type == 'object' return Melomel::ObjectProxy.new(self, value.to_i) elsif data_type == 'string' || data_type.nil? return value else raise UnrecognizedTypeError, "Unknown type: #{data_type}" end end end |
#receive ⇒ Object
Receives a message from the Flash bridge. This is a blocking call.
58 59 60 |
# File 'lib/melomel/bridge.rb', line 58 def receive() @socket.gets("\x00").chomp("\x00") end |
#send(message) ⇒ Object
Sends a message over to the Flash bridge.
53 54 55 |
# File 'lib/melomel/bridge.rb', line 53 def send() @socket.puts("#{}\x00") end |
#set_property(proxy_id, property, value) ⇒ Object
Sets a property on an object in the Flash virtual machine
proxy_id - The identifier of the object proxy. property - The name of the property to mutate. value - The value to set the property to.
Returns the value of the property after being set.
66 67 68 |
# File 'lib/melomel/bridge/messaging.rb', line 66 def set_property(proxy_id, property, value) send_set_property(proxy_id, property, value, false) end |
#set_property!(proxy_id, property, value) ⇒ Object
Same as ‘set_property` except that an error is thrown if the property does not exist.
72 73 74 |
# File 'lib/melomel/bridge/messaging.rb', line 72 def set_property!(proxy_id, property, value) send_set_property(proxy_id, property, value, true) end |
#wait ⇒ Object
Blocks until Melomel.busy in the Flash virtual machine is false.
Returns nothing.
7 8 9 10 11 12 |
# File 'lib/melomel/bridge/ui.rb', line 7 def wait() loop do break unless busy! sleep 0.1 end end |