watir 6.14.0 → 6.15.0

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.
Files changed (133) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +24 -6
  3. data/CHANGES.md +10 -0
  4. data/Gemfile +0 -2
  5. data/README.md +1 -1
  6. data/Rakefile +2 -2
  7. data/lib/watir.rb +2 -3
  8. data/lib/watir/adjacent.rb +2 -2
  9. data/lib/watir/alert.rb +5 -9
  10. data/lib/watir/attribute_helper.rb +2 -3
  11. data/lib/watir/browser.rb +5 -17
  12. data/lib/watir/capabilities.rb +11 -0
  13. data/lib/watir/cell_container.rb +2 -2
  14. data/lib/watir/container.rb +7 -8
  15. data/lib/watir/cookies.rb +2 -12
  16. data/lib/watir/element_collection.rb +2 -2
  17. data/lib/watir/elements/button.rb +2 -11
  18. data/lib/watir/elements/element.rb +43 -25
  19. data/lib/watir/elements/hidden.rb +1 -1
  20. data/lib/watir/elements/iframe.rb +7 -5
  21. data/lib/watir/elements/option.rb +2 -13
  22. data/lib/watir/elements/select.rb +6 -22
  23. data/lib/watir/elements/table.rb +2 -2
  24. data/lib/watir/exception.rb +1 -2
  25. data/lib/watir/generator/base/idl_sorter.rb +1 -1
  26. data/lib/watir/generator/base/spec_extractor.rb +2 -2
  27. data/lib/watir/generator/base/visitor.rb +1 -1
  28. data/lib/watir/generator/html/generator.rb +0 -1
  29. data/lib/watir/generator/html/spec_extractor.rb +1 -1
  30. data/lib/watir/generator/html/visitor.rb +1 -1
  31. data/lib/watir/generator/svg/spec_extractor.rb +1 -1
  32. data/lib/watir/generator/svg/visitor.rb +1 -1
  33. data/lib/watir/js_execution.rb +11 -0
  34. data/lib/watir/js_snippets.rb +1 -1
  35. data/lib/watir/js_snippets/elementObscured.js +14 -0
  36. data/lib/watir/js_snippets/selectedText.js +17 -0
  37. data/lib/watir/legacy_wait.rb +5 -5
  38. data/lib/watir/locators.rb +16 -5
  39. data/lib/watir/locators/anchor/selector_builder.rb +38 -0
  40. data/lib/watir/locators/button/locator.rb +14 -12
  41. data/lib/watir/locators/button/selector_builder.rb +0 -22
  42. data/lib/watir/locators/button/selector_builder/xpath.rb +67 -12
  43. data/lib/watir/locators/button/validator.rb +2 -1
  44. data/lib/watir/locators/cell/selector_builder.rb +0 -14
  45. data/lib/watir/locators/cell/selector_builder/xpath.rb +21 -0
  46. data/lib/watir/locators/element/locator.rb +60 -153
  47. data/lib/watir/locators/element/selector_builder.rb +103 -84
  48. data/lib/watir/locators/element/selector_builder/regexp_disassembler.rb +66 -0
  49. data/lib/watir/locators/element/selector_builder/xpath.rb +195 -82
  50. data/lib/watir/locators/element/selector_builder/xpath_support.rb +27 -0
  51. data/lib/watir/locators/element/validator.rb +2 -9
  52. data/lib/watir/locators/row/selector_builder.rb +5 -22
  53. data/lib/watir/locators/row/selector_builder/xpath.rb +53 -0
  54. data/lib/watir/locators/text_area/selector_builder.rb +1 -1
  55. data/lib/watir/locators/text_area/selector_builder/xpath.rb +19 -0
  56. data/lib/watir/locators/text_field/locator.rb +11 -8
  57. data/lib/watir/locators/text_field/selector_builder.rb +0 -23
  58. data/lib/watir/locators/text_field/selector_builder/xpath.rb +33 -4
  59. data/lib/watir/locators/text_field/validator.rb +4 -4
  60. data/lib/watir/radio_set.rb +5 -5
  61. data/lib/watir/row_container.rb +2 -2
  62. data/lib/watir/user_editable.rb +2 -2
  63. data/lib/watir/version.rb +1 -1
  64. data/lib/watir/wait.rb +24 -37
  65. data/lib/watir/window.rb +11 -8
  66. data/lib/watirspec/remote_server.rb +3 -1
  67. data/spec/locator_spec_helper.rb +1 -1
  68. data/spec/spec_helper.rb +25 -1
  69. data/spec/unit/anchor_locator_spec.rb +68 -0
  70. data/spec/unit/capabilities_spec.rb +27 -0
  71. data/spec/unit/element_locator_spec.rb +184 -101
  72. data/spec/unit/logger_spec.rb +5 -0
  73. data/spec/watirspec/adjacent_spec.rb +34 -34
  74. data/spec/watirspec/after_hooks_spec.rb +78 -35
  75. data/spec/watirspec/alert_spec.rb +10 -0
  76. data/spec/watirspec/browser_spec.rb +27 -1
  77. data/spec/watirspec/element_hidden_spec.rb +6 -0
  78. data/spec/watirspec/elements/button_spec.rb +5 -11
  79. data/spec/watirspec/elements/buttons_spec.rb +1 -1
  80. data/spec/watirspec/elements/checkbox_spec.rb +2 -15
  81. data/spec/watirspec/elements/date_time_field_spec.rb +6 -1
  82. data/spec/watirspec/elements/dd_spec.rb +0 -17
  83. data/spec/watirspec/elements/del_spec.rb +0 -14
  84. data/spec/watirspec/elements/div_spec.rb +0 -18
  85. data/spec/watirspec/elements/dl_spec.rb +0 -17
  86. data/spec/watirspec/elements/dt_spec.rb +0 -17
  87. data/spec/watirspec/elements/element_spec.rb +177 -17
  88. data/spec/watirspec/elements/elements_spec.rb +7 -6
  89. data/spec/watirspec/elements/em_spec.rb +0 -13
  90. data/spec/watirspec/elements/filefield_spec.rb +0 -11
  91. data/spec/watirspec/elements/form_spec.rb +6 -0
  92. data/spec/watirspec/elements/hn_spec.rb +0 -14
  93. data/spec/watirspec/elements/iframe_spec.rb +15 -0
  94. data/spec/watirspec/elements/ins_spec.rb +0 -14
  95. data/spec/watirspec/elements/labels_spec.rb +1 -1
  96. data/spec/watirspec/elements/li_spec.rb +0 -14
  97. data/spec/watirspec/elements/link_spec.rb +22 -14
  98. data/spec/watirspec/elements/links_spec.rb +13 -0
  99. data/spec/watirspec/elements/list_spec.rb +15 -0
  100. data/spec/watirspec/elements/ol_spec.rb +0 -14
  101. data/spec/watirspec/elements/option_spec.rb +0 -10
  102. data/spec/watirspec/elements/p_spec.rb +0 -14
  103. data/spec/watirspec/elements/pre_spec.rb +0 -14
  104. data/spec/watirspec/elements/radio_spec.rb +0 -14
  105. data/spec/watirspec/elements/select_list_spec.rb +0 -10
  106. data/spec/watirspec/elements/span_spec.rb +4 -15
  107. data/spec/watirspec/elements/strong_spec.rb +4 -15
  108. data/spec/watirspec/elements/table_nesting_spec.rb +1 -1
  109. data/spec/watirspec/elements/table_spec.rb +7 -0
  110. data/spec/watirspec/elements/text_field_spec.rb +10 -2
  111. data/spec/watirspec/elements/text_fields_spec.rb +1 -1
  112. data/spec/watirspec/elements/tr_spec.rb +1 -1
  113. data/spec/watirspec/elements/ul_spec.rb +0 -14
  114. data/spec/watirspec/html/closeable.html +8 -0
  115. data/spec/watirspec/html/forms_with_input_elements.html +28 -23
  116. data/spec/watirspec/html/nested_elements.html +9 -9
  117. data/spec/watirspec/html/obscured.html +34 -0
  118. data/spec/watirspec/html/tables.html +13 -13
  119. data/spec/watirspec/radio_set_spec.rb +5 -0
  120. data/spec/watirspec/selector_builder/button_spec.rb +254 -0
  121. data/spec/watirspec/selector_builder/cell_spec.rb +93 -0
  122. data/spec/watirspec/selector_builder/element_spec.rb +639 -0
  123. data/spec/watirspec/selector_builder/row_spec.rb +150 -0
  124. data/spec/watirspec/selector_builder/text_spec.rb +170 -0
  125. data/spec/watirspec/support/rspec_matchers.rb +6 -1
  126. data/spec/watirspec/user_editable_spec.rb +4 -0
  127. data/spec/watirspec/wait_spec.rb +65 -14
  128. data/spec/watirspec/window_switching_spec.rb +54 -1
  129. data/spec/watirspec_helper.rb +2 -0
  130. data/watir.gemspec +7 -1
  131. metadata +86 -8
  132. data/lib/watir/locators/text_area/locator.rb +0 -13
  133. data/lib/watir/xpath_support.rb +0 -18
