Make Watir Support Jquery event

I have been in use watir(1.8.0) and ruby(1.8.7) for Regression test recently. I've got a problem yesterday. Look the demonstration page below:

<html>
	<head>
	<script src="http://code.jquery.com/jquery.min.js" type="text/javascript"></script>
	</head>
	<body>
		<select id ="s1">
			<option value="1">123</option>
			<option value="2">456</option>
			<option value="3">789</option>
		</select>
		<script>
			
			$('#s1').change(function(){
				alert('fired');
			});

			
		</script>
	</body>
</html>

when I use the code below to hope fire the change event of select element,but it can't work.

require "watir"
@browser = Watir::Browser.new
@browser.goto('a.html')
@browser.select_list(:id, 's1').set('456')

I deep in to the source code of watir(1.8.0),and found the code that:

def select_item_in_select_list(attribute, value) #:nodoc:
      assert_exists
      highlight(:set)
      found = false

      value = value.to_s unless [Regexp, String].any? { |e| value.kind_of? e }

      @container.log "Setting box #{@o.name} to #{attribute.inspect} => #{value.inspect}"
      @o.each do |option| # items in the list
        if value.matches(option.invoke(attribute.to_s))
          if option.selected
            found = true
            break
          else
            option.selected = true
            @o.fireEvent("onChange")
            @container.wait
            found = true
            break
          end
        end
      end

      unless found
        raise NoValueFoundException, "No option with #{attribute.inspect} of #{value.inspect} in this select element"
      end
      highlight(:clear)
    end

As the code show,Watir calling API of win32ole object,and raise the native event  "onChange".but this couldn't fire "change" event which jquery support. It's so tricky! 

After a research in google.i got this answer from StackOverFlow.

@browser = Watir::Browser.new
 @browser.goto("http://someurl")
 @browser.select_list(:id, element_id).select(item_to_select)
 @browser.ie.Document.parentWindow.execScript('$("##{element_id}").change();')

it's really cool method and seems resolved my problem(Let's say WATIR SUCKS loudly ). I couldn't use this directly because this is just a demonstration.In production environment,there are a lot of same invoke.To avoid duplication code,i have to extend watir to support our requirement.

......................
............ 
option.selected = true
@o.fireEvent("onChange")
script = %Q{$("##{self.id}").change();}
@o.Document.parentWindow.execScript(script)
@container.wait
found = true
break
.............
................

It works well now!

Posted by Leo 2011年9月28日 02:18