ok-script 2.0.0b4__tar.gz → 2.0.0b6__tar.gz

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 (358) hide show
  1. {ok_script-2.0.0b4/ok_script.egg-info → ok_script-2.0.0b6}/PKG-INFO +2 -2
  2. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/MainWindow.py +46 -6
  3. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/about/AboutTab.py +38 -24
  4. ok_script-2.0.0b6/ok/ui/qt/about/UpdateCard.py +314 -0
  5. ok_script-2.0.0b6/ok/ui/qt/about/VersionCard.py +16 -0
  6. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/design_system.py +1 -1
  7. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/en_US.qm +0 -0
  8. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/en_US.ts +159 -0
  9. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/es_ES.qm +0 -0
  10. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/es_ES.ts +159 -0
  11. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/ja_JP.qm +0 -0
  12. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/ja_JP.ts +159 -0
  13. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/ko_KR.qm +0 -0
  14. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/ko_KR.ts +159 -0
  15. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/zh_CN.qm +0 -0
  16. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/zh_CN.ts +159 -0
  17. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/zh_TW.qm +0 -0
  18. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/zh_TW.ts +159 -0
  19. ok_script-2.0.0b6/ok/ui/qt/resources.py +19337 -0
  20. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/EditTaskTab.py +2 -0
  21. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TemplateTab.py +2 -2
  22. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/ExpandCardLayout.py +4 -0
  23. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/app.py +116 -0
  24. ok_script-2.0.0b6/ok/ui/web/static/app.js +11 -0
  25. ok_script-2.0.0b6/ok/ui/web/static/index.css +1 -0
  26. {ok_script-2.0.0b4 → ok_script-2.0.0b6/ok_script.egg-info}/PKG-INFO +2 -2
  27. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/SOURCES.txt +2 -0
  28. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/requires.txt +1 -1
  29. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/pyproject.toml +1 -1
  30. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_expand_card_layout.py +10 -0
  31. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_main_window_startup_tab.py +20 -1
  32. ok_script-2.0.0b6/tests/test_pyappify_startup_update.py +516 -0
  33. ok_script-2.0.0b6/tests/test_qt_page_layout.py +45 -0
  34. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_task_ui.py +5 -0
  35. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_template_tab.py +10 -0
  36. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_ui_pages.py +53 -0
  37. ok_script-2.0.0b4/ok/ui/qt/about/VersionCard.py +0 -33
  38. ok_script-2.0.0b4/ok/ui/qt/resources.py +0 -15570
  39. ok_script-2.0.0b4/ok/ui/web/static/app.js +0 -11
  40. ok_script-2.0.0b4/ok/ui/web/static/index.css +0 -1
  41. ok_script-2.0.0b4/tests/test_pyappify_startup_update.py +0 -202
  42. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/LICENSE.txt +0 -0
  43. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/MANIFEST.in +0 -0
  44. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/README.md +0 -0
  45. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/diagnostics/qq_trace.py +0 -0
  46. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/__init__.py +0 -0
  47. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/__main__.py +0 -0
  48. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/alas/__init__.py +0 -0
  49. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/alas/emulator_base.py +0 -0
  50. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/alas/emulator_windows.py +0 -0
  51. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/alas/platform_windows.py +0 -0
  52. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/alas/utils.py +0 -0
  53. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/__init__.py +0 -0
  54. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/__init__.py +0 -0
  55. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/deep.py +0 -0
  56. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/minitouch.py +0 -0
  57. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/nemu_ipc.py +0 -0
  58. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/nemu_utils.py +0 -0
  59. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/pool.py +0 -0
  60. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/timer.py +0 -0
  61. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/adb/util.py +0 -0
  62. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/windows/__init__.py +0 -0
  63. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/windows/d3d11.py +0 -0
  64. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/capture/windows/dump.py +0 -0
  65. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/cli.py +0 -0
  66. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/__init__.py +0 -0
  67. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/config_schema.py +0 -0
  68. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/downloads.py +0 -0
  69. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/events.py +0 -0
  70. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/icons.py +0 -0
  71. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/notifications.py +0 -0
  72. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/screenshot.py +0 -0
  73. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/script_editing.py +0 -0
  74. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/script_packager.py +0 -0
  75. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/script_templates.py +0 -0
  76. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/start_controller.py +0 -0
  77. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/task_manager.py +0 -0
  78. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/template_store.py +0 -0
  79. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/translation.py +0 -0
  80. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/core/ui_config.py +0 -0
  81. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/DeviceManager.py +0 -0
  82. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/__init__.py +0 -0
  83. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture.py +0 -0
  84. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/__init__.py +0 -0
  85. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/adb.py +0 -0
  86. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/base.py +0 -0
  87. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/bitblt.py +0 -0
  88. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/bitblt_utils.py +0 -0
  89. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/browser.py +0 -0
  90. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/desktop_duplication.py +0 -0
  91. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/hwnd_window.py +0 -0
  92. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/image.py +0 -0
  93. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/nemu_ipc.py +0 -0
  94. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/types.py +0 -0
  95. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/update.py +0 -0
  96. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/capture_methods/windows_graphics.py +0 -0
  97. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction.py +0 -0
  98. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/__init__.py +0 -0
  99. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/adb.py +0 -0
  100. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/base.py +0 -0
  101. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/browser.py +0 -0
  102. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/do_nothing.py +0 -0
  103. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/foreground_post_message.py +0 -0
  104. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/genshin.py +0 -0
  105. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/keys.py +0 -0
  106. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/post_message.py +0 -0
  107. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/pydirect.py +0 -0
  108. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/pynput.py +0 -0
  109. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/interaction_methods/swipe.py +0 -0
  110. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/device/intercation.py +0 -0
  111. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/feature/Box.py +0 -0
  112. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/feature/Feature.py +0 -0
  113. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/feature/FeatureSet.py +0 -0
  114. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/feature/__init__.py +0 -0
  115. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/gui/__init__.py +0 -0
  116. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/gui/util/pyappify_startup.py +0 -0
  117. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/__init__.py +0 -0
  118. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/manager.py +0 -0
  119. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/messenger_images.py +0 -0
  120. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/pipeline.py +0 -0
  121. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/ppocr.py +0 -0
  122. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/providers.py +0 -0
  123. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/system.py +0 -0
  124. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/notification/windows_messenger.py +0 -0
  125. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ocr/__init__.py +0 -0
  126. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ocr/download_paddle_model.py +0 -0
  127. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Foundation/Collections.py +0 -0
  128. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Foundation/__init__.py +0 -0
  129. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Globalization/__init__.py +0 -0
  130. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Graphics/Capture/__init__.py +0 -0
  131. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Graphics/DirectX/Direct3D11/__init__.py +0 -0
  132. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Graphics/DirectX/__init__.py +0 -0
  133. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Graphics/Imaging/__init__.py +0 -0
  134. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Graphics/__init__.py +0 -0
  135. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Media/Ocr/__init__.py +0 -0
  136. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Media/__init__.py +0 -0
  137. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Security/Cryptography/__init__.py +0 -0
  138. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Security/__init__.py +0 -0
  139. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Storage/Streams/__init__.py +0 -0
  140. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/Storage/__init__.py +0 -0
  141. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/UI/ViewManagement/__init__.py +0 -0
  142. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/UI/__init__.py +0 -0
  143. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/Windows/__init__.py +0 -0
  144. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/__init__.py +0 -0
  145. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/delegate.py +0 -0
  146. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/export.py +0 -0
  147. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/idldsl.py +0 -0
  148. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/inspectable.py +0 -0
  149. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/roapi.py +0 -0
  150. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/types.py +0 -0
  151. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/rotypes/winstring.py +0 -0
  152. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/DiagnosisTask.py +0 -0
  153. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/TaskExecutor.py +0 -0
  154. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/__init__.py +0 -0
  155. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/exceptions.py +0 -0
  156. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/task.py +0 -0
  157. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/task/web.py +0 -0
  158. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/test/OKTestRunner.py +0 -0
  159. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/test/RunTests.py +0 -0
  160. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/test/TaskTestCase.py +0 -0
  161. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/test/__init__.py +0 -0
  162. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/third_party/__init__.py +0 -0
  163. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/third_party/paperclip.py +0 -0
  164. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/__init__.py +0 -0
  165. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/overlay/__init__.py +0 -0
  166. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/overlay/win32_gdi.py +0 -0
  167. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/Communicate.py +0 -0
  168. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/MessageWindow.py +0 -0
  169. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/StartController.py +0 -0
  170. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/TabTitles.py +0 -0
  171. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/__init__.py +0 -0
  172. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/about/HttpTextEdit.py +0 -0
  173. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/about/LinksBar.py +0 -0
  174. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/about/ProjectCard.py +0 -0
  175. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/about/__init__.py +0 -0
  176. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/OKIcon.py +0 -0
  177. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/__init__.py +0 -0
  178. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/accent_color.py +0 -0
  179. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/config.py +0 -0
  180. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/icons.py +0 -0
  181. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/common/style_sheet.py +0 -0
  182. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/debug/DebugTab.py +0 -0
  183. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/debug/OverlayWidget.py +0 -0
  184. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/debug/RunCodeTab.py +0 -0
  185. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/debug/Screenshot.py +0 -0
  186. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/debug/__init__.py +0 -0
  187. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/events.py +0 -0
  188. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/GettextTranslator.py +0 -0
  189. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/__init__.py +0 -0
  190. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/path.py +0 -0
  191. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/i18n/update.py +0 -0
  192. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/overlay/OverlayWindow.py +0 -0
  193. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/overlay/__init__.py +0 -0
  194. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/__init__.py +0 -0
  195. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/card.qss +0 -0
  196. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/discord.svg +0 -0
  197. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/heart.svg +0 -0
  198. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/message_window.qss +0 -0
  199. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/setting_interface.qss +0 -0
  200. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/status_bar.qss +0 -0
  201. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/stop.svg +0 -0
  202. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/dark/tab.qss +0 -0
  203. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/card.qss +0 -0
  204. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/discord.svg +0 -0
  205. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/heart.svg +0 -0
  206. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/message_window.qss +0 -0
  207. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/setting_interface.qss +0 -0
  208. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/status_bar.qss +0 -0
  209. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/stop.svg +0 -0
  210. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qss/light/tab.qss +0 -0
  211. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/qt.qrc +0 -0
  212. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/settings/GlobalConfigCard.py +0 -0
  213. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/settings/GlobalConfigTab.py +0 -0
  214. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/settings/SettingTab.py +0 -0
  215. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/settings/__init__.py +0 -0
  216. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/LogWindow.py +0 -0
  217. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/SelectCaptureListView.py +0 -0
  218. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/SelectInteractionListView.py +0 -0
  219. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/StartCard.py +0 -0
  220. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/StartTab.py +0 -0
  221. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/start/__init__.py +0 -0
  222. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ConfigCard.py +0 -0
  223. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ConfigItemFactory.py +0 -0
  224. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ConfigLabelAndWidget.py +0 -0
  225. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndButtons.py +0 -0
  226. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndDoubleSpinBox.py +0 -0
  227. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndDropDown.py +0 -0
  228. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndFileSelector.py +0 -0
  229. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndGlobal.py +0 -0
  230. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndLineEdit.py +0 -0
  231. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndList.py +0 -0
  232. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndMultiSelection.py +0 -0
  233. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndSpinBox.py +0 -0
  234. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndSwitchButton.py +0 -0
  235. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndTextEdit.py +0 -0
  236. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/LabelAndWidget.py +0 -0
  237. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/MarkUpWindow.py +0 -0
  238. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ModifyListDialog.py +0 -0
  239. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ModifyListItem.py +0 -0
  240. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/OneTimeTaskTab.py +0 -0
  241. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/PythonHighlighter.py +0 -0
  242. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/RecordScript.py +0 -0
  243. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ScheduleTaskTab.py +0 -0
  244. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/ScriptPackager.py +0 -0
  245. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/StartButton.py +0 -0
  246. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TaskCard.py +0 -0
  247. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TaskManger.py +0 -0
  248. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TaskOpButton.py +0 -0
  249. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TaskTab.py +0 -0
  250. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TemplateFactory.py +0 -0
  251. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TooltipTableWidget.py +0 -0
  252. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/TriggerTaskTab.py +0 -0
  253. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/tasks/__init__.py +0 -0
  254. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/Alert.py +0 -0
  255. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/InitWorker.py +0 -0
  256. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/__init__.py +0 -0
  257. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/app.py +0 -0
  258. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/download.py +0 -0
  259. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/pip_util.py +0 -0
  260. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/pyappify_startup.py +0 -0
  261. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/touch_scroll.py +0 -0
  262. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/util/windows_thumbnail.py +0 -0
  263. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/BaseLoading.py +0 -0
  264. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/BaseWindow.py +0 -0
  265. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/Card.py +0 -0
  266. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/CustomTab.py +0 -0
  267. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/EmptyCard.py +0 -0
  268. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/FlowLayout.py +0 -0
  269. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/FramelessDialog.py +0 -0
  270. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/ImageWidget.py +0 -0
  271. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/ListTableWidgetItem.py +0 -0
  272. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/NumericTableWidgetItem.py +0 -0
  273. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/OkCompactSpinBox.py +0 -0
  274. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/SortingTableWidgetItem.py +0 -0
  275. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/StartLoadingDialog.py +0 -0
  276. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/StatusBar.py +0 -0
  277. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/Tab.py +0 -0
  278. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/TabWidget.py +0 -0
  279. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/UpdateConfigWidgetItem.py +0 -0
  280. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/WidgetWithVLabel.py +0 -0
  281. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/YesNonWidgetItem.py +0 -0
  282. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/qt/widget/__init__.py +0 -0
  283. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/__init__.py +0 -0
  284. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/requirements.py +0 -0
  285. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/server.py +0 -0
  286. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/static/chunk-fluent.js +0 -0
  287. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/static/chunk-react.js +0 -0
  288. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/ui/web/static/index.html +0 -0
  289. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/update/__init__.py +0 -0
  290. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/update/copy_ok_folder.py +0 -0
  291. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/update/inline_ok_requirements.py +0 -0
  292. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/Analytics.py +0 -0
  293. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/GlobalConfig.py +0 -0
  294. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/__init__.py +0 -0
  295. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/blur.py +0 -0
  296. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/clazz.py +0 -0
  297. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/collection.py +0 -0
  298. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/color.py +0 -0
  299. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/config.py +0 -0
  300. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/explorer.py +0 -0
  301. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/file.py +0 -0
  302. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/gpu_driver_settings.py +0 -0
  303. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/handler.py +0 -0
  304. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/i18n.py +0 -0
  305. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/logger.py +0 -0
  306. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/partial_sync_repo.py +0 -0
  307. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/print_hwnd.py +0 -0
  308. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/process.py +0 -0
  309. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/window.py +0 -0
  310. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok/util/windows_schedule.py +0 -0
  311. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/dependency_links.txt +0 -0
  312. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/entry_points.txt +0 -0
  313. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/not-zip-safe +0 -0
  314. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/ok_script.egg-info/top_level.txt +0 -0
  315. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/scripts/generate_web_i18n.py +0 -0
  316. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/setup.cfg +0 -0
  317. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/setup.py +0 -0
  318. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_accent_color.py +0 -0
  319. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_app.py +0 -0
  320. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_base_interaction.py +0 -0
  321. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_blur.py +0 -0
  322. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_box.py +0 -0
  323. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_capture_update.py +0 -0
  324. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_cli.py +0 -0
  325. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_config_card.py +0 -0
  326. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_core_events.py +0 -0
  327. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_core_ui_services.py +0 -0
  328. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_device_manager.py +0 -0
  329. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_explorer.py +0 -0
  330. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_global_config.py +0 -0
  331. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_gpu_driver_settings.py +0 -0
  332. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_headless_imports.py +0 -0
  333. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_inline_ok_requirements.py +0 -0
  334. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_logger.py +0 -0
  335. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_main_window_notifications.py +0 -0
  336. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_main_window_system_theme.py +0 -0
  337. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_missing_frame.py +0 -0
  338. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_navigation_state.py +0 -0
  339. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_nemu_ipc_capture.py +0 -0
  340. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_notifications.py +0 -0
  341. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_ok_mutex.py +0 -0
  342. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_overlay_custom_draw.py +0 -0
  343. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_package_metadata.py +0 -0
  344. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_process.py +0 -0
  345. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_qt_events.py +0 -0
  346. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_qt_legacy_imports.py +0 -0
  347. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_runtime_startup.py +0 -0
  348. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_start_controller.py +0 -0
  349. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_task_executor_queue.py +0 -0
  350. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_touch_scroll.py +0 -0
  351. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_translation_fallback.py +0 -0
  352. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_ui_config.py +0 -0
  353. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_app.py +0 -0
  354. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_i18n.py +0 -0
  355. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_server.py +0 -0
  356. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_task_tabs.py +0 -0
  357. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_web_ui_tasks.py +0 -0
  358. {ok_script-2.0.0b4 → ok_script-2.0.0b6}/tests/test_windows_graphics_capture.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ok-script