@@ -0,0 +1,27 @@
1
+ module Watir
2
+ module Locators
3
+ class Element
4
+ class SelectorBuilder
5
+ module XpathSupport
6
+ UPPERCASE_LETTERS = 'ABCDEFGHIJKLMNOPQRSTUVWXYZÀÁÂÃÄÅÆÇÈÉÊËÌÍÎÏÐÑÒÓÔÕÖØÙÚÛÜÝÞŸŽŠŒ'.freeze
7
+ LOWERCASE_LETTERS = 'abcdefghijklmnopqrstuvwxyzàáâãäåæçèéêëìíîïðñòóôõöøùúûüýþÿžšœ'.freeze
8
+
9
+ def self.escape(value)
10
+ if value.include? "'"
11
+ parts = value.split("'", -1).map { |part| "'#{part}'" }
12
+ string = parts.join(%(,"'",))
13
+
14
+ "concat(#{string})"
15
+ else
16
+ "'#{value}'"
17
+ end
18
+ end
19
+
20
+ def self.downcase(value)
21
+ "translate(#{value},'#{UPPERCASE_LETTERS}','#{LOWERCASE_LETTERS}')"
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end # XpathSupport
27
+ end # Watir
@@ -2,15 +2,8 @@ module Watir
2
2
  module Locators
