@_vrsen/openswarm 0.1.0

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 (316) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +152 -0
  3. package/bin/openswarm.js +38 -0
  4. package/config.py +34 -0
  5. package/data_analyst_agent/.cursor/rules/data_analyst.mdc +43 -0
  6. package/data_analyst_agent/__init__.py +3 -0
  7. package/data_analyst_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  8. package/data_analyst_agent/__pycache__/data_analyst_agent.cpython-312.pyc +0 -0
  9. package/data_analyst_agent/data_analyst_agent.py +45 -0
  10. package/data_analyst_agent/instructions.md +173 -0
  11. package/data_analyst_agent/test_files/test_file.csv +21 -0
  12. package/data_analyst_agent/tools/__init__.py +6 -0
  13. package/deep_research/__init__.py +1 -0
  14. package/deep_research/__pycache__/__init__.cpython-312.pyc +0 -0
  15. package/deep_research/__pycache__/deep_research.cpython-312.pyc +0 -0
  16. package/deep_research/deep_research.py +27 -0
  17. package/deep_research/instructions.md +104 -0
  18. package/deep_research/tools/__init__.py +1 -0
  19. package/docs_agent/__init__.py +3 -0
  20. package/docs_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  21. package/docs_agent/__pycache__/docs_agent.cpython-312.pyc +0 -0
  22. package/docs_agent/docs_agent.py +61 -0
  23. package/docs_agent/instructions.md +418 -0
  24. package/docs_agent/tools/ConvertDocument.py +323 -0
  25. package/docs_agent/tools/CreateDocument.py +287 -0
  26. package/docs_agent/tools/ListDocuments.py +134 -0
  27. package/docs_agent/tools/ModifyDocument.py +247 -0
  28. package/docs_agent/tools/RestoreDocument.py +79 -0
  29. package/docs_agent/tools/ViewDocument.py +153 -0
  30. package/docs_agent/tools/__init__.py +1 -0
  31. package/docs_agent/tools/__pycache__/ConvertDocument.cpython-312.pyc +0 -0
  32. package/docs_agent/tools/__pycache__/CreateDocument.cpython-312.pyc +0 -0
  33. package/docs_agent/tools/__pycache__/ListDocuments.cpython-312.pyc +0 -0
  34. package/docs_agent/tools/__pycache__/ModifyDocument.cpython-312.pyc +0 -0
  35. package/docs_agent/tools/__pycache__/RestoreDocument.cpython-312.pyc +0 -0
  36. package/docs_agent/tools/__pycache__/ViewDocument.cpython-312.pyc +0 -0
  37. package/docs_agent/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  38. package/docs_agent/tools/utils/__init__.py +1 -0
  39. package/docs_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  40. package/docs_agent/tools/utils/__pycache__/doc_file_utils.cpython-312.pyc +0 -0
  41. package/docs_agent/tools/utils/__pycache__/html_docx_blocks.cpython-312.pyc +0 -0
  42. package/docs_agent/tools/utils/__pycache__/html_docx_constants.cpython-312.pyc +0 -0
  43. package/docs_agent/tools/utils/__pycache__/html_docx_core.cpython-312.pyc +0 -0
  44. package/docs_agent/tools/utils/__pycache__/html_docx_css.cpython-312.pyc +0 -0
  45. package/docs_agent/tools/utils/__pycache__/html_docx_images.cpython-312.pyc +0 -0
  46. package/docs_agent/tools/utils/__pycache__/html_docx_page.cpython-312.pyc +0 -0
  47. package/docs_agent/tools/utils/__pycache__/html_docx_paragraphs.cpython-312.pyc +0 -0
  48. package/docs_agent/tools/utils/__pycache__/html_docx_playwright.cpython-312.pyc +0 -0
  49. package/docs_agent/tools/utils/__pycache__/html_docx_selectors.cpython-312.pyc +0 -0
  50. package/docs_agent/tools/utils/__pycache__/html_docx_shared.cpython-312.pyc +0 -0
  51. package/docs_agent/tools/utils/__pycache__/html_validation.cpython-312.pyc +0 -0
  52. package/docs_agent/tools/utils/doc_file_utils.py +29 -0
  53. package/docs_agent/tools/utils/html_docx_blocks.py +262 -0
  54. package/docs_agent/tools/utils/html_docx_constants.py +78 -0
  55. package/docs_agent/tools/utils/html_docx_core.py +138 -0
  56. package/docs_agent/tools/utils/html_docx_css.py +262 -0
  57. package/docs_agent/tools/utils/html_docx_images.py +293 -0
  58. package/docs_agent/tools/utils/html_docx_page.py +185 -0
  59. package/docs_agent/tools/utils/html_docx_paragraphs.py +342 -0
  60. package/docs_agent/tools/utils/html_docx_playwright.py +184 -0
  61. package/docs_agent/tools/utils/html_docx_selectors.py +196 -0
  62. package/docs_agent/tools/utils/html_docx_shared.py +23 -0
  63. package/docs_agent/tools/utils/html_docx_tables.py +942 -0
  64. package/docs_agent/tools/utils/html_validation.py +102 -0
  65. package/helpers.py +59 -0
  66. package/image_generation_agent/__init__.py +1 -0
  67. package/image_generation_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  68. package/image_generation_agent/__pycache__/image_generation_agent.cpython-312.pyc +0 -0
  69. package/image_generation_agent/image_generation_agent.py +31 -0
  70. package/image_generation_agent/instructions.md +80 -0
  71. package/image_generation_agent/tools/CombineImages.py +211 -0
  72. package/image_generation_agent/tools/EditImages.py +200 -0
  73. package/image_generation_agent/tools/GenerateImages.py +184 -0
  74. package/image_generation_agent/tools/RemoveBackground.py +108 -0
  75. package/image_generation_agent/tools/__init__.py +2 -0
  76. package/image_generation_agent/tools/__pycache__/CombineImages.cpython-312.pyc +0 -0
  77. package/image_generation_agent/tools/__pycache__/EditImages.cpython-312.pyc +0 -0
  78. package/image_generation_agent/tools/__pycache__/GenerateImages.cpython-312.pyc +0 -0
  79. package/image_generation_agent/tools/__pycache__/RemoveBackground.cpython-312.pyc +0 -0
  80. package/image_generation_agent/tools/utils/__init__.py +2 -0
  81. package/image_generation_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  82. package/image_generation_agent/tools/utils/__pycache__/image_io.cpython-312.pyc +0 -0
  83. package/image_generation_agent/tools/utils/image_io.py +308 -0
  84. package/onboard.py +325 -0
  85. package/orchestrator/__init__.py +3 -0
  86. package/orchestrator/__pycache__/__init__.cpython-312.pyc +0 -0
  87. package/orchestrator/__pycache__/orchestrator.cpython-312.pyc +0 -0
  88. package/orchestrator/instructions.md +90 -0
  89. package/orchestrator/orchestrator.py +33 -0
  90. package/package.json +49 -0
  91. package/patches/__init__.py +1 -0
  92. package/patches/__pycache__/__init__.cpython-312.pyc +0 -0
  93. package/patches/__pycache__/patch_agency_swarm_dual_comms.cpython-312.pyc +0 -0
  94. package/patches/__pycache__/patch_file_attachment_refs.cpython-312.pyc +0 -0
  95. package/patches/__pycache__/patch_ipython_interpreter_composio.cpython-312.pyc +0 -0
  96. package/patches/dom-to-pptx+1.1.5.patch +133440 -0
  97. package/patches/patch_agency_swarm_dual_comms.py +199 -0
  98. package/patches/patch_file_attachment_refs.py +74 -0
  99. package/patches/patch_ipython_interpreter_composio.py +54 -0
  100. package/pyproject.toml +67 -0
  101. package/run.py +343 -0
  102. package/server.py +26 -0
  103. package/shared_instructions.md +119 -0
  104. package/shared_tools/CopyFile.py +68 -0
  105. package/shared_tools/ExecuteTool.py +184 -0
  106. package/shared_tools/FindTools.py +101 -0
  107. package/shared_tools/ManageConnections.py +43 -0
  108. package/shared_tools/SearchTools.py +44 -0
  109. package/shared_tools/__init__.py +7 -0
  110. package/shared_tools/__pycache__/CopyFile.cpython-312.pyc +0 -0
  111. package/shared_tools/__pycache__/ExecuteTool.cpython-312.pyc +0 -0
  112. package/shared_tools/__pycache__/FindTools.cpython-312.pyc +0 -0
  113. package/shared_tools/__pycache__/ManageConnections.cpython-312.pyc +0 -0
  114. package/shared_tools/__pycache__/SearchTools.cpython-312.pyc +0 -0
  115. package/shared_tools/__pycache__/__init__.cpython-312.pyc +0 -0
  116. package/slides_agent/.cursor/rules/slides-agent-workflow.mdc +9 -0
  117. package/slides_agent/__init__.py +1 -0
  118. package/slides_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  119. package/slides_agent/__pycache__/slides_agent.cpython-312.pyc +0 -0
  120. package/slides_agent/instructions.md +298 -0
  121. package/slides_agent/pptx/SKILL.md +528 -0
  122. package/slides_agent/pptx/html2pptx.md +625 -0
  123. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chart.xsd +1499 -0
  124. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chartDrawing.xsd +146 -0
  125. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-diagram.xsd +1085 -0
  126. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-lockedCanvas.xsd +11 -0
  127. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-main.xsd +3081 -0
  128. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-picture.xsd +23 -0
  129. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-spreadsheetDrawing.xsd +185 -0
  130. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-wordprocessingDrawing.xsd +287 -0
  131. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/pml.xsd +1676 -0
  132. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-additionalCharacteristics.xsd +28 -0
  133. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-bibliography.xsd +144 -0
  134. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-commonSimpleTypes.xsd +174 -0
  135. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlDataProperties.xsd +25 -0
  136. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlSchemaProperties.xsd +18 -0
  137. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesCustom.xsd +59 -0
  138. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesExtended.xsd +56 -0
  139. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesVariantTypes.xsd +195 -0
  140. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-math.xsd +582 -0
  141. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-relationshipReference.xsd +25 -0
  142. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/sml.xsd +4439 -0
  143. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-main.xsd +570 -0
  144. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-officeDrawing.xsd +509 -0
  145. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-presentationDrawing.xsd +12 -0
  146. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-spreadsheetDrawing.xsd +108 -0
  147. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-wordprocessingDrawing.xsd +96 -0
  148. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/wml.xsd +3646 -0
  149. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/xml.xsd +116 -0
  150. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-contentTypes.xsd +42 -0
  151. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-coreProperties.xsd +50 -0
  152. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-digSig.xsd +49 -0
  153. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-relationships.xsd +33 -0
  154. package/slides_agent/pptx/ooxml/schemas/mce/mc.xsd +75 -0
  155. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2010.xsd +560 -0
  156. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2012.xsd +67 -0
  157. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2018.xsd +14 -0
  158. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-cex-2018.xsd +20 -0
  159. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-cid-2016.xsd +13 -0
  160. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-sdtdatahash-2020.xsd +4 -0
  161. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-symex-2015.xsd +8 -0
  162. package/slides_agent/pptx/ooxml/scripts/pack.py +169 -0
  163. package/slides_agent/pptx/ooxml/scripts/unpack.py +29 -0
  164. package/slides_agent/pptx/ooxml/scripts/validate.py +69 -0
  165. package/slides_agent/pptx/ooxml/scripts/validation/__init__.py +15 -0
  166. package/slides_agent/pptx/ooxml/scripts/validation/base.py +951 -0
  167. package/slides_agent/pptx/ooxml/scripts/validation/docx.py +274 -0
  168. package/slides_agent/pptx/ooxml/scripts/validation/pptx.py +315 -0
  169. package/slides_agent/pptx/ooxml/scripts/validation/redlining.py +279 -0
  170. package/slides_agent/pptx/ooxml.md +427 -0
  171. package/slides_agent/pptx/scripts/html2pptx.js +1092 -0
  172. package/slides_agent/pptx/scripts/inventory.py +1020 -0
  173. package/slides_agent/pptx/scripts/rearrange.py +231 -0
  174. package/slides_agent/pptx/scripts/replace.py +385 -0
  175. package/slides_agent/pptx/scripts/thumbnail.py +451 -0
  176. package/slides_agent/slides_agent.py +109 -0
  177. package/slides_agent/test_deck/_theme.css +92 -0
  178. package/slides_agent/test_deck/assets/placeholder.svg +11 -0
  179. package/slides_agent/test_deck/slide_01_title.html +10 -0
  180. package/slides_agent/test_deck/slide_02_image_split.html +23 -0
  181. package/slides_agent/test_deck/slide_03_kpi.html +21 -0
  182. package/slides_agent/tools/ApplyPptxTextReplacements.py +91 -0
  183. package/slides_agent/tools/BuildPptxFromHtmlSlides.py +221 -0
  184. package/slides_agent/tools/CheckSlide.py +218 -0
  185. package/slides_agent/tools/CheckSlideCanvasOverflow.py +221 -0
  186. package/slides_agent/tools/CreateImageMontage.py +261 -0
  187. package/slides_agent/tools/CreatePptxThumbnailGrid.py +168 -0
  188. package/slides_agent/tools/DeleteSlide.py +78 -0
  189. package/slides_agent/tools/DownloadImage.py +79 -0
  190. package/slides_agent/tools/EnsureRasterImage.py +157 -0
  191. package/slides_agent/tools/ExtractPptxTextInventory.py +104 -0
  192. package/slides_agent/tools/GenerateImage.py +189 -0
  193. package/slides_agent/tools/ImageSearch.py +127 -0
  194. package/slides_agent/tools/InsertNewSlides.py +393 -0
  195. package/slides_agent/tools/ManageTheme.py +112 -0
  196. package/slides_agent/tools/ModifySlide.py +563 -0
  197. package/slides_agent/tools/ReadSlide.py +26 -0
  198. package/slides_agent/tools/RearrangePptxSlidesFromTemplate.py +114 -0
  199. package/slides_agent/tools/RestoreSnapshot.py +89 -0
  200. package/slides_agent/tools/SlideScreenshot.py +66 -0
  201. package/slides_agent/tools/__init__.py +54 -0
  202. package/slides_agent/tools/__pycache__/ApplyPptxTextReplacements.cpython-312.pyc +0 -0
  203. package/slides_agent/tools/__pycache__/BuildPptxFromHtmlSlides.cpython-312.pyc +0 -0
  204. package/slides_agent/tools/__pycache__/CheckSlide.cpython-312.pyc +0 -0
  205. package/slides_agent/tools/__pycache__/CheckSlideCanvasOverflow.cpython-312.pyc +0 -0
  206. package/slides_agent/tools/__pycache__/CreateImageMontage.cpython-312.pyc +0 -0
  207. package/slides_agent/tools/__pycache__/CreatePptxThumbnailGrid.cpython-312.pyc +0 -0
  208. package/slides_agent/tools/__pycache__/DeleteSlide.cpython-312.pyc +0 -0
  209. package/slides_agent/tools/__pycache__/DownloadImage.cpython-312.pyc +0 -0
  210. package/slides_agent/tools/__pycache__/EnsureRasterImage.cpython-312.pyc +0 -0
  211. package/slides_agent/tools/__pycache__/ExtractPptxTextInventory.cpython-312.pyc +0 -0
  212. package/slides_agent/tools/__pycache__/GenerateImage.cpython-312.pyc +0 -0
  213. package/slides_agent/tools/__pycache__/ImageSearch.cpython-312.pyc +0 -0
  214. package/slides_agent/tools/__pycache__/InsertNewSlides.cpython-312.pyc +0 -0
  215. package/slides_agent/tools/__pycache__/ManageTheme.cpython-312.pyc +0 -0
  216. package/slides_agent/tools/__pycache__/ModifySlide.cpython-312.pyc +0 -0
  217. package/slides_agent/tools/__pycache__/ReadSlide.cpython-312.pyc +0 -0
  218. package/slides_agent/tools/__pycache__/RearrangePptxSlidesFromTemplate.cpython-312.pyc +0 -0
  219. package/slides_agent/tools/__pycache__/RestoreSnapshot.cpython-312.pyc +0 -0
  220. package/slides_agent/tools/__pycache__/SlideScreenshot.cpython-312.pyc +0 -0
  221. package/slides_agent/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  222. package/slides_agent/tools/__pycache__/slide_file_utils.cpython-312.pyc +0 -0
  223. package/slides_agent/tools/__pycache__/slide_html_utils.cpython-312.pyc +0 -0
  224. package/slides_agent/tools/__pycache__/template_registry.cpython-312.pyc +0 -0
  225. package/slides_agent/tools/deck_utils.py +31 -0
  226. package/slides_agent/tools/html2pptx_runner.js +1183 -0
  227. package/slides_agent/tools/html_writer_instructions.md +149 -0
  228. package/slides_agent/tools/slide_file_utils.py +108 -0
  229. package/slides_agent/tools/slide_html_utils.py +354 -0
  230. package/slides_agent/tools/template_registry.py +55 -0
  231. package/swarm.py +82 -0
  232. package/video_generation_agent/__init__.py +1 -0
  233. package/video_generation_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  234. package/video_generation_agent/__pycache__/video_generation_agent.cpython-312.pyc +0 -0
  235. package/video_generation_agent/instructions.md +178 -0
  236. package/video_generation_agent/tools/AddSubtitles.py +425 -0
  237. package/video_generation_agent/tools/CombineImages.py +166 -0
  238. package/video_generation_agent/tools/CombineVideos.py +113 -0
  239. package/video_generation_agent/tools/EditAudio.py +297 -0
  240. package/video_generation_agent/tools/EditImage.py +144 -0
  241. package/video_generation_agent/tools/EditVideoContent.py +369 -0
  242. package/video_generation_agent/tools/GenerateImage.py +133 -0
  243. package/video_generation_agent/tools/GenerateVideo.py +556 -0
  244. package/video_generation_agent/tools/TrimVideo.py +233 -0
  245. package/video_generation_agent/tools/__init__.py +1 -0
  246. package/video_generation_agent/tools/__pycache__/AddSubtitles.cpython-312.pyc +0 -0
  247. package/video_generation_agent/tools/__pycache__/CombineImages.cpython-312.pyc +0 -0
  248. package/video_generation_agent/tools/__pycache__/CombineVideos.cpython-312.pyc +0 -0
  249. package/video_generation_agent/tools/__pycache__/EditAudio.cpython-312.pyc +0 -0
  250. package/video_generation_agent/tools/__pycache__/EditImage.cpython-312.pyc +0 -0
  251. package/video_generation_agent/tools/__pycache__/EditVideoContent.cpython-312.pyc +0 -0
  252. package/video_generation_agent/tools/__pycache__/GenerateImage.cpython-312.pyc +0 -0
  253. package/video_generation_agent/tools/__pycache__/GenerateVideo.cpython-312.pyc +0 -0
  254. package/video_generation_agent/tools/__pycache__/TrimVideo.cpython-312.pyc +0 -0
  255. package/video_generation_agent/tools/utils/__init__.py +1 -0
  256. package/video_generation_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  257. package/video_generation_agent/tools/utils/__pycache__/image_utils.cpython-312.pyc +0 -0
  258. package/video_generation_agent/tools/utils/__pycache__/video_utils.cpython-312.pyc +0 -0
  259. package/video_generation_agent/tools/utils/image_utils.py +174 -0
  260. package/video_generation_agent/tools/utils/video_utils.py +522 -0
  261. package/video_generation_agent/video_generation_agent.py +26 -0
  262. package/virtual_assistant/__init__.py +1 -0
  263. package/virtual_assistant/__pycache__/__init__.cpython-312.pyc +0 -0
  264. package/virtual_assistant/__pycache__/virtual_assistant.cpython-312.pyc +0 -0
  265. package/virtual_assistant/instructions.md +206 -0
  266. package/virtual_assistant/tools/AddLabelToEmail.py +154 -0
  267. package/virtual_assistant/tools/CheckEventsForDate.py +218 -0
  268. package/virtual_assistant/tools/CheckUnreadSlackMessages.py +216 -0
  269. package/virtual_assistant/tools/CreateCalendarEvent.py +261 -0
  270. package/virtual_assistant/tools/DeleteCalendarEvent.py +137 -0
  271. package/virtual_assistant/tools/DeleteDraft.py +95 -0
  272. package/virtual_assistant/tools/DraftEmail.py +239 -0
  273. package/virtual_assistant/tools/EditFile.py +113 -0
  274. package/virtual_assistant/tools/FindEmails.py +330 -0
  275. package/virtual_assistant/tools/GetCurrentTime.py +69 -0
  276. package/virtual_assistant/tools/GetSlackUserInfo.py +117 -0
  277. package/virtual_assistant/tools/ListDirectory.py +113 -0
  278. package/virtual_assistant/tools/ListSkills.py +94 -0
  279. package/virtual_assistant/tools/ManageLabels.py +295 -0
  280. package/virtual_assistant/tools/ProductSearch.py +254 -0
  281. package/virtual_assistant/tools/ReadEmail.py +251 -0
  282. package/virtual_assistant/tools/ReadFile.py +108 -0
  283. package/virtual_assistant/tools/ReadSlackMessages.py +191 -0
  284. package/virtual_assistant/tools/RemoveLabelFromEmail.py +137 -0
  285. package/virtual_assistant/tools/RescheduleCalendarEvent.py +227 -0
  286. package/virtual_assistant/tools/ScholarSearch.py +216 -0
  287. package/virtual_assistant/tools/SendDraft.py +101 -0
  288. package/virtual_assistant/tools/SendSlackMessage.py +148 -0
  289. package/virtual_assistant/tools/WriteFile.py +95 -0
  290. package/virtual_assistant/tools/__init__.py +1 -0
  291. package/virtual_assistant/tools/__pycache__/AddLabelToEmail.cpython-312.pyc +0 -0
  292. package/virtual_assistant/tools/__pycache__/CheckEventsForDate.cpython-312.pyc +0 -0
  293. package/virtual_assistant/tools/__pycache__/CheckUnreadSlackMessages.cpython-312.pyc +0 -0
  294. package/virtual_assistant/tools/__pycache__/CreateCalendarEvent.cpython-312.pyc +0 -0
  295. package/virtual_assistant/tools/__pycache__/DeleteCalendarEvent.cpython-312.pyc +0 -0
  296. package/virtual_assistant/tools/__pycache__/DeleteDraft.cpython-312.pyc +0 -0
  297. package/virtual_assistant/tools/__pycache__/DraftEmail.cpython-312.pyc +0 -0
  298. package/virtual_assistant/tools/__pycache__/EditFile.cpython-312.pyc +0 -0
  299. package/virtual_assistant/tools/__pycache__/FindEmails.cpython-312.pyc +0 -0
  300. package/virtual_assistant/tools/__pycache__/GetCurrentTime.cpython-312.pyc +0 -0
  301. package/virtual_assistant/tools/__pycache__/GetSlackUserInfo.cpython-312.pyc +0 -0
  302. package/virtual_assistant/tools/__pycache__/ListDirectory.cpython-312.pyc +0 -0
  303. package/virtual_assistant/tools/__pycache__/ListSkills.cpython-312.pyc +0 -0
  304. package/virtual_assistant/tools/__pycache__/ManageLabels.cpython-312.pyc +0 -0
  305. package/virtual_assistant/tools/__pycache__/ProductSearch.cpython-312.pyc +0 -0
  306. package/virtual_assistant/tools/__pycache__/ReadEmail.cpython-312.pyc +0 -0
  307. package/virtual_assistant/tools/__pycache__/ReadFile.cpython-312.pyc +0 -0
  308. package/virtual_assistant/tools/__pycache__/ReadSlackMessages.cpython-312.pyc +0 -0
  309. package/virtual_assistant/tools/__pycache__/RemoveLabelFromEmail.cpython-312.pyc +0 -0
  310. package/virtual_assistant/tools/__pycache__/RescheduleCalendarEvent.cpython-312.pyc +0 -0
  311. package/virtual_assistant/tools/__pycache__/ScholarSearch.cpython-312.pyc +0 -0
  312. package/virtual_assistant/tools/__pycache__/SendDraft.cpython-312.pyc +0 -0
  313. package/virtual_assistant/tools/__pycache__/SendSlackMessage.cpython-312.pyc +0 -0
  314. package/virtual_assistant/tools/__pycache__/WriteFile.cpython-312.pyc +0 -0
  315. package/virtual_assistant/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  316. package/virtual_assistant/virtual_assistant.py +52 -0
