fix: 修复自绘颜色行安全点击误判 (#270)

This commit is contained in:
chengma
2026-08-18 16:40:47 +08:00
parent b538370171
commit e2ed00c38c
2 changed files with 78 additions and 1 deletions
+41 -1
View File
@@ -331,9 +331,49 @@ def _non_scrollable_target_region(
heading: Bounds,
screen: Bounds,
) -> Optional[Bounds]:
"""用目标卡片和下一规格标题界定非滚动颜色区域。"""
"""用目标卡片和下一规格标题界定非滚动颜色区域。
PDD 的部分自绘横向颜色行没有 ``scrollable`` 属性,颜色卡片会放在
一个整行可点击的父节点下。此时同一行的颜色选项可能刚好叫“款式”,
不能把它当作规格标题;优先使用该父级行作为区域,避免标题坐标误导。
"""
parents = _parent_map(root)
matching_nodes = [
(node, bounds)
for node in root.iter("node")
if _is_available(node) and _matches_target(node, target)
if (bounds := _parse_bounds(node.get("bounds", ""))) is not None
if _center_in(bounds, screen)
]
if matching_nodes:
target_node, target_bounds = max(
matching_nodes,
key=lambda item: (item[1][2] - item[1][0])
* (item[1][3] - item[1][1]),
)
target_height = target_bounds[3] - target_bounds[1]
row_candidates: list[Bounds] = []
current: Optional[ET.Element] = target_node
while current is not None:
bounds = _parse_bounds(current.get("bounds", ""))
if (
bounds is not None
and current.get("clickable") == "true"
and _is_available(current)
and _contains_bounds(bounds, target_bounds)
and bounds[2] - bounds[0] >= (screen[2] - screen[0]) * 0.60
and bounds[3] - bounds[1]
<= max(180, target_height * 3)
):
row_candidates.append(bounds)
current = parents.get(current)
if row_candidates:
return max(
row_candidates,
key=lambda item: (item[2] - item[0]) * (item[3] - item[1]),
)
target_bounds = [
bounds
for node in root.iter("node")
+37
View File
@@ -263,6 +263,43 @@ class StaticColorSelectionTest(unittest.TestCase):
self.assertTrue(selected)
self.assertEqual(device.clicks, [(194, 1389)])
def test_non_scrollable_row_ignores_same_row_style_option_as_heading(self):
simplified = "纯欲莹白【透.视蕾丝衣.免脱款】"
traditional = "純欲瑩白【透.視蕾絲衣.免脫款】"
panel_xml = f'''<hierarchy>
<node bounds="[0,0][1080,2340]">
<node text="请选择:颜色 尺码" bounds="[36,950][1044,1000]" />
<node clickable="true" bounds="[0,1039][1080,1174]">
<node bounds="[36,1039][220,1174]">
<node text="{simplified}" bounds="[36,1081][216,1134]" />
</node>
<node bounds="[635,1039][1044,1174]">
<node text="款式" bounds="[639,1081][1044,1134]" />
</node>
</node>
<node text="尺码" bounds="[36,1200][126,1253]" />
</node>
</hierarchy>'''
device = StaticColorDevice(
panel_xml,
selected_text=simplified,
)
selected = select_color(
device,
panel_xml,
traditional,
action_delay=0.001,
)
self.assertTrue(selected)
self.assertEqual(device.swipes, [])
self.assertEqual(device.clicks, [(126, 1107)])
self.assertEqual(
color_selection_failure_reason(panel_xml, traditional),
"selection_unconfirmed",
)
def test_traditional_size_matches_unique_simplified_option(self):
simplified = "均码【40.0-60.0公斤】"
traditional = "均碼【40.0-60.0公斤】"