3
3
  class Element
4
4
  class Validator
5
- def validate(element, selector)
6
- selector_tag_name = selector[:tag_name]
7
- element_tag_name = element.tag_name.downcase
8
-
9
- if selector_tag_name
10
- return unless element_tag_name =~ /#{selector_tag_name}/
11
- end
12
-
13
- element
5
+ def validate(element, tag_name)
6
+ element.tag_name.downcase =~ /#{tag_name}/
14
7
  end
15
8
  end
16
9
  end
@@ -2,30 +2,13 @@ module Watir
2
2
  module Locators
3
3
  class Row
4
4
  class SelectorBuilder < Element::SelectorBuilder
5
- def build_wd_selector(selectors)
6
- return if selectors.values.any? { |e| e.is_a? Regexp }
7
-
8
- selectors.delete(:tag_name) || raise('internal error: no tag_name?!')
9
-
10
- expressions = generate_expressions(@query_scope.tag_name.downcase)
11
-
12
- attr_expr = xpath_builder.attribute_expression(nil, selectors)
13
-
14
- expressions.map! { |e| "#{e}[#{attr_expr}]" } unless attr_expr.empty?
15
-
16
- xpath = expressions.join(' | ')
17
-
18
- p build_wd_selector: xpath if $DEBUG
19
-
20
- [:xpath, xpath]
5
+ def initialize(valid_attributes, scope_tag_name)
6
+ @scope_tag_name = scope_tag_name
7
+ super(valid_attributes)
21
8
  end