3
- Version: 2.0.0b4
3
+ Version: 2.0.0b6
4
4
  Summary: Automation with Computer Vision for Python
5
5
  Author-email: ok-oldking <firedcto@gmail.com>
6
6
  Project-URL: Homepage, https://github.com/ok-oldking/ok-script
@@ -16,7 +16,7 @@ Requires-Python: >=3.11
16
16
  Description-Content-Type: text/markdown
17
17
  License-File: LICENSE.txt
18
18
  Requires-Dist: pywin32>=306
19
- Requires-Dist: pyappify>=1.0.6
19
+ Requires-Dist: pyappify>=1.0.9
20
20
  Requires-Dist: typing-extensions>=4.11.0
21
21
  Requires-Dist: requests>=2.32.3
22
22
  Requires-Dist: psutil>=6.0.0
@@ -6,7 +6,8 @@ from PySide6.QtCore import QCoreApplication, QEvent, QSize, Qt, QTimer
6
6
  from PySide6.QtGui import QColor, QScreen
7
7
  from PySide6.QtWidgets import QMenu, QSystemTrayIcon, QApplication
8
8
  from qfluentwidgets import qconfig, FluentIcon, NavigationItemPosition, MessageBox, InfoBar, \
9
- InfoBarPosition, MessageBoxBase, FluentWindow, NavigationDisplayMode, isDarkTheme, Theme
9
+ InfoBarPosition, MessageBoxBase, FluentWindow, NavigationDisplayMode, isDarkTheme, Theme, \
10
+ DotInfoBadge, InfoBadgePosition
10
11
  from qfluentwidgets.components.widgets.scroll_bar import ScrollBarHandleDisplayMode
