def get_hwnd(self): window_name = 'NanoDrive Innova Tapping' innova_hwnd = win32gui.FindWindow(None, window_name) hwnd = innova_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) z_position_hwnd = 0 z_offset_hwnd = 0 for hwnd_child in hwndChildList: name = win32gui.GetWindowText(hwnd_child) if name == 'z_position': z_position_hwnd = hwnd_child elif name == 'z_offset': z_offset_hwnd = hwnd_child hwnd = z_position_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.z_position_hwnd = hwndChildList[3] hwnd = z_offset_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.z_offset_button_hwnd = hwndChildList[0] self.z_offset_text_hwnd = hwndChildList[2] self.z_offset_Button = ButtonWrapper(self.z_offset_button_hwnd) self.z_Edit = EditWrapper(self.z_offset_text_hwnd)
def get_button_status(self, hwnd): """ img button for WEISS """ btn = ButtonWrapper(hwnd) #log.debug(dir(btn)) #log.debug(btn.SendMessage(BM_GETSTATE)) #log.debug(btn.SendMessage(BM_GETIMAGE)) #fn = "%s.png" % int(time.time()) img = btn.CaptureAsImage() conf = { 'p1': (39, 42), 'p2': (36, 46), 'p3': (20, 11), "green": (0, 255, 0), "white": (255, 255, 255), "p": (198, 198, 198) } self.conf.update(conf) left = 1 top = 1 ### check visiable if left > 0 and top > 0: pass ### green rgb1 = im.getpixel(self.p1) ### white rgb2 = im.getpixel(self.p2) ### rgb3 = im.getpixel(self.p3) #assert rgb1 == self.conf['green'] if rgb1 == self.conf['green'] and rgb3 == self.conf['p']: ### running return True if rgb2 == self.conf['white'] and rgb3 == self.conf['p']: ### stoped return False
def work3(conf): """ ['CaptureAsImage', 'Check', 'CheckByClick', 'CheckByClickInput', 'Children', 'Class', 'Click', 'ClickInput', 'ClientRect', 'ClientRects', 'ClientToScreen', 'Close', 'CloseAltF4', 'CloseClick', 'ContextHelpID', 'ControlCount', 'ControlID', 'DebugMessage', 'DoubleClick', 'DoubleClickInput', 'DragMouse', 'DragMouseInput', 'DrawOutline', 'ExStyle', 'Font', 'Fonts', 'FriendlyClassName', 'GetActive', 'GetCheckState', 'GetFocus', 'GetProperties', 'GetShowState', 'GetToolbar', 'HasExStyle', 'HasStyle', 'IsActive', 'IsChild', 'IsDialog', 'IsEnabled', 'IsUnicode', 'IsVisible', 'Maximize', 'Menu', 'MenuItem', 'MenuItems', 'MenuSelect', 'Minimize', 'MoveMouse', 'MoveMouseInput', 'MoveWindow', 'NotifyParent', 'Owner', 'Parent', 'PopupWindow', 'PostCommand', 'PostMessage', 'PressMouse', 'PressMouseInput', 'ProcessID', 'Rectangle', 'ReleaseMouse', 'ReleaseMouseInput', 'Restore', 'RightClick', 'RightClickInput', 'Scroll', 'SendCommand', 'SendMessage', 'SendMessageTimeout', 'SetApplicationData', 'SetCheckIndeterminate', 'SetFocus', 'SetTransparency', 'SetWindowText', 'Style', 'Texts', 'TopLevelParent', 'TypeKeys', 'UnCheck', 'UncheckByClick', 'UncheckByClickInput', 'UserData', 'VerifyActionable', 'VerifyEnabled', 'VerifyVisible', 'WheelMouseInput', 'WindowText', '_NeedsImageProp', '__class__', '__delattr__', '__dict__', '__doc__', '__eq__', '__format__', '__getattribute__', '__hash__', '__init__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_as_parameter_', '_cache', '_menu_handle', '_scroll_types', 'actions', 'appdata', 'can_be_label', 'friendlyclassname', 'handle', 'has_title', 'ref', 'windowclasses', 'writable_props'] """ hwnd = 0x00250234 btn = ButtonWrapper(hwnd) #log.debug(dir(btn)) log.debug(btn.SendMessage(BM_GETSTATE)) #log.debug(btn.SendMessage(BM_GETIMAGE)) #fn = "%s.png" % int(time.time()) #btn.CaptureAsImage(fn) log.debug(btn.Style()) log.debug(btn.NotifyParent("1")) log.debug(btn.ref) #log.debug(btn.GetProperties().keys()) d = btn.GetProperties() img = d['Image'] #btn.SetWindowText("BTN") fn = "%s.jpg" % (int(time.time())) #img.save(fn) for item in d: try: #print(item) , #print "--", pass #print(d[item]) except: #log.debug(traceback.format_exc()) log.debug("======== %s =========" % item)
def data_loading(app, file_path_variable): # from pywinauto.controls.win32_controls import ComboBoxWrapper # from pywinauto.controls.uia_controls import ToolbarWrapper time.sleep(30) # click on the loading button app.window(best_match='National Roads Condition Database - Version*', top_level_only=True)\ .child_window(best_match='Loading').click() # if the file_path_variable directory contains a file 'BatchList' use the 'Select Batch File' # else use 'Create Batch file' if os.path.isfile(file_path_variable + '/BatchList.txt'): filename = file_path_variable + '/BatchList.txt' print("\nfile name exists using Select", filename) time.sleep(30) app.window(best_match='National Roads Condition Database - Version', top_level_only=True) \ .child_window(best_match='Select Batch file').click() filename = filename.replace('/', '\\') print("\nfile exists", filename) time.sleep(15) # check existence of the app2 variable if it is there destroy it as connecting to the file selection # is going to create it and it could get messy if it's still there from processing the previous LA. try: app2 except NameError: print('app2 not used') else: del app2 # Connect to the selection window and enter the batch file name. app2 = Application(backend="uia").connect( title_re='Select a batch file', visible_only=True) print("\nConnect app2 filename is ", filename) app2.window(title_re='Select a batch file') \ .File_name_Edit.set_text(filename) time.sleep(15) batch_split_button2 = app2.window(title_re='Select a batch file') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_split_button2).click() del app2 else: # else pick the first .hmd file and use 'Create Batch File' print("\nBatchfile file missing") time.sleep(30) # app.window(best_match='National Roads Condition Database - Version', top_level_only=True).child_window( # best_match='OK').click() app.window(best_match='National Roads Condition Database - Version', top_level_only=True) \ .child_window(best_match='Create Batch file').click() # filename = filename.replace('/', '\\') # print("\nfile exists", filename) # time.sleep(15) # app2 = Application(backend="uia").connect(title_re='Select a batch file', visible_only=True) # print("\nConnect app2 filename is ", filename) file_search_variable = (file_path_variable + '/*.hmd').replace( '/', '\\') print("\nfile_search_variable = ", file_search_variable) filename = glob.glob(file_search_variable) # filename = filename[0] print("\nFile found : ", filename) filename = filename[1].replace('/', '\\') time.sleep(20) # click on 'Create Batch File' then OK on the following window # app.window(best_match='National Roads Condition Database') \ # .child_window(best_match='Create Batch file').click() time.sleep(30) app.window(best_match='National Roads Condition Database') \ .child_window(title='NRCD').OK.click() # app.window(best_match='National Roads Condition Database Version *') \ # .child_window(best_match='OK').click() time.sleep(30) # There will be a file selection window. Connect to it (it's not part of NRCD) # So it's a new application. # # But first if app3 is already there get rid of it first. try: app3 except NameError: print('app3 not used') else: del app3 app3 = Application(backend="uia").connect( title='Create a file in the required directory') print("\nconnect app3") time.sleep(15) # edit_text_box2 = app3.window(title_re='Select a batch file') \ # .child_window(best_match="File name:") # from pywinauto.controls.win32_controls import EditWrapper # EditWrapper(edit_text_box2).set_text(filename) # app.window(best_match='National Roads Condition Database - Version *') \ # .child_window(best_match='NRCD') \ # .child_window(best_match='OK').click() # put the filename that was found into the filename box # app3.window(title_re='Create a file in the required directory').print_control_identifiers() app3.window(title_re='Create a file in the required directory') \ .File_name_Edit.set_text(filename) # Click on the open button, this is a bit more involved so that it works with a locked screen. batch_split_button1 = app3.window(title_re='Create a file in the required directory') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_split_button1).click() # remove references to the window where the filename was entered as it will use # the same variable next time round (next LA) del app3 # if the file_path_variable directory string contains WDM if "WDM" in file_path_variable: # then Survey Contractor = WDM survey_contractor: str = "WDM" # else if the directory string contains 'G-L' select survey contractor 'Ginger-Lehmann' elif "G-L" in file_path_variable: survey_contractor: str = "Ginger-Lehmann" # else if the directory string contains 'PTS' select survey contractor 'Ginger-Lehmann' elif "PTS" in file_path_variable: survey_contractor: str = "PTS" # it's not one of those we know about. Should another contractor start surveying then add another 'elif' else: survey_contractor = "Unknown contractor" print(survey_contractor) from pywinauto.controls.win32_controls import ComboBoxWrapper surveyor_combobox = app.window(best_match='National Roads Condition Database') \ .child_window(best_match='Survey Contractor', control_type='Group') \ .child_window(auto_id="3", control_type="ComboBox") ComboBoxWrapper(surveyor_combobox).select(survey_contractor) # click 'OK' to close the data loading window as we have all the appropriate details entered in the window. app.window(best_match='National Roads Condition Database') \ .child_window(best_match='OK').click() # back on the NRCD main screen, click the process radio button then the actual 'Process' button app.window(best_match='National Roads Condition Database - Version *', top_level_only=True).child_window(best_match='Process').click() # The log entry contains the first file to be loaded (the rest will not appear and NRCD uses the # batchfile to find them logger.info('Starting loading with ' + filename) time.sleep(60) # wait for the loading to finish. It checks the number of windows open for NECD.exe. If these are less than # two the section is complete, otherwise it loops. while nrcd_running_check('2'): logger.info('waiting for loading to complete') time.sleep(300) logger.info('loading completed') return # back to main
def scanner_qa(app, file_path_variable): from pywinauto.controls.win32_controls import ComboBoxWrapper from pywinauto.controls.win32_controls import ButtonWrapper import re # there is a regex search below ! time.sleep(150) main_screen = app.window( best_match='National Roads Condition Database - V*') # turn all the process check boxes off. main_screen_process_checkbox = main_screen.child_window( title="Process", auto_id="15", control_type="CheckBox") main_screen_process_checkbox2 = main_screen.child_window( title="Process", auto_id="16", control_type="CheckBox") main_screen_process_checkbox3 = main_screen.child_window( title="Process", auto_id="17", control_type="CheckBox") main_screen_process_checkbox4 = main_screen.child_window( title="Process", auto_id="18", control_type="CheckBox") time.sleep(60) ButtonWrapper(main_screen_process_checkbox).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox2).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox3).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox4).uncheck_by_click() filename = file_path_variable.replace('/', '\\') print(filename) # time.sleep(15) # use the location of the file_path_variable to extract the local authority, nation and year. local_authority = filename.split("\\")[-1] nation = filename.split("\\")[-2] year: str = re.search('[1-2][0-9]{3}', filename).group(0) # regex search # logger.info('starting Scanner QA output for ' + local_authority) # print(local_authority) print(nation) print(year) logger.info('starting SCANNER QA for ' + local_authority) # Load the human name to database name csv table lookup_table_filename = '//trllimited/data/INF_ScannerQA/Audit_Reports/Tools/LA_to_NRCD_Name.csv' la_lookup_table = pd.read_csv(lookup_table_filename, index_col='Audit_Report_name', dtype={'INDEX': str}) la_db_name: str = la_lookup_table.loc[local_authority, "NRCD_Name"] # enter the Scanner QA section of NRCD and wait for the Survey QA options group to exist. app.window( best_match='National Roads Condition Database', top_level_only=True).child_window(best_match='Scanner QA').click() time.sleep(30) app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="Survey QA Options", auto_id="9", control_type="Group") \ .wait("exists ready", timeout=90, retry_interval=60) group_control = app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="Survey QA Options", auto_id="9", control_type="Group") # group_control.print_control_identifiers() # exclude the previous year and the U roads (uncheck_by_click) then select the LA abd survey year. ButtonWrapper( group_control.child_window( title="Include Previous Year", control_type="CheckBox")).uncheck_by_click() ButtonWrapper( group_control.child_window( title="U Roads", control_type="CheckBox")).uncheck_by_click() ComboBoxWrapper( group_control.child_window(auto_id="24", control_type="ComboBox")).select(la_db_name) ComboBoxWrapper( group_control.child_window(auto_id="25", control_type="ComboBox")).select(" 2021/22") # Export the data group_control.child_window(auto_id="26", title="Export QA Data").click() # build output file name. # LIVE # output_file_name = os.path.normpath("//trllimited/data/INF_ScannerQA/Audit_Reports/NRCD Data/" + nation + "/" + # local_authority + "_" + year + ".csv") # test output_file_name = os.path.normpath("C:/Users/rjaques/temp/Data/" + nation + "/" + local_authority + "_" + year + ".csv") # add the year combination (year and '-' and 2 digit next year so # convert year string to numeric, add one, convert back to string and use the last 2 chars print(year) print(int(year)) print(int(year) + 1) print(str(int(year) + 1)) next_year = str(int(year) + 1)[-2:] print(next_year) survey_period = year + '-' + next_year print(survey_period) print(output_file_name) time.sleep(60) # connect to the output file name selection window and enter the name from above and save the file. app5 = Application(backend="uia").connect( title_re='Select an output file name', visible_only=True) print("\nConnect app5 filename is ", output_file_name) time.sleep(30) # app5.window(title_re='Select an output file name').print_control_identifiers() # split output_file_name into the directory path and the filename (because Mickysoft has changed the window !) # directory_path = os.path.dirname(output_file_name) # app5.window(title_re='Select an output file name') \ # .Toolbar4_Edit.set_text(directory_path) # selected_filename = os.path.basename(output_file_name) app5.window(title_re='Select an output file name') \ .File_name_Edit.set_text(output_file_name) # app5.window(title_re='Select an output file name').File_name_Edit.set_text(output_file_name) # app5.window(title_re='Select an output file name').print_control_identifiers() batch_split_button1 = app5.window(title_re='Select an output file name') \ .child_window(title='Save', auto_id='1', control_type="Button") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_split_button1).click() # app5.window(title_re='Select an output file name').type_keys(output_file_name, with_spaces=True) # app5.window(title_re='Select an output file name').Save.click() del app5 time.sleep(60) logger.info('waiting for ' + local_authority + ' QA output to finish') app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="NRCD") \ .wait("exists ready", timeout=10000, retry_interval=60) # app.window(best_match='National Roads Condition Database - Version *') \ # .child_window(title="NRCD") \ # .print_control_identifiers() app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="NRCD").OK.click() # Wait patiently # while nrcd_running_check("2"): # logger.info('waiting for ' + local_authority + 'QA output to finish') # time.sleep(90) logger.info(local_authority + ' QA output complete') return # back to main code block
def assign_urb_rural(app): from pywinauto.controls.win32_controls import ComboBoxWrapper from pywinauto.controls.win32_controls import ButtonWrapper time.sleep(60) main_screen = app.window( best_match='National Roads Condition Database - V*') time.sleep(60) # on the main screen turn all the check boxes off. main_screen_process_checkbox = main_screen.child_window( title="Process", auto_id="15", control_type="CheckBox") main_screen_process_checkbox2 = main_screen.child_window( title="Process", auto_id="16", control_type="CheckBox") main_screen_process_checkbox3 = main_screen.child_window( title="Process", auto_id="17", control_type="CheckBox") main_screen_process_checkbox4 = main_screen.child_window( title="Process", auto_id="18", control_type="CheckBox") time.sleep(60) ButtonWrapper(main_screen_process_checkbox).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox2).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox3).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox4).uncheck_by_click() del main_screen_process_checkbox del main_screen_process_checkbox2 del main_screen_process_checkbox3 del main_screen_process_checkbox4 logger.info('starting urban & rural attributes') time.sleep(30) # start the attributes section. app.window( best_match='National Roads Condition Database', top_level_only=True).child_window(best_match='Attributes').click() time.sleep(30) # to set the urban rural attribute the selections are all made in the 'Attributes Options' part of the window. # wait for it to exist. app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="Attributes Options", auto_id="12", control_type="Group") \ .wait("exists ready", timeout=90, retry_interval=60) # set groupcontrol to that part of the window. group_control = app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="Attributes Options", auto_id="12", control_type="Group") # groupcontrol.print_control_identifiers() # Select SCANNER and the survey year and click on OK ComboBoxWrapper(group_control.child_window(auto_id="14", control_type="ComboBox")) \ .select("SCANNER") ComboBoxWrapper(group_control.child_window(auto_id="15", control_type="ComboBox"))\ .select(" 2021/22") app.window(best_match='National Roads Condition Database').child_window( best_match='OK').click() # back to the main window where the process click box is already set by the NRCD prog and it's waiting # for the process button at the bottom to be clicked. main_screen.Process.click() time.sleep(60) # after an appropriate time start waiting for the processing to finish. # wait for the window to close. It checks the number of windows open for NECD.exe. If these are less than # two the section is complete, otherwise it loops. while nrcd_running_check('2'): logger.info('waiting for Urban/Rural Attributes to complete') time.sleep(300) logger.info('U/R attributes complete') return # to the main code block
def fitting(app): from pywinauto.controls.win32_controls import ComboBoxWrapper from pywinauto.controls.win32_controls import ButtonWrapper # from pywinauto.controls import uia_controls # from pywinauto.controls import common_controls # Turn all the process radio buttons off. main_screen_process_checkbox = main_screen.child_window( title="Process", auto_id="15", control_type="CheckBox") main_screen_process_checkbox2 = main_screen.child_window( title="Process", auto_id="16", control_type="CheckBox") main_screen_process_checkbox3 = main_screen.child_window( title="Process", auto_id="17", control_type="CheckBox") main_screen_process_checkbox4 = main_screen.child_window( title="Process", auto_id="18", control_type="CheckBox") ButtonWrapper(main_screen_process_checkbox).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox2).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox3).uncheck_by_click() ButtonWrapper(main_screen_process_checkbox4).uncheck_by_click() del main_screen_process_checkbox del main_screen_process_checkbox2 del main_screen_process_checkbox3 del main_screen_process_checkbox4 logger.info('starting fitting') time.sleep(30) # click fitting to start the next section app.window(best_match='National Roads Condition Database', top_level_only=True).child_window(best_match='Fitting').click() time.sleep(10) # set the check boxes for fitting the data using a grid. ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="Fit unfitted data", auto_id="22", control_type="RadioButton")) \ .check_by_click() ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="Fit using a grid", auto_id="14", control_type="RadioButton")) \ .check_by_click() ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="SCANNER", auto_id="7", control_type="RadioButton")) \ .check_by_click() # and set the survey year batch_combobox24 = app.window(best_match='National Roads Condition Database - Version*') \ .child_window(best_match='Year options:', auto_id="21", control_type="Group") \ .child_window(auto_id='24', control_type="ComboBox") ComboBoxWrapper(batch_combobox24).select(" 2021/22") time.sleep(5) # with everything set click the OK button to return to the main window. main_screen.child_window(title="OK", auto_id="11", control_type="Button").click() time.sleep(60) # the 'process' click box is already set so click on the main screen Process button at the bottom # then wait for the fitting to complete. main_screen.Process.click() time.sleep(600) # wait for the loading to finish. It checks the number of windows open for NECD.exe. If these are less than # two the section is complete, otherwise it loops. while nrcd_running_check('2'): logger.info('waiting for Fitting to complete') time.sleep(300) logger.info('fitting complete') time.sleep(60) # go back to the main code block. return
def assign_la(app, file_path_variable): logger.info('starting local authority assignment') time.sleep(60) app.window( best_match='National Roads Condition Database', top_level_only=True).child_window(best_match='Attributes').click() time.sleep(15) group_control = app.window(best_match='National Roads Condition Database - Version *') \ .child_window(title="Local Authority Attribute", auto_id="3", control_type="Group") group_control.child_window(title="Select Batch File", auto_id="7", control_type="Button") \ .click() time.sleep(30) # app.window(best_match='National Roads Condition Database') \ # .child_window(title='NRCD').OK.click() # app.window(best_match='National Roads Condition Database - Version *') \ # .child_window(title="Local Authority Attribute", auto_id="3", control_type="Group") \ # .child_window(title="Select Batch File", auto_id="7", control_type="Button") \ # .click() filename = file_path_variable + '/BatchList.txt' print("\nfilename is ", filename) logger.info('File name is ' + filename) filename = filename.replace('/', '\\') time.sleep(15) app4 = Application(backend="uia").connect(title_re='Select a batch file', visible_only=True) print("\nConnect app4 filename is ", filename) logger.info('Connecting to the batch file selection with ' + filename) time.sleep(60) # split filename into the directory path and the filename (because Mickysoft has changed the window !) # directory_path = os.path.dirname(filename) # app4.window(title_re='Select a batch file') \ # .Toolbar4_Edit.set_text(directory_path) # selected_filename = os.path.basename(filename) app4.window(title_re='Select a batch file') \ .File_name_Edit.set_text(filename) # app4.window(title_re='Select a batch file').File_name_Edit.set_text(filename) # app4.window(title_re='Select a batch file').print_control_identifiers() # app4.window(title_re='Select a batch file').type_keys('%o') batch_splitbutton1 = app4.window(title_re='Select a batch file') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_splitbutton1).click() time.sleep(60) del app4 # use the location of the BatchList.txt to extract the local authority. It's two from the end. local_authority = filename.split("\\")[-2] # print(local_authority) logger.info('starting to assign attributes for ' + local_authority) # Load the human name to database name csv table lookup_table = '//trllimited/data/INF_ScannerQA/Audit_Reports/Tools/LA_to_NRCD_Name.csv' la_lookup_table = pd.read_csv(lookup_table, index_col='Audit_Report_name', dtype={'INDEX': str}) la_db_name: str = la_lookup_table.loc[local_authority, "NRCD_Name"] logger.info('DB name for the LA is ' + la_db_name) # app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Local Authority Attribute', control_type="Group").print_control_identifiers() time.sleep(15) # app.window(best_match='National Roads Condition Database - Version *') \ # .child_window(title="Local Authority Attribute", control_type="Group") \ # .child_window(best_match='3',control_type="ComboBox").type_keys("%{DOWN}") # app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Local Authority Attribute', control_type="Group") \ # .child_window(auto_id='6', control_type="ComboBox").select(la_db_name) # print(la_db_name) batch_combobox1 = app.window(best_match='National Roads Condition Database - Version*') \ .child_window(best_match='Local Authority Attribute', control_type="Group") \ .child_window(auto_id='6', control_type="ComboBox").wait('exists enabled visible ready') import pywinauto.controls.win32_controls pywinauto.controls.win32_controls.ComboBoxWrapper(batch_combobox1).select( la_db_name) batch_combobox2 = app.window(best_match='National Roads Condition Database - Version*') \ .child_window(best_match='Local Authority Attribute', control_type="Group") \ .child_window(auto_id='4', control_type="ComboBox") # .wait('exists enabled visible ready') pywinauto.controls.win32_controls.ComboBoxWrapper(batch_combobox2).select( " 2021/22") time.sleep(15) # print(survey_year) app.window(best_match='National Roads Condition Database - Version*') \ .child_window(title="Assign Local Authority", auto_id="5", control_type="Button") \ .click() logger.info('waiting for LA assignment to complete') time.sleep(60) # the following contains 10000 seconds. This is to stop the wait timing out, it retries each 90 secs # but the attributes should be finished in under 6 hours... or even one hour. app.window(best_match='National Roads Condition Database - Version*') \ .child_window(title='NRCD', control_type="Window") \ .child_window(title="OK", auto_id="2", control_type="Button") \ .wait("exists ready", timeout=10000, retry_interval=90) time.sleep(120) app.window(best_match='National Roads Condition Database - Version*') \ .child_window(title='NRCD', control_type="Window") \ .child_window(title="OK", auto_id="2", control_type="Button").click() time.sleep(60) app.window(best_match='National Roads Condition Database - Version*') \ .child_window(title="Exit", auto_id="11", control_type="Button").click() return
class MainWindow(QMainWindow): def __init__(self): super().__init__() self.initUI() def initUI(self): self.current_dir = os.path.abspath(__file__).replace('\\', '/') self.current_dir = get_folder_from_file(self.current_dir) self.current_dir += 'support_files/' #self.afp_dir, self.afp, self.bfp_dir, self.bfp = load_known() print(self.current_dir) self.get_hwnd() self.scan_speed = 1 self.total_range = 20 self.font = cv2.FONT_HERSHEY_SIMPLEX self.mouse_pos_initial() self.canvas_blank = np.zeros((512, 512), dtype=np.int8) exitAct = QAction(QIcon(self.current_dir + 'quit.png'), '&Quit', self) exitAct.setShortcut('Ctrl+Q') exitAct.triggered.connect(qApp.quit) help_contact = QAction(QIcon(self.current_dir + 'email.png'), 'Contact', self) help_contact.triggered.connect(self.contact) help_about = QAction('About', self) help_about.triggered.connect(self.about) self.menubar = self.menuBar() FileMenu = self.menubar.addMenu('&File') FileMenu.addAction(exitAct) HelpMenu = self.menubar.addMenu('&Help') HelpMenu.addAction(help_contact) HelpMenu.addAction(help_about) self.read_button = QToolButton() self.read_button.setIcon(QIcon(self.current_dir + 'read.png')) self.read_button.setToolTip('Read Ctrl+R') self.read_button.clicked.connect(self.read) self.read_button.setShortcut('Ctrl+R') self.select_button = QToolButton() self.select_button.setIcon(QIcon(self.current_dir + 'select.png')) self.select_button.setToolTip('Select') self.select_button.clicked.connect(self.select_move_shape) self.select_button.setCheckable(True) self.select = False self.selecting = False self.select_rec = Rectangle() self.cursor_on_select = False self.moving = False self.move_start = [0, 0] self.move_end = [0, 0] self.drag_button = QToolButton() self.drag_button.setIcon(QIcon(self.current_dir + 'drag.png')) self.drag_button.setToolTip('Move') self.drag_button.clicked.connect(self.drag_shape) self.draw_shape_action_list = [] self.draw_shape_list = [] self.draw_shape_action_list_for_redo = [] self.draw_shape_count = 1 self.line_button = QToolButton() self.line_button.setIcon(QIcon(self.current_dir + 'line.png')) self.line_button.setToolTip('Draw line') self.line_button.clicked.connect(self.draw_line) self.line_button.setCheckable(True) self.draw_shape_line = False self.drawing_shape_line = False self.show_distance = False self.grating_button = QToolButton() self.grating_button.setIcon(QIcon(self.current_dir + 'grating.png')) self.grating_button.setToolTip('Grating') self.grating_button.clicked.connect(self.draw_grating) # line = Line(0,0,100,100) self.eraser_button = QToolButton() self.eraser_button.setIcon(QIcon(self.current_dir + 'eraser.png')) self.eraser_button.setToolTip('eraser') self.eraser_button.clicked.connect(self.erase_shape) self.eraser_button.setCheckable(True) self.erase = False self.drawing_eraser = False self.undo_button = QToolButton() self.undo_button.setIcon( QIcon(self.current_dir + 'undo_gray_opacity.png')) self.undo_button.setToolTip('undo Ctrl+Z') self.undo_button.clicked.connect(self.undo_draw) self.undo_button.setShortcut('Ctrl+Z') self.redo_button = QToolButton() self.redo_button.setIcon( QIcon(self.current_dir + 'redo_gray_opacity.png')) self.redo_button.setToolTip('redo Ctrl+Y') self.redo_button.clicked.connect(self.redo_draw) self.redo_button.setShortcut('Ctrl+Y') self.clear_button = QToolButton() self.clear_button.setIcon(QIcon(self.current_dir + 'clear.png')) self.clear_button.setToolTip('clear drawing') self.clear_button.clicked.connect(self.clear_draw) self.run_button = QToolButton() self.run_button.setIcon(QIcon(self.current_dir + 'run.png')) self.run_button.setToolTip('Run F5') self.run_button.clicked.connect(self.run_cut) self.run_button.setShortcut('F5') self.repeat_button = QToolButton() self.repeat_button.setIcon(QIcon(self.current_dir + 'repeat.png')) self.repeat_button.setToolTip('Repeat') self.repeat_button.clicked.connect(self.repeat_cut) self.stop_button = QToolButton() self.stop_button.setIcon(QIcon(self.current_dir + 'stop.png')) self.stop_button.setToolTip('Stop') self.stop_button.clicked.connect(self.stop_cut) self.toolbar1 = self.addToolBar('Read') self.toolbar1.addWidget(self.read_button) self.toolbar2 = self.addToolBar('Select') self.toolbar2.addWidget(self.select_button) self.toolbar2.addWidget(self.drag_button) self.toolbar3 = self.addToolBar('Draw') self.toolbar3.addWidget(self.line_button) self.toolbar3.addWidget(self.grating_button) self.toolbar3.addWidget(self.undo_button) self.toolbar3.addWidget(self.redo_button) self.toolbar3.addWidget(self.eraser_button) self.toolbar3.addWidget(self.clear_button) self.toolbar4 = self.addToolBar('Run') self.toolbar4.addWidget(self.run_button) self.toolbar4.addWidget(self.repeat_button) self.toolbar4.addWidget(self.stop_button) self.toolbar = self.addToolBar(' ') self.pixmap = QPixmap() self.lbl_main = QLabel(self) self.lbl_main.setAlignment(Qt.AlignTop) # self.lbl_main.setAlignment(Qt.AlignCenter) self.lbl_main.setPixmap(self.pixmap) self.lbl_main.setMouseTracking(True) self.vbox = QVBoxLayout() self.vbox.addWidget(self.lbl_main) self.central_widget = QWidget() self.central_widget.setMouseTracking(True) self.layout = QVBoxLayout(self.central_widget) self.setCentralWidget(self.central_widget) self.layout.addLayout(self.vbox) self.refresh_timer = QTimer() self.refresh_timer.timeout.connect(self.refresh_show) self.setMouseTracking(True) self.setWindowTitle('Auto Cut') self.show() def read(self): window_name = 'Scanning control' self.scan_control_hwnd = win32gui.FindWindow(None, window_name) if self.scan_control_hwnd == 0: window_name = 'Scanning control ( Lift Mode )' self.scan_control_hwnd = win32gui.FindWindow(None, window_name) # win32gui.ShowWindow(scan_control_hwnd, win32con.SW_MAXIMIZE) try: win32gui.SendMessage(self.scan_control_hwnd, win32con.WM_SYSCOMMAND, win32con.SC_RESTORE, 0) win32gui.SetForegroundWindow(self.scan_control_hwnd) except: print('Can not set foreground window ') time.sleep(0.5) hwnd = self.scan_control_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.frame_hwnd = 0 probe_position_hwnd = 0 for hwnd_child in hwndChildList: name = win32gui.GetWindowText(hwnd_child) if 'Scan Area' in name: self.frame_hwnd = hwnd_child self.total_range = float(name[11:-3]) print(self.total_range) elif name == 'probe_position': probe_position_hwnd = hwnd_child hwnd = probe_position_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.move_time_hwnd = hwndChildList[0] self.new_x_hwnd = hwndChildList[3] self.new_y_hwnd = hwndChildList[2] self.move_time_Edit = EditWrapper(self.move_time_hwnd) self.x_Edit = EditWrapper(self.new_x_hwnd) self.y_Edit = EditWrapper(self.new_y_hwnd) # run_hwnd = hwndChildList[3] # self.frame_hwnd = hwndChildList[54] # self.frame_hwnd = self.scan_control_hwnd ''' self.left, self.top, self.right, self.bottom = win32gui.GetWindowRect(self.frame_hwnd) print(self.left, self.top, self.right, self.bottom) self.screenshot = pyautogui.screenshot(region=[self.left,self.top,\ self.right-self.left,\ self.bottom-self.top]) self.screenshot = np.asarray(self.screenshot) ''' self.screenshot = cv2.imread( 'F:/Desktop2020.1.17/AutoCut/screenshot2.bmp') self.screenshot = cv2.cvtColor(self.screenshot, cv2.COLOR_BGR2RGB) self.crop_left, self.crop_top, self.crop_right, self.crop_bottom = find_region( self.screenshot) self.screenshot = self.screenshot[self.crop_top: self.crop_bottom, \ self.crop_left: self.crop_right] # self.img = cv2.cvtColor(np.asarray(self.img),cv2.COLOR_RGB2BGR) #self.read_z_pos() self.start_refresh() print('Read') def contact(self): QMessageBox.information(self, 'contact','Please contact [email protected] '+\ 'for support. Thanks!') def about(self): QMessageBox.information(self, 'About', 'AFM Auto Cut v1.0. '+ \ 'Proudly designed and created by Jingxu Xie(谢京旭).\n \n' 'Copyright © 2020 Jingxu Xie. All Rights Reserved.') def draw_shape_initial(self): self.line_button.setChecked(False) self.draw_shape_line = False self.drawing_shape_line = False self.select_button.setChecked(False) self.select = False self.selecting = False self.select_rec = Rectangle() self.cursor_on_select = False self.moving = False self.eraser_button.setChecked(False) self.erase = False self.drawing_eraser = False def draw_line(self): if self.line_button.isChecked(): self.draw_shape_initial() self.draw_shape_line = True self.line_button.setChecked(True) else: self.draw_shape_line = False self.drawing_shape_line = False self.line_button.setChecked(False) print('draw line') def select_move_shape(self): if self.select_button.isChecked(): self.draw_shape_initial() self.select = True self.select_button.setChecked(True) else: self.draw_shape_line = False self.select = False self.select_button.setChecked(False) print('select') def drag_shape(self): print('drag') def draw_grating(self): self.grating_property_widget = GratingProperty() self.grating_property_widget.confirmed.connect(self.creat_grating) self.grating_property_widget.show() print('grating') def creat_grating(self, s): if s == 'confirmed': total_width = float(self.grating_property_widget.total_width) total_height = float(self.grating_property_widget.total_height) lines = int(self.grating_property_widget.lines) standard_distance = self.img.shape[0] / self.total_range x1 = int((self.total_range - total_width) / 2 * standard_distance) y1 = int((self.total_range - total_height) / 2 * standard_distance) x2 = x1 + int(total_width / self.total_range * self.img.shape[0]) y2 = y1 + int(total_height / self.total_range * self.img.shape[1]) grating_temp = Grating(x1, y1, x2, y2, total_width = total_width, \ total_height = total_height, \ standard_distance = standard_distance,\ lines = lines, color = (0,255,0),\ num = self.draw_shape_count) self.draw_shape_count += 1 self.draw_shape_action_list.append(grating_temp) print('confirmed') self.grating_property_widget.close() def erase_shape(self): if self.eraser_button.isChecked(): self.draw_shape_initial() self.erase = True self.eraser_button.setChecked(True) else: self.erase = False self.eraser_button.setChecked(False) def undo_redo_setting(self): self.undo_button.setIcon(QIcon(self.current_dir + 'undo.png')) self.draw_shape_action_list_for_redo = [] self.redo_button.setIcon( QIcon(self.current_dir + 'redo_gray_opacity.png')) def undo_draw(self): if len(self.draw_shape_action_list) > 0: self.draw_shape_action_list_for_redo.append( self.draw_shape_action_list[-1]) self.redo_button.setIcon(QIcon(self.current_dir + 'redo.png')) self.draw_shape_action_list.pop() if len(self.draw_shape_action_list) == 0: self.undo_button.setIcon( QIcon(self.current_dir + 'undo_gray_opacity.png')) def redo_draw(self): if len(self.draw_shape_action_list_for_redo) > 0: self.draw_shape_action_list.append( self.draw_shape_action_list_for_redo[-1]) self.undo_button.setIcon(QIcon(self.current_dir + 'undo.png')) self.draw_shape_action_list_for_redo.pop() if len(self.draw_shape_action_list_for_redo) == 0: self.redo_button.setIcon( QIcon(self.current_dir + 'redo_gray_opacity.png')) def clear_draw(self): self.draw_shape_initial() self.draw_shape_action_list.append(Clear_All()) def mouse_pos_initial(self): self.mouse_x1, self.mouse_y1 = 0, 0 self.mouse_x2, self.mouse_y2 = 0, 0 self.mouse_x1_raw, self.mouse_y1_raw = 0, 0 self.mouse_x2_raw, self.mouse_y2_raw = 0, 0 self.mouse_pos_right = True def mousePressEvent(self, event): self.mouse_x1_raw = max(0, event.pos().x()) self.mouse_y1_raw = max(0, event.pos().y()) self.mouse_x2_raw, self.mouse_y2_raw = self.mouse_x1_raw, self.mouse_y1_raw self.mouse_pos_correct() if event.buttons() == Qt.LeftButton and self.draw_shape_line: if self.check_mouse_valid(): self.draw_shape_action_list.append(Line(self.mouse_x1, self.mouse_y1, \ self.mouse_x2, self.mouse_y2, \ color = (0,255,0),\ num = self.draw_shape_count,\ show_distance = self.show_distance)) self.draw_shape_count += 1 self.drawing_shape_line = True self.undo_redo_setting() elif event.buttons() == Qt.LeftButton and self.erase: if self.check_mouse_valid(): self.draw_shape_action_list.append(Eraser(self.mouse_x1, \ self.mouse_y1, num = [0])) self.drawing_eraser = True elif event.buttons( ) == Qt.LeftButton and self.select and not self.cursor_on_select: if self.check_mouse_valid(): self.select_rec = Rectangle(self.mouse_x1, self.mouse_y1,\ self.mouse_x2, self.mouse_y2,\ num = -1, color = (0,0,0), width = 2) self.selecting = True elif event.buttons() == Qt.LeftButton and self.cursor_on_select: self.move_start = [self.mouse_x1, self.mouse_y1] self.moving = True print(self.mouse_x1, self.mouse_y1) #print(self.get_pos_on_screen(769, 769)) def mouseMoveEvent(self, event): self.mouse_x2_raw = max(0, event.pos().x()) self.mouse_y2_raw = max(0, event.pos().y()) self.mouse_pos_correct() if self.drawing_shape_line and len(self.draw_shape_action_list) > 0: if self.check_mouse_valid(): self.draw_shape_action_list[-1].x2 = self.mouse_x2 self.draw_shape_action_list[-1].y2 = self.mouse_y2 self.draw_shape_action_list[-1].pos_refresh() elif self.drawing_eraser and len(self.draw_shape_action_list) > 0: if self.check_mouse_valid(): self.draw_shape_action_list[-1].x1 = self.mouse_x2 self.draw_shape_action_list[-1].y1 = self.mouse_y2 self.draw_shape_action_list[-1].pos_refresh() elif self.selecting: if self.check_mouse_valid(): self.select_rec.x2 = self.mouse_x2 self.select_rec.y2 = self.mouse_y2 self.select_rec.pos_refresh() elif self.select and not self.moving: x_temp, y_temp = Pos_in_Circle(self.mouse_x2, self.mouse_y2, 20) self.cursor_on_select = False for i in range(len(x_temp)): if x_temp[i] < self.canvas_blank.shape[1] and y_temp[ i] < self.canvas_blank.shape[0]: num = self.canvas_blank[y_temp[i], x_temp[i]] if num == -1: self.setCursor(Qt.SizeAllCursor) self.cursor_on_select = True break if not self.cursor_on_select: self.setCursor(Qt.ArrowCursor) if self.moving: self.move_end = [self.mouse_x2, self.mouse_y2] move_x = self.move_end[0] - self.move_start[0] move_y = self.move_end[1] - self.move_start[1] self.select_rec.x1 += move_x self.select_rec.x2 += move_x self.select_rec.y1 += move_y self.select_rec.y2 += move_y self.select_rec.pos_refresh() self.move_start = [self.mouse_x2, self.mouse_y2] def mouseReleaseEvent(self, event): # if self.mouse_x1_raw == self.mouse_x2_raw and self.mouse_y1_raw == self.mouse_y2_raw: # if self.drawing_shape_line: # self.draw_shape_action_list.pop() if event.button() == Qt.RightButton and self.drawing_shape_line: self.drawing_shape_line = False if len(self.draw_shape_action_list) > 0: self.draw_shape_action_list.pop() if event.button() == Qt.LeftButton and self.drawing_eraser: self.drawing_eraser = False if len(self.draw_shape_action_list[-1].num) == 1: self.draw_shape_action_list.pop() if event.button() == Qt.LeftButton and self.selecting: self.selecting = False elif event.button() == Qt.LeftButton and self.moving: self.moving = False def mouse_pos_correct(self): lbl_main_x = self.lbl_main.pos().x() lbl_main_y = self.lbl_main.pos().y() + self.menubar.height( ) + self.toolbar.height() self.mouse_x1 = self.mouse_x1_raw - lbl_main_x self.mouse_x2 = self.mouse_x2_raw - lbl_main_x self.mouse_y1 = self.mouse_y1_raw - lbl_main_y self.mouse_y2 = self.mouse_y2_raw - lbl_main_y def check_mouse_valid(self): if 1 <= self.mouse_x2 < self.img.shape[1] - 1 and \ 1 <= self.mouse_x2 < self.img.shape[1] - 1 and \ 1 <= self.mouse_y2 < self.img.shape[0] - 1 and \ 1 <= self.mouse_y2 < self.img.shape[0] - 1: return True else: return False def refresh_show(self): self.img = self.screenshot.copy() #self.canvas_blank = np.zeros((self.img.shape[0], self.img.shape[1]), dtype = int) if self.drawing_eraser: eraser_temp = self.draw_shape_action_list[-1] cv2.circle(self.img, *eraser_temp.pos, eraser_temp.size, \ eraser_temp.color, eraser_temp.width) cv2.circle(self.img, *eraser_temp.pos, eraser_temp.size, \ (0,0,0), 1) self.find_eraser_num() if len(self.draw_shape_action_list) > 0: self.generate_draw_shape_list() self.draw_shape_canvas() if self.select: cv2.rectangle(self.img, *self.select_rec.pos,\ self.select_rec.color, self.select_rec.width) x_temp, y_temp = Pos_of_Rec(*list(self.select_rec.pos[0]), \ *list(self.select_rec.pos[1])) self.canvas_blank = record_draw_shape(self.canvas_blank, \ np.array(x_temp), np.array(y_temp), \ self.select_rec.num) if not self.selecting: pass # x_temp, y_temp = Pos_in_Circle(self.mouse_x2, self.mouse_y2, 10) # on_rec = False # for i in range(len(x_temp)): # if x_temp[i] < self.canvas_blank.shape[1] and y_temp[i] < self.canvas_blank.shape[0]: # num = self.canvas_blank[y_temp[i], x_temp[i]] # if num == -1: # self.setCursor(Qt.SizeAllCursor) # on_rec = True # break # if not on_rec: # self.setCursor(Qt.ArrowCursor) self.show_on_screen() def generate_draw_shape_list(self): self.draw_shape_list = [] for action in self.draw_shape_action_list: if action.prop != 'eraser' and action.prop != 'clear': self.draw_shape_list.append(action) elif action.prop == 'eraser': i = 0 while i < len(self.draw_shape_list): if self.draw_shape_list[i].num in action.num: #print(action.num) self.draw_shape_list.pop(i) i -= 1 i += 1 if i == len(self.draw_shape_list): break elif action.prop == 'clear': self.draw_shape_list = [] def draw_shape_canvas(self): #目前canvas还没什么用,均可用img_show代替,但也可以先留着 self.canvas = np.zeros(self.img.shape, dtype=np.uint8) self.canvas_blank = np.zeros((self.img.shape[0], self.img.shape[1]), dtype=int) count = 1 if len(self.draw_shape_list) == 0: pass for shape in self.draw_shape_list: # shape.x1, shape.y1 = self.mouse_pos_ratio_change_line(shape.x1, shape.y1) # shape.x2, shape.y2 = self.mouse_pos_ratio_change_line(shape.x2, shape.y2) # shape.pos_refresh() if shape.prop == 'line' or shape.prop == 'base line': x_temp, y_temp = Pos_of_Line(*list(shape.pos[0]), *list(shape.pos[1])) self.canvas_blank = record_draw_shape(self.canvas_blank, \ np.array(x_temp), np.array(y_temp), \ shape.num) cv2.circle(self.img, shape.pos[0], 5, shape.color, 1) cv2.line(self.img, *shape.pos, shape.color, shape.width) cv2.putText(self.img, str(count), shape.pos[1], self.font, 0.7, \ shape.color, 1, cv2.LINE_AA) #print(self.get_distance(shape.pos[0][0], shape.pos[0][1],\ # shape.pos[1][0], shape.pos[1][1])) count += 1 if shape.show_distance: distance = self.calculate_distance(shape.x1, shape.y1, shape.x2, shape.y2) pos = (round((shape.x1 + shape.x2) / 2), round((shape.y1 + shape.y2) / 2)) cv2.putText(self.img, str(round(distance, 2)), pos, \ self.font, 0.7, (255,0,0), 1, cv2.LINE_AA) elif shape.prop == 'grating': cv2.putText(self.img, str(count), (shape.x2, shape.y2), self.font, 0.7, \ shape.color, 1, cv2.LINE_AA) count += 1 for grating in shape.grating_list: x_temp, y_temp = Pos_of_Line(*list(grating.pos[0]), *list(grating.pos[1])) self.canvas_blank = record_draw_shape(self.canvas_blank, \ np.array(x_temp), np.array(y_temp), \ shape.num) cv2.circle(self.img, grating.pos[0], 5, grating.color, 1) cv2.line(self.img, *grating.pos, grating.color, grating.width) def find_eraser_num(self): x_temp, y_temp = Pos_in_Circle(*list(self.draw_shape_action_list[-1].pos[0]), \ self.draw_shape_action_list[-1].size) for i in range(len(x_temp)): if x_temp[i] < self.canvas_blank.shape[1] and y_temp[ i] < self.canvas_blank.shape[0]: num = self.canvas_blank[y_temp[i], x_temp[i]] if num != 0: self.draw_shape_action_list[-1].num.append(num) break def start_refresh(self): self.refresh_timer.start(30) def show_on_screen(self): self.img_qi = QImage(self.img[:], self.img.shape[1], self.img.shape[0],\ self.img.shape[1] * 3, QImage.Format_RGB888) self.pixmap = QPixmap(self.img_qi) self.lbl_main.setPixmap(self.pixmap) def stop_cut(self): print('stop') def run_cut(self): draw_list_length = len(self.draw_shape_list) i = 0 while i < draw_list_length: shape = self.draw_shape_list[i] if shape.prop == 'grating': for grating in shape: shape_list = [shape] self.cutting(shape_list) else: shape_list = [shape] # shape_points = self.get_read_list(shape.pos[0][0], shape.pos[0][1],\ # shape.pos[1][0], shape.pos[1][1]) for j in range(i, draw_list_length - 1): shape_current = self.draw_shape_list[j] shape_next = self.draw_shape_list[j + 1] if shape_current.pos[1][0] == shape_next.pos[0][0] and \ shape_current.pos[1][1] == shape_next.pos[0][1]: # shape_points += self.get_read_list(shape_next.pos[0][0], shape_next.pos[0][1],\ # shape_next.pos[1][0], shape_next.pos[1][1]) shape_list.append(shape_next) i = j + 1 else: break #z_pos_read = self.read_z_on_line(shape_points) self.cutting(shape_list) #, z_pos_read) i += 1 # z_pos_read = self.read_z_on_line(shape.pos[0][0], shape.pos[0][1],\ # shape.pos[1][0], shape.pos[1][1]) # # self.cutting(shape.pos[0][0], shape.pos[0][1],\ # shape.pos[1][0], shape.pos[1][1],\ # z_pos_read) def get_hwnd(self): window_name = 'NanoDrive Innova Tapping' innova_hwnd = win32gui.FindWindow(None, window_name) hwnd = innova_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) z_position_hwnd = 0 z_offset_hwnd = 0 for hwnd_child in hwndChildList: name = win32gui.GetWindowText(hwnd_child) if name == 'z_position': z_position_hwnd = hwnd_child elif name == 'z_offset': z_offset_hwnd = hwnd_child hwnd = z_position_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.z_position_hwnd = hwndChildList[3] hwnd = z_offset_hwnd hwndChildList = [] win32gui.EnumChildWindows(hwnd, lambda hwnd, param: param.append(hwnd), hwndChildList) self.z_offset_button_hwnd = hwndChildList[0] self.z_offset_text_hwnd = hwndChildList[2] self.z_offset_Button = ButtonWrapper(self.z_offset_button_hwnd) self.z_Edit = EditWrapper(self.z_offset_text_hwnd) def drag_prob(self, x, y): self.x_Edit.set_text(str(x)) self.y_Edit.set_text(str(y)) win32api.SendMessage(self.new_y_hwnd, win32con.WM_CHAR, 13, 0) def read_z_pos(self): left, top, right, bottom = win32gui.GetWindowRect(self.z_position_hwnd) for i in range(5): screenshot = pyautogui.screenshot(region=[left+1,top+1,\ right-left-2,\ bottom-top-2]) screenshot = np.asarray(screenshot) ret, num = identify_num(screenshot, self.afp_dir, self.afp, self.bfp_dir, self.bfp) if ret: return True, num return False, num def set_offset(self, offset_number): self.z_Edit.set_text(str(round(offset_number, 4))) win32api.SendMessage(self.z_offset_text_hwnd, win32con.WM_CHAR, 13, 0) def cutting(self, shape_list, z_pos_read=[]): self.move_time_Edit.set_text(str(0.5)) win32api.SendMessage(self.move_time_hwnd, win32con.WM_CHAR, 13, 0) time.sleep(0.2) pos_x, pos_y = self.get_pos_on_screen(shape_list[0].pos[0][0], \ shape_list[0].pos[0][1]) self.drag_prob(pos_x, pos_y) time.sleep(0.6) for i in range(10): try: self.z_offset_Button.click() break except: time.sleep(0.1) time.sleep(0.5) text = 0 for i in range(26): text += 0.01 self.set_offset(text) time.sleep(0.2) # points = self.get_read_list(x1, y1, x2, y2) for shape in shape_list: distance = self.get_distance(shape.pos[0][0], shape.pos[0][1],\ shape.pos[1][0], shape.pos[1][1]) time_cut = self.scan_speed * distance #time_interval = time_cut/len(z_pos_read) time_cut = round(time_cut, 3) self.move_time_Edit.set_text(str(time_cut)) win32api.SendMessage(self.move_time_hwnd, win32con.WM_CHAR, 13, 0) #time.sleep(0.1) pos_x, pos_y = self.get_pos_on_screen(shape.pos[1][0], shape.pos[1][1]) self.drag_prob(pos_x, pos_y) #time.sleep(0.1) #self.z_offset_Button.click() #time.sleep(0.2) #time.sleep(time_cut-2) ''' for i in range(1, len(z_pos_read) + 1): if i < len(z_pos_read): diff = (int(z_pos_read[-i + -1]) - int(z_pos_read[-i]))/10000 else: diff = 0 text += diff print(text) self.set_offset(text) time.sleep(round(time_interval - 0.05, 6)) ''' ''' for i in range(1,len(points)+1): pos_x, pos_y = self.get_pos_on_screen(points[-i][0], points[-i][1]) self.drag_prob(pos_x, pos_y) time.sleep(0.4) if i < len(points): # if z_pos_read[i + 1] > z_pos_read[i]: diff = (int(z_pos_read[-i + -1]) - int(z_pos_read[-i]))/10000 else: diff = 0 text += diff print(text) #self.set_offset(text) #time.sleep(0.2) ''' for i in range(10): try: self.z_offset_Button.click() break except: time.sleep(0.1) time.sleep(0.2) self.move_time_Edit.set_text(str(0.5)) win32api.SendMessage(self.move_time_hwnd, win32con.WM_CHAR, 13, 0) time.sleep(0.5) def read_z_on_line(self, points): # points = self.get_read_list(x1, y1, x2, y2) z_pos_read = [] for point in points: pos_x, pos_y = self.get_pos_on_screen(point[0], point[1]) self.drag_prob(pos_x, pos_y) time.sleep(0.6) ret, z_temp = self.read_z_pos() print(z_temp) if ret: z_pos_read.append(z_temp) else: if len(z_pos_read) > 0: z_pos_read.append(z_pos_read[-1]) for i in range(len(points) - len(z_pos_read)): z_pos_read.append(z_pos_read[-1]) return z_pos_read def get_distance(self, x1, y1, x2, y2): total_pixel = self.img.shape[0] total_distance = self.total_range pixel = np.sqrt((x2 - x1)**2 + (y2 - y1)**2) distance = pixel / total_pixel * total_distance distance = round(distance, 2) return distance def get_pos_on_screen(self, x, y): x -= int((self.img.shape[1] / 2)) x_pos = self.get_distance(0, 0, x, 0) x_pos = round(x_pos, 4) if x < 0: x_pos = -x_pos y = -y y += int((self.img.shape[0]) / 2) y_pos = self.get_distance(0, 0, 0, y) y_pos = round(y_pos, 4) if y < 0: y_pos = -y_pos return x_pos, y_pos def get_read_list(self, x1, y1, x2, y2): x_temp, y_temp = Pos_of_Line(x1, y1, x2, y2) points = [[x1, y1]] x_start, y_start = x1, y1 for i in range(len(x_temp)): if self.get_distance(x_temp[i], y_temp[i], x_start, y_start) > 2: points.append([x_temp[i], y_temp[i]]) x_start, y_start = x_temp[i], y_temp[i] if points[-1][0] != x2 or points[-1][1] != y2: points.append([x2, y2]) return points def wait_cut(self): pass def repeat_cut(self): print('repeat cut')
def data_loading(app, file_path_variable): # from pywinauto.controls.win32_controls import ComboBoxWrapper # click on the loading button app.window(best_match='National Roads Condition Database - Version*', top_level_only=True).child_window(best_match='Loading').click() # if the file_path_variable directory contains a file 'BatchList' use the 'Select Batch File' # else use 'Create Batch file' if os.path.isfile(file_path_variable + '/BatchList.txt'): filename = file_path_variable + '/BatchList.txt' print("\nfile name exists using Select", filename) time.sleep(30) app.window(best_match='National Roads Condition Database - Version', top_level_only=True) \ .child_window(best_match='Select Batch file').click() filename = filename.replace('/', '\\') print("\nfile exists", filename) time.sleep(15) app2 = Application(backend="uia").connect( title_re='Select a batch file', visible_only=True) print("\nConnect app2 filename is ", filename) # edit_text_box1 = app2.window(title_re='Select a batch file') \ # .child_window(best_match="File name:") # from pywinauto.controls.win32_controls import EditWrapper # EditWrapper(edit_text_box1).set_text(filename) # app2.window(title_re='Select a batch file').type_keys(filename, with_spaces=True) app2.window( title_re='Select a batch file').File_name_Edit.set_text(filename) # app2.window(title_re='Select a batch file').print_control_identifiers() # app2.window(title_re='Select a batch file').type_keys('%o') batch_split_button2 = app2.window(title_re='Select a batch file') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_split_button2).click() # app2.window(title_re='Select a batch file').OpenSplitButton.click_input # app2.window(title_re='Select a batch file') \ # .child_window(title='Pane1') \ # .child_window(title='Open', auto_id=1).click() # .child_window(title='Open', auto_id=1, control_type="UIA_SplitButtonControlTypeId").click() # .child_window(title='SplitButton6').click() del app2 else: # else pick the first .hmd file and use 'Create Batch File' print("\nBatchfile file missing") # app.window(best_match='National Roads Condition Database - Version', top_level_only=True).child_window( # best_match='OK').click() #filename = filename.replace('/', '\\') file_search_variable = (file_path_variable + '/*.hmd').replace( '/', '\\') print("\nfile_search_variable = ", file_search_variable) filename = glob.glob(file_search_variable) filename = filename[1] print("\nFile found : ", filename[1]) time.sleep(20) # click on 'Create Batch File' then OK on the following window app.window(best_match='National Roads Condition Database - Version *', top_level_only=True) \ .child_window(best_match='Create Batch file').click() time.sleep(30) app.window(best_match='National Roads Condition Database - Version *') \ .child_window(best_match='NRCD') \ .child_window(best_match='OK').click() # app.window(best_match='National Roads Condition Database Version *') \ # .child_window(best_match='OK').click() time.sleep(30) # There will be a file selection window. Connect to it (it's not part of NRCD) # So it's a new application. app3 = Application(backend="uia").connect( title='Create a file in the required directory') print("\nconnect app3") time.sleep(15) # edit_text_box2 = app3.window(title_re='Select a batch file') \ # .child_window(best_match="File name:") # from pywinauto.controls.win32_controls import EditWrapper # EditWrapper(edit_text_box2).set_text(filename) # put the filename that was found into the filename box app3.window(title_re='Create a file in the required directory') \ .File_name_Edit.set_text(filename) # app3.window(title_re='Create a file in the required directory').type_keys(filename[0], with_spaces=True) # app3.window(title_re='Create a file in the required directory').print_control_identifiers() # app3.window(title_re='Create a file in the required directory') \ # .Open3_SplitButton.click() # Click on the open button, this is a bit more involved so that it works with a locked screen. batch_split_button1 = app3.window(title_re='Create a file in the required directory') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_split_button1).click() # child_window(title="Open", auto_id="1", control_type="SplitButton") # .child_window(best_match='Open3').click() del app3 # if the file_path_variable directory string contains WDM if "WDM" in file_path_variable: # then Survey Contractor = WDM survey_contractor: str = "WDM" # else if the directory string contains 'G-L' select survey contractor 'Ginger-Lehmann' elif "G-L" in file_path_variable: survey_contractor: str = "Ginger-Lehmann" # it's not one of the two we know about. Should another contractor start surveying then add another 'elif' else: survey_contractor = "Unknown" print(survey_contractor) # ComboBoxWrapper(group_control.child_window(auto_id="24", # control_type="ComboBox")).select(la_db_name) # app.window(best_match='National Roads Condition Database', # top_level_only=True).print_control_identifiers() # batch_combobox1 = app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Local Authority Attribute', control_type="Group") \ # .child_window(title="OK", auto_id="6", control_type="Button")\ # .wait('exists enabled visible ready') # from pywinauto.controls.uia_controls import ComboBoxWrapper # from pywinauto.controls.win32_controls import EditWrapper # batch_combobox1 = app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Local Authority Attribute', control_type="Group") \ # .child_window(title="Survey Contractor", auto_id="1", control_type="Group") \ # .child_window(title="OK", auto_id="6", control_type="Button") # best_match='National Roads Condition Database', # top_level_only=True).child_window(best_match='Survey Contractor' # app.window(best_match='National Roads Condition Database', # top_level_only=True).child_window(best_match='Survey Contractor').Edit.type_keys(surveycontractor) from pywinauto.controls.win32_controls import ComboBoxWrapper surveyor_combobox = app.window(best_match='National Roads Condition Database') \ .child_window(best_match='Survey Contractor', control_type='Group') \ .child_window(auto_id="3", control_type="ComboBox") # .child_window(title="Survey Contractor", auto_id="5", control_type="Edit") # EditWrapper(surveyor_menu).set_text(survey_contractor) ComboBoxWrapper(surveyor_combobox).select(survey_contractor) # contractor_combobox = app.window(best_match='National Roads Condition Database', # top_level_only=True).child_window(best_match='Survey Contractor') # ComboBoxWrapper(contractor_combobox).select(survey_contractor) # contractor_combobox.Survey_Contractor_Edit.set_text(survey_contractor) # batch_combobox2 = app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Local Authority Attribute', control_type="Group") \ # .child_window(auto_id='4', control_type="ComboBox") # .wait('exists enabled visible ready') # click 'OK' to close the data loading window as we have all the appropriate details entered in the window. app.window(best_match='National Roads Condition Database') \ .child_window(best_match='OK').click() # back on the NRCD main screen, click the process radio button then the actual 'Process' button app.window(best_match='National Roads Condition Database - Version *', top_level_only=True).child_window(best_match='Process').click() # print(filename) # The log entry contains the first file to be loaded (the rest will not appear and NRCD uses the # batchfile to find them logger.info('Starting loading with ' + filename[0]) time.sleep(60) # wait for the loading to finish. It checks the number of windows open for NECD.exe. If these are less than # two the section is complete, otherwise it loops. while nrcd_running_check("2"): logger.info('waiting for loading to complete') time.sleep(300) logger.info('loading completed') return # back to main
def data_loading(app, file_path_variable): app.window(best_match='National Roads Condition Database - Version*', top_level_only=True).child_window(best_match='Loading').click() # if the file_path_variable directory contains a file 'BatchList' use 'Select Batch File' if os.path.isfile(file_path_variable + '/BatchList.txt'): filename = file_path_variable + '/BatchList.txt' print("\nfile name exists using Select", filename) time.sleep(30) app.window(best_match='National Roads Condition Database Version', top_level_only=True) \ .child_window(best_match='Select Batch file').click() filename = filename.replace('/', '\\') print("\nfile exists", filename) time.sleep(15) app2 = Application(backend="uia").connect( title_re='Select a batch file', visible_only=True) print("\nConnect app2 filename is ", filename) # edit_text_box1 = app2.window(title_re='Select a batch file') \ # .child_window(best_match="File name:") # from pywinauto.controls.win32_controls import EditWrapper # EditWrapper(edit_text_box1).set_text(filename) # app2.window(title_re='Select a batch file').type_keys(filename, with_spaces=True) app2.window( title_re='Select a batch file').File_name_Edit.set_text(filename) app2.window(title_re='Select a batch file').print_control_identifiers() # app2.window(title_re='Select a batch file').type_keys('%o') batch_splitbutton2 = app2.window(title_re='Select a batch file') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_splitbutton2).click() # app2.window(title_re='Select a batch file').OpenSplitButton.click_input # app2.window(title_re='Select a batch file') \ # .child_window(title='Pane1') \ # .child_window(title='Open', auto_id=1).click() # .child_window(title='Open', auto_id=1, control_type="UIA_SplitButtonControlTypeId").click() # .child_window(title='SplitButton6').click() del app2 else: # else pick the first .hmd file and use 'Create Batch File' print("\nfile missing") # app.window(best_match='National Roads Condition Database - Version', top_level_only=True).child_window( # best_match='OK').click() file_search_variable = (file_path_variable + '/*.hmd').replace( '/', '\\') print("\nfile_search_variable = ", file_search_variable) filename = glob.glob(file_search_variable) # filename = filename[0] print("\nFile found : ", filename[0]) # time.sleep(30) app.window(best_match='National Roads Condition Database Version *', top_level_only=True) \ .child_window(best_match='Create Batch file').click() time.sleep(30) app.window(best_match='National Roads Condition Database Version *') \ .child_window(best_match='NRCD') \ .child_window(best_match='OK').click() # app.window(best_match='National Roads Condition Database Version *') \ # .child_window(best_match='OK').click() time.sleep(30) app3 = Application(backend="uia").connect( title='Create a file in the required directory') print("\nconnect app3") time.sleep(15) # edit_text_box2 = app3.window(title_re='Select a batch file') \ # .child_window(best_match="File name:") # from pywinauto.controls.win32_controls import EditWrapper # EditWrapper(edit_text_box2).set_text(filename) app3.window(title_re='Create a file in the required directory') \ .File_name_Edit.set_text(filename[0]) # app3.window(title_re='Create a file in the required directory').type_keys(filename[0], with_spaces=True) app3.window(title_re='Create a file in the required directory' ).print_control_identifiers() # app3.window(title_re='Create a file in the required directory') \ # .Open3_SplitButton.click() batch_splitbutton1 = app3.window(title_re='Create a file in the required directory') \ .child_window(auto_id='1', control_type="SplitButton") from pywinauto.controls.win32_controls import ButtonWrapper ButtonWrapper(batch_splitbutton1).click() # child_window(title="Open", auto_id="1", control_type="SplitButton") # .child_window(best_match='Open3').click() del app3 # if the file_path_variable directory string contains WDM if "WDM" in file_path_variable: # then Survey Contractor = WDM surveycontractor = "WDM" # else if the directory string contains 'G-L' select survey contractor 'Ginger-Lehmann' elif "G-L" in file_path_variable: surveycontractor = "Ginger-Lehmann" else: surveycontractor = "Unknown" print(surveycontractor) app.window( best_match='National Roads Condition Database', top_level_only=True).child_window( best_match='Survey Contractor').Edit.type_keys(surveycontractor) # click 'OK' to close the data loading window app.window(best_match='National Roads Condition Database') \ .child_window(best_match='OK').click() # back on the main screen, click the process radio button then the actual 'Process' button app.window(best_match='National Roads Condition Database - Version *', top_level_only=True).child_window(best_match='Process').click() print(filename) logger.info('Starting loading with ' + filename[0]) time.sleep(60) # wait for the loading to finish. It checks the number of windows open for NECD.exe. If these are less than # two the section is complete, otherwise it loops. while nrcd_running_check("2"): logger.info('waiting for loading to complete') time.sleep(120) logger.info('loading completed') return
def fitting(app): from pywinauto.controls.win32_controls import ComboBoxWrapper from pywinauto.controls.win32_controls import ButtonWrapper # from pywinauto.controls import uia_controls # from pywinauto.controls import common_controls main_screen = app.window( best_match='National Roads Condition Database - V*') main_screen_ProcessCheckbox = main_screen.child_window( title="Process", auto_id="15", control_type="CheckBox") main_screen_ProcessCheckbox2 = main_screen.child_window( title="Process", auto_id="16", control_type="CheckBox") main_screen_ProcessCheckbox3 = main_screen.child_window( title="Process", auto_id="17", control_type="CheckBox") main_screen_ProcessCheckbox4 = main_screen.child_window( title="Process", auto_id="18", control_type="CheckBox") ButtonWrapper(main_screen_ProcessCheckbox).uncheck_by_click() ButtonWrapper(main_screen_ProcessCheckbox2).uncheck_by_click() ButtonWrapper(main_screen_ProcessCheckbox3).uncheck_by_click() ButtonWrapper(main_screen_ProcessCheckbox4).uncheck_by_click() logger.info('starting fitting') time.sleep(30) app.window(best_match='National Roads Condition Database', top_level_only=True).child_window(best_match='Fitting').click() time.sleep(10) # set the check boxes for fitting the data using a grid. ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="Fit unfitted data", auto_id="22", control_type="RadioButton")) \ .check_by_click() ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="Fit using a grid", auto_id="14", control_type="RadioButton")) \ .check_by_click() ButtonWrapper(app.window(best_match='National Roads Condition Database') .child_window(title="SCANNER", auto_id="7", control_type="RadioButton")) \ .check_by_click() # and set the survey year batch_combobox24 = app.window(best_match='National Roads Condition Database - Version*') \ .child_window(best_match='Year options:', auto_id="21", control_type="Group") \ .child_window(auto_id='24', control_type="ComboBox") ComboBoxWrapper(batch_combobox24).select(" 2019/20") time.sleep(5) # with everything set click the OK button to return to the main window. main_screen.child_window(title="OK", auto_id="11", control_type="Button").click() time.sleep(15) # app.window(best_match='National Roads Condition Database - Version*') \ # .child_window(best_match='Year options', control_type="Group") \ # .child_window(control_type="ComboBox").wait('exists enabled visible ready') # main_screen_group = main_screen.child_window(auto_id="11", control_type="Group") # main_screen_ProcessCheckbox = main_screen.child_window(title="Process", auto_id="15", control_type="CheckBox") # main_screen_ProcessCheckbox2 = main_screen.child_window(title="Process", auto_id="16", control_type="CheckBox") # main_screen_ProcessCheckbox3 = main_screen.child_window(title="Process", auto_id="17", control_type="CheckBox") # main_screen_ProcessCheckbox4 = main_screen.child_window(title="Process", auto_id="18", control_type="CheckBox") # ButtonWrapper(main_screen_ProcessCheckbox).uncheck_by_click() # ButtonWrapper(main_screen_ProcessCheckbox2).uncheck_by_click() # ButtonWrapper(main_screen_ProcessCheckbox3).check_by_click() # ButtonWrapper(main_screen_ProcessCheckbox4).uncheck_by_click() # the 'process' click box is already set so click on the main scree Process button at the bottom # then wait for the fitting to complete. main_screen.Process.click() time.sleep(60) while nrcd_running_check("2"): logger.info('waiting for Fitting to complete') time.sleep(90) logger.info('fitting complete') return # to the main code block.