22
9
 
23
- protected
24
-
25
- def generate_expressions(tag_name)
26
- expressions = %w[./tr]
27
- expressions += %w[./tbody/tr ./thead/tr ./tfoot/tr] unless %w[tbody tfoot thead].include?(tag_name)
28
- expressions
10
+ def build_wd_selector(selector)
11
+ Kernel.const_get("#{self.class.name}::XPath").new.build(selector, @scope_tag_name)
29
12
  end
30
13
  end
31
14
  end
@@ -0,0 +1,53 @@
1
+ module Watir
2
+ module Locators
3
+ class Row
4
+ class SelectorBuilder
5
+ class XPath < Element::SelectorBuilder::XPath
6
+ def build(selector, scope_tag_name)
7
+ return super(selector) if selector.key?(:adjacent)
8
+
9
+ index = selector.delete(:index)
10
+
11
+ common_string = super(selector)[:xpath]
12
+ expressions = generate_expressions(scope_tag_name)
13
+ expressions.map! { |e| "#{e}#{common_string}" } unless common_string.empty?
14
+
15
+ xpath = expressions.join(' | ').to_s
16
+
17
+ xpath = index ? add_index(xpath, index) : xpath
18
+
19
+ @selector.merge! @requires_matches
20
+
21
+ {xpath: xpath}
22
+ end
23
+
24
+ private
25
+
26
+ def start_string
27
+ @adjacent ? './' : ''
28
+ end
29
+
30
+ def text_string
31
+ return super if @adjacent
32
+
33
+ # Can not directly locate a Row with Text because all text is in the Cells;
34
+ # needs to use Locator#locate_matching_elements
35
+ @requires_matches[:text] = @selector.delete(:text) if @selector.key?(:text)
36
+ ''
37
+ end
38
+
39
+ def generate_expressions(scope_tag_name)
40
+ if %w[tbody tfoot thead].include?(scope_tag_name)
41
+ ["./*[local-name()='tr']"]
42
+ else
43
+ ["./*[local-name()='tr']",
44
+ "./*[local-name()='tbody']/*[local-name()='tr']",
45
+ "./*[local-name()='thead']/*[local-name()='tr']",
46
+ "./*[local-name()='tfoot']/*[local-name()='tr']"]
47
+ end
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
53
+ end
@@ -4,7 +4,7 @@ module Watir
4
4
  class SelectorBuilder < Element::SelectorBuilder
5
5
  private
6
6
 
7
- def normalize_selector(how, what)
7
+ def normalize_locator(how, what)
8
8
  # We need to iterate through located elements and fetch
9
9
  # attribute value using Selenium because XPath doesn't understand
10
10
  # difference between IDL vs content attribute.
@@ -0,0 +1,19 @@
1
+ module Watir
2
+ module Locators
3
+ class TextArea
4
+ class SelectorBuilder
5
+ class XPath < Element::SelectorBuilder::XPath
6
+ private
7
+
8
+ # value always requires a wire call since we want the property not the attribute
9
+ def predicate_conversion(key, regexp)
10
+ return super unless key == :value
11
+
12
+ @requires_matches[:value] = regexp
13
+ nil
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
@@ -8,20 +8,23 @@ module Watir
8
8
  # force Watir usage
9
9
  end
10
10
 
11
- def matches_selector?(element, rx_selector)
12
- rx_selector = rx_selector.dup
11
+ def matches_values?(element, rx_selector)
12
+ conversions = %i[text value label visible_text] & rx_selector.keys
13
13
 
14
- tag_name = element.tag_name.downcase
14
+ tag_name = nil
15
15
 