11
12
  from qfluentwidgets.common.style_sheet import updateStyleSheet
12
13
 
@@ -47,6 +48,10 @@ NAVIGATION_EXPAND_MAX_WIDTH = 240
47
48
  NAVIGATION_EXPAND_FIT_PADDING = 23
48
49
 
49
50
 
51
+ def update_check_delay_ms():
52
+ return 10_000 if "PYAPPIFY_PYTHON_TEST" in os.environ else 30_000
53
+
54
+
50
55
  class MainWindow(FluentWindow):
51
56
 
52
57
  def __init__(self, app, config, ok_config, icon, title, version, debug=False, about=None, exit_event=None,
@@ -207,9 +212,14 @@ class MainWindow(FluentWindow):
207
212
  position=NavigationItemPosition.BOTTOM)
208
213
 
209
214
  from ok.ui.qt.about.AboutTab import AboutTab
210
- self.about_tab = AboutTab(config)
215
+ self.about_tab = AboutTab(config, exit_event=exit_event)
211
216
  self.addSubInterface(self.about_tab, FluentIcon.QUESTION, self.tr('About'),
212
217
  position=NavigationItemPosition.BOTTOM)
218
+ self.about_update_badge = None
219
+ self.update_check_timer = None
220
+ if self.about_tab.update_card is not None:
221
+ self.about_tab.update_card.update_available_changed.connect(self._set_about_update_available)
222
+ self.about_tab.update_card.check_started.connect(self._cancel_scheduled_update_check)
213
223
 
