项目概述
这个工具的主要功能包括:
- 文件搜索:用户可以输入关键字来搜索文件。
- 文件管理:用户可以查看搜索结果,选择文件并将其添加到管理列表。
- 数据导出:用户可以将管理列表中的文件信息导出为 excel 文件。
- 配置文件生成:用户可以生成配置文件,方便后续使用。
环境准备
确保安装了以下库:
pip install wxpython pandas pywin32,everytools
代码实现
以下是完整的代码实现:
import wx from everytools import everytools import pandas as pd import os import pythoncom import win32com.client class myframe(wx.frame): def __init__(self, *args, **kw): super(myframe, self).__init__(*args, **kw) self.initui() self.all_items = [] # 用于存储listview1的所有项目 def initui(self): panel = wx.panel(self) vbox = wx.boxsizer(wx.vertical) # 搜索框 self.search_ctrl = wx.textctrl(panel, style=wx.te_process_enter) self.search_ctrl.bind(wx.evt_text_enter, self.onsearch) # listview1 self.list_ctrl1 = wx.listctrl(panel, style=wx.lc_report) self.list_ctrl1.insertcolumn(0, 'file name', width=200) self.list_ctrl1.insertcolumn(1, 'file path', width=300) self.list_ctrl1.bind(wx.evt_list_item_activated, self.onitemactivated) # listview2 self.list_ctrl2 = wx.listctrl(panel, style=wx.lc_report) self.list_ctrl2.insertcolumn(0, 'file name', width=200) self.list_ctrl2.insertcolumn(1, 'file path', width=300) # 导出excel按钮 self.export_button = wx.button(panel, label='export to excel') self.export_button.bind(wx.evt_button, self.onexport) # 生成配置文件按钮 self.config_button = wx.button(panel, label='generate config file') self.config_button.bind(wx.evt_button, self.ongenerateconfig) # 删除选中项按钮 self.delete_button = wx.button(panel, label='delete selected') self.delete_button.bind(wx.evt_button, self.ondelete) # 过滤框 self.filter_ctrl = wx.textctrl(panel, style=wx.te_process_enter) self.filter_ctrl.sethint("search listview1...") self.filter_ctrl.bind(wx.evt_text_enter, self.onfilterlistview) # 布局 vbox.add(self.search_ctrl, 0, wx.expand | wx.all, 5) vbox.add(self.filter_ctrl, 0, wx.expand | wx.all, 5) vbox.add(self.list_ctrl1, 1, wx.expand | wx.all, 5) vbox.add(self.list_ctrl2, 1, wx.expand | wx.all, 5) vbox.add(self.export_button, 0, wx.expand | wx.all, 5) vbox.add(self.config_button, 0, wx.expand | wx.all, 5) vbox.add(self.delete_button, 0, wx.expand | wx.all, 5) panel.setsizer(vbox) self.settitle('file search and management') self.centre() def onsearch(self, event): keyword = self.search_ctrl.getvalue() es = everytools() es.search(keyword) try: results = es.results() if results.empty: wx.messagebox("no results found.", "info", wx.ok | wx.icon_information) return except oserror as e: wx.messagebox(f"error retrieving results: {e}", "error", wx.ok | wx.icon_error) return except exception as e: wx.messagebox(f"an unexpected error occurred: {e}", "error", wx.ok | wx.icon_error) return if 'name' not in results.columns or 'path' not in results.columns: wx.messagebox("expected columns 'name' or 'path' not found in results.", "error", wx.ok | wx.icon_error) return self.list_ctrl1.deleteallitems() self.all_items = [] # 重置存储所有项目的列表 for index, row in results.iterrows(): self.list_ctrl1.insertitem(index, row['name']) self.list_ctrl1.setitem(index, 1, row['path']) self.all_items.append((row['name'], row['path'])) # 存储所有项目 def onitemactivated(self, event): index = event.getindex() file_name = self.list_ctrl1.getitemtext(index, 0) file_path = self.list_ctrl1.getitemtext(index, 1) self.list_ctrl2.insertitem(self.list_ctrl2.getitemcount(), file_name) self.list_ctrl2.setitem(self.list_ctrl2.getitemcount() - 1, 1, file_path) def onexport(self, event): dialog = wx.dirdialog(none, "choose a directory to save the excel file:", style=wx.dd_default_style) if dialog.showmodal() == wx.id_ok: directory = dialog.getpath() file_path = f"{directory}/exported_files.xlsx" data = [] for i in range(self.list_ctrl2.getitemcount()): data.append({ 'file name': self.list_ctrl2.getitemtext(i, 0), 'file path': self.list_ctrl2.getitemtext(i, 1) }) df = pd.dataframe(data) df.to_excel(file_path, index=false) wx.messagebox(f"data exported successfully to {file_path}", "info", wx.ok | wx.icon_information) dialog.destroy() def ongenerateconfig(self, event): dialog = wx.dirdialog(none, "choose a directory to save the config file:", style=wx.dd_default_style) if dialog.showmodal() == wx.id_ok: directory = dialog.getpath() file_path = os.path.join(directory, "buttons.ini") self.exporttoini(file_path) wx.messagebox(f"config file generated successfully at {file_path}", "info", wx.ok | wx.icon_information) dialog.destroy() def exporttoini(self, path): shell = win32com.client.dispatch("wscript.shell") # with open(path, 'w') as file: # for idx, lnk_path in enumerate(self.get_selected_file_paths(), start=1): # try: # if lnk_path.endswith('.lnk'): # shortcut = shell.createshortcut(lnk_path) # target_path = shortcut.targetpath # caption = os.path.splitext(os.path.basename(lnk_path))[0] # else: # # 处理非 .lnk 文件,直接使用文件路径 # target_path = lnk_path # caption = os.path.splitext(os.path.basename(lnk_path))[0] # file.write(f"[button{idx}]\n") # file.write(f"caption = {caption}\n") # file.write(f"link = {target_path}\n") # file.write("color = clgreen\n") # file.write("width = 150\n") # file.write("height = 70\n\n") # except exception as e: # wx.messagebox(f"error processing file {lnk_path}: {e}", "error", wx.ok | wx.icon_error) with open(path, 'w') as file: for idx, lnk_path in enumerate(self.get_selected_file_paths(), start=1): try: if lnk_path.lower().endswith('.lnk'): # 判断文件名后缀是否为".lnk" shortcut = shell.createshortcut(lnk_path) target_path = shortcut.targetpath else: target_path = lnk_path caption = os.path.splitext(os.path.basename(lnk_path))[0] file.write(f"[button{idx}]\n") file.write(f"caption = {caption}\n") file.write(f"link = {target_path}\n") file.write("color = clgreen\n") file.write("width = 150\n") file.write("height = 70\n\n") except exception as e: wx.messagebox(f"error processing file {lnk_path}: {e}", "error", wx.ok | wx.icon_error) # def get_selected_file_paths(self): # """获取所有选定的文件路径""" # file_paths = [] # for i in range(self.list_ctrl2.getitemcount()): # file_paths.append(self.list_ctrl2.getitemtext(i, 1)) # return file_paths def get_selected_file_paths(self): """获取所有选定的文件路径,包含文件名""" file_paths = [] for i in range(self.list_ctrl2.getitemcount()): directory_path = self.list_ctrl2.getitemtext(i, 1) # 假设第0列是目录路径 file_name = self.list_ctrl2.getitemtext(i, 0) # 假设第1列是文件名 full_path = os.path.join(directory_path, file_name) file_paths.append(full_path) return file_paths def ondelete(self, event): selected = self.list_ctrl2.getfirstselected() while selected != -1: self.list_ctrl2.deleteitem(selected) selected = self.list_ctrl2.getfirstselected() def resolve_shortcut(self, path): """解析 .lnk 文件,返回它指向的可执行文件完整路径(包含exe名称)""" shell = win32com.client.dispatch("wscript.shell") shortcut = shell.createshortcut(path) return shortcut.targetpath # def onfilterlistview(self, event): # filter_text = self.filter_ctrl.getvalue().lower() # self.list_ctrl1.deleteallitems() # for index, (name, path) in enumerate(self.all_items): # if filter_text in name.lower() or filter_text in path.lower(): # self.list_ctrl1.insertitem(index, name) # self.list_ctrl1.setitem(index, 1, path) # def onfilterlistview(self): # filtered_items = self.filter_items_based_on_some_criteria() # self.list_ctrl1.deleteallitems() # for item in filtered_items: # index = self.list_ctrl1.insertitem(self.list_ctrl1.getitemcount(), item[0]) # if index != -1: # 确保索引有效 # self.list_ctrl1.setitem(index, 1, item[1]) # else: # wx.messagebox(f"failed to insert item {item[0]}", "error", wx.ok | wx.icon_error) # def onfilterlistview(self, event): # # 从过滤框获取输入的过滤条件 # filter_text = self.filter_ctrl.getvalue().lower() # # 清空list_ctrl1中的所有项目 # self.list_ctrl1.deleteallitems() # # 遍历所有项目,找到与过滤条件匹配的项目并重新添加到list_ctrl1中 # for index, (name, path) in enumerate(self.all_items): # if filter_text in name.lower() or filter_text in path.lower(): # self.list_ctrl1.insertitem(index, name) # self.list_ctrl1.setitem(index, 1, path) def onfilterlistview(self, event): # 从过滤框获取输入的过滤条件 filter_text = self.filter_ctrl.getvalue().lower() # 清空list_ctrl1中的所有项目 self.list_ctrl1.deleteallitems() # 遍历所有项目,找到与过滤条件匹配的项目并重新添加到list_ctrl1中 for name, path in self.all_items: if filter_text in name.lower() or filter_text in path.lower(): # 使用insertitem返回的index new_index = self.list_ctrl1.insertitem(self.list_ctrl1.getitemcount(), name) # 使用返回的index设置第二列 self.list_ctrl1.setitem(new_index, 1, path) def main(): app = wx.app() frame = myframe(none) frame.show() app.mainloop() if __name__ == '__main__': main()
代码解析
界面布局
代码使用 wx.boxsizer
来布局界面组件,包括搜索框、两个列表视图和多个按钮。每个组件都有相应的事件绑定,用于处理用户交互。
文件搜索功能
用户在搜索框中输入关键字,按下回车后,程序会调用 everytools
类进行搜索,并将结果显示在第一个列表视图中。如果没有找到结果,程序会弹出提示框。
文件管理功能
用户可以通过双击搜索结果,将文件添加到第二个列表视图中。选中的文件可以被删除。
数据导出与配置文件生成
用户可以将第二个列表视图中的文件信息导出为 excel 文件,或生成配置文件。
结果如下
总结
这个简单的文件搜索和管理工具展示了 everytools的基本用法,适合初学者学习和实践。通过这个项目,您可以了解如何处理用户输入、管理列表视图和文件操作等。
以上就是python使用everything库构建文件搜索和管理工具的详细内容,更多关于python everything文件搜索和管理的资料请关注代码网其它相关文章!
发表评论