16
- %i[text value label].each do |key|
17
- if rx_selector.key?(key)
18
- correct_key = tag_name == 'input' ? :value : :text
19
- rx_selector[correct_key] = rx_selector.delete(key)
20
- end
16
+ conversions.each do |key|
17
+ tag_name ||= element.tag_name.downcase
18
+ correct_key = tag_name == 'input' ? :value : :text
19
+ rx_selector[correct_key] = rx_selector.delete(key)
21
20
  end
22
21
 
23
22
  super
24
23
  end
24
+
25
+ def text_regexp_deprecation(*)
26
+ # does not apply to text_field
27
+ end
25
28
  end
26
29
  end
27
30
  end
@@ -2,29 +2,6 @@ module Watir
2
2
  module Locators
3
3
  class TextField
4
4
  class SelectorBuilder < Element::SelectorBuilder
5
- def build_wd_selector(selectors)
6
- return if selectors.values.any? { |e| e.is_a? Regexp }
7
-
8
- selectors.delete(:tag_name)
9
-
10
- input_attr_exp = xpath_builder.attribute_expression(:input, selectors)
11
-
12
- xpath = ".//input[(not(@type) or (#{negative_type_expr}))"
13
- xpath << " and #{input_attr_exp}" unless input_attr_exp.empty?
14
- xpath << ']'
15
-
16
- p build_wd_selector: xpath if $DEBUG
17
-
18
- [:xpath, xpath]
19
- end
20
-
21
- private
22
-
23
- def negative_type_expr
24
- Watir::TextField::NON_TEXT_TYPES.map { |type|
25
- format('%s!=%s', XpathSupport.downcase('@type'), type.inspect)
26
- }.join(' and ')
27
- end
28
5
  end
29
6
  end
30
7
  end
@@ -3,13 +3,42 @@ module Watir
3
3
  class TextField
4
4
  class SelectorBuilder
5
5
  class XPath < Element::SelectorBuilder::XPath
6
- def lhs_for(building, key)
7
- if building == :input && key == :text
8
- '@value'
6
+ def text_string
7
+ return super if @adjacent
8
+
9
+ @requires_matches[:text] = @selector.delete(:text) if @selector.key?(:text)
10
+ ''
11
+ end
12
+
13
+ def additional_string
14
+ return '' if @adjacent
15
+
16
+ type_string(@selector.delete(:type))
17
+ end
18
+
19
+ def tag_string
20
+ @selector[:tag_name] = 'input' unless @adjacent
21
+ super
22
+ end
23
+
24
+ def type_string(type)
25
+ if type.eql?(true)
26
+ "[#{negative_type_text}]"
27
+ elsif Watir::TextField::NON_TEXT_TYPES.include?(type)
28
+ msg = "TextField Elements can not be located by type: #{type}"
29
+ raise LocatorException, msg
30
+ elsif type.nil?
31
+ "[not(@type) or (#{negative_type_text})]"
9
32
  else
10
- super
33
+ "[#{process_attribute(:type, type)}]"
11
34
  end
12
35
  end
36
+
37
+ def negative_type_text
38
+ Watir::TextField::NON_TEXT_TYPES.map { |type|
39
+ "#{lhs_for(:type, true)}!=#{SelectorBuilder::XpathSupport.escape type}"
40
+ }.join(' and ')
41
+ end
13
42
  end
14
43
  end
15
44
  end
@@ -2,10 +2,10 @@ module Watir
2
2
  module Locators
3
3
  class TextField
4
4
  class Validator < Element::Validator
5
- def validate(element, _selector)
6
- return unless element.tag_name.casecmp('input').zero?
7
-
8
- element
5
+ def validate(element, _tag_name)
6
+ # Zero for Ruby 2.3, Ruby 2.4+ this evaluates true/false
7
+ result = element.tag_name.casecmp('input')
8
+ result.zero? || result.eq(true)
9
9
  end
10
10
  end
11
11
  end
@@ -1,7 +1,7 @@
1
1
  module Watir