214
224
  dev = self.tr('Debug')
215
225
  profile = config.get('profile', "")
@@ -243,6 +253,31 @@ class MainWindow(FluentWindow):
243
253
 
244
254
  logger.info('main window __init__ done')
245
255
 
256
+ def _set_about_update_available(self, available):
257
+ if available and self.about_update_badge is None:
258
+ about_navigation_item = self.navigationInterface.widget(self.about_tab.objectName())
259
+ self.about_update_badge = DotInfoBadge.error(
260
+ self, target=about_navigation_item, position=InfoBadgePosition.NAVIGATION_ITEM
261
+ )
262
+ if self.about_update_badge is not None:
263
+ self.about_update_badge.setVisible(available)
264
+
265
+ def _schedule_update_check(self):
266
+ if self.about_tab.update_card is None:
267
+ return
268
+ if self.update_check_timer is None:
269
+ self.update_check_timer = QTimer(self)
270
+ self.update_check_timer.setSingleShot(True)
271
+ self.update_check_timer.timeout.connect(self.about_tab.check_for_updates)
272
+ update_delay = update_check_delay_ms()
273
+ logger.info(f'schedule pyappify update check in {update_delay}ms')
274
+ self.update_check_timer.start(update_delay)
275
+
276
+ def _cancel_scheduled_update_check(self):
277
+ if self.update_check_timer is not None and self.update_check_timer.isActive():
278
+ logger.info('cancel scheduled pyappify update check because a check has started')
279
+ self.update_check_timer.stop()
280
+
246
281
  @staticmethod
247
282
  def _get_dwm_accent_color():
248
283
  """Return the DWM accent color as a compatibility fallback."""
@@ -491,14 +526,18 @@ class MainWindow(FluentWindow):
491
526
  self.shown = True
492
527
  pyappify.hide_pyappify()
493
528
  if update_pyappify := self.config.get("update_pyappify"):
494
- pyappify.upgrade(update_pyappify.get('to_version'), update_pyappify.get('sha256'),
495
- [update_pyappify.get('zip_url')], self.exit_event)
529
+ pyappify.upgrade(
530
+ update_pyappify.get('to_version'),
531
+ update_pyappify.get('sha256'),
532
+ [update_pyappify.get('zip_url')],
533
+ exit_event=self.exit_event,
534
+ )
496
535
  logger.info("Window has fully displayed")
