updated code to find search box by finding the box next to the go button since the control id was ambiguous
This commit is contained in:
@@ -93,15 +93,53 @@ def connect_main(ctrl, log):
|
|||||||
# PER-DRAWER EXPORT
|
# PER-DRAWER EXPORT
|
||||||
# ---------------------------------------------------------------------------
|
# ---------------------------------------------------------------------------
|
||||||
|
|
||||||
def navigate_to_drawer(main, drawer_id, ctrl, timeouts, log):
|
def find_search_box(main, ctrl, timeouts, log):
|
||||||
"""Type the drawer ID into the search box and click Go."""
|
"""Locate the drawer search box reliably using the Go button as an anchor.
|
||||||
# Use best_match name "Edit" instead of title — the title is placeholder
|
|
||||||
# text that changes once the user types in the box.
|
|
||||||
box = main["Edit"]
|
|
||||||
box.wait("visible ready", timeout=timeouts["nav"])
|
|
||||||
|
|
||||||
box.set_edit_text("")
|
The main window has several Edit controls (notably the data-location box
|
||||||
box.set_edit_text(drawer_id)
|
inside a ComboBox). Their best_match names ("Edit", "Edit0"...) are
|
||||||
|
unstable and the placeholder title only exists in a fresh session, so we
|
||||||
|
anchor off the Go button instead: the search box sits on the same row
|
||||||
|
(same top Y) as Go, immediately to its left. Call once before the drawer
|
||||||
|
loop — the returned wrapper stays valid for the window's lifetime.
|
||||||
|
"""
|
||||||
|
go = main.child_window(title=ctrl["go_button_title"], class_name="Button")
|
||||||
|
go.wait("visible ready", timeout=timeouts["nav"])
|
||||||
|
go_rect = go.rectangle()
|
||||||
|
|
||||||
|
edits = main.children(class_name="Edit")
|
||||||
|
if not edits:
|
||||||
|
edits = main.descendants(class_name="Edit")
|
||||||
|
|
||||||
|
tolerance = 10
|
||||||
|
candidates = [
|
||||||
|
e for e in edits
|
||||||
|
if abs(e.rectangle().top - go_rect.top) <= tolerance
|
||||||
|
]
|
||||||
|
if not candidates:
|
||||||
|
raise RuntimeError(
|
||||||
|
"Could not find the drawer search box (no Edit control on the "
|
||||||
|
"Go button's row). FCCS may not be on the main drawer view."
|
||||||
|
)
|
||||||
|
|
||||||
|
# If several share the row, pick the one whose right edge is closest to
|
||||||
|
# (and left of) the Go button — that's the box directly beside Go.
|
||||||
|
left_of_go = [e for e in candidates if e.rectangle().right <= go_rect.left]
|
||||||
|
pool = left_of_go if left_of_go else candidates
|
||||||
|
box = max(pool, key=lambda e: e.rectangle().right)
|
||||||
|
|
||||||
|
r = box.rectangle()
|
||||||
|
log(f" Search box located at {(r.left, r.top, r.right, r.bottom)} "
|
||||||
|
f"(Go button top={go_rect.top})")
|
||||||
|
return box
|
||||||
|
|
||||||
|
|
||||||
|
def navigate_to_drawer(main, search_box, drawer_id, ctrl, timeouts, log):
|
||||||
|
"""Type the drawer ID into the search box and click Go."""
|
||||||
|
search_box.wait("visible ready", timeout=timeouts["nav"])
|
||||||
|
|
||||||
|
search_box.set_edit_text("")
|
||||||
|
search_box.set_edit_text(drawer_id)
|
||||||
time.sleep(timeouts["settle"])
|
time.sleep(timeouts["settle"])
|
||||||
|
|
||||||
main.child_window(title=ctrl["go_button_title"], class_name="Button").click()
|
main.child_window(title=ctrl["go_button_title"], class_name="Button").click()
|
||||||
@@ -257,8 +295,8 @@ def wait_for_export(app, ctrl, timeouts, log):
|
|||||||
return True
|
return True
|
||||||
|
|
||||||
|
|
||||||
def export_drawer(app, main, drawer_id, ctrl, timeouts, screenshot_dir,
|
def export_drawer(app, main, search_box, drawer_id, ctrl, timeouts,
|
||||||
manifest_dir, log):
|
screenshot_dir, manifest_dir, log):
|
||||||
"""Full per-drawer sequence. Returns True on success."""
|
"""Full per-drawer sequence. Returns True on success."""
|
||||||
log(f"Drawer {drawer_id}: starting")
|
log(f"Drawer {drawer_id}: starting")
|
||||||
|
|
||||||
@@ -266,7 +304,7 @@ def export_drawer(app, main, drawer_id, ctrl, timeouts, screenshot_dir,
|
|||||||
dismiss_any_dialog(app, ctrl, log)
|
dismiss_any_dialog(app, ctrl, log)
|
||||||
|
|
||||||
# 1. Navigate
|
# 1. Navigate
|
||||||
if not navigate_to_drawer(main, drawer_id, ctrl, timeouts, log):
|
if not navigate_to_drawer(main, search_box, drawer_id, ctrl, timeouts, log):
|
||||||
take_screenshot(main, drawer_id, "nav_fail", screenshot_dir, log)
|
take_screenshot(main, drawer_id, "nav_fail", screenshot_dir, log)
|
||||||
return False
|
return False
|
||||||
|
|
||||||
@@ -364,6 +402,12 @@ def main():
|
|||||||
|
|
||||||
app, main_win = connect_main(ctrl, log)
|
app, main_win = connect_main(ctrl, log)
|
||||||
|
|
||||||
|
try:
|
||||||
|
search_box = find_search_box(main_win, ctrl, timeouts, log)
|
||||||
|
except Exception as e:
|
||||||
|
log(f"ERROR: {e}")
|
||||||
|
sys.exit(1)
|
||||||
|
|
||||||
success_count = 0
|
success_count = 0
|
||||||
fail_count = 0
|
fail_count = 0
|
||||||
failed_ids = []
|
failed_ids = []
|
||||||
@@ -371,8 +415,8 @@ def main():
|
|||||||
for i, drawer_id in enumerate(pending, start=1):
|
for i, drawer_id in enumerate(pending, start=1):
|
||||||
log(f"--- [{i}/{len(pending)}] Drawer {drawer_id} ---")
|
log(f"--- [{i}/{len(pending)}] Drawer {drawer_id} ---")
|
||||||
try:
|
try:
|
||||||
ok = export_drawer(app, main_win, drawer_id, ctrl, timeouts,
|
ok = export_drawer(app, main_win, search_box, drawer_id, ctrl,
|
||||||
paths["screenshot_dir"],
|
timeouts, paths["screenshot_dir"],
|
||||||
paths["manifest_dir"], log)
|
paths["manifest_dir"], log)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
log(f" UNEXPECTED ERROR on drawer {drawer_id}: {e}")
|
log(f" UNEXPECTED ERROR on drawer {drawer_id}: {e}")
|
||||||
|
|||||||
Reference in New Issue
Block a user