2
2
  class RadioSet
3
3
  extend Forwardable
4
- include Watir::Exception
4
+ include Exception
5
5
  include Enumerable
6
6
 
7
7
  delegate %i[exists? present? visible? browser] => :source
@@ -12,7 +12,7 @@ module Watir
12
12
  raise ArgumentError, "invalid argument: #{selector.inspect}" unless selector.is_a? Hash
13
13
 
14
14
  @source = Radio.new(query_scope, selector)
15
- @frame = @source.parent(tag_name: :form)
15
+ @frame = @source.parent(tag_name: 'form')
16
16
  end
17
17
 
18
18
  #
@@ -52,7 +52,7 @@ module Watir
52
52
  elsif n.empty?
53
53
  return source
54
54
  else
55
- raise Watir::Exception::UnknownObjectException, "#{opt[:name]} does not match name of RadioSet: #{n}"
55
+ raise UnknownObjectException, "#{opt[:name]} does not match name of RadioSet: #{n}"
56
56
  end
57
57
  end
58
58
 
@@ -65,9 +65,9 @@ module Watir
65
65
  if !n.empty? && (!opt[:name] || opt[:name] == n)
66
66
  element_call(:wait_for_present) { frame.radios(opt.merge(name: n)) }
67
67
  elsif n.empty?
68
- Watir::RadioCollection.new(frame, element: source.wd)
68
+ RadioCollection.new(frame, element: source.wd)
69
69
  else
70
- raise Watir::Exception::UnknownObjectException, "#{opt[:name]} does not match name of RadioSet: #{n}"
70
+ raise UnknownObjectException, "#{opt[:name]} does not match name of RadioSet: #{n}"
71
71
  end
72
72
  end
73
73
 
@@ -5,7 +5,7 @@ module Watir
5
5
  #
6
6
 
7
7
  def row(*args)
8
- Row.new(self, extract_selector(args).merge(tag_name: 'tr'))
8
+ Row.new(self, extract_selector(args))
9
9
  end
10
10
 
11
11
  #
@@ -13,7 +13,7 @@ module Watir
13
13
  #
14
14
 
15
15
  def rows(*args)
16
- RowCollection.new(self, extract_selector(args).merge(tag_name: 'tr'))
16
+ RowCollection.new(self, extract_selector(args))
17
17
  end
18
18
 
19
19
  #
@@ -33,7 +33,7 @@ module Watir
33
33
  append(input_value[-1])
34
34
  return if value == input_value
35
35
 
36
- raise Watir::Exception::Error, "#set! value: '#{value}' does not match expected input: '#{input_value}'"
36
+ raise Exception::Error, "#set! value: '#{value}' does not match expected input: '#{input_value}'"
37
37
  end
38
38
 
39
39
  #
@@ -66,7 +66,7 @@ module Watir
66
66
  element_call { execute_js(:setText, @element, input_text) }
67
67
  return if text == input_text
68
68
 
69
- raise Watir::Exception::Error, "#set! text: '#{text}' does not match expected input: '#{input_text}'"
69
+ raise Exception::Error, "#set! text: '#{text}' does not match expected input: '#{input_text}'"
70
70
  end
71
71
  end # UserEditable
72
72
  end # Watir
@@ -1,3 +1,3 @@
1
1
  module Watir
2
- VERSION = '6.14.0'.freeze
2
+ VERSION = '6.15.0'.freeze
3
3
  end
@@ -121,7 +121,7 @@ module Watir
121
121
 
122
122
  raise ArgumentError, "Unknown keyword(s): #{opt.keys} " if block_given? && !opt.empty?
123
123
 
124
- proc = block_given? ? blk : create_proc(opt)
124
+ proc = create_proc(opt, &blk)
125
125
 
126
126
  Wait.until(timeout: timeout, message: message, interval: interval, object: self, &proc)
127
127
 
@@ -151,9 +151,7 @@ module Watir
151
151
  end
