capybara-ui 0.10.0 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/capybara/ui.rb +33 -0
- data/lib/capybara/ui/assertions.rb +21 -0
- data/lib/{capybara-ui → capybara/ui}/capybara.rb +0 -0
- data/lib/capybara/ui/checkpoint.rb +113 -0
- data/lib/capybara/ui/conversions.rb +33 -0
- data/lib/capybara/ui/cucumber.rb +5 -0
- data/lib/capybara/ui/dsl.rb +109 -0
- data/lib/capybara/ui/instance_conversions.rb +21 -0
- data/lib/{capybara-ui → capybara/ui}/matchers.rb +4 -4
- data/lib/capybara/ui/optional_dependencies.rb +7 -0
- data/lib/capybara/ui/rails.rb +5 -0
- data/lib/capybara/ui/rails/role.rb +11 -0
- data/lib/capybara/ui/role.rb +21 -0
- data/lib/capybara/ui/text_table.rb +109 -0
- data/lib/capybara/ui/text_table/cell_text.rb +9 -0
- data/lib/capybara/ui/text_table/mapping.rb +42 -0
- data/lib/capybara/ui/text_table/transformations.rb +15 -0
- data/lib/capybara/ui/text_table/void_mapping.rb +10 -0
- data/lib/capybara/ui/version.rb +5 -0
- data/lib/capybara/ui/widgets.rb +63 -0
- data/lib/capybara/ui/widgets/check_box.rb +28 -0
- data/lib/capybara/ui/widgets/cucumber_methods.rb +75 -0
- data/lib/capybara/ui/widgets/document.rb +21 -0
- data/lib/capybara/ui/widgets/dsl.rb +49 -0
- data/lib/capybara/ui/widgets/field.rb +24 -0
- data/lib/capybara/ui/widgets/field_group.rb +331 -0
- data/lib/capybara/ui/widgets/form.rb +28 -0
- data/lib/capybara/ui/widgets/list.rb +202 -0
- data/lib/capybara/ui/widgets/list_item.rb +24 -0
- data/lib/capybara/ui/widgets/parts/container.rb +48 -0
- data/lib/capybara/ui/widgets/parts/struct.rb +119 -0
- data/lib/capybara/ui/widgets/radio_button.rb +64 -0
- data/lib/capybara/ui/widgets/select.rb +59 -0
- data/lib/capybara/ui/widgets/string_value.rb +45 -0
- data/lib/capybara/ui/widgets/table.rb +78 -0
- data/lib/capybara/ui/widgets/text_field.rb +29 -0
- data/lib/capybara/ui/widgets/widget.rb +394 -0
- data/lib/capybara/ui/widgets/widget/node_filter.rb +50 -0
- data/lib/capybara/ui/widgets/widget_class.rb +13 -0
- data/lib/capybara/ui/widgets/widget_name.rb +58 -0
- metadata +47 -43
- data/lib/capybara-ui.rb +0 -31
- data/lib/capybara-ui/assertions.rb +0 -19
- data/lib/capybara-ui/checkpoint.rb +0 -111
- data/lib/capybara-ui/conversions.rb +0 -31
- data/lib/capybara-ui/cucumber.rb +0 -5
- data/lib/capybara-ui/dsl.rb +0 -107
- data/lib/capybara-ui/instance_conversions.rb +0 -19
- data/lib/capybara-ui/optional_dependencies.rb +0 -5
- data/lib/capybara-ui/rails.rb +0 -5
- data/lib/capybara-ui/rails/role.rb +0 -9
- data/lib/capybara-ui/role.rb +0 -19
- data/lib/capybara-ui/text_table.rb +0 -107
- data/lib/capybara-ui/text_table/cell_text.rb +0 -7
- data/lib/capybara-ui/text_table/mapping.rb +0 -40
- data/lib/capybara-ui/text_table/transformations.rb +0 -13
- data/lib/capybara-ui/text_table/void_mapping.rb +0 -8
- data/lib/capybara-ui/version.rb +0 -3
- data/lib/capybara-ui/widgets.rb +0 -61
- data/lib/capybara-ui/widgets/check_box.rb +0 -26
- data/lib/capybara-ui/widgets/cucumber_methods.rb +0 -73
- data/lib/capybara-ui/widgets/document.rb +0 -19
- data/lib/capybara-ui/widgets/dsl.rb +0 -47
- data/lib/capybara-ui/widgets/field.rb +0 -22
- data/lib/capybara-ui/widgets/field_group.rb +0 -329
- data/lib/capybara-ui/widgets/form.rb +0 -26
- data/lib/capybara-ui/widgets/list.rb +0 -200
- data/lib/capybara-ui/widgets/list_item.rb +0 -22
- data/lib/capybara-ui/widgets/parts/container.rb +0 -46
- data/lib/capybara-ui/widgets/parts/struct.rb +0 -117
- data/lib/capybara-ui/widgets/radio_button.rb +0 -62
- data/lib/capybara-ui/widgets/select.rb +0 -57
- data/lib/capybara-ui/widgets/string_value.rb +0 -43
- data/lib/capybara-ui/widgets/table.rb +0 -76
- data/lib/capybara-ui/widgets/text_field.rb +0 -27
- data/lib/capybara-ui/widgets/widget.rb +0 -392
- data/lib/capybara-ui/widgets/widget/node_filter.rb +0 -48
- data/lib/capybara-ui/widgets/widget_class.rb +0 -11
- data/lib/capybara-ui/widgets/widget_name.rb +0 -56
@@ -1,57 +0,0 @@
|
|
1
|
-
module CapybaraUI
|
2
|
-
# A select.
|
3
|
-
class Select < Field
|
4
|
-
def selected
|
5
|
-
root.all(:xpath, ".//option", visible: true).select(&:selected?).first
|
6
|
-
end
|
7
|
-
|
8
|
-
module Selectable
|
9
|
-
def select
|
10
|
-
root.select_option
|
11
|
-
end
|
12
|
-
end
|
13
|
-
|
14
|
-
widget :option, -> (opt) {
|
15
|
-
opt.is_a?(Regexp) ? ["option", text: opt] : [:option, opt]
|
16
|
-
} do
|
17
|
-
include Selectable
|
18
|
-
end
|
19
|
-
|
20
|
-
widget :option_by_value, -> (opt) { "option[value = #{opt.inspect}]" } do
|
21
|
-
include Selectable
|
22
|
-
end
|
23
|
-
|
24
|
-
# @return [String] The text of the selected option.
|
25
|
-
def get
|
26
|
-
selected.text unless selected.nil?
|
27
|
-
end
|
28
|
-
|
29
|
-
# @return [String] The value of the selected option.
|
30
|
-
def value
|
31
|
-
selected.value unless selected.nil?
|
32
|
-
end
|
33
|
-
|
34
|
-
# Selects the given +option+.
|
35
|
-
#
|
36
|
-
# You may pass in the option text or value.
|
37
|
-
def set(option)
|
38
|
-
widget(:option, option).select
|
39
|
-
rescue
|
40
|
-
begin
|
41
|
-
widget(:option_by_value, option).select
|
42
|
-
rescue CapybaraUI::MissingWidget => e
|
43
|
-
raise InvalidOption.new(e.message).
|
44
|
-
tap { |x| x.set_backtrace e.backtrace }
|
45
|
-
end
|
46
|
-
end
|
47
|
-
|
48
|
-
# @!method to_s
|
49
|
-
# @return the text of the selected option, or the empty string if
|
50
|
-
# no option is selected.
|
51
|
-
def_delegator :get, :to_s
|
52
|
-
|
53
|
-
def to_cell
|
54
|
-
get
|
55
|
-
end
|
56
|
-
end
|
57
|
-
end
|
@@ -1,43 +0,0 @@
|
|
1
|
-
module CapybaraUI
|
2
|
-
class StringValue < String
|
3
|
-
def to_date(format = nil)
|
4
|
-
format ? Date.strptime(self, format) : super()
|
5
|
-
end
|
6
|
-
|
7
|
-
def to_key
|
8
|
-
fst, rest = first, self[1..-1]
|
9
|
-
decamelized = fst + rest.gsub(/([A-Z])/, '_\1')
|
10
|
-
underscored = decamelized.gsub(/[\W_]+/, '_')
|
11
|
-
stripped = underscored.gsub(/^_|_$/, '')
|
12
|
-
downcased = stripped.downcase
|
13
|
-
key = downcased.to_sym
|
14
|
-
|
15
|
-
key
|
16
|
-
end
|
17
|
-
|
18
|
-
class Money
|
19
|
-
extend Forwardable
|
20
|
-
|
21
|
-
delegate %w(to_i to_f) => :str
|
22
|
-
|
23
|
-
def initialize(str)
|
24
|
-
fail ArgumentError, "can't convert `#{str}` to money" \
|
25
|
-
unless str =~ /^-?\$\d+(?:,\d{3})*(?:\.\d+)?/
|
26
|
-
|
27
|
-
@str = (str =~ /^-/ ? '-' : '') + str.gsub(/^-?\$|,/, '')
|
28
|
-
end
|
29
|
-
|
30
|
-
private
|
31
|
-
|
32
|
-
attr_reader :str
|
33
|
-
end
|
34
|
-
|
35
|
-
def to_usd
|
36
|
-
Money.new(self)
|
37
|
-
end
|
38
|
-
|
39
|
-
def to_split
|
40
|
-
split(',').map(&:strip).map { |e| self.class.new(e) }
|
41
|
-
end
|
42
|
-
end
|
43
|
-
end
|
@@ -1,76 +0,0 @@
|
|
1
|
-
module CapybaraUI
|
2
|
-
class Table < CapybaraUI::Widget
|
3
|
-
root 'table'
|
4
|
-
|
5
|
-
class Row < CapybaraUI::List
|
6
|
-
def self.column(*args, &block)
|
7
|
-
item(*args, &block)
|
8
|
-
end
|
9
|
-
end
|
10
|
-
|
11
|
-
def self.header_row(selector, &block)
|
12
|
-
widget :header_row, selector, Row, &block
|
13
|
-
end
|
14
|
-
|
15
|
-
header_row 'thead tr' do
|
16
|
-
column 'th'
|
17
|
-
end
|
18
|
-
|
19
|
-
def self.data_row(selector, &block)
|
20
|
-
widget :data_row, selector, Row, &block
|
21
|
-
end
|
22
|
-
|
23
|
-
data_row 'tbody tr' do
|
24
|
-
column 'td'
|
25
|
-
end
|
26
|
-
|
27
|
-
class Columns
|
28
|
-
include Enumerable
|
29
|
-
|
30
|
-
def initialize(parent)
|
31
|
-
@parent = parent
|
32
|
-
end
|
33
|
-
|
34
|
-
def [](header_or_index)
|
35
|
-
case header_or_index
|
36
|
-
when Integer
|
37
|
-
values_by_index(header_or_index)
|
38
|
-
when String
|
39
|
-
values_by_header(header_or_index)
|
40
|
-
else
|
41
|
-
raise TypeError,
|
42
|
-
"can't convert #{header_or_index.inspect} to Integer or String"
|
43
|
-
end
|
44
|
-
end
|
45
|
-
|
46
|
-
def each(&block)
|
47
|
-
parent.each(&block)
|
48
|
-
end
|
49
|
-
|
50
|
-
private
|
51
|
-
|
52
|
-
attr_reader :parent
|
53
|
-
|
54
|
-
def values_by_index(index)
|
55
|
-
parent.rows.transpose[index]
|
56
|
-
end
|
57
|
-
|
58
|
-
def values_by_header(header)
|
59
|
-
values_by_index(find_header_index(header))
|
60
|
-
end
|
61
|
-
|
62
|
-
def find_header_index(header)
|
63
|
-
parent.widget(:header_row).value.find_index(header) or
|
64
|
-
raise ArgumentError, "header not found: #{header.inspect}"
|
65
|
-
end
|
66
|
-
end
|
67
|
-
|
68
|
-
def columns
|
69
|
-
Columns.new(self)
|
70
|
-
end
|
71
|
-
|
72
|
-
def rows
|
73
|
-
widgets(:data_row).map(&:value)
|
74
|
-
end
|
75
|
-
end
|
76
|
-
end
|
@@ -1,27 +0,0 @@
|
|
1
|
-
module CapybaraUI
|
2
|
-
# A text field.
|
3
|
-
class TextField < Field
|
4
|
-
# @!method get
|
5
|
-
# @return The text field value.
|
6
|
-
def_delegator :root, :value, :get
|
7
|
-
|
8
|
-
# @!method set(value)
|
9
|
-
# Sets the text field value.
|
10
|
-
#
|
11
|
-
# @param value [String] the value to set.
|
12
|
-
def_delegator :root, :set
|
13
|
-
|
14
|
-
# @!method to_s
|
15
|
-
# @return the text field value, or the empty string if the field is
|
16
|
-
# empty.
|
17
|
-
def_delegator :get, :to_s
|
18
|
-
|
19
|
-
def to_cell
|
20
|
-
get
|
21
|
-
end
|
22
|
-
|
23
|
-
def content?
|
24
|
-
get.respond_to?(:empty?) ? ! get.empty? : !! get
|
25
|
-
end
|
26
|
-
end
|
27
|
-
end
|
@@ -1,392 +0,0 @@
|
|
1
|
-
module CapybaraUI
|
2
|
-
class Widget
|
3
|
-
extend Forwardable
|
4
|
-
extend Widgets::DSL
|
5
|
-
|
6
|
-
include WidgetParts::Struct
|
7
|
-
include WidgetParts::Container
|
8
|
-
include CucumberMethods
|
9
|
-
|
10
|
-
class Removed < StandardError; end
|
11
|
-
|
12
|
-
attr_reader :root
|
13
|
-
|
14
|
-
# @!group Widget macros
|
15
|
-
|
16
|
-
# Defines a new action.
|
17
|
-
#
|
18
|
-
# This is a shortcut to help defining a widget and a method that clicks
|
19
|
-
# on that widget. You can then send a widget instance the message given
|
20
|
-
# by +name+.
|
21
|
-
#
|
22
|
-
# You can access the underlying widget by appending "_widget" to the
|
23
|
-
# action name.
|
24
|
-
#
|
25
|
-
# @example
|
26
|
-
# # Consider the widget will encapsulate the following HTML
|
27
|
-
# #
|
28
|
-
# # <div id="profile">
|
29
|
-
# # <a href="/profiles/1/edit" rel="edit">Edit</a>
|
30
|
-
# # </div>
|
31
|
-
# class PirateProfile < CapybaraUI::Widget
|
32
|
-
# root "#profile"
|
33
|
-
#
|
34
|
-
# # Declare the action
|
35
|
-
# action :edit, '[rel = edit]'
|
36
|
-
# end
|
37
|
-
#
|
38
|
-
# pirate_profile = widget(:pirate_profile)
|
39
|
-
#
|
40
|
-
# # Access the action widget
|
41
|
-
# action_widget = pirate_profile.widget(:edit_widget)
|
42
|
-
# action_widget = pirate_profile.edit_widget
|
43
|
-
#
|
44
|
-
# # Click the link
|
45
|
-
# pirate_profile.edit
|
46
|
-
#
|
47
|
-
# @param name the name of the action
|
48
|
-
# @param selector the selector for the widget that will be clicked
|
49
|
-
def self.action(name, selector = nil)
|
50
|
-
block = if selector
|
51
|
-
wname = :"#{name}_widget"
|
52
|
-
|
53
|
-
widget wname, selector
|
54
|
-
|
55
|
-
-> { widget(wname).click; self }
|
56
|
-
else
|
57
|
-
-> { click; self }
|
58
|
-
end
|
59
|
-
|
60
|
-
define_method name, &block
|
61
|
-
end
|
62
|
-
|
63
|
-
# Creates a delegator for one child widget message.
|
64
|
-
#
|
65
|
-
# Since widgets are accessed through {WidgetParts::Container#widget}, we
|
66
|
-
# can't use {Forwardable} to delegate messages to widgets.
|
67
|
-
#
|
68
|
-
# @param name the name of the receiver child widget
|
69
|
-
# @param widget_message the name of the message to be sent to the child widget
|
70
|
-
# @param method_name the name of the delegator. If +nil+ the method will
|
71
|
-
# have the same name as the message it will send.
|
72
|
-
def self.widget_delegator(name, widget_message, method_name = nil)
|
73
|
-
method_name = method_name || widget_message
|
74
|
-
|
75
|
-
class_eval <<-RUBY
|
76
|
-
def #{method_name}(*args)
|
77
|
-
if args.size == 1
|
78
|
-
widget(:#{name}).#{widget_message} args.first
|
79
|
-
else
|
80
|
-
widget(:#{name}).#{widget_message} *args
|
81
|
-
end
|
82
|
-
end
|
83
|
-
RUBY
|
84
|
-
end
|
85
|
-
|
86
|
-
# @!endgroup
|
87
|
-
|
88
|
-
# Finds a single instance of the current widget in +node+.
|
89
|
-
#
|
90
|
-
# @param node the node we want to search in
|
91
|
-
#
|
92
|
-
# @return a new instance of the current widget class.
|
93
|
-
#
|
94
|
-
# @raise [Capybara::ElementNotFoundError] if the widget can't be found
|
95
|
-
def self.find_in(parent, *args)
|
96
|
-
new(filter.node(parent, *args))
|
97
|
-
rescue Capybara::Ambiguous => e
|
98
|
-
raise AmbiguousWidget.new(e.message).
|
99
|
-
tap { |x| x.set_backtrace e.backtrace }
|
100
|
-
rescue Capybara::ElementNotFound => e
|
101
|
-
raise MissingWidget.new(e.message).
|
102
|
-
tap { |x| x.set_backtrace e.backtrace }
|
103
|
-
end
|
104
|
-
|
105
|
-
def self.find_all_in(parent, *args)
|
106
|
-
filter.nodes(parent, *args).map { |e| new(e) }
|
107
|
-
end
|
108
|
-
|
109
|
-
# Determines if an instance of this widget class exists in
|
110
|
-
# +parent_node+.
|
111
|
-
#
|
112
|
-
# @param parent_node [Capybara::Node] the node we want to search in
|
113
|
-
#
|
114
|
-
# @return +true+ if a widget instance is found, +false+ otherwise.
|
115
|
-
def self.present_in?(parent, *args)
|
116
|
-
filter.node?(parent, *args)
|
117
|
-
end
|
118
|
-
|
119
|
-
def self.not_present_in?(parent, *args)
|
120
|
-
filter.nodeless?(parent, *args)
|
121
|
-
end
|
122
|
-
|
123
|
-
# Sets this widget's default selector.
|
124
|
-
#
|
125
|
-
# You can pass more than one argument to it, or a single Array. Any valid
|
126
|
-
# Capybara selector accepted by Capybara::Node::Finders#find will work.
|
127
|
-
#
|
128
|
-
# === Examples
|
129
|
-
#
|
130
|
-
# Most of the time, your selectors will be Strings:
|
131
|
-
#
|
132
|
-
# class MyWidget < CapybaraUI::Widget
|
133
|
-
# root '.selector'
|
134
|
-
# end
|
135
|
-
#
|
136
|
-
# This will match any element with a class of "selector". For example:
|
137
|
-
#
|
138
|
-
# <span class="selector">Pick me!</span>
|
139
|
-
#
|
140
|
-
# ==== Composite selectors
|
141
|
-
#
|
142
|
-
# If you're using CSS as the query language, it's useful to be able to use
|
143
|
-
# +text: 'Some text'+ to zero in on a specific node:
|
144
|
-
#
|
145
|
-
# class MySpecificWidget < CapybaraUI::Widget
|
146
|
-
# root '.selector', text: 'Pick me!'
|
147
|
-
# end
|
148
|
-
#
|
149
|
-
# This is especially useful, e.g., when you want to create a widget
|
150
|
-
# to match a specific error or notification:
|
151
|
-
#
|
152
|
-
# class NoFreeSpace < CapybaraUI::Widget
|
153
|
-
# root '.error', text: 'No free space left!'
|
154
|
-
# end
|
155
|
-
#
|
156
|
-
# So, given the following HTML:
|
157
|
-
#
|
158
|
-
# <body>
|
159
|
-
# <div class="error">No free space left!</div>
|
160
|
-
#
|
161
|
-
# <!-- ... -->
|
162
|
-
# </body>
|
163
|
-
#
|
164
|
-
# You can test for the error's present using the following code:
|
165
|
-
#
|
166
|
-
# document.visible?(:no_free_space) #=> true
|
167
|
-
#
|
168
|
-
# Note: When you want to match text, consider using +I18n.t+ instead of
|
169
|
-
# hard-coding the text, so that your tests don't break when the text changes.
|
170
|
-
#
|
171
|
-
# Finally, you may want to override the query language:
|
172
|
-
#
|
173
|
-
# class MyWidgetUsesXPath < CapybaraUI::Widget
|
174
|
-
# root :xpath, '//some/node'
|
175
|
-
# end
|
176
|
-
def self.root(*selector, &block)
|
177
|
-
@filter = NodeFilter.new(block || selector)
|
178
|
-
end
|
179
|
-
|
180
|
-
class MissingSelector < StandardError
|
181
|
-
end
|
182
|
-
|
183
|
-
def self.filter
|
184
|
-
@filter || superclass.filter
|
185
|
-
rescue NoMethodError
|
186
|
-
raise MissingSelector, 'no selector defined'
|
187
|
-
end
|
188
|
-
|
189
|
-
def self.filter?
|
190
|
-
filter rescue false
|
191
|
-
end
|
192
|
-
|
193
|
-
def self.selector
|
194
|
-
filter.selector
|
195
|
-
end
|
196
|
-
|
197
|
-
def initialize(root)
|
198
|
-
@root = root
|
199
|
-
end
|
200
|
-
|
201
|
-
# Clicks the current widget, or the child widget given by +name+.
|
202
|
-
#
|
203
|
-
# === Usage
|
204
|
-
#
|
205
|
-
# Given the following widget definition:
|
206
|
-
#
|
207
|
-
# class Container < CapybaraUI::Widget
|
208
|
-
# root '#container'
|
209
|
-
#
|
210
|
-
# widget :link, 'a'
|
211
|
-
# end
|
212
|
-
#
|
213
|
-
# Send +click+ with no arguments to trigger a +click+ event on +#container+.
|
214
|
-
#
|
215
|
-
# widget(:container).click
|
216
|
-
#
|
217
|
-
# This is the equivalent of doing the following using Capybara:
|
218
|
-
#
|
219
|
-
# find('#container').click
|
220
|
-
#
|
221
|
-
# Send +click :link+ to trigger a +click+ event on +a+:
|
222
|
-
#
|
223
|
-
# widget(:container).click :link
|
224
|
-
#
|
225
|
-
# This is the equivalent of doing the following using Capybara:
|
226
|
-
#
|
227
|
-
# find('#container a').click
|
228
|
-
def click(*args)
|
229
|
-
if args.empty?
|
230
|
-
root.click
|
231
|
-
else
|
232
|
-
widget(*args).click
|
233
|
-
end
|
234
|
-
end
|
235
|
-
|
236
|
-
# Hovers over the current widget, or the child widget given by +name+.
|
237
|
-
#
|
238
|
-
# === Usage
|
239
|
-
#
|
240
|
-
# Given the following widget definition:
|
241
|
-
#
|
242
|
-
# class Container < CapybaraUI::Widget
|
243
|
-
# root '#container'
|
244
|
-
#
|
245
|
-
# widget :link, 'a'
|
246
|
-
# end
|
247
|
-
#
|
248
|
-
# Send +hover+ with no arguments to trigger a +hover+ event on +#container+.
|
249
|
-
#
|
250
|
-
# widget(:container).hover
|
251
|
-
#
|
252
|
-
# This is the equivalent of doing the following using Capybara:
|
253
|
-
#
|
254
|
-
# find('#container').hover
|
255
|
-
#
|
256
|
-
# Send +hover :link+ to trigger a +hover+ event on +a+:
|
257
|
-
#
|
258
|
-
# widget(:container).hover :link
|
259
|
-
#
|
260
|
-
# This is the equivalent of doing the following using Capybara:
|
261
|
-
#
|
262
|
-
# find('#container a').hover
|
263
|
-
def hover(*args)
|
264
|
-
if args.empty?
|
265
|
-
root.hover
|
266
|
-
else
|
267
|
-
widget(*args).hover
|
268
|
-
end
|
269
|
-
end
|
270
|
-
|
271
|
-
# Double clicks the current widget, or the child widget given by +name+.
|
272
|
-
#
|
273
|
-
# === Usage
|
274
|
-
#
|
275
|
-
# Given the following widget definition:
|
276
|
-
#
|
277
|
-
# class Container < CapybaraUI::Widget
|
278
|
-
# root '#container'
|
279
|
-
#
|
280
|
-
# widget :link, 'a'
|
281
|
-
# end
|
282
|
-
#
|
283
|
-
# Send +double_click+ with no arguments to trigger an +ondblclick+ event on +#container+.
|
284
|
-
#
|
285
|
-
# widget(:container).double_click
|
286
|
-
#
|
287
|
-
# This is the equivalent of doing the following using Capybara:
|
288
|
-
#
|
289
|
-
# find('#container').double_click
|
290
|
-
def double_click(*args)
|
291
|
-
if args.empty?
|
292
|
-
root.double_click
|
293
|
-
else
|
294
|
-
widget(*args).double_click
|
295
|
-
end
|
296
|
-
end
|
297
|
-
|
298
|
-
# Right clicks the current widget, or the child widget given by +name+.
|
299
|
-
#
|
300
|
-
# === Usage
|
301
|
-
#
|
302
|
-
# Given the following widget definition:
|
303
|
-
#
|
304
|
-
# class Container < CapybaraUI::Widget
|
305
|
-
# root '#container'
|
306
|
-
#
|
307
|
-
# widget :link, 'a'
|
308
|
-
# end
|
309
|
-
#
|
310
|
-
# Send +right_click+ with no arguments to trigger an +oncontextmenu+ event on +#container+.
|
311
|
-
#
|
312
|
-
# widget(:container).right_click
|
313
|
-
#
|
314
|
-
# This is the equivalent of doing the following using Capybara:
|
315
|
-
#
|
316
|
-
# find('#container').right_click
|
317
|
-
def right_click(*args)
|
318
|
-
if args.empty?
|
319
|
-
root.right_click
|
320
|
-
else
|
321
|
-
widget(*args).right_click
|
322
|
-
end
|
323
|
-
end
|
324
|
-
|
325
|
-
# Determines if the widget underlying an action exists.
|
326
|
-
#
|
327
|
-
# @param name the name of the action
|
328
|
-
#
|
329
|
-
# @raise Missing if an action with +name+ can't be found.
|
330
|
-
#
|
331
|
-
# @return [Boolean] +true+ if the action widget is found, +false+
|
332
|
-
# otherwise.
|
333
|
-
def has_action?(name)
|
334
|
-
raise Missing, "couldn't find `#{name}' action" unless respond_to?(name)
|
335
|
-
|
336
|
-
visible?(:"#{name}_widget")
|
337
|
-
end
|
338
|
-
|
339
|
-
def id
|
340
|
-
root['id']
|
341
|
-
end
|
342
|
-
|
343
|
-
def classes
|
344
|
-
root['class'].split
|
345
|
-
end
|
346
|
-
|
347
|
-
# Determines if the widget has a specific class
|
348
|
-
#
|
349
|
-
# @param name the name of the class
|
350
|
-
#
|
351
|
-
# @return [Boolean] +true+ if the class is found, +false+ otherwise
|
352
|
-
def class?(name)
|
353
|
-
classes.include?(name)
|
354
|
-
end
|
355
|
-
|
356
|
-
def html
|
357
|
-
xml = Nokogiri::HTML(page.body).at(root.path).to_xml
|
358
|
-
|
359
|
-
Nokogiri::XML(xml, &:noblanks).to_xhtml.gsub("\n", "")
|
360
|
-
end
|
361
|
-
|
362
|
-
def text
|
363
|
-
StringValue.new(root.text.strip)
|
364
|
-
end
|
365
|
-
|
366
|
-
# Converts this widget into a string representation suitable to be displayed
|
367
|
-
# in a Cucumber table cell. By default calls #text.
|
368
|
-
#
|
369
|
-
# This method will be called by methods that build tables or rows (usually
|
370
|
-
# #to_table or #to_row) so, in general, you won't call it directly, but feel
|
371
|
-
# free to override it when needed.
|
372
|
-
#
|
373
|
-
# Returns a String.
|
374
|
-
def to_cell
|
375
|
-
text
|
376
|
-
end
|
377
|
-
|
378
|
-
def to_s
|
379
|
-
text
|
380
|
-
end
|
381
|
-
|
382
|
-
def value
|
383
|
-
text
|
384
|
-
end
|
385
|
-
|
386
|
-
private
|
387
|
-
|
388
|
-
def page
|
389
|
-
Capybara.current_session
|
390
|
-
end
|
391
|
-
end
|
392
|
-
end
|