497
536
  from ok import og
498
537
  og.ok.start_runtime()
499
538
  if self.basic_global_config.get(KILL_LAUNCHER_AFTER_START):
500
539
  logger.info(f'MainWindow showEvent Kill Launcher After Start')
501
- pyappify.kill_pyappify()
540
+ pyappify.kill_pyappify(exit_event=self.exit_event)
502
541
  startup_version_change = get_startup_version_change()
503
542
  if self.version != self.main_window_config.get('last_version'):
504
543
  self.main_window_config['last_version'] = self.version
@@ -513,6 +552,7 @@ class MainWindow(FluentWindow):
513
552
  if first_show:
514
553
  QTimer.singleShot(0, self.bring_to_front)
515
554
  QTimer.singleShot(250, self.show_startup_version_change_notice)
555
+ self._schedule_update_check()
516
556
 
517
557
  def set_window_size(self, width, height, min_width, min_height):
518
558
  screen = QScreen.availableGeometry(self.screen())
@@ -703,5 +743,5 @@ class MainWindow(FluentWindow):
703
743
  self.executor.destroy()
704
744
  event.accept()
705
745
  if not self.do_not_quit:
706
- pyappify.kill_pyappify()
746
+ pyappify.kill_pyappify(exit_event=self.exit_event)
707
747
  QApplication.instance().exit()
@@ -1,32 +1,58 @@
1
1
  from PySide6.QtCore import Qt
2
2
  from PySide6.QtWidgets import QGridLayout, QWidget, QSizePolicy
3
- from qfluentwidgets import BodyLabel, SettingCardGroup
3
+ from qfluentwidgets import BodyLabel
4
4
 
5
5
  from ok.ui.qt.about.ProjectCard import ProjectCard
6
6
  from ok.ui.qt.about.VersionCard import VersionCard
7
+ from ok.ui.qt.about.UpdateCard import ChangeLogView, UpdateCard
7
8
  from ok.ui.qt.util.app import get_localized_app_config
8
9
  from ok.ui.qt.util.pyappify_startup import get_startup_version_change
9
10
  from ok.ui.qt.widget.Tab import Tab
10
11
  from ok.util.file import get_path_relative_to_exe
12
+ from ok.util.logger import Logger
13
+
14
+
15
+ logger = Logger.get_logger(__name__)
11
16
 
12
17
 
13
18
  class AboutTab(Tab):
14
- def __init__(self, config):
19
+ def __init__(self, config, pyappify_module=None, exit_event=None):
15
20
  super().__init__()
21
+ if pyappify_module is None:
22
+ import pyappify as pyappify_module
16
23
  self.version_card = VersionCard(config, get_path_relative_to_exe(config.get('gui_icon')),
17
24
  config.get('gui_title'), config.get('version'),
18
25
  config.get('debug'), self)
19
26
  # The About page uses the same section rhythm as the rest of the app.
20
27
  self.add_widget(self.version_card)
21
28
 
22
- if version_change := get_startup_version_change():
23
- update_note_label = BodyLabel()
24
- update_note_label.setText(version_change.content)
25
- update_note_label.setWordWrap(True)
26
- update_note_label.setTextInteractionFlags(Qt.TextInteractionFlag.TextSelectableByMouse)
29
+ self.update_card = None
30
+ if callable(getattr(pyappify_module, 'get_version_list', None)):
31
+ self.update_card = UpdateCard(
32
+ config.get('version'), pyappify_module, self, exit_event=exit_event
33
+ )
34
+ self.add_card(self.tr("App update"), self.update_card)
35
+ else:
36
+ logger.warning(
37
+ "pyappify.get_version_list is unavailable; update controls are disabled. "
38
+ f"Loaded module: {getattr(pyappify_module, '__file__', type(pyappify_module).__name__)!r}"
39
+ )
40
+
41
+ if version_change := get_startup_version_change(pyappify_module):
42
+ update_note_label = ChangeLogView(version_change.content)
27
43
  update_note_label.setContentsMargins(0, 0, 0, 0)
28
44
  self.add_card(self._startup_version_change_title(version_change), update_note_label)
29
45
 
46
+ if about := config.get('about'):
47
+ about_label = BodyLabel()
48
+ about_label.setText(about)
49
+ about_label.setWordWrap(True)
50
+ about_label.setOpenExternalLinks(True)
51
+ about_label.setTextInteractionFlags(Qt.TextBrowserInteraction)
52
+ about_label.setContentsMargins(0, 0, 0, 0)
53
+
54
+ self.add_card(self.tr("Disclaimer"), about_label)
55
+
30
56
  projects = [
31
57
  {"name": self.tr("ok-py Automation Tool"), "url": "https://github.com/ok-oldking/ok-py"},
32
58
  {"name": self.tr("ok-script App Template"), "url": "https://github.com/ok-oldking/ok-script-app"},
@@ -49,10 +75,6 @@ class AboutTab(Tab):
49
75
  filtered_projects = [p for p in projects if normalize_url(p['url']) != current_github_norm]
50
76
 
51
77
  if filtered_projects:
52
- self.group = SettingCardGroup(self.tr("Other Projects"), self)
53
-
54
- self.group.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Fixed)
55
-
56
78
  grid_widget = QWidget()
57
79
  grid_widget.setSizePolicy(grid_widget.sizePolicy().horizontalPolicy(), QSizePolicy.Fixed)
58
80
 
@@ -66,22 +88,14 @@ class AboutTab(Tab):
66
88
  card = ProjectCard(project['name'], project['url'], grid_widget)