@@ -0,0 +1,451 @@
1
+ #!/usr/bin/env python3
2
+ """
3
+ Create thumbnail grids from PowerPoint presentation slides.
4
+
5
+ Creates a grid layout of slide thumbnails with configurable columns (max 6).
6
+ Each grid contains up to cols×(cols+1) images. For presentations with more
7
+ slides, multiple numbered grid files are created automatically.
8
+
9
+ The program outputs the names of all files created.
10
+
11
+ Output:
12
+ - Single grid: {prefix}.jpg (if slides fit in one grid)
13
+ - Multiple grids: {prefix}-1.jpg, {prefix}-2.jpg, etc.
14
+
15
+ Grid limits by column count:
16
+ - 3 cols: max 12 slides per grid (3×4)
17
+ - 4 cols: max 20 slides per grid (4×5)
18
+ - 5 cols: max 30 slides per grid (5×6) [default]
19
+ - 6 cols: max 42 slides per grid (6×7)
20
+
21
+ Usage:
22
+ python thumbnail.py input.pptx [output_prefix] [--cols N] [--outline-placeholders]
23
+
24
+ Examples:
25
+ python thumbnail.py presentation.pptx
26
+ # Creates: thumbnails.jpg (using default prefix)
27
+ # Outputs:
28
+ # Created 1 grid(s):
29
+ # - thumbnails.jpg
30
+
31
+ python thumbnail.py large-deck.pptx grid --cols 4
32
+ # Creates: grid-1.jpg, grid-2.jpg, grid-3.jpg
33
+ # Outputs:
34
+ # Created 3 grid(s):
35
+ # - grid-1.jpg
36
+ # - grid-2.jpg
37
+ # - grid-3.jpg
38
+
39
+ python thumbnail.py template.pptx analysis --outline-placeholders
40
+ # Creates thumbnail grids with red outlines around text placeholders
41
+ """
42
+
43
+ import argparse
44
+ import os
45
+ import subprocess
46
+ import sys
47
+ import tempfile
48
+ from pathlib import Path
49
+
50
+ from inventory import extract_text_inventory
51
+ from PIL import Image, ImageDraw
52
+ from pptx import Presentation
53
+
54
+ # Constants
55
+ THUMBNAIL_WIDTH = 420 # Fixed thumbnail width in pixels
56
+ CONVERSION_DPI = 100 # DPI for PDF to image conversion
57
+ MAX_COLS = 6 # Maximum number of columns
58
+ DEFAULT_COLS = 5 # Default number of columns
59
+ JPEG_QUALITY = 95 # JPEG compression quality
60
+ SOFFICE_TIMEOUT = 60 # Seconds for LibreOffice conversion
61
+ PDFTOPPM_TIMEOUT = 60 # Seconds for Poppler rasterization
62
+
63
+ # Grid layout constants
64
+ GRID_PADDING = 20 # Padding between thumbnails
65
+ BORDER_WIDTH = 2 # Border width around thumbnails
66
+
67
+
68
+ def main():
69
+ parser = argparse.ArgumentParser(
70
+ description="Create thumbnail grids from PowerPoint slides."
71
+ )
72
+ parser.add_argument("input", help="Input PowerPoint file (.pptx)")
73
+ parser.add_argument(
74
+ "output_prefix",
75
+ nargs="?",
76
+ default="thumbnails",
77
+ help="Output prefix for image files (default: thumbnails, will create prefix.jpg or prefix-N.jpg)",
78
+ )
79
+ parser.add_argument(
80
+ "--cols",
81
+ type=int,
82
+ default=DEFAULT_COLS,
83
+ help=f"Number of columns (default: {DEFAULT_COLS}, max: {MAX_COLS})",
84
+ )
85
+ parser.add_argument(
86
+ "--outline-placeholders",
87
+ action="store_true",
88
+ help="Outline text placeholders with a colored border",
89
+ )
90
+
91
+ args = parser.parse_args()
92
+
93
+ # Validate columns
94
+ cols = min(args.cols, MAX_COLS)
95
+ if args.cols > MAX_COLS:
96
+ print(f"Warning: Columns limited to {MAX_COLS} (requested {args.cols})")
97
+
98
+ # Validate input
99
+ input_path = Path(args.input)
100
+ if not input_path.exists() or input_path.suffix.lower() != ".pptx":
101
+ print(f"Error: Invalid PowerPoint file: {args.input}")
102
+ sys.exit(1)
103
+
104
+ # Construct output path (always JPG)
105
+ output_path = Path(f"{args.output_prefix}.jpg")
106
+
107
+ print(f"Processing: {args.input}")
108
+
109
+ try:
110
+ with tempfile.TemporaryDirectory() as temp_dir:
111
+ # Get placeholder regions if outlining is enabled
112
+ placeholder_regions = None
113
+ slide_dimensions = None
114
+ if args.outline_placeholders:
115
+ print("Extracting placeholder regions...")
116
+ placeholder_regions, slide_dimensions = get_placeholder_regions(
117
+ input_path
118
+ )
119
+ if placeholder_regions:
120
+ print(f"Found placeholders on {len(placeholder_regions)} slides")
121
+
122
+ # Convert slides to images
123
+ slide_images = convert_to_images(input_path, Path(temp_dir), CONVERSION_DPI)
124
+ if not slide_images:
125
+ print("Error: No slides found")
126
+ sys.exit(1)
127
+
128
+ print(f"Found {len(slide_images)} slides")
129
+
130
+ # Create grids (max cols×(cols+1) images per grid)
131
+ grid_files = create_grids(
132
+ slide_images,
133
+ cols,
134
+ THUMBNAIL_WIDTH,
135
+ output_path,
136
+ placeholder_regions,
137
+ slide_dimensions,
138
+ )
139
+
140
+ # Print saved files
141
+ print(f"Created {len(grid_files)} grid(s):")
142
+ for grid_file in grid_files:
143
+ print(f" - {grid_file}")
144
+
145
+ except Exception as e:
146
+ print(f"Error: {e}")
147
+ sys.exit(1)
148
+
149
+
150
+ def create_hidden_slide_placeholder(size):
151
+ """Create placeholder image for hidden slides."""
152
+ img = Image.new("RGB", size, color="#F0F0F0")
153
+ draw = ImageDraw.Draw(img)
154
+ line_width = max(5, min(size) // 100)
155
+ draw.line([(0, 0), size], fill="#CCCCCC", width=line_width)
156
+ draw.line([(size[0], 0), (0, size[1])], fill="#CCCCCC", width=line_width)
157
+ return img
158
+
159
+
160
+ def get_placeholder_regions(pptx_path):
161
+ """Extract ALL text regions from the presentation.
162
+
163
+ Returns a tuple of (placeholder_regions, slide_dimensions).
164
+ text_regions is a dict mapping slide indices to lists of text regions.
165
+ Each region is a dict with 'left', 'top', 'width', 'height' in inches.
166
+ slide_dimensions is a tuple of (width_inches, height_inches).
167
+ """
168
+ prs = Presentation(str(pptx_path))
169
+ inventory = extract_text_inventory(pptx_path, prs)
170
+ placeholder_regions = {}
171
+
172
+ # Get actual slide dimensions in inches (EMU to inches conversion)
173
+ slide_width_inches = (prs.slide_width or 9144000) / 914400.0
174
+ slide_height_inches = (prs.slide_height or 5143500) / 914400.0
175
+
176
+ for slide_key, shapes in inventory.items():
177
+ # Extract slide index from "slide-N" format
178
+ slide_idx = int(slide_key.split("-")[1])
179
+ regions = []
180
+
181
+ for shape_key, shape_data in shapes.items():
182
+ # The inventory only contains shapes with text, so all shapes should be highlighted
183
+ regions.append(
184
+ {
185
+ "left": shape_data.left,
186
+ "top": shape_data.top,
187
+ "width": shape_data.width,
188
+ "height": shape_data.height,
189
+ }
190
+ )
191
+
192
+ if regions:
193
+ placeholder_regions[slide_idx] = regions
194
+
195
+ return placeholder_regions, (slide_width_inches, slide_height_inches)
196
+
197
+
198
+ def convert_to_images(pptx_path, temp_dir, dpi):
199
+ """Convert PowerPoint to images via PDF, handling hidden slides."""
200
+ # Detect hidden slides
201
+ print("Analyzing presentation...")
202
+ prs = Presentation(str(pptx_path))
203
+ total_slides = len(prs.slides)
204
+
205
+ # Find hidden slides (1-based indexing for display)
206
+ hidden_slides = {
207
+ idx + 1
208
+ for idx, slide in enumerate(prs.slides)
209
+ if slide.element.get("show") == "0"
210
+ }
211
+
212
+ print(f"Total slides: {total_slides}")
213
+ if hidden_slides:
214
+ print(f"Hidden slides: {sorted(hidden_slides)}")
215
+
216
+ pdf_path = temp_dir / f"{pptx_path.stem}.pdf"
217
+
218
+ # Convert to PDF
219
+ print("Converting to PDF...")
220
+ try:
221
+ kwargs = {
222
+ "capture_output": True,
223
+ "text": True,
224
+ "timeout": SOFFICE_TIMEOUT,
225
+ "input": "\n",
226
+ }
227
+ if os.name == "nt":
228
+ kwargs["creationflags"] = 0x08000000 # CREATE_NO_WINDOW
229
+
230
+ # On Windows, prefer soffice.com for CLI usage as it handles headless mode better than soffice.exe
231
+ soffice_bin = "soffice.com" if os.name == "nt" else "soffice"
232
+
233
+ result = subprocess.run(
234
+ [
235
+ soffice_bin,
236
+ "--headless",
237
+ "--convert-to",
238
+ "pdf",
239
+ "--outdir",
240
+ str(temp_dir),
241
+ str(pptx_path),
242
+ ],
243
+ **kwargs
244
+ )
245
+ except subprocess.TimeoutExpired as exc:
246
+ raise RuntimeError(f"PDF conversion timed out after {SOFFICE_TIMEOUT}s") from exc
247
+ if result.returncode != 0 or not pdf_path.exists():
248
+ raise RuntimeError("PDF conversion failed")
249
+
250
+ # Convert PDF to images
251
+ print(f"Converting to images at {dpi} DPI...")
252
+ try:
253
+ kwargs = {
254
+ "capture_output": True,
255
+ "text": True,
256
+ "timeout": PDFTOPPM_TIMEOUT,
257
+ "stdin": subprocess.DEVNULL,
258
+ }
259
+ if os.name == "nt":
260
+ kwargs["creationflags"] = 0x08000000 # CREATE_NO_WINDOW
261
+
262
+ result = subprocess.run(
263
+ ["pdftoppm", "-jpeg", "-r", str(dpi), str(pdf_path), str(temp_dir / "slide")],
264
+ **kwargs
265
+ )
266
+ except subprocess.TimeoutExpired as exc:
267
+ raise RuntimeError(
268
+ f"Image conversion timed out after {PDFTOPPM_TIMEOUT}s"
269
+ ) from exc
270
+ if result.returncode != 0:
271
+ raise RuntimeError("Image conversion failed")
272
+
273
+ visible_images = sorted(temp_dir.glob("slide-*.jpg"))
274
+
275
+ # Create full list with placeholders for hidden slides
276
+ all_images = []
277
+ visible_idx = 0
278
+
279
+ # Get placeholder dimensions from first visible slide
280
+ if visible_images:
281
+ with Image.open(visible_images[0]) as img:
282
+ placeholder_size = img.size
283
+ else:
284
+ placeholder_size = (1920, 1080)
285
+
286
+ for slide_num in range(1, total_slides + 1):
287
+ if slide_num in hidden_slides:
288
+ # Create placeholder image for hidden slide
289
+ placeholder_path = temp_dir / f"hidden-{slide_num:03d}.jpg"
290
+ placeholder_img = create_hidden_slide_placeholder(placeholder_size)
291
+ placeholder_img.save(placeholder_path, "JPEG")
292
+ all_images.append(placeholder_path)
293
+ else:
294
+ # Use the actual visible slide image
295
+ if visible_idx < len(visible_images):
296
+ all_images.append(visible_images[visible_idx])
297
+ visible_idx += 1
298
+
299
+ return all_images
300
+
301
+
302
+ def create_grids(
303
+ image_paths,
304
+ cols,
305
+ width,
306
+ output_path,
307
+ placeholder_regions=None,
308
+ slide_dimensions=None,
309
+ ):
310
+ """Create multiple thumbnail grids from slide images, max cols×(cols+1) images per grid."""
311
+ # Maximum images per grid is cols × (cols + 1) for better proportions
312
+ max_images_per_grid = cols * (cols + 1)
313
+ grid_files = []
314
+
315
+ print(
316
+ f"Creating grids with {cols} columns (max {max_images_per_grid} images per grid)"
317
+ )
318
+
319
+ # Split images into chunks
320
+ for chunk_idx, start_idx in enumerate(
321
+ range(0, len(image_paths), max_images_per_grid)
322
+ ):
323
+ end_idx = min(start_idx + max_images_per_grid, len(image_paths))
324
+ chunk_images = image_paths[start_idx:end_idx]
325
+
326
+ # Create grid for this chunk
327
+ grid = create_grid(
328
+ chunk_images, cols, width, start_idx, placeholder_regions, slide_dimensions
329
+ )
330
+
331
+ # Generate output filename
332
+ if len(image_paths) <= max_images_per_grid:
333
+ # Single grid - use base filename without suffix
334
+ grid_filename = output_path
335
+ else:
336
+ # Multiple grids - insert index before extension with dash
337
+ stem = output_path.stem
338
+ suffix = output_path.suffix
339
+ grid_filename = output_path.parent / f"{stem}-{chunk_idx + 1}{suffix}"
340
+
341
+ # Save grid
342
+ grid_filename.parent.mkdir(parents=True, exist_ok=True)
343
+ grid.save(str(grid_filename), quality=JPEG_QUALITY)
344
+ grid_files.append(str(grid_filename))
345
+
346
+ return grid_files
347
+
348
+
349
+ def create_grid(
350
+ image_paths,
351
+ cols,
352
+ width,
353
+ start_slide_num=0,
354
+ placeholder_regions=None,
355
+ slide_dimensions=None,
356
+ ):
357
+ """Create thumbnail grid from slide images with optional placeholder outlining."""
358
+ # Get dimensions
359
+ with Image.open(image_paths[0]) as img:
360
+ aspect = img.height / img.width
361
+ height = int(width * aspect)
362
+
363
+ # Calculate grid size
364
+ rows = (len(image_paths) + cols - 1) // cols
365
+ grid_w = cols * width + (cols + 1) * GRID_PADDING
366
+ grid_h = rows * height + (rows + 1) * GRID_PADDING
367
+
368
+ # Create grid
369
+ grid = Image.new("RGB", (grid_w, grid_h), "white")
370
+ draw = ImageDraw.Draw(grid)
371
+
372
+ # Place thumbnails
373
+ for i, img_path in enumerate(image_paths):
374
+ row, col = i // cols, i % cols
375
+ x = col * width + (col + 1) * GRID_PADDING
376
+ y_thumbnail = row * height + (row + 1) * GRID_PADDING
377
+
378
+ with Image.open(img_path) as img:
379
+ # Get original dimensions before thumbnail
380
+ orig_w, orig_h = img.size
381
+
382
+ # Apply placeholder outlines if enabled
383
+ if placeholder_regions and (start_slide_num + i) in placeholder_regions:
384
+ # Convert to RGBA for transparency support
385
+ if img.mode != "RGBA":
386
+ img = img.convert("RGBA")
387
+
388
+ # Get the regions for this slide
389
+ regions = placeholder_regions[start_slide_num + i]
390
+
391
+ # Calculate scale factors using actual slide dimensions
392
+ if slide_dimensions:
393
+ slide_width_inches, slide_height_inches = slide_dimensions
394
+ else:
395
+ # Fallback: estimate from image size at CONVERSION_DPI
396
+ slide_width_inches = orig_w / CONVERSION_DPI
397
+ slide_height_inches = orig_h / CONVERSION_DPI
398
+
399
+ x_scale = orig_w / slide_width_inches
400
+ y_scale = orig_h / slide_height_inches
401
+
402
+ # Create a highlight overlay
403
+ overlay = Image.new("RGBA", img.size, (255, 255, 255, 0))
404
+ overlay_draw = ImageDraw.Draw(overlay)
405
+
406
+ # Highlight each placeholder region
407
+ for region in regions:
408
+ # Convert from inches to pixels in the original image
409
+ px_left = int(region["left"] * x_scale)
410
+ px_top = int(region["top"] * y_scale)
411
+ px_width = int(region["width"] * x_scale)
412
+ px_height = int(region["height"] * y_scale)
413
+
414
+ # Draw highlight outline with red color and thick stroke
415
+ # Using a bright red outline instead of fill
416
+ stroke_width = max(
417
+ 5, min(orig_w, orig_h) // 150
418
+ ) # Thicker proportional stroke width
419
+ overlay_draw.rectangle(
420
+ [(px_left, px_top), (px_left + px_width, px_top + px_height)],
421
+ outline=(255, 0, 0, 255), # Bright red, fully opaque
422
+ width=stroke_width,
423
+ )
424
+
425
+ # Composite the overlay onto the image using alpha blending
426
+ img = Image.alpha_composite(img, overlay)
427
+ # Convert back to RGB for JPEG saving
428
+ img = img.convert("RGB")
429
+
430
+ img.thumbnail((width, height), Image.Resampling.LANCZOS)
431
+ w, h = img.size
432
+ tx = x + (width - w) // 2
433
+ ty = y_thumbnail + (height - h) // 2
434
+ grid.paste(img, (tx, ty))
435
+
436
+ # Add border
437
+ if BORDER_WIDTH > 0:
438
+ draw.rectangle(
439
+ [
440
+ (tx - BORDER_WIDTH, ty - BORDER_WIDTH),
441
+ (tx + w + BORDER_WIDTH - 1, ty + h + BORDER_WIDTH - 1),
442
+ ],
443
+ outline="gray",
444
+ width=BORDER_WIDTH,
445
+ )
446
+
447
+ return grid
448
+
449
+
450
+ if __name__ == "__main__":
451
+ main()
@@ -0,0 +1,109 @@
1
+ from agency_swarm import Agent, ModelSettings
2
+ from agency_swarm.tools import IPythonInterpreter, PersistentShellTool, LoadFileAttachment, WebSearchTool
3
+ from datetime import datetime, timezone
4
+ from openai.types.shared import Reasoning
5
+ from pathlib import Path
6
+ from virtual_assistant.tools.ReadFile import ReadFile
7
+
8
+ from config import get_default_model, is_openai_provider
9
+
10
+ # Import slide tools
11
+ from .tools import (
12
+ InsertNewSlides,
13
+ ModifySlide,
14
+ ManageTheme,
15
+ DeleteSlide,
16
+ SlideScreenshot,
17
+ ReadSlide,
18
+ BuildPptxFromHtmlSlides,
19
+ RestoreSnapshot,
20
+ CreatePptxThumbnailGrid,
21
+ CheckSlideCanvasOverflow,
22
+ CheckSlide,
23
+ DownloadImage,
24
+ EnsureRasterImage,
25
+ # ExtractPptxTextInventory,
26
+ # RearrangePptxSlidesFromTemplate,
27
+ # ApplyPptxTextReplacements,
28
+ ImageSearch,
29
+ GenerateImage,
30
+ )
31
+
32
+ _INSTRUCTIONS_PATH = Path(__file__).parent / "instructions.md"
33
+
34
+
35
+ def _list_existing_projects() -> str:
36
+ from .tools.slide_file_utils import get_mnt_dir
37
+ base = get_mnt_dir()
38
+ if not base.exists():
39
+ return "(none)"
40
+ dirs = sorted(d.name for d in base.iterdir() if d.is_dir())
41
+ return "\n".join(f" - {d}" for d in dirs) if dirs else "(none)"
42
+
43
+
44
+ def _build_instructions() -> str:
45
+ now_utc = datetime.now(timezone.utc).strftime("%Y-%m-%d %H:%M UTC")
46
+ body = _INSTRUCTIONS_PATH.read_text(encoding="utf-8")
47
+ projects_block = _list_existing_projects()
48
+ return (
49
+ f"{body}\n\n"
50
+ f"Current date/time (UTC): {now_utc}\n\n"
51
+ f"Existing project folders (do NOT reuse these names for a new presentation):\n{projects_block}"
52
+ )
53
+
54
+
55
+ def create_slides_agent() -> Agent:
56
+ return Agent(
57
+ name="Slides Agent",
58
+ description="PowerPoint presentation specialist for creating, editing, and analyzing .pptx files",
59
+ instructions=_build_instructions(),
60
+ # files_folder=os.path.join(current_dir, "files"),
61
+ # tools_folder=os.path.join(current_dir, "tools"),
62
+ tools=[
63
+ # Slide creation and management: InsertNewSlides then ModifySlide
64
+ InsertNewSlides,
65
+ ModifySlide,
66
+ ManageTheme,
67
+ DeleteSlide,
68
+ SlideScreenshot,
69
+ ReadSlide,
70
+ # PPTX building
71
+ BuildPptxFromHtmlSlides,
72
+ RestoreSnapshot,
73
+ CreatePptxThumbnailGrid,
74
+ CheckSlideCanvasOverflow,
75
+ CheckSlide,
76
+ # Image download
77
+ DownloadImage,
78
+ EnsureRasterImage,
79
+ GenerateImage,
80
+ # Template-based editing
81
+ # ExtractPptxTextInventory,
82
+ # RearrangePptxSlidesFromTemplate,
83
+ # ApplyPptxTextReplacements,
84
+ ImageSearch,
85
+ # Utility tools
86
+ IPythonInterpreter,
87
+ PersistentShellTool,
88
+ LoadFileAttachment,
89
+ ReadFile,
90
+ WebSearchTool(search_context_size="high"),
91
+ ],
92
+ model=get_default_model(),
93
+ model_settings=ModelSettings(
94
+ reasoning=Reasoning(effort="high", summary="auto") if is_openai_provider() else None,
95
+ verbosity="medium" if is_openai_provider() else None,
96
+ response_include=["web_search_call.action.sources"] if is_openai_provider() else None,
97
+ ),
98
+ conversation_starters=[
99
+ "Create a new presentation about the benefits of using AI in the workplace.",
100
+ "Edit my existing presentation and improve the design.",
101
+ "Create a pitch deck for my startup idea.",
102
+ "Turn this document into a professional slide deck.",
103
+ ],
104
+ )
105
+
106
+
107
+ if __name__ == "__main__":
108
+ from agency_swarm import Agency
109
+ Agency(create_slides_agent()).terminal_demo(reload=False)
@@ -0,0 +1,92 @@
1
+ :root {
2
+ --bg: #F7F4EF;
3
+ --ink: #141518;
4
+ --muted: #5B606A;
5
+ --accent: #E36A2E;
6
+ --card: #FFFFFF;
7
+ --line: #D7D1C7;
8
+ --dark: #0F0F10;
9
+ }
10
+
11
+ * { box-sizing: border-box; }
12
+ body {
13
+ margin: 0;
14
+ background: var(--bg);
15
+ color: var(--ink);
16
+ font-family: "Inter", Helvetica, Arial, sans-serif;
17
+ }
18
+ h1, h2, h3, p, ul, ol { margin: 0; }
19
+
20
+ h1 { font-size: 56px; line-height: 1.05; font-weight: 800; letter-spacing: -0.4px; }
21
+ h2 { font-size: 36px; line-height: 1.12; font-weight: 800; letter-spacing: -0.25px; }
22
+ h3 { font-size: 24px; line-height: 1.18; font-weight: 800; }
23
+ p { font-size: 20px; line-height: 1.35; color: var(--ink); }
24
+
25
+ .small { font-size: 16px; line-height: 1.35; color: var(--muted); }
26
+ .kicker { font-size: 16px; letter-spacing: 2px; font-weight: 800; color: var(--accent); }
27
+
28
+ .canvas {
29
+ width: 100%;
30
+ height: 100%;
31
+ padding: 32px 32px 48px 32px;
32
+ overflow: hidden;
33
+ }
34
+
35
+ .title-block { display: flex; flex-direction: column; gap: 24px; }
36
+ .subtitle { font-size: 28px; line-height: 1.35; color: var(--muted); }
37
+ .footer { position: absolute; left: 32px; right: 32px; bottom: 48px; }
38
+
39
+ .font-serif { font-family: "Merriweather", serif; }
40
+ .font-sans { font-family: "Inter", sans-serif; }
41
+ .font-mono { font-family: "Roboto Mono", monospace; }
42
+
43
+ .split { display: flex; gap: 32px; height: 100%; }
44
+ .leftPanel {
45
+ width: 420px;
46
+ background: var(--dark);
47
+ color: #FFFFFF;
48
+ border-radius: 20px;
49
+ padding: 32px;
50
+ display: flex;
51
+ flex-direction: column;
52
+ justify-content: space-between;
53
+ }
54
+ .leftPanel h1, .leftPanel h2, .leftPanel h3, .leftPanel p { color: #FFFFFF; }
55
+ .rightPanel {
56
+ flex: 1;
57
+ background: var(--card);
58
+ border: 2px solid var(--line);
59
+ border-radius: 20px;
60
+ padding: 32px;
61
+ display: flex;
62
+ flex-direction: column;
63
+ gap: 20px;
64
+ }
65
+
66
+ .image-frame {
67
+ width: 100%;
68
+ height: 360px;
69
+ border-radius: 16px;
70
+ overflow: hidden;
71
+ border: 2px solid var(--line);
72
+ background: #FFFFFF;
73
+ }
74
+ .image-frame img {
75
+ width: 100%;
76
+ height: 100%;
77
+ object-fit: cover;
78
+ }
79
+
80
+ .kpi-row { display: flex; gap: 20px; margin-top: 24px; }
81
+ .kpi-card {
82
+ flex: 1;
83
+ background: var(--card);
84
+ border: 2px solid var(--line);
85
+ border-radius: 16px;
86
+ padding: 20px;
87
+ }
88
+ .kpi-value { font-size: 48px; font-weight: 800; color: var(--dark); }
89
+ .kpi-label { font-size: 18px; color: var(--muted); }
90
+
91
+ ul { padding-left: 22px; }
92
+ ul li { font-size: 18px; line-height: 1.35; margin: 8px 0; }
@@ -0,0 +1,11 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" width="1200" height="800" viewBox="0 0 1200 800">
2
+ <rect width="1200" height="800" fill="#F2EEE8"/>
3
+ <rect x="40" y="40" width="1120" height="720" fill="#FFFFFF" stroke="#D7D1C7" stroke-width="6" rx="24"/>
4
+ <circle cx="220" cy="240" r="70" fill="#E36A2E" opacity="0.85"/>
5
+ <rect x="340" y="200" width="700" height="22" fill="#141518" opacity="0.85"/>
6
+ <rect x="340" y="250" width="560" height="18" fill="#5B606A" opacity="0.7"/>
7
+ <rect x="340" y="300" width="620" height="18" fill="#5B606A" opacity="0.6"/>
8
+ <rect x="140" y="430" width="920" height="180" fill="#F7F4EF" stroke="#D7D1C7" stroke-width="4" rx="16"/>
9
+ <text x="600" y="520" text-anchor="middle" font-family="Arial, Helvetica, sans-serif" font-size="36" fill="#141518">Image Placeholder</text>
10
+ <text x="600" y="570" text-anchor="middle" font-family="Arial, Helvetica, sans-serif" font-size="22" fill="#5B606A">Replace with a real visual</text>
11
+ </svg>
@@ -0,0 +1,10 @@
1
+ <div class="canvas">
2
+ <div class="title-block">
3
+ <p class="kicker">TEST DECK</p>
4
+ <h1>Slides Agent Layout Smoke Test</h1>
5
+ <p class="subtitle">Full-size 1280x720 canvas with safe margins.</p>
6
+ </div>
7
+ <div class="footer">
8
+ <p class="small">Internal QA deck • Includes image and KPI layouts</p>
9
+ </div>
10
+ </div>
@@ -0,0 +1,23 @@
1
+ <div class="canvas">
2
+ <div class="split">
3
+ <div class="leftPanel">
4
+ <div>
5
+ <p class="kicker">VISUAL</p>
6
+ <h2>Image-led split layout</h2>
7
+ <p class="small">Use real imagery and keep explicit sizing.</p>
8
+ </div>
9
+ <ul>
10
+ <li>Image fills a framed container</li>
11
+ <li>Text stays inside fixed panels</li>
12
+ <li>No overlap or overflow</li>
13
+ </ul>
14
+ <p class="small">Inline SVG or image icons only</p>
15
+ </div>
16
+ <div class="rightPanel">
17
+ <div class="image-frame">
18
+ <img src="./assets/placeholder.svg" alt="Placeholder image" />
19
+ </div>
20
+ <p class="small">Example: product mockup or market photo</p>
21
+ </div>
22
+ </div>
23
+ </div>