152
152
  message ||= proc { |obj| "waiting for false condition on #{obj.inspect}" }
153
153
 
154
- raise ArgumentError, "Unknown keyword(s): #{opt.keys} " if block_given? && !opt.empty?
155
-
156
- proc = block_given? ? blk : create_proc(opt)
154
+ proc = create_proc(opt, &blk)
157
155
 
158
156
  Wait.while(timeout: timeout, message: message, interval: interval, object: self, &proc)
159
157
 
@@ -176,22 +174,13 @@ module Watir
176
174
  #
177
175
 
178
176
  def wait_until_present(depr_timeout = nil, timeout: nil, interval: nil, message: nil)
179
- if depr_timeout
180
- Watir.logger.deprecate 'Using arguments for #wait_until_present', 'keywords', ids: [:timeout_arguments]
181
- timeout = depr_timeout
182
- end
183
- if is_a? Watir::Element
184
- message ||= proc { |obj| "waiting for element #{obj.inspect} to become present" }
185
- wait_until(timeout: timeout, interval: interval, message: message) do
186
- reset! if is_a? Watir::Element
187
- present?
188
- end
189
- else
190
- Watir.logger.deprecate "#{self.class}#wait_until_present",
191
- "#{self.class}#wait_until(&:present?)",
192
- ids: [:wait_until_present]
193
- wait_until(timeout: timeout, interval: interval, message: message, &:present?)
194
- end
177
+ timeout = depr_timeout if depr_timeout
178
+ Watir.logger.deprecate "#{self.class}#wait_until_present",
179
+ "#{self.class}#wait_until(&:present?)",
180
+ ids: [:wait_until_present]
181
+
182
+ message ||= proc { |obj| "waiting for #{obj.inspect} to become present" }
183
+ wait_until(timeout: timeout, interval: interval, message: message, &:present?)
195
184
  end
196
185
 
197
186
  #
@@ -210,31 +199,29 @@ module Watir
210
199
  #
211
200
 
212
201
  def wait_while_present(depr_timeout = nil, timeout: nil, interval: nil, message: nil)
213
- if depr_timeout
214
- Watir.logger.deprecate 'Using arguments for #wait_while_present', 'keywords', ids: [:timeout_arguments]
215
- timeout = depr_timeout
216
- end
217
- if is_a? Watir::Element
218
- message ||= proc { |obj| "waiting for element #{obj.inspect} not to be present" }
219
- wait_while(timeout: timeout, interval: interval, message: message) do
220
- reset! if is_a? Watir::Element
221
- present?
222
- end
223
- else
224
- Watir.logger.deprecate "#{self.class}#wait_while_present",
225
- "#{self.class}#wait_while(&:present?)",
226
- ids: [:wait_while_present]
227
- wait_while(timeout: timeout, interval: interval, message: message, &:present?)
228
- end
202
+ timeout = depr_timeout if depr_timeout
203
+ Watir.logger.deprecate "#{self.class}#wait_while_present",
204
+ "#{self.class}#wait_while(&:present?)",
205
+ ids: [:wait_while_present]
206
+
207
+ message ||= proc { |obj| "waiting for #{obj.inspect} not to be present" }
208
+ wait_while(timeout: timeout, interval: interval, message: message, &:present?)
229
209
  end
230
210
 
231
211
  private
232
212
 
233
213
  def create_proc(opt)
214
+ proc do
215
+ reset! if is_a?(Element)
216
+ (opt.empty? || match_attributes(opt).call) && (!block_given? || yield(self))
217
+ end
218
+ end
219
+
220
+ def match_attributes(opt)
234
221
  proc do
235
222
  opt.keys.all? do |key|
236
223
  expected = opt[key]
237
- actual = if is_a?(Watir::Element) && !respond_to?(key)
224
+ actual = if is_a?(Element) && !respond_to?(key)
238
225
  attribute_value(key)
239
226
  else
240
227
  send(key)