67
89
  grid_layout.addWidget(card, i // 2, i % 2)
68
90
 
69
- self.group.addSettingCard(grid_widget)
70
- self.group.setContentsMargins(0, 0, 0, 0)
71
- self.add_widget(self.group)
72
-
73
- if about := config.get('about'):
74
- about_label = BodyLabel()
75
- about_label.setText(about)
76
- about_label.setWordWrap(True)
77
- about_label.setOpenExternalLinks(True)
78
- about_label.setTextInteractionFlags(Qt.TextBrowserInteraction)
79
- about_label.setContentsMargins(0, 0, 0, 0)
80
-
81
- self.add_card(None, about_label)
91
+ self.group = self.add_card(self.tr("Other Projects"), grid_widget)
82
92
 
83
93
  self.vBoxLayout.addStretch(1)
84
94
 
95
+ def check_for_updates(self):
96
+ if self.update_card is not None:
97
+ self.update_card.check_for_updates()
98
+
85
99
  def _startup_version_change_title(self, version_change):
86
100
  if version_change.action == "update":
87
101
  title = self.tr("Update success {from_version} -> {to_version}")
@@ -0,0 +1,314 @@
1
+ import os
2
+ import threading
3
+
4
+ from PySide6.QtCore import QEvent, Signal, Qt
5
+ from PySide6.QtGui import QFontMetrics, QIcon, QPixmap
6
+ from PySide6.QtWidgets import QHBoxLayout, QSizePolicy, QVBoxLayout, QWidget
7
+ from qfluentwidgets import BodyLabel, CheckBox, ComboBox, FluentIcon, IndeterminateProgressRing, \
8
+ PrimaryPushButton, PushButton
9
+
10
+ from ok.util.logger import Logger
11
+
12
+
13
+ logger = Logger.get_logger(__name__)
14
+
15
+
16
+ def _is_numeric_version(version):
17
+ try:
18
+ return bool(version) and all(part.isdigit() for part in version.lstrip("v").split("."))
19
+ except AttributeError:
20
+ return False
21
+
22
+
23
+ class ChangeLogView(BodyLabel):
24
+ """A non-interactive, word-wrapped changelog that follows its text height."""
25
+
26
+ def __init__(self, text="", parent=None):
27
+ super().__init__(parent)
28
+ self.setText(text)
29
+ self.setWordWrap(True)
30
+ self.setTextFormat(Qt.TextFormat.PlainText)
31
+ self.setTextInteractionFlags(Qt.TextInteractionFlag.NoTextInteraction)
32
+ self.setAlignment(Qt.AlignmentFlag.AlignLeft | Qt.AlignmentFlag.AlignTop)
33
+ size_policy = QSizePolicy(QSizePolicy.Policy.Expanding, QSizePolicy.Policy.Minimum)
34
+ size_policy.setHeightForWidth(True)
35
+ self.setSizePolicy(size_policy)
36
+
37
+ def setPlainText(self, text):
38
+ self.setText(text)
39
+
40
+ def toPlainText(self):
41
+ return self.text()
42
+
43
+
44
+ class UpdateCard(QWidget):
45
+ """Version picker and release-note viewer backed by the PyAppify launcher API."""
46
+
47
+ update_available_changed = Signal(bool)
48
+ check_started = Signal()
49
+ _versions_loaded = Signal(object)
50
+ _update_finished = Signal(object)
51
+ VERSION_COMBO_MIN_WIDTH = 100
52
+ VERSION_COMBO_MAX_WIDTH = 240
53
+
54
+ def __init__(self, current_version, pyappify_module, parent=None, exit_event=None):
55
+ super().__init__(parent)
56
+ self.current_version = current_version or getattr(pyappify_module, "app_version", None) or ""
57
+ if "PYAPPIFY_PYTHON_TEST" in os.environ and not _is_numeric_version(self.current_version):
58
+ logger.info(f"using v0.0.0 for nonnumeric test version {self.current_version!r}")
59
+ self.current_version = "v0.0.0"
60
+ self.pyappify_module = pyappify_module
61
+ self.exit_event = exit_event
62
+ self.versions = []
63
+ self._busy = False
64
+ logger.info(
65
+ f"initialized current_version={self.current_version!r}, "
66
+ f"pyappify_module={getattr(pyappify_module, '__file__', type(pyappify_module).__name__)!r}, "
67
+ f"pyappify_app_version={getattr(pyappify_module, 'app_version', None)!r}, "
68
+ f"test_mode={'PYAPPIFY_PYTHON_TEST' in os.environ}"
69
+ )
70
+
71
+ self.version_combo = ComboBox(self)
72
+ self.version_combo.setFixedWidth(self.VERSION_COMBO_MIN_WIDTH)
73
+ self.version_combo.currentIndexChanged.connect(self._selection_changed)
74
+
75
+ self.test_version_checkbox = CheckBox(self.tr("Check Test Version"), self)
76
+ self.test_version_checkbox.setChecked(False)
77
+ self.check_button = PushButton(FluentIcon.SYNC, self.tr("Check for updates"), self)
78
+ loading_icon_pixmap = QPixmap(16, 16)
79
+ loading_icon_pixmap.fill(Qt.GlobalColor.transparent)
80
+ self._loading_placeholder_icon = QIcon(loading_icon_pixmap)
81
+ self.check_progress = IndeterminateProgressRing(self.check_button, start=False)
82
+ self.check_progress.setFixedSize(16, 16)
83
+ self.check_progress.setStrokeWidth(2)
84
+ self.check_progress.hide()
85
+ self.check_button.setMinimumWidth(self.check_button.sizeHint().width())
86
+ self.check_button.installEventFilter(self)
87
+ self.check_button.clicked.connect(self.check_for_updates)
88
+ self.update_button = PrimaryPushButton(FluentIcon.UPDATE, self.tr("Update"), self)
89
+ self.update_button.clicked.connect(self.update_to_selected_version)
90
+ self.update_button.setEnabled(False)
91
+
92
+ self.controls_layout = QHBoxLayout()
93
+ self.controls_layout.setContentsMargins(0, 0, 0, 0)
94
+ self.version_label = BodyLabel(self.tr("Version"), self)
95
+ self.status_label = BodyLabel(self.tr("Click to check for updates"), self)
96
+ self.controls_layout.addWidget(self.version_label)
97
+ self.controls_layout.addWidget(self.version_combo)
98
+ self.controls_layout.addWidget(self.status_label)
99
+ self.controls_layout.addStretch(1)
100
+ self.controls_layout.addWidget(self.test_version_checkbox)
101
+ self.controls_layout.addWidget(self.check_button)
102
+ self.controls_layout.addWidget(self.update_button)
103
+ self._set_version_controls_visible(False)
104
+
105
+ self.notes_edit = ChangeLogView("", self)
106
+ self.notes_edit.hide()
107
+
108
+ layout = QVBoxLayout(self)
109
+ layout.setContentsMargins(0, 0, 0, 0)
110
+ layout.setSpacing(12)
111
+ layout.addLayout(self.controls_layout)
112
+ layout.addWidget(self.notes_edit)
113
+
114
+ self._versions_loaded.connect(self._apply_versions)
115
+ self._update_finished.connect(self._apply_update_result)
116
+
117
+ def check_for_updates(self):
118
+ if self._busy:
119
+ return
120
+ get_versions = getattr(self.pyappify_module, "get_version_list", None)
121
+ if not callable(get_versions):
122
+ self._show_error(self.tr("Update checking is not supported by this PyAppify version."))
123
+ return
124
+ self._set_busy(True, checking=True)
125
+ self.check_started.emit()
126
+ self._set_status(self.tr("Checking for updates…"))
127
+ release_only = not self.test_version_checkbox.isChecked()
128
+ self._run_in_background(
129
+ lambda: get_versions(release_only=release_only, exit_event=self.exit_event),
130
+ self._versions_loaded,
131
+ f"pyappify.get_version_list(release_only={release_only})",
132
+ )
133
+
134
+ def update_to_selected_version(self):
135
+ if self._busy or self.version_combo.currentIndex() < 0:
136
+ return
137
+ update_to_version = getattr(self.pyappify_module, "update_to_version", None)
138
+ if not callable(update_to_version):
139
+ self._show_error(self.tr("Updating is not supported by this PyAppify version."))
140
+ return
141
+ version = self.version_combo.currentText()
142
+ self._set_busy(True)
143
+ self._set_status(self.tr("Starting change to {version}…").format(version=version))
144
+ self._run_in_background(
145
+ lambda: update_to_version(version, exit_event=self.exit_event),
146
+ self._update_finished,
147
+ f"pyappify.update_to_version({version!r})",
148
+ )
149
+
150
+ def _run_in_background(self, operation, signal, operation_name):
151
+ def run():
152
+ logger.info(f"calling {operation_name}")
153
+ try:
154
+ result = operation()
155
+ logger.info(f"{operation_name} result={result!r}")
156
+ signal.emit((True, result))
157
+ except Exception as error:
158
+ logger.error(f"{operation_name} failed: {error}", error)
159
+ signal.emit((False, str(error)))
160
+
161
+ threading.Thread(target=run, daemon=True, name="pyappify-update").start()
162
+
163
+ def _apply_versions(self, result):
164
+ self._set_busy(False, refresh_selection=False)
165
+ successful, value = result
166
+ if not successful:
167
+ self.versions = []
168
+ self.version_combo.clear()
169
+ self._set_version_controls_visible(False)
170
+ self.update_available_changed.emit(False)
171
+ self._show_error(self.tr("Failed to check for updates: {error}").format(error=value))
172
+ return
173
+
174
+ self.versions = [item for item in value if isinstance(item, dict) and item.get("version")]
175
+ self.version_combo.blockSignals(True)
176
+ self.version_combo.clear()
177
+ self.version_combo.addItems([str(item["version"]) for item in self.versions])
178
+ self.version_combo.blockSignals(False)
179
+ self._resize_version_combo()
180
+ logger.info(
181
+ f"loaded {len(self.versions)} valid versions into selector: "
182
+ f"{[item['version'] for item in self.versions]!r}"
183
+ )
184
+
185
+ newest_update = next(
186
+ (index for index, item in enumerate(self.versions)
187
+ if self._compare_versions(str(item["version"]), self.current_version) > 0),
188
+ None,
189
+ )
190
+ self.update_available_changed.emit(newest_update is not None)
191
+ logger.info(
192
+ f"update_available={newest_update is not None}, current_version={self.current_version!r}, "
193
+ f"newest_update_index={newest_update!r}"
194
+ )
195
+ if not self.versions:
196
+ self._set_version_controls_visible(False)
197
+ self._set_notes("")
198
+ self._set_status(self.tr("No versions are available."))
199
+ self.update_button.setEnabled(False)
200
+ return
201
+ self._set_version_controls_visible(True)
202
+ self._set_status("" if newest_update is not None else self.tr("No updates available."))
203
+ self.version_combo.setCurrentIndex(0)
204
+ self._selection_changed()
205
+
206
+ def _selection_changed(self, _index=None):
207
+ index = self.version_combo.currentIndex()
208
+ if index < 0 or index >= len(self.versions):
209
+ self.update_button.setEnabled(False)
210
+ return
211
+ selected = self.versions[index]
212
+ target = str(selected["version"])
213
+ direction = self._compare_versions(target, self.current_version)
214
+ logger.debug(
215
+ f"selected version={target!r}, current_version={self.current_version!r}, direction={direction}"
216
+ )
217
+ self.update_button.setEnabled(direction != 0 and not self._busy)
218
+ self.update_button.setText(self.tr("Update") if direction > 0 else self.tr("Downgrade"))
219
+
220
+ if direction == 0:
221
+ self.update_button.setText(self.tr("Current version"))
222
+
223
+ calculate_notes = getattr(self.pyappify_module, "calculate_update_notes", None)
224
+ if not callable(calculate_notes):
225
+ self._set_notes("")
226
+ self._set_status(self.tr("Update-note calculation is not supported."), error=True)
227
+ return
228
+ try:
229
+ notes = calculate_notes(self.versions, self.current_version, target)
230
+ self._set_notes(
231
+ "\n".join(f"• {note}" for note in notes) or self.tr("No release notes.")
232
+ )
233
+ except Exception as error:
234
+ logger.error(f"pyappify.calculate_update_notes failed: {error}", error)
235
+ self._set_notes("")
236
+ self._set_status(self.tr("Failed to calculate update notes: {error}").format(error=error), error=True)
237
+
238
+ def _resize_version_combo(self):
239
+ font_metrics = QFontMetrics(self.version_combo.font())
240
+ text_width = max(
241
+ (font_metrics.horizontalAdvance(str(item["version"])) for item in self.versions),
242
+ default=0,
243
+ )
244
+ content_width = text_width + 48
245
+ width = max(self.VERSION_COMBO_MIN_WIDTH, min(self.VERSION_COMBO_MAX_WIDTH, content_width))
246
+ self.version_combo.setFixedWidth(width)
247
+
248
+ def _set_version_controls_visible(self, visible):
249
+ self.version_label.setVisible(visible)
250
+ self.version_combo.setVisible(visible)
251
+
252
+ def _set_notes(self, text):
253
+ self.notes_edit.setPlainText(text)
254
+ self.notes_edit.setVisible(bool(text))
255
+
256
+ def _set_check_loading(self, loading):
257
+ if loading:
258
+ self.check_button.setIcon(self._loading_placeholder_icon)
259
+ self.check_progress.show()
260
+ self.check_progress.start()
261
+ else:
262
+ self.check_progress.stop()
263
+ self.check_progress.hide()
264
+ self.check_button.setIcon(FluentIcon.SYNC)
265
+ self._position_check_progress()
266
+
267
+ def _position_check_progress(self):
268
+ minimum_width = self.check_button.minimumSizeHint().width()
269
+ x = 12 + max(0, (self.check_button.width() - minimum_width) // 2)
270
+ self.check_progress.move(x, (self.check_button.height() - self.check_progress.height()) // 2)
271
+
272
+ def eventFilter(self, watched, event):
273
+ if watched is self.check_button and event.type() == QEvent.Type.Resize:
274
+ self._position_check_progress()
275
+ return super().eventFilter(watched, event)
276
+
277
+ def _apply_update_result(self, result):
278
+ self._set_busy(False)
279
+ successful, value = result
280
+ if successful:
281
+ self._set_status(self.tr("Update request accepted. The app will restart to apply it."))
282
+ else:
283
+ self._show_error(self.tr("Failed to change version: {error}").format(error=value))
284
+
285
+ def _set_busy(self, busy, checking=False, refresh_selection=True):
286
+ self._busy = busy
287
+ self.check_button.setEnabled(not busy)
288
+ self._set_check_loading(busy and checking)
289
+ self.test_version_checkbox.setEnabled(not busy)
290
+ self.version_combo.setEnabled(not busy)
291
+ if busy:
292
+ self.update_button.setEnabled(False)
293
+ elif refresh_selection:
294
+ self._selection_changed()
295
+
296
+ def _show_error(self, message):
297
+ self._set_busy(False, refresh_selection=False)
298
+ self._set_notes("")
299
+ self._set_status(message, error=True)
300
+
301
+ def _set_status(self, message, error=False):
302
+ self.status_label.setText(message)
303
+ self.status_label.setStyleSheet("color: #d13438;" if error else "")
304
+
305
+ def _compare_versions(self, left, right):
306
+ if left == right:
307
+ return 0
308
+ is_greater = getattr(self.pyappify_module, "is_greater_version", None)
309
+ if callable(is_greater):
310
+ if is_greater(left, right):
311
+ return 1
312
+ if is_greater(right, left):
313
+ return -1
314
+ return 0
@@ -0,0 +1,16 @@
1
+ from qfluentwidgets import SettingCard
2
+
3
+ from ok.ui.qt.about.LinksBar import LinksBar
4
+
5
+
6
+ class VersionCard(SettingCard):
7
+ """ Sample card """
8
+
9
+ def __init__(self, config, icon, title, version, debug, parent=None):
10
+ super().__init__(icon, title, f'{version} {self.get_type(debug)}')
11
+ links_bar = LinksBar(config)
12
+ self.iconLabel.setFixedSize(36, 36)
13
+ self.hBoxLayout.addWidget(links_bar)
14
+
15
+ def get_type(self, debug=None):
16
+ return self.tr('Debug') if debug else self.tr('Release')
@@ -11,7 +11,7 @@ from PySide6.QtWidgets import QLayout, QWidget
11
11
  class DesignToken:
12
12
  """The app's 8-point-grid-derived layout and sizing tokens."""
13
13
 
14
- PAGE_MARGIN = 24
14
+ PAGE_MARGIN = 16
15
15
  PAGE_SPACING = 12
16
16
 
17
17
  SECTION_SPACING = 12