reflectt-node 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 (486) hide show
  1. package/LICENSE +178 -0
  2. package/README.md +188 -0
  3. package/dist/activationEvents.d.ts +110 -0
  4. package/dist/activationEvents.d.ts.map +1 -0
  5. package/dist/activationEvents.js +378 -0
  6. package/dist/activationEvents.js.map +1 -0
  7. package/dist/activity-signal.d.ts +30 -0
  8. package/dist/activity-signal.d.ts.map +1 -0
  9. package/dist/activity-signal.js +93 -0
  10. package/dist/activity-signal.js.map +1 -0
  11. package/dist/alert-integrity.d.ts +100 -0
  12. package/dist/alert-integrity.d.ts.map +1 -0
  13. package/dist/alert-integrity.js +333 -0
  14. package/dist/alert-integrity.js.map +1 -0
  15. package/dist/alert-preflight.d.ts +40 -0
  16. package/dist/alert-preflight.d.ts.map +1 -0
  17. package/dist/alert-preflight.js +235 -0
  18. package/dist/alert-preflight.js.map +1 -0
  19. package/dist/analytics.d.ts +131 -0
  20. package/dist/analytics.d.ts.map +1 -0
  21. package/dist/analytics.js +371 -0
  22. package/dist/analytics.js.map +1 -0
  23. package/dist/artifact-mirror.d.ts +26 -0
  24. package/dist/artifact-mirror.d.ts.map +1 -0
  25. package/dist/artifact-mirror.js +170 -0
  26. package/dist/artifact-mirror.js.map +1 -0
  27. package/dist/artifact-resolver.d.ts +48 -0
  28. package/dist/artifact-resolver.d.ts.map +1 -0
  29. package/dist/artifact-resolver.js +164 -0
  30. package/dist/artifact-resolver.js.map +1 -0
  31. package/dist/assignment.d.ts +116 -0
  32. package/dist/assignment.d.ts.map +1 -0
  33. package/dist/assignment.js +475 -0
  34. package/dist/assignment.js.map +1 -0
  35. package/dist/auditLedger.d.ts +50 -0
  36. package/dist/auditLedger.d.ts.map +1 -0
  37. package/dist/auditLedger.js +136 -0
  38. package/dist/auditLedger.js.map +1 -0
  39. package/dist/boardHealthWorker.d.ts +134 -0
  40. package/dist/boardHealthWorker.d.ts.map +1 -0
  41. package/dist/boardHealthWorker.js +882 -0
  42. package/dist/boardHealthWorker.js.map +1 -0
  43. package/dist/bootstrap-team.d.ts +42 -0
  44. package/dist/bootstrap-team.d.ts.map +1 -0
  45. package/dist/bootstrap-team.js +111 -0
  46. package/dist/bootstrap-team.js.map +1 -0
  47. package/dist/buildInfo.d.ts +17 -0
  48. package/dist/buildInfo.d.ts.map +1 -0
  49. package/dist/buildInfo.js +56 -0
  50. package/dist/buildInfo.js.map +1 -0
  51. package/dist/calendar-events.d.ts +133 -0
  52. package/dist/calendar-events.d.ts.map +1 -0
  53. package/dist/calendar-events.js +615 -0
  54. package/dist/calendar-events.js.map +1 -0
  55. package/dist/calendar-ical.d.ts +41 -0
  56. package/dist/calendar-ical.d.ts.map +1 -0
  57. package/dist/calendar-ical.js +413 -0
  58. package/dist/calendar-ical.js.map +1 -0
  59. package/dist/calendar-reminder-engine.d.ts +10 -0
  60. package/dist/calendar-reminder-engine.d.ts.map +1 -0
  61. package/dist/calendar-reminder-engine.js +143 -0
  62. package/dist/calendar-reminder-engine.js.map +1 -0
  63. package/dist/calendar.d.ts +75 -0
  64. package/dist/calendar.d.ts.map +1 -0
  65. package/dist/calendar.js +391 -0
  66. package/dist/calendar.js.map +1 -0
  67. package/dist/canvas-multiplexer.d.ts +44 -0
  68. package/dist/canvas-multiplexer.d.ts.map +1 -0
  69. package/dist/canvas-multiplexer.js +150 -0
  70. package/dist/canvas-multiplexer.js.map +1 -0
  71. package/dist/canvas-slots.d.ts +83 -0
  72. package/dist/canvas-slots.d.ts.map +1 -0
  73. package/dist/canvas-slots.js +144 -0
  74. package/dist/canvas-slots.js.map +1 -0
  75. package/dist/canvas-types.d.ts +56 -0
  76. package/dist/canvas-types.d.ts.map +1 -0
  77. package/dist/canvas-types.js +54 -0
  78. package/dist/canvas-types.js.map +1 -0
  79. package/dist/cf-keepalive.d.ts +40 -0
  80. package/dist/cf-keepalive.d.ts.map +1 -0
  81. package/dist/cf-keepalive.js +153 -0
  82. package/dist/cf-keepalive.js.map +1 -0
  83. package/dist/changeFeed.d.ts +38 -0
  84. package/dist/changeFeed.d.ts.map +1 -0
  85. package/dist/changeFeed.js +324 -0
  86. package/dist/changeFeed.js.map +1 -0
  87. package/dist/channels.d.ts +28 -0
  88. package/dist/channels.d.ts.map +1 -0
  89. package/dist/channels.js +23 -0
  90. package/dist/channels.js.map +1 -0
  91. package/dist/chat-approval-detector.d.ts +47 -0
  92. package/dist/chat-approval-detector.d.ts.map +1 -0
  93. package/dist/chat-approval-detector.js +224 -0
  94. package/dist/chat-approval-detector.js.map +1 -0
  95. package/dist/chat.d.ts +119 -0
  96. package/dist/chat.d.ts.map +1 -0
  97. package/dist/chat.js +666 -0
  98. package/dist/chat.js.map +1 -0
  99. package/dist/cli.d.ts +3 -0
  100. package/dist/cli.d.ts.map +1 -0
  101. package/dist/cli.js +1142 -0
  102. package/dist/cli.js.map +1 -0
  103. package/dist/cloud.d.ts +45 -0
  104. package/dist/cloud.d.ts.map +1 -0
  105. package/dist/cloud.js +962 -0
  106. package/dist/cloud.js.map +1 -0
  107. package/dist/config.d.ts +17 -0
  108. package/dist/config.d.ts.map +1 -0
  109. package/dist/config.js +33 -0
  110. package/dist/config.js.map +1 -0
  111. package/dist/connectivity.d.ts +59 -0
  112. package/dist/connectivity.d.ts.map +1 -0
  113. package/dist/connectivity.js +173 -0
  114. package/dist/connectivity.js.map +1 -0
  115. package/dist/contacts.d.ts +59 -0
  116. package/dist/contacts.d.ts.map +1 -0
  117. package/dist/contacts.js +183 -0
  118. package/dist/contacts.js.map +1 -0
  119. package/dist/content.d.ts +130 -0
  120. package/dist/content.d.ts.map +1 -0
  121. package/dist/content.js +186 -0
  122. package/dist/content.js.map +1 -0
  123. package/dist/context-budget.d.ts +87 -0
  124. package/dist/context-budget.d.ts.map +1 -0
  125. package/dist/context-budget.js +459 -0
  126. package/dist/context-budget.js.map +1 -0
  127. package/dist/continuity-loop.d.ts +55 -0
  128. package/dist/continuity-loop.d.ts.map +1 -0
  129. package/dist/continuity-loop.js +267 -0
  130. package/dist/continuity-loop.js.map +1 -0
  131. package/dist/dashboard.d.ts +6 -0
  132. package/dist/dashboard.d.ts.map +1 -0
  133. package/dist/dashboard.js +2348 -0
  134. package/dist/dashboard.js.map +1 -0
  135. package/dist/db.d.ts +44 -0
  136. package/dist/db.d.ts.map +1 -0
  137. package/dist/db.js +648 -0
  138. package/dist/db.js.map +1 -0
  139. package/dist/doctor.d.ts +30 -0
  140. package/dist/doctor.d.ts.map +1 -0
  141. package/dist/doctor.js +159 -0
  142. package/dist/doctor.js.map +1 -0
  143. package/dist/duplicateClosureGuard.d.ts +31 -0
  144. package/dist/duplicateClosureGuard.d.ts.map +1 -0
  145. package/dist/duplicateClosureGuard.js +83 -0
  146. package/dist/duplicateClosureGuard.js.map +1 -0
  147. package/dist/embeddings.d.ts +13 -0
  148. package/dist/embeddings.d.ts.map +1 -0
  149. package/dist/embeddings.js +78 -0
  150. package/dist/embeddings.js.map +1 -0
  151. package/dist/escalation.d.ts +80 -0
  152. package/dist/escalation.d.ts.map +1 -0
  153. package/dist/escalation.js +213 -0
  154. package/dist/escalation.js.map +1 -0
  155. package/dist/events.d.ts +130 -0
  156. package/dist/events.d.ts.map +1 -0
  157. package/dist/events.js +382 -0
  158. package/dist/events.js.map +1 -0
  159. package/dist/executionSweeper.d.ts +97 -0
  160. package/dist/executionSweeper.d.ts.map +1 -0
  161. package/dist/executionSweeper.js +875 -0
  162. package/dist/executionSweeper.js.map +1 -0
  163. package/dist/experiments.d.ts +47 -0
  164. package/dist/experiments.d.ts.map +1 -0
  165. package/dist/experiments.js +133 -0
  166. package/dist/experiments.js.map +1 -0
  167. package/dist/feedback.d.ts +179 -0
  168. package/dist/feedback.d.ts.map +1 -0
  169. package/dist/feedback.js +397 -0
  170. package/dist/feedback.js.map +1 -0
  171. package/dist/files.d.ts +52 -0
  172. package/dist/files.d.ts.map +1 -0
  173. package/dist/files.js +172 -0
  174. package/dist/files.js.map +1 -0
  175. package/dist/format-duration.d.ts +19 -0
  176. package/dist/format-duration.d.ts.map +1 -0
  177. package/dist/format-duration.js +33 -0
  178. package/dist/format-duration.js.map +1 -0
  179. package/dist/github-actor-auth.d.ts +20 -0
  180. package/dist/github-actor-auth.d.ts.map +1 -0
  181. package/dist/github-actor-auth.js +54 -0
  182. package/dist/github-actor-auth.js.map +1 -0
  183. package/dist/github-ci.d.ts +16 -0
  184. package/dist/github-ci.d.ts.map +1 -0
  185. package/dist/github-ci.js +37 -0
  186. package/dist/github-ci.js.map +1 -0
  187. package/dist/github-identity.d.ts +30 -0
  188. package/dist/github-identity.d.ts.map +1 -0
  189. package/dist/github-identity.js +96 -0
  190. package/dist/github-identity.js.map +1 -0
  191. package/dist/github-reviews.d.ts +24 -0
  192. package/dist/github-reviews.d.ts.map +1 -0
  193. package/dist/github-reviews.js +56 -0
  194. package/dist/github-reviews.js.map +1 -0
  195. package/dist/health.d.ts +391 -0
  196. package/dist/health.d.ts.map +1 -0
  197. package/dist/health.js +1841 -0
  198. package/dist/health.js.map +1 -0
  199. package/dist/host-keepalive.d.ts +22 -0
  200. package/dist/host-keepalive.d.ts.map +1 -0
  201. package/dist/host-keepalive.js +126 -0
  202. package/dist/host-keepalive.js.map +1 -0
  203. package/dist/host-registry.d.ts +43 -0
  204. package/dist/host-registry.d.ts.map +1 -0
  205. package/dist/host-registry.js +93 -0
  206. package/dist/host-registry.js.map +1 -0
  207. package/dist/inbox.d.ts +87 -0
  208. package/dist/inbox.d.ts.map +1 -0
  209. package/dist/inbox.js +410 -0
  210. package/dist/inbox.js.map +1 -0
  211. package/dist/index.d.ts +2 -0
  212. package/dist/index.d.ts.map +1 -0
  213. package/dist/index.js +306 -0
  214. package/dist/index.js.map +1 -0
  215. package/dist/insight-mutation.d.ts +32 -0
  216. package/dist/insight-mutation.d.ts.map +1 -0
  217. package/dist/insight-mutation.js +160 -0
  218. package/dist/insight-mutation.js.map +1 -0
  219. package/dist/insight-promotion.d.ts +89 -0
  220. package/dist/insight-promotion.d.ts.map +1 -0
  221. package/dist/insight-promotion.js +278 -0
  222. package/dist/insight-promotion.js.map +1 -0
  223. package/dist/insight-task-bridge.d.ts +77 -0
  224. package/dist/insight-task-bridge.d.ts.map +1 -0
  225. package/dist/insight-task-bridge.js +556 -0
  226. package/dist/insight-task-bridge.js.map +1 -0
  227. package/dist/insights.d.ts +222 -0
  228. package/dist/insights.d.ts.map +1 -0
  229. package/dist/insights.js +871 -0
  230. package/dist/insights.js.map +1 -0
  231. package/dist/intake-pipeline.d.ts +74 -0
  232. package/dist/intake-pipeline.d.ts.map +1 -0
  233. package/dist/intake-pipeline.js +199 -0
  234. package/dist/intake-pipeline.js.map +1 -0
  235. package/dist/intensity.d.ts +31 -0
  236. package/dist/intensity.d.ts.map +1 -0
  237. package/dist/intensity.js +94 -0
  238. package/dist/intensity.js.map +1 -0
  239. package/dist/knowledge-auto-index.d.ts +37 -0
  240. package/dist/knowledge-auto-index.d.ts.map +1 -0
  241. package/dist/knowledge-auto-index.js +149 -0
  242. package/dist/knowledge-auto-index.js.map +1 -0
  243. package/dist/knowledge-docs.d.ts +45 -0
  244. package/dist/knowledge-docs.d.ts.map +1 -0
  245. package/dist/knowledge-docs.js +188 -0
  246. package/dist/knowledge-docs.js.map +1 -0
  247. package/dist/lane-config.d.ts +25 -0
  248. package/dist/lane-config.d.ts.map +1 -0
  249. package/dist/lane-config.js +105 -0
  250. package/dist/lane-config.js.map +1 -0
  251. package/dist/lineage.d.ts +86 -0
  252. package/dist/lineage.d.ts.map +1 -0
  253. package/dist/lineage.js +303 -0
  254. package/dist/lineage.js.map +1 -0
  255. package/dist/logStore.d.ts +25 -0
  256. package/dist/logStore.d.ts.map +1 -0
  257. package/dist/logStore.js +83 -0
  258. package/dist/logStore.js.map +1 -0
  259. package/dist/manage.d.ts +12 -0
  260. package/dist/manage.d.ts.map +1 -0
  261. package/dist/manage.js +253 -0
  262. package/dist/manage.js.map +1 -0
  263. package/dist/mcp.d.ts +5 -0
  264. package/dist/mcp.d.ts.map +1 -0
  265. package/dist/mcp.js +604 -0
  266. package/dist/mcp.js.map +1 -0
  267. package/dist/memory.d.ts +47 -0
  268. package/dist/memory.d.ts.map +1 -0
  269. package/dist/memory.js +149 -0
  270. package/dist/memory.js.map +1 -0
  271. package/dist/mention-ack.d.ts +80 -0
  272. package/dist/mention-ack.d.ts.map +1 -0
  273. package/dist/mention-ack.js +175 -0
  274. package/dist/mention-ack.js.map +1 -0
  275. package/dist/messageRouter.d.ts +60 -0
  276. package/dist/messageRouter.d.ts.map +1 -0
  277. package/dist/messageRouter.js +309 -0
  278. package/dist/messageRouter.js.map +1 -0
  279. package/dist/mutationAlert.d.ts +44 -0
  280. package/dist/mutationAlert.d.ts.map +1 -0
  281. package/dist/mutationAlert.js +174 -0
  282. package/dist/mutationAlert.js.map +1 -0
  283. package/dist/noise-budget.d.ts +136 -0
  284. package/dist/noise-budget.d.ts.map +1 -0
  285. package/dist/noise-budget.js +340 -0
  286. package/dist/noise-budget.js.map +1 -0
  287. package/dist/notifications.d.ts +67 -0
  288. package/dist/notifications.d.ts.map +1 -0
  289. package/dist/notifications.js +253 -0
  290. package/dist/notifications.js.map +1 -0
  291. package/dist/openclaw.d.ts +34 -0
  292. package/dist/openclaw.d.ts.map +1 -0
  293. package/dist/openclaw.js +208 -0
  294. package/dist/openclaw.js.map +1 -0
  295. package/dist/pause-controls.d.ts +31 -0
  296. package/dist/pause-controls.d.ts.map +1 -0
  297. package/dist/pause-controls.js +130 -0
  298. package/dist/pause-controls.js.map +1 -0
  299. package/dist/pidlock.d.ts +25 -0
  300. package/dist/pidlock.d.ts.map +1 -0
  301. package/dist/pidlock.js +179 -0
  302. package/dist/pidlock.js.map +1 -0
  303. package/dist/policy.d.ts +139 -0
  304. package/dist/policy.d.ts.map +1 -0
  305. package/dist/policy.js +264 -0
  306. package/dist/policy.js.map +1 -0
  307. package/dist/polls.d.ts +47 -0
  308. package/dist/polls.d.ts.map +1 -0
  309. package/dist/polls.js +162 -0
  310. package/dist/polls.js.map +1 -0
  311. package/dist/portability.d.ts +55 -0
  312. package/dist/portability.d.ts.map +1 -0
  313. package/dist/portability.js +292 -0
  314. package/dist/portability.js.map +1 -0
  315. package/dist/pr-integrity.d.ts +45 -0
  316. package/dist/pr-integrity.d.ts.map +1 -0
  317. package/dist/pr-integrity.js +124 -0
  318. package/dist/pr-integrity.js.map +1 -0
  319. package/dist/prAutoMerge.d.ts +62 -0
  320. package/dist/prAutoMerge.d.ts.map +1 -0
  321. package/dist/prAutoMerge.js +493 -0
  322. package/dist/prAutoMerge.js.map +1 -0
  323. package/dist/preflight.d.ts +66 -0
  324. package/dist/preflight.d.ts.map +1 -0
  325. package/dist/preflight.js +864 -0
  326. package/dist/preflight.js.map +1 -0
  327. package/dist/presence.d.ts +98 -0
  328. package/dist/presence.d.ts.map +1 -0
  329. package/dist/presence.js +347 -0
  330. package/dist/presence.js.map +1 -0
  331. package/dist/provisioning.d.ts +101 -0
  332. package/dist/provisioning.d.ts.map +1 -0
  333. package/dist/provisioning.js +430 -0
  334. package/dist/provisioning.js.map +1 -0
  335. package/dist/reflection-automation.d.ts +59 -0
  336. package/dist/reflection-automation.d.ts.map +1 -0
  337. package/dist/reflection-automation.js +350 -0
  338. package/dist/reflection-automation.js.map +1 -0
  339. package/dist/reflections.d.ts +65 -0
  340. package/dist/reflections.d.ts.map +1 -0
  341. package/dist/reflections.js +306 -0
  342. package/dist/reflections.js.map +1 -0
  343. package/dist/release.d.ts +67 -0
  344. package/dist/release.d.ts.map +1 -0
  345. package/dist/release.js +275 -0
  346. package/dist/release.js.map +1 -0
  347. package/dist/request-tracker.d.ts +36 -0
  348. package/dist/request-tracker.d.ts.map +1 -0
  349. package/dist/request-tracker.js +109 -0
  350. package/dist/request-tracker.js.map +1 -0
  351. package/dist/research.d.ts +75 -0
  352. package/dist/research.d.ts.map +1 -0
  353. package/dist/research.js +171 -0
  354. package/dist/research.js.map +1 -0
  355. package/dist/routing-approvals.d.ts +73 -0
  356. package/dist/routing-approvals.d.ts.map +1 -0
  357. package/dist/routing-approvals.js +88 -0
  358. package/dist/routing-approvals.js.map +1 -0
  359. package/dist/routing-override.d.ts +94 -0
  360. package/dist/routing-override.d.ts.map +1 -0
  361. package/dist/routing-override.js +290 -0
  362. package/dist/routing-override.js.map +1 -0
  363. package/dist/scope-routing.d.ts +18 -0
  364. package/dist/scope-routing.d.ts.map +1 -0
  365. package/dist/scope-routing.js +29 -0
  366. package/dist/scope-routing.js.map +1 -0
  367. package/dist/secrets.d.ts +77 -0
  368. package/dist/secrets.d.ts.map +1 -0
  369. package/dist/secrets.js +287 -0
  370. package/dist/secrets.js.map +1 -0
  371. package/dist/server.d.ts +3 -0
  372. package/dist/server.d.ts.map +1 -0
  373. package/dist/server.js +10887 -0
  374. package/dist/server.js.map +1 -0
  375. package/dist/service-probe.d.ts +53 -0
  376. package/dist/service-probe.d.ts.map +1 -0
  377. package/dist/service-probe.js +225 -0
  378. package/dist/service-probe.js.map +1 -0
  379. package/dist/shared-workspace-api.d.ts +73 -0
  380. package/dist/shared-workspace-api.d.ts.map +1 -0
  381. package/dist/shared-workspace-api.js +281 -0
  382. package/dist/shared-workspace-api.js.map +1 -0
  383. package/dist/shipped-heartbeat.d.ts +91 -0
  384. package/dist/shipped-heartbeat.d.ts.map +1 -0
  385. package/dist/shipped-heartbeat.js +272 -0
  386. package/dist/shipped-heartbeat.js.map +1 -0
  387. package/dist/starter-team.d.ts +23 -0
  388. package/dist/starter-team.d.ts.map +1 -0
  389. package/dist/starter-team.js +88 -0
  390. package/dist/starter-team.js.map +1 -0
  391. package/dist/suppression-ledger.d.ts +73 -0
  392. package/dist/suppression-ledger.d.ts.map +1 -0
  393. package/dist/suppression-ledger.js +125 -0
  394. package/dist/suppression-ledger.js.map +1 -0
  395. package/dist/system-loop-state.d.ts +4 -0
  396. package/dist/system-loop-state.d.ts.map +1 -0
  397. package/dist/system-loop-state.js +40 -0
  398. package/dist/system-loop-state.js.map +1 -0
  399. package/dist/taskCommentIngest.d.ts +43 -0
  400. package/dist/taskCommentIngest.d.ts.map +1 -0
  401. package/dist/taskCommentIngest.js +59 -0
  402. package/dist/taskCommentIngest.js.map +1 -0
  403. package/dist/taskPrecheck.d.ts +20 -0
  404. package/dist/taskPrecheck.d.ts.map +1 -0
  405. package/dist/taskPrecheck.js +329 -0
  406. package/dist/taskPrecheck.js.map +1 -0
  407. package/dist/taskStateSync.d.ts +8 -0
  408. package/dist/taskStateSync.d.ts.map +1 -0
  409. package/dist/taskStateSync.js +79 -0
  410. package/dist/taskStateSync.js.map +1 -0
  411. package/dist/tasks.d.ts +140 -0
  412. package/dist/tasks.d.ts.map +1 -0
  413. package/dist/tasks.js +1281 -0
  414. package/dist/tasks.js.map +1 -0
  415. package/dist/team-config.d.ts +24 -0
  416. package/dist/team-config.d.ts.map +1 -0
  417. package/dist/team-config.js +221 -0
  418. package/dist/team-config.js.map +1 -0
  419. package/dist/team-doctor.d.ts +22 -0
  420. package/dist/team-doctor.d.ts.map +1 -0
  421. package/dist/team-doctor.js +270 -0
  422. package/dist/team-doctor.js.map +1 -0
  423. package/dist/team-pulse.d.ts +52 -0
  424. package/dist/team-pulse.d.ts.map +1 -0
  425. package/dist/team-pulse.js +176 -0
  426. package/dist/team-pulse.js.map +1 -0
  427. package/dist/telemetry.d.ts +74 -0
  428. package/dist/telemetry.d.ts.map +1 -0
  429. package/dist/telemetry.js +256 -0
  430. package/dist/telemetry.js.map +1 -0
  431. package/dist/test-task-filter.d.ts +21 -0
  432. package/dist/test-task-filter.d.ts.map +1 -0
  433. package/dist/test-task-filter.js +48 -0
  434. package/dist/test-task-filter.js.map +1 -0
  435. package/dist/types.d.ts +126 -0
  436. package/dist/types.d.ts.map +1 -0
  437. package/dist/types.js +4 -0
  438. package/dist/types.js.map +1 -0
  439. package/dist/usage-tracking.d.ts +101 -0
  440. package/dist/usage-tracking.d.ts.map +1 -0
  441. package/dist/usage-tracking.js +325 -0
  442. package/dist/usage-tracking.js.map +1 -0
  443. package/dist/vector-store.d.ts +87 -0
  444. package/dist/vector-store.d.ts.map +1 -0
  445. package/dist/vector-store.js +247 -0
  446. package/dist/vector-store.js.map +1 -0
  447. package/dist/watchdog/idleNudgeLane.d.ts +22 -0
  448. package/dist/watchdog/idleNudgeLane.d.ts.map +1 -0
  449. package/dist/watchdog/idleNudgeLane.js +98 -0
  450. package/dist/watchdog/idleNudgeLane.js.map +1 -0
  451. package/dist/webhooks.d.ts +103 -0
  452. package/dist/webhooks.d.ts.map +1 -0
  453. package/dist/webhooks.js +398 -0
  454. package/dist/webhooks.js.map +1 -0
  455. package/dist/working-contract.d.ts +42 -0
  456. package/dist/working-contract.d.ts.map +1 -0
  457. package/dist/working-contract.js +228 -0
  458. package/dist/working-contract.js.map +1 -0
  459. package/dist/ws-heartbeat.d.ts +66 -0
  460. package/dist/ws-heartbeat.d.ts.map +1 -0
  461. package/dist/ws-heartbeat.js +174 -0
  462. package/dist/ws-heartbeat.js.map +1 -0
  463. package/package.json +87 -0
  464. package/plugins/reflectt-channel/README.md +96 -0
  465. package/plugins/reflectt-channel/index.ts +789 -0
  466. package/plugins/reflectt-channel/openclaw.plugin.json +23 -0
  467. package/plugins/reflectt-channel/package.json +23 -0
  468. package/plugins/reflectt-channel/src/channel.ts +433 -0
  469. package/plugins/reflectt-channel/src/types.ts +29 -0
  470. package/public/avatars/echo.png +0 -0
  471. package/public/avatars/harmony.png +0 -0
  472. package/public/avatars/kai.png +0 -0
  473. package/public/avatars/link.png +0 -0
  474. package/public/avatars/pixel.png +0 -0
  475. package/public/avatars/rhythm.png +0 -0
  476. package/public/avatars/ryan.png +0 -0
  477. package/public/avatars/sage.png +0 -0
  478. package/public/avatars/scout.png +0 -0
  479. package/public/avatars/spark.png +0 -0
  480. package/public/dashboard-animations.css +381 -0
  481. package/public/dashboard.js +3479 -0
  482. package/public/docs.md +1062 -0
  483. package/public/file-upload-mock.html +1097 -0
  484. package/public/og-card.png +0 -0
  485. package/public/ui-kit.html +318 -0
  486. package/public/widget/feedback.js +194 -0
@@ -0,0 +1,2348 @@
1
+ // SPDX-License-Identifier: Apache-2.0
2
+ // Copyright (c) Reflectt AI
3
+ /**
4
+ * Dashboard HTML — self-contained page served at /dashboard
5
+ * v2: Pixel's redesign + chat input for Ryan
6
+ */
7
+ export function getDashboardHTML() {
8
+ return `<!DOCTYPE html>
9
+ <html lang="en">
10
+ <head>
11
+ <meta charset="UTF-8">
12
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
13
+ <title>reflectt-node dashboard</title>
14
+ <style>
15
+ /* ============================================================
16
+ REFLECTT DESIGN SYSTEM TOKENS v1
17
+ Source of truth for node + cloud UI parity.
18
+ Cloud should import/mirror these variables.
19
+ ============================================================ */
20
+ :root {
21
+ /* --- Color: Backgrounds --- */
22
+ --bg: #0a0e14;
23
+ --surface: #141920;
24
+ --surface-raised: #1a2028;
25
+
26
+ /* --- Color: Borders --- */
27
+ --border: #252d38;
28
+ --border-subtle: #1e2530;
29
+
30
+ /* --- Color: Text --- */
31
+ --text: #d4dae3;
32
+ --text-bright: #eef1f5;
33
+ --text-muted: #6b7a8d;
34
+
35
+ /* --- Color: Brand / Accent --- */
36
+ --accent: #4da6ff;
37
+ --accent-dim: rgba(77, 166, 255, 0.12);
38
+ --accent-hover: #6ab8ff;
39
+
40
+ /* --- Color: Semantic --- */
41
+ --green: #3fb950;
42
+ --green-dim: rgba(63, 185, 80, 0.12);
43
+ --yellow: #d4a017;
44
+ --yellow-dim: rgba(212, 160, 23, 0.12);
45
+ --red: #f85149;
46
+ --red-dim: rgba(248, 81, 73, 0.12);
47
+ --purple: #b48eff;
48
+ --orange: #e08a20;
49
+ --orange-dim: rgba(224, 138, 32, 0.12);
50
+
51
+ /* --- Typography: Scale (modular, base 14px) --- */
52
+ --font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', Helvetica, Arial, sans-serif;
53
+ --font-mono: 'SF Mono', 'Fira Code', 'Cascadia Code', 'Consolas', monospace;
54
+ --text-xs: 10px;
55
+ --text-sm: 11px;
56
+ --text-base: 13px;
57
+ --text-md: 14px;
58
+ --text-lg: 16px;
59
+ --text-xl: 18px;
60
+ --text-2xl: 22px;
61
+ --text-3xl: 28px;
62
+ --line-height-tight: 1.3;
63
+ --line-height-normal: 1.55;
64
+ --line-height-relaxed: 1.7;
65
+ --font-weight-normal: 400;
66
+ --font-weight-medium: 500;
67
+ --font-weight-semibold: 600;
68
+ --font-weight-bold: 700;
69
+ --letter-spacing-tight: -0.3px;
70
+ --letter-spacing-normal: 0;
71
+ --letter-spacing-wide: 0.5px;
72
+
73
+ /* --- Spacing: Scale (4px base) --- */
74
+ --space-1: 4px;
75
+ --space-2: 8px;
76
+ --space-3: 12px;
77
+ --space-4: 16px;
78
+ --space-5: 20px;
79
+ --space-6: 24px;
80
+ --space-8: 32px;
81
+ --space-10: 40px;
82
+ --space-12: 48px;
83
+ --space-16: 64px;
84
+
85
+ /* --- Radii --- */
86
+ --radius-sm: 4px;
87
+ --radius: 8px;
88
+ --radius-md: 10px;
89
+ --radius-lg: 14px;
90
+ --radius-full: 999px;
91
+
92
+ /* --- Shadows --- */
93
+ --shadow-sm: 0 1px 3px rgba(0, 0, 0, 0.12);
94
+ --shadow-md: 0 4px 12px rgba(0, 0, 0, 0.15);
95
+ --shadow-lg: 0 8px 24px rgba(0, 0, 0, 0.2);
96
+ --shadow-hover: 0 4px 12px rgba(0, 0, 0, 0.15);
97
+ --shadow-active: 0 2px 6px rgba(0, 0, 0, 0.10);
98
+
99
+ /* --- Transitions --- */
100
+ --transition-fast: 150ms;
101
+ --transition-normal: 250ms;
102
+ --transition-slow: 400ms;
103
+ --easing-smooth: cubic-bezier(0.4, 0, 0.2, 1);
104
+
105
+ /* --- Interaction (focus / hover) --- */
106
+ --focus-ring: 2px solid var(--accent);
107
+ --focus-offset: 2px;
108
+ --focus-offset-strong: 4px;
109
+ }
110
+ * { margin: 0; padding: 0; box-sizing: border-box; }
111
+
112
+ /* ============================================================
113
+ CANONICAL BUTTON PRIMITIVES
114
+ ============================================================ */
115
+ .btn {
116
+ display: inline-flex; align-items: center; gap: 6px;
117
+ padding: 6px 14px; border-radius: var(--radius-sm);
118
+ font-size: var(--text-base); font-weight: var(--font-weight-semibold);
119
+ font-family: inherit; cursor: pointer;
120
+ border: 1px solid var(--border); background: var(--bg); color: var(--text);
121
+ transition: all var(--transition-fast) var(--easing-smooth);
122
+ text-decoration: none; line-height: 1.4; min-height: 32px;
123
+ }
124
+ .btn:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
125
+ .btn:disabled, .btn[aria-disabled="true"] { opacity: 0.4; cursor: not-allowed; pointer-events: none; }
126
+ @media (hover: hover) and (pointer: fine) {
127
+ .btn:hover:not(:disabled) { border-color: var(--accent); color: var(--accent); }
128
+ }
129
+ .btn-primary { background: var(--accent); color: #fff; border-color: var(--accent); }
130
+ @media (hover: hover) and (pointer: fine) {
131
+ .btn-primary:hover:not(:disabled) { opacity: 0.85; border-color: var(--accent); color: #fff; }
132
+ }
133
+ .btn-danger { background: var(--red-dim); color: var(--red); border-color: var(--red); }
134
+ @media (hover: hover) and (pointer: fine) {
135
+ .btn-danger:hover:not(:disabled) { background: var(--red); color: #fff; border-color: var(--red); }
136
+ }
137
+ .btn-ghost { background: transparent; border-color: transparent; color: var(--text-muted); padding: 4px 8px; }
138
+ @media (hover: hover) and (pointer: fine) {
139
+ .btn-ghost:hover:not(:disabled) { background: var(--accent-dim); color: var(--accent); border-color: transparent; }
140
+ }
141
+ .btn.active, .btn[aria-pressed="true"] { background: var(--accent-dim); border-color: var(--accent); color: var(--accent); }
142
+
143
+ .link {
144
+ color: var(--accent); text-decoration: none; font-weight: var(--font-weight-semibold);
145
+ transition: color var(--transition-fast) var(--easing-smooth);
146
+ }
147
+ .link:hover { text-decoration: underline; }
148
+ .link:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); border-radius: 3px; }
149
+
150
+ body {
151
+ font-family: var(--font-family);
152
+ background: var(--bg);
153
+ color: var(--text);
154
+ line-height: var(--line-height-normal);
155
+ font-size: var(--text-md);
156
+ overflow-x: hidden;
157
+ }
158
+ .header {
159
+ display: flex; align-items: center; justify-content: space-between;
160
+ padding: var(--space-4) var(--space-8);
161
+ background: linear-gradient(180deg, #0f141a 0%, var(--bg) 100%);
162
+ border-bottom: 1px solid var(--border-subtle);
163
+ min-height: 56px;
164
+ }
165
+ .header-left { display: flex; align-items: center; gap: 10px; }
166
+ .header-logo { font-size: var(--text-xl); font-weight: var(--font-weight-bold); color: var(--text-bright); letter-spacing: var(--letter-spacing-tight); white-space: nowrap; }
167
+ .header-logo span { color: var(--accent); }
168
+ .header-right { display: flex; align-items: center; gap: var(--space-3); font-size: var(--text-base); color: var(--text-muted); flex-wrap: wrap; }
169
+
170
+ /* ============================================================
171
+ SIDEBAR NAV
172
+ Hash-based client-side routing. Sidebar + page containers.
173
+ ============================================================ */
174
+ .app-layout { display: flex; min-height: calc(100vh - 56px); max-width: 1400px; margin: 0 auto; }
175
+ .sidebar {
176
+ width: 200px; flex-shrink: 0; background: var(--surface);
177
+ border-right: 1px solid var(--border); padding: var(--space-4) 0;
178
+ position: sticky; top: 0; height: calc(100vh - 56px); overflow-y: auto;
179
+ display: flex; flex-direction: column;
180
+ }
181
+ .sidebar-nav { display: flex; flex-direction: column; gap: 2px; padding: 0 var(--space-2); flex: 1; }
182
+ .sidebar-link {
183
+ display: flex; align-items: center; gap: var(--space-2);
184
+ padding: var(--space-2) var(--space-3); border-radius: var(--radius-sm);
185
+ font-size: var(--text-base); font-weight: var(--font-weight-medium);
186
+ color: var(--text-muted); text-decoration: none; cursor: pointer;
187
+ border: none; background: transparent; font-family: inherit; width: 100%;
188
+ transition: all var(--transition-fast) var(--easing-smooth);
189
+ min-height: 36px;
190
+ }
191
+ .sidebar-link:focus-visible {
192
+ outline: var(--focus-ring); outline-offset: -2px;
193
+ }
194
+ .sidebar-link .nav-icon { font-size: 16px; width: 22px; text-align: center; flex-shrink: 0; }
195
+ .sidebar-link .nav-label { flex: 1; text-align: left; }
196
+ .sidebar-link .nav-badge {
197
+ font-size: 10px; font-weight: 700; min-width: 18px; text-align: center;
198
+ padding: 1px 5px; border-radius: 999px;
199
+ background: var(--border); color: var(--text-muted);
200
+ }
201
+ @media (hover: hover) and (pointer: fine) {
202
+ .sidebar-link:hover { background: var(--surface-raised); color: var(--text); }
203
+ }
204
+ .sidebar-link.active {
205
+ background: var(--accent-dim); color: var(--accent); font-weight: var(--font-weight-semibold);
206
+ }
207
+ .sidebar-link.active .nav-badge {
208
+ background: var(--accent-dim); color: var(--accent);
209
+ }
210
+ .sidebar-divider { height: 1px; background: var(--border); margin: var(--space-2) var(--space-3); }
211
+ .sidebar-section {
212
+ font-size: 10px; text-transform: uppercase; letter-spacing: 0.8px;
213
+ color: var(--text-muted); font-weight: var(--font-weight-semibold);
214
+ padding: var(--space-3) var(--space-3) var(--space-1);
215
+ }
216
+
217
+ /* Page containers: show/hide based on route */
218
+ .page { display: none; }
219
+ .page.active { display: block; }
220
+
221
+ /* Mobile: collapse sidebar */
222
+ .sidebar-toggle {
223
+ display: none; position: fixed; top: var(--space-2); left: var(--space-2);
224
+ z-index: 60; width: 36px; height: 36px; border-radius: var(--radius-sm);
225
+ border: 1px solid var(--border); background: var(--surface); color: var(--text-muted);
226
+ font-size: 18px; cursor: pointer; align-items: center; justify-content: center;
227
+ }
228
+ .sidebar-overlay {
229
+ display: none; position: fixed; inset: 0;
230
+ background: rgba(0,0,0,0.5); z-index: 45;
231
+ }
232
+ @media (max-width: 767px) {
233
+ .sidebar-toggle { display: flex; }
234
+ .sidebar {
235
+ position: fixed; top: 0; left: 0; z-index: 50; height: 100vh;
236
+ transform: translateX(-100%); transition: transform var(--transition-normal) var(--easing-smooth);
237
+ }
238
+ .sidebar.open { transform: translateX(0); }
239
+ .sidebar-overlay.open { display: block; }
240
+ .app-layout { flex-direction: column; }
241
+ .header-left { padding-left: 40px; }
242
+ }
243
+
244
+ .release-badge {
245
+ display: inline-flex;
246
+ align-items: center;
247
+ gap: 6px;
248
+ font-size: var(--text-sm);
249
+ padding: 4px 8px;
250
+ border-radius: var(--radius-full);
251
+ border: 1px solid var(--border);
252
+ color: var(--text-muted);
253
+ background: var(--surface-raised);
254
+ }
255
+ .release-badge.stale {
256
+ border-color: var(--orange);
257
+ background: var(--orange-dim);
258
+ color: #f4c27a;
259
+ }
260
+ .release-badge.fresh {
261
+ border-color: var(--green);
262
+ background: var(--green-dim);
263
+ color: #9de6a8;
264
+ }
265
+ .status-dot {
266
+ display: inline-block; width: 8px; height: 8px; border-radius: 50%;
267
+ background: var(--green); margin-right: 5px; vertical-align: middle;
268
+ box-shadow: 0 0 6px rgba(63, 185, 80, 0.4);
269
+ }
270
+ .agent-strip-wrapper {
271
+ position: relative; overflow: hidden; border-bottom: 1px solid var(--border-subtle); background: var(--surface);
272
+ }
273
+ .agent-strip-wrapper::after {
274
+ content: ''; position: absolute; top: 0; right: 0; bottom: 0; width: 48px; pointer-events: none;
275
+ background: linear-gradient(to right, transparent, var(--surface));
276
+ opacity: 0; transition: opacity var(--transition-fast);
277
+ }
278
+ .agent-strip-wrapper.has-overflow::after { opacity: 1; }
279
+ .agent-strip {
280
+ display: flex; gap: var(--space-3); padding: var(--space-4) var(--space-8); overflow-x: auto;
281
+ max-width: 100vw; box-sizing: border-box; scrollbar-width: thin;
282
+ scroll-snap-type: x proximity; -webkit-overflow-scrolling: touch;
283
+ }
284
+ .agent-strip::-webkit-scrollbar { height: 4px; }
285
+ .agent-strip::-webkit-scrollbar-track { background: transparent; }
286
+ .agent-strip::-webkit-scrollbar-thumb { background: var(--border); border-radius: 2px; }
287
+ .agent-card {
288
+ flex: 0 0 auto; display: flex; align-items: center; gap: var(--space-2);
289
+ padding: var(--space-2) var(--space-3); background: var(--surface-raised); border: 1px solid var(--border);
290
+ border-radius: var(--radius-md); min-width: 160px; max-width: 240px; transition: border-color var(--transition-fast) var(--easing-smooth);
291
+ scroll-snap-align: start;
292
+ }
293
+ .agent-card:hover { border-color: var(--accent); }
294
+ .agent-card.active { border-left: 3px solid var(--green); }
295
+ .agent-card.idle { opacity: 0.6; }
296
+ .agent-card.offline { opacity: 0.35; }
297
+ .agent-avatar { width: 32px; height: 32px; border-radius: 50%; object-fit: cover; flex-shrink: 0; }
298
+ .agent-emoji { font-size: var(--text-2xl); line-height: 1; }
299
+ .agent-info { flex: 1; min-width: 0; }
300
+ .agent-name { font-size: var(--text-base); font-weight: var(--font-weight-semibold); color: var(--text-bright); }
301
+ .agent-role { font-size: var(--text-xs); color: var(--purple); text-transform: uppercase; letter-spacing: var(--letter-spacing-wide); margin-bottom: var(--space-1); }
302
+ .agent-status-text { font-size: var(--text-sm); color: var(--text-muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
303
+ .agent-pr-link {
304
+ display: inline-flex;
305
+ margin-top: 3px;
306
+ font-size: var(--text-xs);
307
+ color: var(--accent);
308
+ text-decoration: none;
309
+ font-weight: 600;
310
+ width: fit-content;
311
+ }
312
+ .agent-pr-link:hover { text-decoration: underline; }
313
+ .agent-pr-link:focus-visible {
314
+ outline: 2px solid var(--accent);
315
+ outline-offset: 2px;
316
+ border-radius: 3px;
317
+ }
318
+ .agent-badge { font-size: var(--text-xs); font-weight: 600; padding: 2px 8px; border-radius: var(--radius-md); text-transform: uppercase; letter-spacing: 0.3px; }
319
+ .agent-badge.working { background: var(--green-dim); color: var(--green); }
320
+ .agent-badge.idle { background: var(--border); color: var(--text-muted); }
321
+ .agent-badge.offline { background: transparent; color: var(--text-muted); border: 1px solid var(--border); }
322
+ .main { padding: 24px 28px; display: flex; flex-direction: column; gap: var(--space-6); flex: 1; min-width: 0; }
323
+ .panel {
324
+ background: var(--surface); border: 1px solid var(--border);
325
+ border-radius: var(--radius-md); overflow: hidden;
326
+ transition: border-color var(--transition-fast) var(--easing-smooth);
327
+ }
328
+ .panel-header {
329
+ padding: var(--space-4) var(--space-5); font-size: var(--text-lg); font-weight: var(--font-weight-semibold); color: var(--text-bright);
330
+ border-bottom: 1px solid var(--border); display: flex; align-items: center; justify-content: space-between;
331
+ }
332
+ .panel-header .count { font-size: var(--text-sm); color: var(--text-muted); font-weight: var(--font-weight-normal); }
333
+ .panel-body { padding: var(--space-4) var(--space-5); max-height: 450px; overflow-y: auto; }
334
+ .truth-grid {
335
+ display: grid;
336
+ grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
337
+ gap: 10px;
338
+ }
339
+ .truth-item {
340
+ border: 1px solid var(--border-subtle);
341
+ border-radius: var(--radius-sm);
342
+ background: var(--bg);
343
+ padding: 10px 12px;
344
+ }
345
+ .truth-label {
346
+ font-size: var(--text-xs);
347
+ text-transform: uppercase;
348
+ letter-spacing: 0.6px;
349
+ color: var(--text-muted);
350
+ margin-bottom: 6px;
351
+ }
352
+ .truth-value {
353
+ font-size: 12px;
354
+ color: var(--text-bright);
355
+ line-height: 1.35;
356
+ word-break: break-word;
357
+ }
358
+ .project-tabs { display: flex; gap: 2px; padding: 10px 18px 0; border-bottom: 1px solid var(--border); }
359
+ .project-tab {
360
+ padding: 8px 16px; font-size: var(--text-base); font-weight: 500; border: none; background: transparent;
361
+ color: var(--text-muted); cursor: pointer; border-bottom: 2px solid transparent;
362
+ transition: all 0.15s; margin-bottom: -1px;
363
+ }
364
+ .project-tab:hover { color: var(--text); }
365
+ .project-tab.active { color: var(--accent); border-bottom-color: var(--accent); }
366
+ .kanban { display: flex; gap: var(--space-3); padding: 16px 18px; overflow-x: auto; min-height: 180px; align-items: flex-start; }
367
+ .kanban-col { flex: 1; min-width: 160px; max-height: 75vh; overflow-y: auto; scrollbar-width: thin; }
368
+ .kanban-col::-webkit-scrollbar { width: 4px; }
369
+ .kanban-col::-webkit-scrollbar-track { background: transparent; }
370
+ .kanban-col::-webkit-scrollbar-thumb { background: var(--border); border-radius: 2px; }
371
+ .kanban-col-header {
372
+ font-size: var(--text-sm); text-transform: uppercase; letter-spacing: 0.8px; font-weight: 600;
373
+ color: var(--text-muted); margin-bottom: 10px; padding-bottom: 8px;
374
+ border-bottom: 2px solid var(--border); display: flex; justify-content: space-between; align-items: center;
375
+ }
376
+ .kanban-col-header .cnt { font-weight: 400; font-size: var(--text-sm); background: var(--border); padding: 1px 7px; border-radius: var(--radius); }
377
+ .kanban-col[data-status="doing"] .kanban-col-header { border-bottom-color: var(--accent); }
378
+ .kanban-col[data-status="blocked"] .kanban-col-header { border-bottom-color: var(--red); }
379
+ .kanban-col[data-status="validating"] .kanban-col-header { border-bottom-color: var(--yellow); }
380
+ .kanban-col[data-status="done"] .kanban-col-header { border-bottom-color: var(--green); }
381
+ .task-card {
382
+ background: var(--bg); border: 1px solid var(--border); border-radius: var(--radius-sm);
383
+ padding: 10px 12px; margin-bottom: 8px; transition: border-color 0.15s;
384
+ cursor: pointer;
385
+ }
386
+ .task-card:hover { border-color: var(--accent); }
387
+
388
+ /* Task Modal */
389
+ .modal-overlay {
390
+ position: fixed; top: 0; left: 0; right: 0; bottom: 0;
391
+ background: rgba(0, 0, 0, 0.7); display: none; align-items: center; justify-content: center;
392
+ z-index: 1000;
393
+ }
394
+ .modal-overlay.show { display: flex; }
395
+ .modal {
396
+ background: var(--surface); border: 1px solid var(--border); border-radius: var(--radius);
397
+ width: 90%; max-width: 600px; max-height: 80vh; overflow-y: auto;
398
+ }
399
+ .modal-header {
400
+ padding: 18px 20px; border-bottom: 1px solid var(--border);
401
+ display: flex; align-items: center; justify-content: space-between;
402
+ }
403
+ .modal-header h2 { font-size: var(--text-lg); font-weight: 600; color: var(--text-bright); margin: 0; }
404
+ .modal-close {
405
+ background: none; border: none; color: var(--text-muted); cursor: pointer;
406
+ font-size: 20px; padding: 0; width: 24px; height: 24px;
407
+ }
408
+ .modal-close:hover { color: var(--text); }
409
+ .modal-body { padding: 20px; }
410
+ .modal-section { margin-bottom: 20px; }
411
+ .modal-section:last-child { margin-bottom: 0; }
412
+
413
+ /* Artifact list (task modal) */
414
+ .artifact-list { display: flex; flex-direction: column; gap: 10px; }
415
+ .artifact-row {
416
+ background: var(--bg);
417
+ border: 1px solid var(--border-subtle);
418
+ border-radius: var(--radius-sm);
419
+ padding: 10px 12px;
420
+ }
421
+ .artifact-top { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
422
+ .artifact-path { font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, 'Liberation Mono', 'Courier New', monospace; font-size: 12px; color: var(--text-bright); }
423
+ .artifact-meta { font-size: var(--text-sm); color: var(--text-muted); margin-top: 4px; }
424
+ .artifact-actions { display: flex; gap: var(--space-2); margin-top: 8px; flex-wrap: wrap; }
425
+ .artifact-btn {
426
+ border: 1px solid var(--border);
427
+ background: transparent;
428
+ color: var(--text);
429
+ border-radius: var(--radius-sm);
430
+ padding: 4px 10px;
431
+ font-size: var(--text-sm);
432
+ font-weight: var(--font-weight-semibold);
433
+ cursor: pointer;
434
+ text-decoration: none;
435
+ display: inline-flex;
436
+ align-items: center;
437
+ gap: 6px;
438
+ font-family: inherit;
439
+ transition: all var(--transition-fast) var(--easing-smooth);
440
+ }
441
+ @media (hover: hover) and (pointer: fine) {
442
+ .artifact-btn:hover { border-color: var(--accent); color: var(--accent); }
443
+ }
444
+ .artifact-pill {
445
+ display: inline-flex;
446
+ align-items: center;
447
+ border-radius: var(--radius-full);
448
+ padding: 2px 8px;
449
+ font-size: var(--text-xs);
450
+ font-weight: 700;
451
+ letter-spacing: 0.2px;
452
+ border: 1px solid var(--border);
453
+ color: var(--text-muted);
454
+ background: var(--surface-raised);
455
+ flex-shrink: 0;
456
+ }
457
+ .artifact-pill.ok { border-color: var(--green); color: #9de6a8; background: var(--green-dim); }
458
+ .artifact-pill.missing { border-color: var(--red); color: #ff9a94; background: var(--red-dim); }
459
+ .modal-label { font-size: var(--text-sm); text-transform: uppercase; letter-spacing: 0.8px;
460
+ color: var(--text-muted); font-weight: 600; margin-bottom: 8px;
461
+ }
462
+ .modal-value { font-size: var(--text-md); color: var(--text); line-height: 1.5; }
463
+ .modal-inline-row { display: flex; align-items: center; gap: 10px; }
464
+ .modal-copy-btn {
465
+ border: 1px solid var(--border-subtle); background: transparent; color: var(--text-muted);
466
+ border-radius: var(--radius-sm); font-size: var(--text-sm); padding: 4px 8px;
467
+ cursor: pointer; font-family: inherit;
468
+ transition: all var(--transition-fast) var(--easing-smooth);
469
+ }
470
+ @media (hover: hover) and (pointer: fine) {
471
+ .modal-copy-btn:hover { border-color: var(--accent); color: var(--accent); }
472
+ }
473
+ .modal-select, .modal-input {
474
+ width: 100%; background: var(--bg); color: var(--text); border: 1px solid var(--border);
475
+ border-radius: var(--radius-sm); padding: 8px 12px; font-size: var(--text-md); outline: none;
476
+ }
477
+ .modal-select:focus, .modal-input:focus { border-color: var(--accent); }
478
+ .status-buttons {
479
+ display: flex; gap: var(--space-2); flex-wrap: wrap;
480
+ }
481
+ .status-btn {
482
+ padding: 6px 14px; font-size: var(--text-base); font-weight: var(--font-weight-semibold);
483
+ border-radius: var(--radius-sm);
484
+ border: 1px solid var(--border); background: var(--bg); color: var(--text);
485
+ cursor: pointer; font-family: inherit;
486
+ transition: all var(--transition-fast) var(--easing-smooth);
487
+ }
488
+ @media (hover: hover) and (pointer: fine) {
489
+ .status-btn:hover { border-color: var(--accent); color: var(--accent); }
490
+ }
491
+ .status-btn.active { background: var(--accent-dim); border-color: var(--accent); color: var(--accent); }
492
+ .modal-btn {
493
+ padding: 8px 16px; font-size: var(--text-base); font-weight: var(--font-weight-semibold);
494
+ border-radius: var(--radius-sm);
495
+ border: none; cursor: pointer; font-family: inherit;
496
+ transition: all var(--transition-fast) var(--easing-smooth);
497
+ }
498
+ .modal-btn-primary {
499
+ background: var(--accent); color: #fff;
500
+ }
501
+ @media (hover: hover) and (pointer: fine) {
502
+ .modal-btn-primary:hover { opacity: 0.85; }
503
+ }
504
+ .modal-btn-secondary {
505
+ background: var(--border); color: var(--text);
506
+ }
507
+ @media (hover: hover) and (pointer: fine) {
508
+ .modal-btn-secondary:hover { background: var(--text-muted); }
509
+ }
510
+ .task-title { font-size: var(--text-base); font-weight: 500; color: var(--text-bright); margin-bottom: 6px; line-height: 1.4; }
511
+ .task-meta { display: flex; gap: var(--space-2); align-items: center; flex-wrap: wrap; }
512
+ .priority-badge { display: inline-block; padding: 2px 7px; border-radius: var(--radius-sm); font-size: var(--text-xs); font-weight: 700; letter-spacing: 0.3px; }
513
+ .priority-badge.P0 { background: var(--red-dim); color: var(--red); }
514
+ .priority-badge.P1 { background: var(--orange-dim); color: var(--orange); }
515
+ .priority-badge.P2 { background: var(--yellow-dim); color: var(--yellow); }
516
+ .priority-badge.P3 { background: var(--border); color: var(--text-muted); }
517
+ .assignee-tag { font-size: var(--text-sm); color: var(--text-muted); display: flex; align-items: center; gap: var(--space-1); }
518
+ .assignee-tag .role-small { font-size: 9px; color: var(--purple); background: rgba(180, 142, 255, 0.08); padding: 1px 5px; border-radius: 3px; text-transform: uppercase; letter-spacing: 0.3px; }
519
+ .done-toggle { font-size: 12px; color: var(--text-muted); background: none; border: none; cursor: pointer; padding: 4px 0; }
520
+ .done-toggle:hover { color: var(--text); }
521
+ .two-col { display: grid; grid-template-columns: 1fr 1fr; gap: var(--space-6); }
522
+ @media (max-width: 900px) { .two-col { grid-template-columns: 1fr; } }
523
+ .channel-tabs { display: flex; gap: 2px; padding: 8px 18px 0; overflow-x: auto; }
524
+ .channel-tab {
525
+ padding: 6px 12px; font-size: 12px; border-radius: var(--radius-sm) var(--radius-sm) 0 0;
526
+ cursor: pointer; background: transparent; border: none; color: var(--text-muted); font-weight: 500; transition: all 0.15s;
527
+ }
528
+ .channel-tab:hover { background: var(--surface-raised); color: var(--text); }
529
+ .channel-tab.active { background: var(--surface-raised); color: var(--accent); }
530
+ .channel-tab .meta { font-size: var(--text-xs); color: var(--text-muted); margin-left: 6px; }
531
+ .channel-tab .mention-dot {
532
+ display: inline-block; width: 7px; height: 7px; border-radius: 50%;
533
+ background: var(--accent); margin-left: 6px; box-shadow: 0 0 8px rgba(77, 166, 255, 0.6);
534
+ }
535
+ .msg { padding: 7px 0; border-bottom: 1px solid var(--border-subtle); font-size: var(--text-base); }
536
+ .msg:last-child { border-bottom: none; }
537
+ .msg-header { display: flex; align-items: center; flex-wrap: wrap; gap: 6px; margin-bottom: 3px; }
538
+ .msg-from { font-weight: 600; color: var(--accent); font-size: var(--text-base); max-width: 140px; overflow: hidden; text-overflow: ellipsis; }
539
+ .msg-role { font-size: var(--text-xs); color: var(--purple); background: rgba(180, 142, 255, 0.08); padding: 2px 6px; border-radius: 3px; text-transform: uppercase; letter-spacing: 0.3px; }
540
+ .msg-channel { font-size: var(--text-sm); color: var(--purple); background: rgba(180, 142, 255, 0.08); padding: 1px 6px; border-radius: 3px; }
541
+ .msg-time { font-size: var(--text-sm); color: var(--text-muted); margin-left: auto; white-space: nowrap; }
542
+ .msg-edited { font-size: var(--text-xs); color: var(--text-muted); opacity: 0.8; }
543
+ .msg-content { color: var(--text); font-size: 12.5px; line-height: 1.4; word-break: break-word; white-space: pre-wrap; }
544
+ .task-id-link {
545
+ color: var(--accent);
546
+ text-decoration: underline;
547
+ text-underline-offset: 2px;
548
+ font-weight: 600;
549
+ cursor: pointer;
550
+ }
551
+ .task-id-link:hover { opacity: 0.9; }
552
+ .task-id-link .task-preview-tooltip {
553
+ display: none; position: absolute; z-index: 200; bottom: 120%; left: 50%; transform: translateX(-50%);
554
+ background: var(--surface-raised); border: 1px solid var(--border-subtle); border-radius: 6px;
555
+ padding: 8px 10px; font-size: var(--text-sm); line-height: 1.4; white-space: nowrap; pointer-events: none;
556
+ box-shadow: 0 4px 12px rgba(0,0,0,.3); color: var(--text);
557
+ }
558
+ .task-id-link:hover .task-preview-tooltip, .task-id-link:focus .task-preview-tooltip { display: block; }
559
+ .task-preview-tooltip .tp-title { font-weight: 600; color: var(--text); }
560
+ .task-preview-tooltip .tp-meta { color: var(--text-muted); font-size: var(--text-xs); margin-top: 2px; }
561
+ .task-id-link:focus-visible {
562
+ outline: 2px solid var(--accent);
563
+ outline-offset: 2px;
564
+ border-radius: 3px;
565
+ }
566
+ .msg-attachments { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 6px; }
567
+ .msg-att-file { display: inline-flex; align-items: center; gap: 4px; padding: 3px 8px; background: var(--surface-raised); border: 1px solid var(--border); border-radius: var(--radius-sm); color: var(--accent); font-size: 11px; text-decoration: none; transition: background var(--transition-fast); }
568
+ .msg-att-file:hover { background: var(--accent-dim); }
569
+ .msg-att-file .att-size { color: var(--text-muted); font-size: 10px; }
570
+ .msg-att-img { display: inline-block; max-width: 200px; border-radius: var(--radius-sm); overflow: hidden; border: 1px solid var(--border); }
571
+ .msg-att-img img { display: block; max-width: 100%; max-height: 150px; object-fit: cover; }
572
+ .msg-att-img:hover { border-color: var(--accent); }
573
+ .msg-content.collapsed { max-height: 80px; overflow: hidden; position: relative; cursor: pointer; }
574
+ .msg-content.collapsed::after {
575
+ content: '▼ click to expand'; display: block; position: absolute; bottom: 0; left: 0; right: 0;
576
+ background: linear-gradient(transparent, var(--surface) 60%); padding-top: 30px; text-align: center;
577
+ font-size: var(--text-sm); color: var(--accent); font-style: italic;
578
+ }
579
+ .msg-content.expanded { max-height: none; cursor: pointer; }
580
+ .msg.mentioned {
581
+ border-left: 2px solid var(--accent);
582
+ padding-left: 8px;
583
+ background: linear-gradient(90deg, rgba(77, 166, 255, 0.08), transparent 65%);
584
+ }
585
+ .event-row { padding: 6px 0; border-bottom: 1px solid var(--border-subtle); font-size: 12px; display: flex; align-items: center; gap: var(--space-2); }
586
+ .event-row:last-child { border-bottom: none; }
587
+ .event-type { display: inline-block; padding: 2px 8px; border-radius: var(--radius-sm); font-size: var(--text-xs); font-weight: 600; background: var(--border); color: var(--text-muted); text-transform: uppercase; letter-spacing: 0.3px; flex-shrink: 0; }
588
+ .event-agent { color: var(--accent); font-weight: 600; flex-shrink: 0; }
589
+ .event-desc { color: var(--text); flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
590
+ .event-time { color: var(--text-muted); font-size: var(--text-sm); flex-shrink: 0; }
591
+ .empty {
592
+ color: var(--text-muted); font-style: normal; font-size: var(--text-base);
593
+ padding: 28px 16px; text-align: center; line-height: 1.5;
594
+ background: var(--bg); border: 1px dashed var(--border);
595
+ border-radius: var(--radius-sm); margin: 4px 0;
596
+ }
597
+ .ssot-meta {
598
+ display: flex; align-items: center; justify-content: space-between; gap: 10px;
599
+ margin-bottom: 8px; padding: 8px 10px; border: 1px solid var(--border-subtle);
600
+ border-radius: var(--radius-sm); background: var(--surface-raised); font-size: 12px;
601
+ }
602
+ .ssot-meta-text { color: var(--text-muted); }
603
+ .ssot-state-badge {
604
+ font-size: var(--text-sm); font-weight: 700; border-radius: var(--radius-full); padding: 2px 8px;
605
+ border: 1px solid transparent; text-transform: uppercase; letter-spacing: 0.2px;
606
+ }
607
+ .ssot-state-badge.fresh { color: var(--green); border-color: var(--green); background: var(--green-dim); }
608
+ .ssot-state-badge.warn { color: var(--yellow); border-color: var(--yellow); background: var(--yellow-dim); }
609
+ .ssot-state-badge.stale { color: var(--red); border-color: var(--red); background: var(--red-dim); }
610
+ .ssot-state-badge.unknown { color: var(--text-muted); border-color: var(--text-muted); background: var(--border); }
611
+ .ssot-list { display: grid; gap: var(--space-2); }
612
+ .ssot-item {
613
+ display: flex; align-items: center; justify-content: space-between; gap: 10px;
614
+ padding: 8px 10px; border: 1px solid var(--border-subtle); border-radius: var(--radius-sm);
615
+ background: var(--surface-raised);
616
+ }
617
+ .ssot-item-label { font-size: 12px; color: var(--text); }
618
+ .ssot-link {
619
+ color: var(--accent); text-decoration: none; font-size: 12px; font-weight: 600;
620
+ }
621
+ .ssot-link:hover { text-decoration: underline; }
622
+ .ssot-link:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; border-radius: 3px; }
623
+ .ssot-missing { font-size: var(--text-sm); color: var(--yellow); border: 1px solid var(--yellow); border-radius: var(--radius-md); padding: 2px 6px; }
624
+ /* Chat input */
625
+ .chat-input-bar {
626
+ display: flex; gap: var(--space-2); padding: 12px 18px;
627
+ border-top: 1px solid var(--border); background: var(--surface-raised);
628
+ }
629
+ .chat-input-bar select {
630
+ background: var(--bg); color: var(--text); border: 1px solid var(--border);
631
+ border-radius: var(--radius-sm); padding: 8px 10px; font-size: var(--text-base); min-width: 120px;
632
+ }
633
+ .chat-input-bar input {
634
+ flex: 1; background: var(--bg); color: var(--text); border: 1px solid var(--border);
635
+ border-radius: var(--radius-sm); padding: 8px 12px; font-size: var(--text-base); outline: none;
636
+ }
637
+ .chat-input-bar input:focus { border-color: var(--accent); }
638
+ .chat-input-bar input::placeholder { color: var(--text-muted); }
639
+ .chat-input-bar button {
640
+ background: var(--accent); color: #fff; border: none; border-radius: var(--radius-sm);
641
+ padding: 8px 18px; font-size: var(--text-base); font-weight: var(--font-weight-semibold);
642
+ cursor: pointer; font-family: inherit;
643
+ transition: all var(--transition-fast) var(--easing-smooth);
644
+ }
645
+ @media (hover: hover) and (pointer: fine) {
646
+ .chat-input-bar button:hover { opacity: 0.85; }
647
+ }
648
+ .chat-input-bar button:disabled { opacity: 0.4; cursor: not-allowed; }
649
+ ::-webkit-scrollbar { width: 6px; height: 6px; }
650
+ ::-webkit-scrollbar-track { background: transparent; }
651
+ ::-webkit-scrollbar-thumb { background: var(--border); border-radius: 3px; }
652
+ ::-webkit-scrollbar-thumb:hover { background: var(--text-muted); }
653
+
654
+ /* Team Health Widget */
655
+ .health-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(240px, 1fr)); gap: var(--space-3); margin-bottom: 20px; }
656
+ .health-card {
657
+ background: var(--bg); border: 1px solid var(--border); border-radius: var(--radius-sm);
658
+ padding: 12px 14px; display: flex; align-items: center; gap: 10px; transition: all 0.2s;
659
+ }
660
+ .health-card:hover { border-color: var(--accent); }
661
+ .health-card.health-critical {
662
+ border-color: rgba(248, 81, 73, 0.55);
663
+ background: linear-gradient(90deg, rgba(248, 81, 73, 0.12), transparent 72%);
664
+ }
665
+ .health-card.health-warning {
666
+ border-color: rgba(212, 160, 23, 0.45);
667
+ background: linear-gradient(90deg, rgba(212, 160, 23, 0.09), transparent 72%);
668
+ }
669
+ .health-card.health-info {
670
+ border-color: rgba(63, 185, 80, 0.35);
671
+ background: linear-gradient(90deg, rgba(63, 185, 80, 0.07), transparent 75%);
672
+ }
673
+ .health-indicator {
674
+ width: 10px; height: 10px; border-radius: 50%; flex-shrink: 0;
675
+ box-shadow: 0 0 8px currentColor;
676
+ }
677
+ .health-indicator.active { background: var(--green); color: var(--green); }
678
+ .health-indicator.idle { background: var(--yellow); color: var(--yellow); }
679
+ .health-indicator.silent { background: var(--orange); color: var(--orange); }
680
+ .health-indicator.watch { background: var(--yellow); color: var(--yellow); }
681
+ .health-indicator.blocked, .health-indicator.offline { background: var(--red); color: var(--red); }
682
+ .health-card.needs-review {
683
+ border-color: rgba(212, 160, 23, 0.45);
684
+ background: linear-gradient(90deg, rgba(212, 160, 23, 0.08), transparent 70%);
685
+ }
686
+ .health-card.stuck-active-task {
687
+ border-color: rgba(248, 81, 73, 0.55);
688
+ background: linear-gradient(90deg, rgba(248, 81, 73, 0.14), transparent 75%);
689
+ }
690
+ .health-card.stale-ghost {
691
+ opacity: 0.35;
692
+ order: 99;
693
+ }
694
+ .health-grid { display: grid; }
695
+ .health-grid-collapse-toggle {
696
+ display: inline-flex; align-items: center; gap: 4px;
697
+ font-size: var(--text-sm); color: var(--text-muted); cursor: pointer;
698
+ background: none; border: none; padding: 4px 8px; margin-top: 4px;
699
+ transition: color var(--transition-fast);
700
+ }
701
+ .health-grid-collapse-toggle:hover { color: var(--text-bright); }
702
+ .health-info { flex: 1; min-width: 0; }
703
+ .health-name { font-size: var(--text-base); font-weight: 600; color: var(--text-bright); }
704
+ .health-status { font-size: var(--text-sm); color: var(--text-muted); }
705
+ .health-task { font-size: var(--text-sm); color: var(--purple); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; margin-top: 2px; }
706
+ .health-section { margin-bottom: 16px; }
707
+ .health-section:last-child { margin-bottom: 0; }
708
+ .health-section-title { font-size: var(--text-sm); text-transform: uppercase; letter-spacing: 0.8px; font-weight: 600; color: var(--text-muted); margin-bottom: 8px; }
709
+ .blocker-item {
710
+ background: var(--red-dim); border-left: 3px solid var(--red); padding: 8px 10px;
711
+ border-radius: var(--radius-sm); margin-bottom: 6px; font-size: 12px;
712
+ }
713
+ .blocker-item:last-child { margin-bottom: 0; }
714
+ .blocker-agent { font-weight: 600; color: var(--red); }
715
+ .blocker-text { color: var(--text); margin-top: 3px; line-height: 1.4; }
716
+ .blocker-meta { font-size: var(--text-xs); color: var(--text-muted); margin-top: 3px; }
717
+ .overlap-item {
718
+ background: var(--yellow-dim); border-left: 3px solid var(--yellow); padding: 8px 10px;
719
+ border-radius: var(--radius-sm); margin-bottom: 6px; font-size: 12px;
720
+ }
721
+ .overlap-item:last-child { margin-bottom: 0; }
722
+ .overlap-agents { font-weight: 600; color: var(--yellow); }
723
+ .overlap-topic { color: var(--text); margin-top: 3px; }
724
+
725
+ /* Collaboration Compliance */
726
+ .compliance-summary { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--space-2); margin-bottom: 12px; }
727
+ .sla-chip {
728
+ border: 1px solid var(--border); border-radius: var(--radius-sm); padding: 8px 10px; font-size: 12px;
729
+ display: flex; justify-content: space-between; gap: var(--space-2); background: var(--bg);
730
+ }
731
+ .sla-chip.ok { border-color: rgba(63,185,80,.4); background: rgba(63,185,80,.08); }
732
+ .sla-chip.warning { border-color: rgba(212,160,23,.45); background: rgba(212,160,23,.1); }
733
+ .sla-chip.violation, .sla-chip.escalated { border-color: rgba(248,81,73,.5); background: rgba(248,81,73,.12); }
734
+ .compliance-table { width: 100%; border-collapse: collapse; margin-bottom: 12px; }
735
+ .compliance-table th, .compliance-table td { text-align: left; padding: 8px; font-size: 12px; border-bottom: 1px solid var(--border-subtle); }
736
+ .compliance-table th { color: var(--text-muted); font-size: var(--text-sm); text-transform: uppercase; letter-spacing: .4px; }
737
+ .state-pill { display: inline-block; padding: 2px 8px; border-radius: var(--radius-full); font-size: var(--text-sm); text-transform: uppercase; letter-spacing: .3px; }
738
+ .state-pill.ok { color: var(--green); background: var(--green-dim); }
739
+ .state-pill.warning { color: var(--yellow); background: var(--yellow-dim); }
740
+ .state-pill.violation, .state-pill.escalated { color: var(--red); background: var(--red-dim); }
741
+ .copy-template-btn {
742
+ background: var(--surface-raised); color: var(--text); border: 1px solid var(--border);
743
+ border-radius: var(--radius-sm); padding: 5px 8px; font-size: var(--text-sm);
744
+ cursor: pointer; font-family: inherit;
745
+ transition: all var(--transition-fast) var(--easing-smooth);
746
+ }
747
+ @media (hover: hover) and (pointer: fine) {
748
+ .copy-template-btn:hover { border-color: var(--accent); color: var(--accent); }
749
+ }
750
+
751
+ /* Review Queue Panel */
752
+ .review-item {
753
+ display: flex; align-items: center; justify-content: space-between; gap: 10px;
754
+ padding: 10px 12px; border-bottom: 1px solid var(--border-subtle);
755
+ font-size: var(--text-base); transition: background 0.15s;
756
+ }
757
+ .review-item:last-child { border-bottom: none; }
758
+ .review-item:hover { background: var(--surface-raised); cursor: pointer; }
759
+ .review-item-left { flex: 1; min-width: 0; }
760
+ .review-item-title { color: var(--text-bright); font-weight: 500; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
761
+ .review-item-meta { font-size: var(--text-sm); color: var(--text-muted); margin-top: 2px; display: flex; gap: var(--space-2); flex-wrap: wrap; }
762
+ .review-item-right { display: flex; align-items: center; gap: var(--space-2); flex-shrink: 0; }
763
+ .sla-badge {
764
+ display: inline-flex; align-items: center; padding: 3px 8px;
765
+ border-radius: var(--radius-full); font-size: var(--text-sm); font-weight: 600; letter-spacing: 0.2px;
766
+ }
767
+ .sla-badge.ok { color: var(--green); background: var(--green-dim); border: 1px solid rgba(63,185,80,.3); }
768
+ .sla-badge.warning { color: var(--yellow); background: var(--yellow-dim); border: 1px solid rgba(212,160,23,.3); }
769
+ .sla-badge.breach { color: var(--red); background: var(--red-dim); border: 1px solid rgba(248,81,73,.3); animation: sla-pulse 2s ease-in-out infinite; }
770
+ @keyframes sla-pulse { 0%, 100% { opacity: 1; } 50% { opacity: 0.7; } }
771
+ .review-empty { text-align: center; padding: 24px; color: var(--text-muted); font-size: var(--text-base); }
772
+
773
+ /* Outcome Feed */
774
+ .outcome-rollup {
775
+ display: grid;
776
+ grid-template-columns: repeat(3, minmax(0, 1fr));
777
+ gap: var(--space-2);
778
+ margin-bottom: 10px;
779
+ }
780
+ .outcome-rollup-card {
781
+ border: 1px solid var(--border);
782
+ border-radius: var(--radius-sm);
783
+ background: var(--bg);
784
+ padding: 8px 10px;
785
+ }
786
+ .outcome-rollup-card .label {
787
+ font-size: var(--text-xs);
788
+ color: var(--text-muted);
789
+ text-transform: uppercase;
790
+ letter-spacing: 0.5px;
791
+ }
792
+ .outcome-rollup-card .value {
793
+ margin-top: 2px;
794
+ font-size: var(--text-xl);
795
+ font-weight: 700;
796
+ color: var(--text-bright);
797
+ }
798
+ .outcome-rollup-card.high { border-color: rgba(248,81,73,.45); background: rgba(248,81,73,.08); }
799
+ .outcome-rollup-card.medium { border-color: rgba(212,160,23,.45); background: rgba(212,160,23,.10); }
800
+ .outcome-rollup-card.low { border-color: rgba(63,185,80,.40); background: rgba(63,185,80,.10); }
801
+ .outcome-item {
802
+ border-bottom: 1px solid var(--border-subtle);
803
+ padding: 9px 0;
804
+ }
805
+ .outcome-item:last-child { border-bottom: none; }
806
+ .outcome-item-title {
807
+ font-size: var(--text-base);
808
+ font-weight: 600;
809
+ color: var(--text-bright);
810
+ }
811
+ .outcome-item-meta {
812
+ margin-top: 3px;
813
+ font-size: var(--text-sm);
814
+ color: var(--text-muted);
815
+ display: flex;
816
+ gap: var(--space-2);
817
+ flex-wrap: wrap;
818
+ }
819
+ .outcome-impact-pill {
820
+ border-radius: var(--radius-full);
821
+ padding: 1px 8px;
822
+ font-size: var(--text-xs);
823
+ letter-spacing: 0.4px;
824
+ text-transform: uppercase;
825
+ font-weight: 700;
826
+ }
827
+ .outcome-impact-pill.high { color: var(--red); background: var(--red-dim); }
828
+ .outcome-impact-pill.medium { color: var(--yellow); background: var(--yellow-dim); }
829
+ .outcome-impact-pill.low { color: var(--green); background: var(--green-dim); }
830
+
831
+ .incident-item {
832
+ border-left: 3px solid var(--orange); background: var(--orange-dim); border-radius: var(--radius-sm);
833
+ padding: 8px 10px; margin-bottom: 6px; font-size: 12px;
834
+ }
835
+ .incident-type { font-weight: 600; color: var(--text-bright); }
836
+ .template-box {
837
+ margin-top: 8px; border: 1px dashed var(--border); border-radius: var(--radius-sm); padding: 8px;
838
+ font-family: ui-monospace, SFMono-Regular, Menlo, monospace; white-space: pre-wrap; font-size: var(--text-sm); color: var(--text-muted);
839
+ }
840
+
841
+ @media (max-width: 767px) {
842
+ .header, .agent-strip, .main {
843
+ padding-left: 16px;
844
+ padding-right: 16px;
845
+ }
846
+ .header {
847
+ padding-top: 12px;
848
+ padding-bottom: 12px;
849
+ align-items: flex-start;
850
+ gap: var(--space-3);
851
+ flex-wrap: wrap;
852
+ }
853
+ .header-right {
854
+ width: 100%;
855
+ justify-content: space-between;
856
+ gap: 10px;
857
+ font-size: 12px;
858
+ flex-wrap: wrap;
859
+ }
860
+ .agent-strip { gap: var(--space-2); }
861
+ .agent-card { min-width: 170px; padding: 8px 10px; border-radius: 12px; }
862
+ .main { padding-top: 20px; padding-bottom: 20px; gap: var(--space-5); }
863
+ .panel { border-radius: 12px; }
864
+ .panel-header { padding: 12px 16px; font-size: var(--text-md); }
865
+ .panel-body { padding: 12px 16px; max-height: 360px; }
866
+ .project-tabs, .channel-tabs {
867
+ padding-left: 16px;
868
+ padding-right: 16px;
869
+ gap: 6px;
870
+ flex-wrap: wrap;
871
+ }
872
+ .kanban {
873
+ display: block;
874
+ padding: 12px 16px;
875
+ overflow-x: visible;
876
+ min-height: 0;
877
+ }
878
+ .kanban-col { min-width: 0; margin-bottom: 14px; max-height: none; overflow-y: visible; }
879
+ .kanban-col:last-child { margin-bottom: 0; }
880
+ .task-card { margin-bottom: 12px; border-radius: var(--radius); }
881
+ .project-tab, .channel-tab, .done-toggle {
882
+ min-height: 44px;
883
+ display: inline-flex;
884
+ align-items: center;
885
+ }
886
+ .project-tab { padding: 10px 14px; }
887
+ .channel-tab { padding: 8px 12px; }
888
+ .done-toggle { padding: 8px 0; }
889
+ .chat-input-bar { padding: 10px 12px; flex-wrap: wrap; }
890
+ .chat-input-bar select { min-width: 105px; flex: 0 0 auto; }
891
+ .chat-input-bar input { min-width: 0; width: 100%; }
892
+ .chat-input-bar button { width: 100%; min-height: 44px; }
893
+ .health-grid { grid-template-columns: 1fr; gap: var(--space-2); }
894
+ .outcome-rollup { grid-template-columns: 1fr; }
895
+ }
896
+
897
+ @media (max-width: 420px) {
898
+ .header, .agent-strip, .main { padding-left: 12px; padding-right: 12px; }
899
+ .agent-card { min-width: 150px; }
900
+ .panel-header { padding: 10px 12px; }
901
+ .panel-body { padding: 10px 12px; max-height: 320px; }
902
+ .kanban { padding: 10px 12px; }
903
+ .task-card { padding: 9px 10px; }
904
+ .task-title { font-size: 12px; }
905
+ .msg { padding: 5px 0; }
906
+ .msg-header { gap: var(--space-1); }
907
+ .msg-from { max-width: none; }
908
+ .msg-time { margin-left: 0; }
909
+ .chat-input-bar { padding: 8px 10px; }
910
+ .chat-input-bar select { min-width: 0; width: 100%; }
911
+ }
912
+
913
+ @media (min-width: 768px) and (max-width: 1023px) {
914
+ .header, .agent-strip, .main {
915
+ padding-left: 16px;
916
+ padding-right: 16px;
917
+ }
918
+ .header { gap: 10px; flex-wrap: wrap; }
919
+ .header-right { margin-left: auto; gap: 10px; flex-wrap: wrap; justify-content: flex-end; }
920
+ .two-col { gap: var(--space-4); }
921
+ .kanban { padding: 14px 16px; gap: 10px; }
922
+ .kanban-col { min-width: 180px; }
923
+ }
924
+
925
+ @media (min-width: 1024px) {
926
+ .header, .agent-strip {
927
+ max-width: 1400px;
928
+ margin-left: auto;
929
+ margin-right: auto;
930
+ width: 100%;
931
+ padding-left: 24px;
932
+ padding-right: 24px;
933
+ }
934
+ .main { padding-left: 24px; padding-right: 24px; }
935
+ .header-right { gap: var(--space-3); }
936
+ }
937
+
938
+ /* ============================================
939
+ Dashboard Animations - Pixel Design System
940
+ ============================================ */
941
+ :root {
942
+ --transition-fast: 150ms;
943
+ --transition-base: 250ms;
944
+ --transition-slow: 400ms;
945
+ --easing-smooth: cubic-bezier(0.4, 0.0, 0.2, 1);
946
+ --easing-bounce: cubic-bezier(0.68, -0.55, 0.265, 1.55);
947
+ --easing-ease-out: cubic-bezier(0.0, 0.0, 0.2, 1);
948
+ }
949
+
950
+ /* Task Card Interactions */
951
+ .task-card {
952
+ transition: all var(--transition-base) var(--easing-smooth);
953
+ transform: translateY(0);
954
+ animation: fadeSlideIn var(--transition-slow) var(--easing-ease-out);
955
+ }
956
+ .task-card:hover {
957
+ transform: translateY(-2px);
958
+ box-shadow: 0 8px 24px rgba(0, 0, 0, 0.12);
959
+ }
960
+ .task-card:active {
961
+ transform: translateY(0);
962
+ transition-duration: var(--transition-fast);
963
+ }
964
+
965
+ @keyframes fadeSlideIn {
966
+ from { opacity: 0; transform: translateY(10px); }
967
+ to { opacity: 1; transform: translateY(0); }
968
+ }
969
+
970
+ /* Stagger animation for task lists */
971
+ .task-card:nth-child(1) { animation-delay: 0ms; }
972
+ .task-card:nth-child(2) { animation-delay: 50ms; }
973
+ .task-card:nth-child(3) { animation-delay: 100ms; }
974
+ .task-card:nth-child(4) { animation-delay: 150ms; }
975
+ .task-card:nth-child(5) { animation-delay: 200ms; }
976
+ .task-card:nth-child(n+6) { animation-delay: 250ms; }
977
+
978
+ /* Priority Badge Animations */
979
+ .priority-badge {
980
+ transition: transform var(--transition-fast) var(--easing-bounce);
981
+ }
982
+ .task-card:hover .priority-badge {
983
+ transform: scale(1.1);
984
+ }
985
+ .priority-P0 {
986
+ animation: pulseCritical 2s ease-in-out infinite;
987
+ }
988
+ @keyframes pulseCritical {
989
+ 0%, 100% { opacity: 1; }
990
+ 50% { opacity: 0.7; }
991
+ }
992
+
993
+ /* Status Transitions */
994
+ .status-badge {
995
+ transition: all var(--transition-base) var(--easing-smooth);
996
+ }
997
+ .task-card[data-status-changed="true"] {
998
+ animation: statusFlash var(--transition-slow) ease-out;
999
+ }
1000
+ @keyframes statusFlash {
1001
+ 0% { background-color: rgba(34, 197, 94, 0.1); }
1002
+ 100% { background-color: transparent; }
1003
+ }
1004
+
1005
+ /* Modal Animations */
1006
+ .modal-overlay {
1007
+ animation: fadeIn var(--transition-base) ease-out;
1008
+ }
1009
+ .modal {
1010
+ animation: slideUpFade var(--transition-slow) var(--easing-ease-out);
1011
+ }
1012
+ @keyframes fadeIn {
1013
+ from { opacity: 0; }
1014
+ to { opacity: 1; }
1015
+ }
1016
+ @keyframes slideUpFade {
1017
+ from { opacity: 0; transform: translateY(20px) scale(0.95); }
1018
+ to { opacity: 1; transform: translateY(0) scale(1); }
1019
+ }
1020
+ .modal-overlay.closing {
1021
+ animation: fadeOut var(--transition-fast) ease-in;
1022
+ }
1023
+ .modal.closing {
1024
+ animation: slideDownFade var(--transition-fast) ease-in;
1025
+ }
1026
+ @keyframes fadeOut {
1027
+ from { opacity: 1; }
1028
+ to { opacity: 0; }
1029
+ }
1030
+ @keyframes slideDownFade {
1031
+ from { opacity: 1; transform: translateY(0) scale(1); }
1032
+ to { opacity: 0; transform: translateY(10px) scale(0.98); }
1033
+ }
1034
+
1035
+ /* Button Interactions */
1036
+ button, .button {
1037
+ transition: all var(--transition-fast) var(--easing-smooth);
1038
+ position: relative;
1039
+ }
1040
+
1041
+ /* Avoid sticky hover on touch devices */
1042
+ @media (hover: hover) and (pointer: fine) {
1043
+ button:hover, .button:hover {
1044
+ transform: translateY(-1px);
1045
+ box-shadow: var(--shadow-hover);
1046
+ }
1047
+ }
1048
+
1049
+ button:active, .button:active {
1050
+ transform: translateY(0);
1051
+ box-shadow: var(--shadow-active);
1052
+ }
1053
+
1054
+ /* Avatar Animations */
1055
+ .agent-emoji {
1056
+ transition: transform var(--transition-base) var(--easing-smooth);
1057
+ }
1058
+ .agent-card:hover .agent-emoji {
1059
+ transform: scale(1.1) rotate(5deg);
1060
+ }
1061
+
1062
+ /* Status Indicator Breathing */
1063
+ .status-dot {
1064
+ animation: breathe 2s ease-in-out infinite;
1065
+ }
1066
+ @keyframes breathe {
1067
+ 0%, 100% { opacity: 1; transform: scale(1); }
1068
+ 50% { opacity: 0.8; transform: scale(1.1); }
1069
+ }
1070
+
1071
+ /* Kanban Column Transitions */
1072
+ .kanban-col {
1073
+ transition: background-color var(--transition-base) var(--easing-smooth);
1074
+ }
1075
+
1076
+ /* Focus States (Accessibility) */
1077
+ :focus-visible {
1078
+ outline: var(--focus-ring);
1079
+ outline-offset: var(--focus-offset);
1080
+ transition: outline-offset var(--transition-fast) var(--easing-smooth);
1081
+ }
1082
+ :focus-visible:not(:active) {
1083
+ outline-offset: var(--focus-offset-strong);
1084
+ }
1085
+
1086
+ /* Link interactions (make links feel like links) */
1087
+ .panel a {
1088
+ text-decoration: none;
1089
+ text-underline-offset: 3px;
1090
+ text-decoration-thickness: 1px;
1091
+ }
1092
+ .panel a:hover {
1093
+ text-decoration: underline;
1094
+ }
1095
+
1096
+ /* ── Focus-visible parity: match hover styles for keyboard nav ── */
1097
+
1098
+ /* Buttons: lift effect on focus matches hover */
1099
+ button:focus-visible, .button:focus-visible {
1100
+ transform: translateY(-1px);
1101
+ box-shadow: var(--shadow-hover, 0 4px 12px rgba(0, 0, 0, 0.15));
1102
+ }
1103
+
1104
+ /* Cards: accent border on focus matches hover */
1105
+ .task-card:focus-visible { border-color: var(--accent); }
1106
+ .task-card:focus-visible:not(:active) { box-shadow: 0 0 0 1px var(--accent-dim); }
1107
+ .health-card:focus-visible { border-color: var(--accent); }
1108
+ .health-card:focus-visible:not(:active) { box-shadow: 0 0 0 1px var(--accent-dim); }
1109
+ .agent-card:focus-visible { border-color: var(--accent); }
1110
+ .agent-card:focus-visible .agent-emoji { transform: scale(1.1) rotate(5deg); }
1111
+
1112
+ /* Tabs: background + text highlight matches hover */
1113
+ .channel-tab:focus-visible { background: var(--surface-raised); color: var(--text); }
1114
+ .project-tab:focus-visible { color: var(--text); border-bottom-color: var(--text-muted); }
1115
+
1116
+ /* Interactive controls: border highlight matches hover */
1117
+ .focus-toggle:focus-visible { border-color: var(--accent); color: var(--text); }
1118
+ .status-btn:focus-visible { border-color: var(--accent); color: var(--accent); }
1119
+ .artifact-btn:focus-visible { border-color: var(--accent); color: var(--accent); }
1120
+ .modal-copy-btn:focus-visible { border-color: var(--accent); color: var(--accent); }
1121
+ .copy-template-btn:focus-visible { border-color: var(--accent); color: var(--accent); }
1122
+ .modal-close:focus-visible { color: var(--text); }
1123
+ .modal-btn-primary:focus-visible { opacity: 0.85; }
1124
+ .modal-btn-secondary:focus-visible { background: var(--text-muted); }
1125
+ .done-toggle:focus-visible { color: var(--text); }
1126
+ .gs-link:focus-visible { text-decoration: underline; }
1127
+
1128
+ /* Panels: row highlight on focus matches hover */
1129
+ .panel-row:focus-visible { background: var(--surface-raised); }
1130
+ .panel-row:hover { background: var(--surface-raised); }
1131
+ .review-item:focus-visible { background: var(--surface-raised); }
1132
+
1133
+ /* Table rows: highlight on focus matches hover */
1134
+ .table tr:focus-visible td,
1135
+ table tr:focus-visible td { background: var(--surface-raised); }
1136
+
1137
+ /* Feedback cards: interactive elements focus parity */
1138
+ .feedback-card:focus-visible { border-color: var(--accent); }
1139
+ .fb-vote-btn:focus-visible { border-color: var(--accent); color: var(--accent); }
1140
+
1141
+ /* Reduced Motion Preferences */
1142
+ @media (prefers-reduced-motion: reduce) {
1143
+ *, *::before, *::after {
1144
+ animation-duration: 0.01ms !important;
1145
+ animation-iteration-count: 1 !important;
1146
+ transition-duration: 0.01ms !important;
1147
+ }
1148
+ }
1149
+
1150
+ /* ============================================
1151
+ Focus Mode — single active lane emphasis
1152
+ ============================================ */
1153
+ .focus-toggle {
1154
+ display: inline-flex; align-items: center; gap: 6px;
1155
+ padding: 5px 12px; border-radius: var(--radius-full); font-size: 12px; font-weight: 600;
1156
+ cursor: pointer; border: 1px solid var(--border); background: var(--surface-raised);
1157
+ color: var(--text-muted); transition: all var(--transition-base) var(--easing-smooth);
1158
+ user-select: none;
1159
+ }
1160
+ .focus-toggle:hover { border-color: var(--accent); color: var(--text); }
1161
+ .focus-toggle.active {
1162
+ background: var(--accent-dim); border-color: var(--accent); color: var(--accent);
1163
+ }
1164
+ .focus-toggle .focus-icon { font-size: var(--text-md); }
1165
+
1166
+ /* Focus mode active: dim non-active kanban columns */
1167
+ body.focus-mode .kanban-col:not([data-status="doing"]) {
1168
+ opacity: 0.3;
1169
+ transform: scale(0.97);
1170
+ transition: all var(--transition-slow) var(--easing-smooth);
1171
+ pointer-events: none;
1172
+ }
1173
+ body.focus-mode .kanban-col:not([data-status="doing"]):hover {
1174
+ opacity: 0.6;
1175
+ pointer-events: auto;
1176
+ }
1177
+ body.focus-mode .kanban-col[data-status="doing"] {
1178
+ flex: 2;
1179
+ transition: flex var(--transition-slow) var(--easing-smooth);
1180
+ }
1181
+ body.focus-mode .kanban-col[data-status="doing"] .kanban-col-header {
1182
+ border-bottom-color: var(--accent);
1183
+ color: var(--accent);
1184
+ }
1185
+
1186
+ /* QA contract badge on task cards in focus mode */
1187
+ .qa-contract {
1188
+ margin-top: 8px; padding: 6px 8px; border-radius: var(--radius-sm);
1189
+ background: var(--surface-raised); border: 1px solid var(--border-subtle);
1190
+ font-size: var(--text-sm); line-height: 1.5;
1191
+ }
1192
+ .qa-contract .qa-row { display: flex; justify-content: space-between; align-items: center; gap: 6px; }
1193
+ .qa-contract .qa-row + .qa-row { margin-top: 3px; }
1194
+ .qa-contract .qa-label { color: var(--text-muted); text-transform: uppercase; letter-spacing: 0.4px; font-size: var(--text-xs); }
1195
+ .qa-contract .qa-value { color: var(--text-bright); font-weight: 500; }
1196
+ .qa-contract .qa-value.missing { color: var(--yellow); font-style: italic; }
1197
+ .qa-contract .qa-value.has-artifact { color: var(--green); }
1198
+
1199
+ /* Feedback Cards */
1200
+ .feedback-card {
1201
+ padding: 10px 12px; border-bottom: 1px solid var(--border-subtle);
1202
+ }
1203
+ .feedback-card:last-child { border-bottom: none; }
1204
+ .feedback-card .fb-header {
1205
+ display: flex; align-items: center; gap: 6px; font-size: var(--text-sm);
1206
+ }
1207
+ .feedback-card .fb-category { font-weight: 600; }
1208
+ .feedback-card .fb-category.bug { color: var(--red); }
1209
+ .feedback-card .fb-category.feature { color: var(--accent); }
1210
+ .feedback-card .fb-category.general { color: var(--text-muted); }
1211
+ .feedback-card .fb-source { color: var(--text-dim); }
1212
+ .feedback-card .fb-time { color: var(--text-dim); margin-left: auto; }
1213
+ .feedback-card .fb-message {
1214
+ font-size: 12px; color: var(--text-bright); margin-top: 4px; line-height: 1.4;
1215
+ }
1216
+ .feedback-card .fb-footer {
1217
+ display: flex; align-items: center; gap: var(--space-2); margin-top: 6px; font-size: var(--text-xs);
1218
+ }
1219
+ .feedback-card .fb-email { color: var(--text-dim); }
1220
+ .feedback-card .fb-votes { color: var(--text-muted); cursor: pointer; }
1221
+ .feedback-card .fb-votes:hover { color: var(--accent); }
1222
+ .feedback-card .fb-actions { margin-left: auto; display: flex; gap: var(--space-1); }
1223
+ .feedback-card .fb-actions button {
1224
+ font-size: var(--text-xs); padding: 2px 8px; border-radius: var(--radius-sm); cursor: pointer;
1225
+ border: 1px solid var(--border-subtle); background: none; color: var(--text-muted);
1226
+ }
1227
+ .feedback-card .fb-actions button:hover { background: var(--surface-raised); color: var(--text-bright); }
1228
+
1229
+ /* Approval Queue */
1230
+ .approval-card {
1231
+ padding: 10px 12px; margin-bottom: 6px; border-radius: var(--radius-sm);
1232
+ background: var(--surface-raised); border: 1px solid var(--border-subtle);
1233
+ }
1234
+ .approval-card .approval-header {
1235
+ display: flex; justify-content: space-between; align-items: center; gap: var(--space-2);
1236
+ }
1237
+ .approval-card .approval-title { font-size: 12px; font-weight: 600; color: var(--text-bright); flex: 1; }
1238
+ .approval-card .approval-meta {
1239
+ font-size: var(--text-xs); color: var(--text-muted); margin-top: 4px;
1240
+ }
1241
+ .approval-card .approval-actions {
1242
+ display: flex; gap: var(--space-1); margin-top: 8px; justify-content: flex-end;
1243
+ }
1244
+ .approval-card .approval-actions button {
1245
+ font-size: var(--text-xs); padding: 3px 10px; border-radius: var(--radius-sm); cursor: pointer; border: none;
1246
+ }
1247
+ .approval-card .btn-approve { background: var(--green); color: #fff; }
1248
+ .approval-card .btn-reject { background: var(--red); color: #fff; }
1249
+ .approval-card .btn-edit { background: none; border: 1px solid var(--border) !important; color: var(--text-muted); }
1250
+ .approval-card .confidence-score {
1251
+ font-size: var(--text-sm); font-weight: 700; padding: 2px 6px; border-radius: var(--radius);
1252
+ }
1253
+ .approval-card .confidence-score.high { background: rgba(76,175,80,0.15); color: var(--green); }
1254
+ .approval-card .confidence-score.low { background: rgba(255,193,7,0.15); color: var(--yellow); }
1255
+ .batch-approve-bar {
1256
+ display: flex; justify-content: space-between; align-items: center;
1257
+ padding: 8px 12px; background: var(--surface); border-bottom: 1px solid var(--border-subtle);
1258
+ font-size: var(--text-sm); color: var(--text-muted);
1259
+ }
1260
+ .batch-approve-bar button {
1261
+ font-size: var(--text-sm); padding: 4px 12px; border-radius: var(--radius-sm); border: none;
1262
+ background: var(--green); color: #fff; cursor: pointer; font-weight: 600;
1263
+ }
1264
+ .batch-approve-bar button:disabled { opacity: 0.5; cursor: not-allowed; }
1265
+ /* Routing Policy Editor */
1266
+ .policy-agent-card {
1267
+ padding: 10px 12px; margin-bottom: 8px; border-radius: var(--radius-sm);
1268
+ background: var(--surface-raised); border: 1px solid var(--border-subtle);
1269
+ }
1270
+ .policy-agent-card .agent-name { font-size: var(--text-base); font-weight: 600; color: var(--text-bright); }
1271
+ .policy-agent-card .tag-row { display: flex; flex-wrap: wrap; gap: var(--space-1); margin-top: 6px; }
1272
+ .policy-agent-card .tag-chip {
1273
+ display: inline-flex; align-items: center; gap: 3px;
1274
+ font-size: var(--text-xs); padding: 2px 8px; border-radius: var(--radius-md);
1275
+ background: var(--surface); border: 1px solid var(--border-subtle); color: var(--text-muted);
1276
+ }
1277
+ .policy-agent-card .tag-chip .tag-remove {
1278
+ cursor: pointer; color: var(--red); font-size: var(--text-sm); margin-left: 2px;
1279
+ }
1280
+ .policy-agent-card .weight-row {
1281
+ display: flex; align-items: center; gap: var(--space-2); margin-top: 8px; font-size: var(--text-sm);
1282
+ }
1283
+ .policy-agent-card .weight-row input[type="range"] { flex: 1; }
1284
+ .policy-agent-card .weight-row .weight-val { font-weight: 600; color: var(--text-bright); min-width: 28px; }
1285
+ .policy-save-bar {
1286
+ display: flex; justify-content: flex-end; align-items: center; gap: var(--space-2);
1287
+ padding: 8px 0; margin-top: 8px; border-top: 1px solid var(--border-subtle);
1288
+ }
1289
+ .policy-save-bar button { font-size: var(--text-sm); padding: 4px 12px; border-radius: var(--radius-sm); border: none; cursor: pointer; }
1290
+ .policy-save-bar .btn-save { background: var(--accent); color: #fff; font-weight: 600; }
1291
+ .policy-save-bar .btn-discard { background: none; border: 1px solid var(--border) !important; color: var(--text-muted); }
1292
+
1293
+ /* PR Review Quality Panel */
1294
+ .pr-review-section { margin-bottom: 14px; }
1295
+ .pr-review-section-title {
1296
+ font-size: 12px; font-weight: 600; color: var(--text-bright);
1297
+ margin-bottom: 8px; display: flex; align-items: center; gap: 6px;
1298
+ }
1299
+ .pr-review-header {
1300
+ padding: 10px 12px; background: var(--surface-raised); border-radius: var(--radius-sm);
1301
+ border: 1px solid var(--border-subtle); margin-bottom: 10px;
1302
+ }
1303
+ .pr-review-header .pr-title { font-size: var(--text-base); font-weight: 600; color: var(--text-bright); }
1304
+ .pr-review-header .pr-meta { font-size: var(--text-sm); color: var(--text-muted); margin-top: 4px; }
1305
+ .pr-review-header a { color: var(--accent); text-decoration: none; }
1306
+ .pr-review-header a:hover { text-decoration: underline; }
1307
+ .diff-scope-grid {
1308
+ display: grid; grid-template-columns: repeat(auto-fill, minmax(100px, 1fr)); gap: var(--space-2);
1309
+ margin-bottom: 8px;
1310
+ }
1311
+ .diff-stat-card {
1312
+ padding: 8px 10px; background: var(--surface-raised); border-radius: var(--radius-sm);
1313
+ border: 1px solid var(--border-subtle); text-align: center;
1314
+ }
1315
+ .diff-stat-card .stat-value { font-size: var(--text-lg); font-weight: 700; color: var(--text-bright); }
1316
+ .diff-stat-card .stat-label { font-size: var(--text-xs); color: var(--text-muted); text-transform: uppercase; letter-spacing: 0.3px; }
1317
+ .risk-badge {
1318
+ display: inline-block; padding: 2px 8px; border-radius: var(--radius-md);
1319
+ font-size: var(--text-sm); font-weight: 600;
1320
+ }
1321
+ .risk-badge.small { background: rgba(76,175,80,0.15); color: var(--green); }
1322
+ .risk-badge.medium { background: rgba(255,193,7,0.15); color: var(--yellow); }
1323
+ .risk-badge.large { background: rgba(244,67,54,0.15); color: var(--red); }
1324
+ .dir-row {
1325
+ display: flex; justify-content: space-between; align-items: center;
1326
+ padding: 3px 0; font-size: var(--text-sm); border-bottom: 1px solid var(--border-subtle);
1327
+ }
1328
+ .dir-row:last-child { border-bottom: none; }
1329
+ .dir-name { color: var(--text-bright); font-family: monospace; font-size: var(--text-sm); }
1330
+ .dir-stats { color: var(--text-muted); font-size: var(--text-xs); }
1331
+ .ci-check-row {
1332
+ display: flex; align-items: center; gap: 6px;
1333
+ padding: 4px 0; font-size: var(--text-sm);
1334
+ }
1335
+ .ci-check-row .check-icon { font-size: var(--text-base); flex-shrink: 0; }
1336
+ .ci-check-row .check-name { color: var(--text-bright); flex: 1; }
1337
+ .ci-check-row .check-duration { color: var(--text-dim); font-size: var(--text-xs); }
1338
+ .ci-check-row a { color: var(--accent); text-decoration: none; font-size: var(--text-xs); }
1339
+ .criterion-row {
1340
+ padding: 6px 8px; margin-bottom: 4px; border-radius: var(--radius-sm);
1341
+ background: var(--surface-raised); border: 1px solid var(--border-subtle);
1342
+ }
1343
+ .criterion-row .criterion-text { font-size: 12px; color: var(--text-bright); margin-bottom: 4px; display: flex; align-items: flex-start; gap: 6px; }
1344
+ .criterion-row .criterion-evidence { font-size: var(--text-xs); color: var(--text-muted); padding-left: 20px; }
1345
+ .criterion-row .criterion-evidence .evidence-item { margin-top: 2px; }
1346
+ .confidence-badge {
1347
+ display: inline-block; padding: 1px 6px; border-radius: var(--radius);
1348
+ font-size: 9px; font-weight: 600; text-transform: uppercase; letter-spacing: 0.3px;
1349
+ }
1350
+ .confidence-badge.high { background: rgba(76,175,80,0.15); color: var(--green); }
1351
+ .confidence-badge.medium { background: rgba(255,193,7,0.15); color: var(--yellow); }
1352
+ .confidence-badge.low { background: rgba(255,152,0,0.15); color: #ff9800; }
1353
+ .confidence-badge.none { background: rgba(244,67,54,0.15); color: var(--red); }
1354
+
1355
+ /* Focus mode: dim agent cards not working on active tasks */
1356
+ body.focus-mode .agent-card:not(.active) {
1357
+ opacity: 0.25;
1358
+ transition: opacity var(--transition-base) var(--easing-smooth);
1359
+ }
1360
+ body.focus-mode .agent-card:not(.active):hover {
1361
+ opacity: 0.7;
1362
+ }
1363
+
1364
+ /* Focus mode: collapse non-essential panels */
1365
+ body.focus-mode .panel.focus-collapse .panel-body,
1366
+ body.focus-mode .panel.focus-collapse .channel-tabs,
1367
+ body.focus-mode .panel.focus-collapse .chat-input-bar,
1368
+ body.focus-mode .panel.focus-collapse .project-tabs,
1369
+ body.focus-mode .panel.focus-collapse .kanban {
1370
+ display: none;
1371
+ }
1372
+ body.focus-mode .panel.focus-collapse {
1373
+ opacity: 0.5;
1374
+ transition: opacity var(--transition-base) var(--easing-smooth);
1375
+ cursor: pointer;
1376
+ }
1377
+ body.focus-mode .panel.focus-collapse:hover {
1378
+ opacity: 0.8;
1379
+ }
1380
+ body.focus-mode .panel.focus-collapse .panel-header::after {
1381
+ content: ' (click to expand)';
1382
+ font-size: var(--text-sm); color: var(--text-muted); font-weight: 400; font-style: italic;
1383
+ }
1384
+
1385
+ /* Getting Started panel */
1386
+ .getting-started {
1387
+ background: linear-gradient(135deg, var(--surface) 0%, var(--bg) 100%);
1388
+ border: 1px solid var(--accent);
1389
+ border-radius: var(--radius-md); overflow: hidden;
1390
+ box-shadow: 0 0 20px rgba(77, 166, 255, 0.08), 0 4px 12px rgba(0, 0, 0, 0.15);
1391
+ }
1392
+ .getting-started.hidden { display: none; }
1393
+ .getting-started .panel-header {
1394
+ display: flex; align-items: center; justify-content: space-between;
1395
+ padding: 16px 20px; font-weight: 700; font-size: 16px; color: var(--text-bright);
1396
+ border-bottom: 1px solid var(--border);
1397
+ background: rgba(77, 166, 255, 0.04);
1398
+ }
1399
+ .getting-started .dismiss-btn {
1400
+ background: none; border: none; color: var(--text-muted); cursor: pointer; font-size: var(--text-base);
1401
+ padding: 4px 8px; border-radius: var(--radius-sm);
1402
+ }
1403
+ .getting-started .dismiss-btn:hover { color: var(--text); background: var(--accent-dim); }
1404
+ .getting-started .dismiss-btn:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
1405
+ .getting-started .gs-steps { padding: 18px 20px; display: flex; flex-direction: column; gap: 10px; }
1406
+ .getting-started .gs-step {
1407
+ display: flex; align-items: flex-start; gap: var(--space-3);
1408
+ padding: 14px 16px; border-radius: var(--radius-sm);
1409
+ background: var(--surface-raised); border: 1px solid var(--border);
1410
+ transition: border-color var(--transition-fast) var(--easing-smooth);
1411
+ }
1412
+ @media (hover: hover) and (pointer: fine) {
1413
+ .getting-started .gs-step:hover { border-color: var(--accent); }
1414
+ }
1415
+ .getting-started .gs-step.done { opacity: 0.6; }
1416
+ .getting-started .gs-step .gs-icon {
1417
+ flex-shrink: 0; width: 28px; height: 28px; border-radius: 50%;
1418
+ display: flex; align-items: center; justify-content: center;
1419
+ font-size: var(--text-md); background: var(--accent-dim); color: var(--accent);
1420
+ }
1421
+ .getting-started .gs-step.done .gs-icon { background: var(--green-dim); color: var(--green); }
1422
+ .getting-started .gs-step .gs-content { flex: 1; }
1423
+ .getting-started .gs-step .gs-title {
1424
+ font-size: var(--text-base); font-weight: 600; color: var(--text-bright); margin-bottom: 2px;
1425
+ }
1426
+ .getting-started .gs-step .gs-desc {
1427
+ font-size: 12px; color: var(--text-muted); line-height: 1.4;
1428
+ }
1429
+ .getting-started .gs-step .gs-link {
1430
+ display: inline-block; margin-top: 4px; font-size: 12px;
1431
+ color: var(--accent); text-decoration: none;
1432
+ }
1433
+ .getting-started .gs-step .gs-link:hover { text-decoration: underline; }
1434
+
1435
+ /* Polls */
1436
+ .poll-new-btn {
1437
+ float: right; font-size: var(--text-xs, 11px); background: none;
1438
+ border: 1px solid var(--border, #2a2a4a); color: var(--text-muted, #888);
1439
+ padding: 2px 8px; border-radius: var(--radius-sm, 4px); cursor: pointer;
1440
+ }
1441
+ .poll-new-btn:hover { border-color: var(--accent, #60a5fa); color: var(--text-primary, #e0e0e0); }
1442
+ .poll-new-btn:focus-visible { outline: var(--focus-ring); outline-offset: 2px; }
1443
+ .poll-create-form {
1444
+ border-top: 1px solid var(--border-subtle, #222); padding: 12px;
1445
+ }
1446
+ .poll-form-label {
1447
+ display: block; font-size: var(--text-xs, 11px); color: var(--text-muted, #888);
1448
+ text-transform: uppercase; letter-spacing: 0.05em; margin-bottom: 4px; margin-top: 8px;
1449
+ }
1450
+ .poll-form-label:first-child { margin-top: 0; }
1451
+ .poll-input {
1452
+ width: 100%; padding: 6px 8px; margin-bottom: 4px;
1453
+ border: 1px solid var(--border, #2a2a4a); border-radius: var(--radius-sm, 4px);
1454
+ background: var(--bg-secondary, #1a1a2e); color: var(--text-primary, #e0e0e0);
1455
+ font-size: var(--text-sm, 13px); box-sizing: border-box;
1456
+ }
1457
+ .poll-input:focus { border-color: var(--accent, #60a5fa); outline: none; }
1458
+ .poll-select {
1459
+ font-size: var(--text-xs, 11px); padding: 4px 8px;
1460
+ border: 1px solid var(--border, #2a2a4a); border-radius: var(--radius-sm, 4px);
1461
+ background: var(--bg-secondary, #1a1a2e); color: var(--text-primary, #e0e0e0);
1462
+ }
1463
+ .poll-anon-label {
1464
+ font-size: var(--text-xs, 11px); color: var(--text-muted, #888);
1465
+ display: flex; align-items: center; gap: 4px;
1466
+ }
1467
+ .poll-form-row { display: flex; gap: 8px; margin-top: 8px; align-items: center; }
1468
+ .poll-btn-primary {
1469
+ font-size: var(--text-xs, 11px); background: var(--accent, #60a5fa); border: none;
1470
+ color: #fff; padding: 4px 12px; border-radius: var(--radius-sm, 4px); cursor: pointer;
1471
+ }
1472
+ .poll-btn-primary:hover { opacity: 0.9; }
1473
+ .poll-btn-primary:focus-visible { outline: var(--focus-ring); outline-offset: 2px; }
1474
+ .poll-btn-secondary {
1475
+ font-size: var(--text-xs, 11px); background: none;
1476
+ border: 1px solid var(--border, #2a2a4a); color: var(--text-muted, #888);
1477
+ padding: 4px 8px; border-radius: var(--radius-sm, 4px); cursor: pointer;
1478
+ }
1479
+ .poll-btn-secondary:hover { border-color: var(--accent, #60a5fa); color: var(--text-primary, #e0e0e0); }
1480
+ .poll-btn-secondary:focus-visible { outline: var(--focus-ring); outline-offset: 2px; }
1481
+
1482
+ /* Poll cards */
1483
+ .poll-card {
1484
+ background: var(--surface-raised, var(--surface, #1e1e38)); border: 1px solid var(--border, #2a2a4a);
1485
+ border-radius: var(--radius-sm, 4px); padding: 12px; margin-bottom: 12px;
1486
+ }
1487
+ .poll-meta {
1488
+ display: flex; align-items: center; gap: 6px; font-size: var(--text-xs, 11px);
1489
+ color: var(--text-muted, #888); margin-bottom: 6px;
1490
+ }
1491
+ .poll-badge-open {
1492
+ background: var(--green-dim, rgba(74, 222, 128, 0.12)); color: var(--green, #4ade80);
1493
+ padding: 1px 6px; border-radius: var(--radius-sm, 4px); font-size: 10px; font-weight: 500;
1494
+ }
1495
+ .poll-badge-closed {
1496
+ background: var(--border, #2a2a4a); color: var(--text-muted, #888);
1497
+ padding: 1px 6px; border-radius: var(--radius-sm, 4px); font-size: 10px; font-weight: 500;
1498
+ }
1499
+ .poll-question {
1500
+ font-size: var(--text-md, 14px); font-weight: var(--font-weight-semibold, 600);
1501
+ color: var(--text-bright, #fff); margin-bottom: 8px;
1502
+ }
1503
+ .poll-option {
1504
+ position: relative; margin-bottom: 4px; border: 1px solid var(--border, #2a2a4a);
1505
+ border-radius: var(--radius-sm, 4px); min-height: 40px; overflow: hidden; cursor: pointer;
1506
+ transition: border-color 0.15s;
1507
+ }
1508
+ .poll-option:hover { border-color: var(--accent, #60a5fa); }
1509
+ .poll-option:focus-visible { outline: var(--focus-ring); outline-offset: -2px; }
1510
+ .poll-option[aria-checked="true"] { border-color: var(--accent, #60a5fa); background: rgba(96,165,250,0.04); }
1511
+ .poll-option-bar {
1512
+ position: absolute; top: 0; left: 0; height: 100%;
1513
+ background: var(--accent-dim, rgba(96,165,250,0.12)); border-radius: var(--radius-sm, 4px);
1514
+ transition: width 0.3s ease;
1515
+ }
1516
+ .poll-option-content {
1517
+ position: relative; display: flex; align-items: center; justify-content: space-between;
1518
+ padding: 8px 12px; font-size: var(--text-sm, 13px); z-index: 1;
1519
+ }
1520
+ .poll-option-label { display: flex; align-items: center; gap: 8px; }
1521
+ .poll-option-check {
1522
+ width: 16px; height: 16px; border-radius: 50%; border: 2px solid var(--border, #2a2a4a);
1523
+ display: flex; align-items: center; justify-content: center; flex-shrink: 0;
1524
+ }
1525
+ .poll-option[aria-checked="true"] .poll-option-check {
1526
+ border-color: var(--accent, #60a5fa); background: var(--accent, #60a5fa);
1527
+ }
1528
+ .poll-option[aria-checked="true"] .poll-option-check::after {
1529
+ content: '✓'; color: #fff; font-size: 10px; line-height: 1;
1530
+ }
1531
+ .poll-option-stats {
1532
+ display: flex; align-items: center; gap: 8px;
1533
+ font-size: var(--text-xs, 11px); color: var(--text-muted, #888);
1534
+ }
1535
+ .poll-voter-dots { display: flex; gap: 2px; }
1536
+ .poll-voter-dot {
1537
+ width: 18px; height: 18px; border-radius: 50%; font-size: 9px; font-weight: 600;
1538
+ display: flex; align-items: center; justify-content: center; color: #fff;
1539
+ text-transform: uppercase;
1540
+ }
1541
+ .poll-footer {
1542
+ display: flex; align-items: center; justify-content: space-between;
1543
+ font-size: var(--text-xs, 11px); color: var(--text-muted, #888); margin-top: 8px;
1544
+ }
1545
+
1546
+ /* Intensity control */
1547
+ .intensity-control {
1548
+ display: flex; align-items: center; gap: 8px; padding: 8px 16px;
1549
+ background: var(--surface, #1a1a2e); border-bottom: 1px solid var(--border, #2a2a4a);
1550
+ }
1551
+ .intensity-label { font-size: var(--text-xs, 11px); color: var(--text-muted, #888); text-transform: uppercase; letter-spacing: 0.05em; margin-right: 4px; }
1552
+ .intensity-btn {
1553
+ font-size: var(--text-sm, 13px); padding: 4px 12px; border-radius: var(--radius-sm, 4px);
1554
+ border: 1px solid var(--border, #2a2a4a); background: transparent; color: var(--text-secondary, #aaa);
1555
+ cursor: pointer; transition: all 0.15s ease;
1556
+ }
1557
+ .intensity-btn:hover { border-color: var(--accent, #60a5fa); color: var(--text-primary, #e0e0e0); }
1558
+ .intensity-btn:focus-visible { outline: var(--focus-ring); outline-offset: 2px; }
1559
+ .intensity-btn.intensity-active {
1560
+ background: var(--accent, #60a5fa); color: #fff; border-color: var(--accent, #60a5fa);
1561
+ }
1562
+ .intensity-info { font-size: var(--text-xs, 11px); color: var(--text-muted, #888); margin-left: 8px; }
1563
+ .intensity-sep { color: var(--border, #2a2a4a); margin: 0 4px; }
1564
+ .pause-toggle-btn {
1565
+ font-size: var(--text-sm, 13px); padding: 4px 12px; border-radius: var(--radius-sm, 4px);
1566
+ border: 1px solid var(--border, #2a2a4a); background: transparent; color: var(--text-secondary, #aaa);
1567
+ cursor: pointer; transition: all 0.15s ease;
1568
+ }
1569
+ .pause-toggle-btn:hover { border-color: var(--red, #f87171); color: var(--red, #f87171); }
1570
+ .pause-toggle-btn:focus-visible { outline: var(--focus-ring); outline-offset: 2px; }
1571
+ .pause-toggle-btn.paused {
1572
+ background: var(--red-dim, rgba(248,113,113,0.12)); color: var(--red, #f87171);
1573
+ border-color: var(--red, #f87171);
1574
+ }
1575
+ .pause-toggle-btn.paused:hover { background: var(--green-dim, rgba(74,222,128,0.12)); color: var(--green, #4ade80); border-color: var(--green, #4ade80); }
1576
+
1577
+ /* ============================================================
1578
+ FILE UPLOAD — drop zone, progress queue, file browser, attachments
1579
+ ============================================================ */
1580
+
1581
+ /* Drop zone */
1582
+ .drop-zone {
1583
+ border: 2px dashed var(--border);
1584
+ border-radius: var(--radius-md);
1585
+ padding: var(--space-6) var(--space-4);
1586
+ text-align: center;
1587
+ cursor: pointer;
1588
+ transition: all var(--transition-normal) var(--easing-smooth);
1589
+ position: relative;
1590
+ min-height: 140px;
1591
+ display: flex;
1592
+ flex-direction: column;
1593
+ align-items: center;
1594
+ justify-content: center;
1595
+ gap: var(--space-2);
1596
+ }
1597
+ .drop-zone input[type="file"] {
1598
+ position: absolute;
1599
+ inset: 0;
1600
+ opacity: 0;
1601
+ cursor: pointer;
1602
+ width: 100%;
1603
+ height: 100%;
1604
+ }
1605
+ @media (hover: hover) and (pointer: fine) {
1606
+ .drop-zone:hover {
1607
+ border-color: var(--accent);
1608
+ background: var(--accent-dim);
1609
+ }
1610
+ }
1611
+ .drop-zone.drag-over {
1612
+ border-color: var(--accent);
1613
+ background: var(--accent-dim);
1614
+ border-style: solid;
1615
+ transform: scale(1.01);
1616
+ }
1617
+ .drop-zone:focus-within {
1618
+ outline: var(--focus-ring);
1619
+ outline-offset: var(--focus-offset);
1620
+ border-color: var(--accent);
1621
+ }
1622
+
1623
+ /* Upload progress queue */
1624
+ .upload-queue {
1625
+ margin-top: var(--space-3);
1626
+ display: flex;
1627
+ flex-direction: column;
1628
+ gap: var(--space-2);
1629
+ }
1630
+ .upload-item {
1631
+ display: flex;
1632
+ align-items: center;
1633
+ gap: var(--space-3);
1634
+ padding: var(--space-2) var(--space-3);
1635
+ background: var(--surface-raised);
1636
+ border-radius: var(--radius-sm);
1637
+ border: 1px solid var(--border-subtle);
1638
+ }
1639
+ .upload-item .file-icon { font-size: 18px; flex-shrink: 0; width: 24px; text-align: center; }
1640
+ .upload-item .file-info { flex: 1; min-width: 0; }
1641
+ .upload-item .file-name {
1642
+ font-size: var(--text-sm);
1643
+ font-weight: var(--font-weight-medium);
1644
+ white-space: nowrap;
1645
+ overflow: hidden;
1646
+ text-overflow: ellipsis;
1647
+ }
1648
+ .upload-item .file-size { font-size: var(--text-xs); color: var(--text-muted); }
1649
+ .upload-item .progress-bar {
1650
+ flex: 1;
1651
+ height: 4px;
1652
+ background: var(--border-subtle);
1653
+ border-radius: 2px;
1654
+ overflow: hidden;
1655
+ max-width: 200px;
1656
+ }
1657
+ .upload-item .progress-fill {
1658
+ height: 100%;
1659
+ border-radius: 2px;
1660
+ transition: width var(--transition-normal) var(--easing-smooth);
1661
+ }
1662
+ .upload-item .progress-fill.uploading { background: var(--accent); width: 40%; }
1663
+ .upload-item .progress-fill.done { background: var(--green); width: 100%; }
1664
+ .upload-item .progress-fill.error { background: var(--red); width: 100%; }
1665
+ .upload-item .status-icon { flex-shrink: 0; font-size: var(--text-sm); }
1666
+ .upload-item .status-icon.done { color: var(--green); }
1667
+ .upload-item .status-icon.error { color: var(--red); }
1668
+ .upload-item .cancel-btn {
1669
+ background: none;
1670
+ border: none;
1671
+ color: var(--text-muted);
1672
+ cursor: pointer;
1673
+ font-size: var(--text-sm);
1674
+ padding: var(--space-1);
1675
+ border-radius: var(--radius-sm);
1676
+ transition: color var(--transition-fast);
1677
+ font-family: inherit;
1678
+ }
1679
+ .upload-item .cancel-btn:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1680
+ @media (hover: hover) and (pointer: fine) {
1681
+ .upload-item .cancel-btn:hover { color: var(--red); }
1682
+ }
1683
+
1684
+ /* File browser toolbar */
1685
+ .file-toolbar {
1686
+ display: flex;
1687
+ align-items: center;
1688
+ gap: var(--space-2);
1689
+ margin-bottom: var(--space-3);
1690
+ flex-wrap: wrap;
1691
+ }
1692
+ .file-search {
1693
+ flex: 1;
1694
+ min-width: 180px;
1695
+ background: var(--surface-raised);
1696
+ border: 1px solid var(--border-subtle);
1697
+ border-radius: var(--radius-sm);
1698
+ padding: var(--space-2) var(--space-3);
1699
+ color: var(--text);
1700
+ font-size: var(--text-sm);
1701
+ font-family: inherit;
1702
+ transition: border-color var(--transition-fast);
1703
+ }
1704
+ .file-search:focus { outline: none; border-color: var(--accent); }
1705
+ .file-search::placeholder { color: var(--text-muted); }
1706
+ .view-toggle {
1707
+ display: flex;
1708
+ border: 1px solid var(--border-subtle);
1709
+ border-radius: var(--radius-sm);
1710
+ overflow: hidden;
1711
+ }
1712
+ .view-toggle button {
1713
+ background: var(--surface-raised);
1714
+ border: none;
1715
+ color: var(--text-muted);
1716
+ padding: var(--space-1) var(--space-2);
1717
+ cursor: pointer;
1718
+ font-size: var(--text-sm);
1719
+ font-family: inherit;
1720
+ transition: all var(--transition-fast);
1721
+ }
1722
+ .view-toggle button:focus-visible { outline: var(--focus-ring); outline-offset: -2px; }
1723
+ .view-toggle button.active { background: var(--accent-dim); color: var(--accent); }
1724
+ .view-toggle button + button { border-left: 1px solid var(--border-subtle); }
1725
+ @media (hover: hover) and (pointer: fine) {
1726
+ .view-toggle button:not(.active):hover { background: var(--surface-raised); color: var(--text); }
1727
+ }
1728
+
1729
+ /* File grid */
1730
+ .file-grid {
1731
+ display: grid;
1732
+ grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
1733
+ gap: var(--space-3);
1734
+ }
1735
+ .file-card {
1736
+ background: var(--surface-raised);
1737
+ border: 1px solid var(--border-subtle);
1738
+ border-radius: var(--radius-md);
1739
+ padding: var(--space-3);
1740
+ cursor: pointer;
1741
+ transition: all var(--transition-normal) var(--easing-smooth);
1742
+ text-align: center;
1743
+ }
1744
+ .file-card:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1745
+ @media (hover: hover) and (pointer: fine) {
1746
+ .file-card:hover {
1747
+ border-color: var(--border);
1748
+ box-shadow: var(--shadow-hover);
1749
+ transform: translateY(-1px);
1750
+ }
1751
+ }
1752
+ .file-card .thumb {
1753
+ width: 100%;
1754
+ aspect-ratio: 4/3;
1755
+ background: var(--surface);
1756
+ border-radius: var(--radius-sm);
1757
+ margin-bottom: var(--space-2);
1758
+ display: flex;
1759
+ align-items: center;
1760
+ justify-content: center;
1761
+ overflow: hidden;
1762
+ }
1763
+ .file-card .thumb img { width: 100%; height: 100%; object-fit: cover; border-radius: var(--radius-sm); }
1764
+ .file-card .thumb .type-icon { font-size: 28px; opacity: 0.5; }
1765
+ .file-card .card-name {
1766
+ font-size: var(--text-sm);
1767
+ font-weight: var(--font-weight-medium);
1768
+ white-space: nowrap;
1769
+ overflow: hidden;
1770
+ text-overflow: ellipsis;
1771
+ }
1772
+ .file-card .card-meta { font-size: var(--text-xs); color: var(--text-muted); margin-top: 2px; }
1773
+ .file-card .card-actions { display: flex; gap: var(--space-1); justify-content: center; margin-top: var(--space-2); opacity: 0; transition: opacity var(--transition-fast); }
1774
+ .file-card:focus-within .card-actions { opacity: 1; }
1775
+ @media (hover: hover) and (pointer: fine) {
1776
+ .file-card:hover .card-actions { opacity: 1; }
1777
+ }
1778
+
1779
+ /* File list */
1780
+ .file-list {
1781
+ display: flex;
1782
+ flex-direction: column;
1783
+ gap: 1px;
1784
+ background: var(--border-subtle);
1785
+ border-radius: var(--radius-md);
1786
+ overflow: hidden;
1787
+ }
1788
+ .file-list-item {
1789
+ display: flex;
1790
+ align-items: center;
1791
+ gap: var(--space-3);
1792
+ padding: var(--space-2) var(--space-3);
1793
+ background: var(--surface-raised);
1794
+ cursor: pointer;
1795
+ transition: background var(--transition-fast);
1796
+ }
1797
+ .file-list-item:focus-visible { outline: var(--focus-ring); outline-offset: -2px; position: relative; z-index: 1; }
1798
+ @media (hover: hover) and (pointer: fine) {
1799
+ .file-list-item:hover { background: var(--bg); }
1800
+ }
1801
+ .file-list-item .list-icon { font-size: 16px; flex-shrink: 0; width: 24px; text-align: center; }
1802
+ .file-list-item .list-thumb { width: 32px; height: 32px; border-radius: 4px; object-fit: cover; flex-shrink: 0; }
1803
+ .file-list-item .list-name {
1804
+ flex: 1;
1805
+ font-size: var(--text-sm);
1806
+ font-weight: var(--font-weight-medium);
1807
+ white-space: nowrap;
1808
+ overflow: hidden;
1809
+ text-overflow: ellipsis;
1810
+ }
1811
+ .file-list-item .list-meta { font-size: var(--text-xs); color: var(--text-muted); flex-shrink: 0; }
1812
+ .file-list-item .list-actions {
1813
+ display: flex;
1814
+ gap: var(--space-1);
1815
+ opacity: 0;
1816
+ transition: opacity var(--transition-fast);
1817
+ }
1818
+ .file-list-item:focus-within .list-actions { opacity: 1; }
1819
+ @media (hover: hover) and (pointer: fine) {
1820
+ .file-list-item:hover .list-actions { opacity: 1; }
1821
+ }
1822
+ .action-btn {
1823
+ background: none;
1824
+ border: none;
1825
+ color: var(--text-muted);
1826
+ cursor: pointer;
1827
+ padding: var(--space-1);
1828
+ border-radius: var(--radius-sm);
1829
+ font-size: var(--text-xs);
1830
+ font-family: inherit;
1831
+ transition: color var(--transition-fast);
1832
+ }
1833
+ .action-btn:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1834
+ @media (hover: hover) and (pointer: fine) {
1835
+ .action-btn:hover { color: var(--text); }
1836
+ .action-btn.delete:hover { color: var(--red); }
1837
+ }
1838
+
1839
+ /* Chat attachment button */
1840
+ .attach-btn {
1841
+ background: none;
1842
+ border: none;
1843
+ color: var(--text-muted);
1844
+ cursor: pointer;
1845
+ font-size: 18px;
1846
+ padding: var(--space-1);
1847
+ border-radius: var(--radius-sm);
1848
+ transition: color var(--transition-fast);
1849
+ flex-shrink: 0;
1850
+ font-family: inherit;
1851
+ position: relative;
1852
+ line-height: 1;
1853
+ }
1854
+ .attach-btn:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1855
+ @media (hover: hover) and (pointer: fine) {
1856
+ .attach-btn:hover { color: var(--accent); }
1857
+ }
1858
+
1859
+ /* Attachment preview strip (above chat input) */
1860
+ .attachment-preview {
1861
+ display: flex;
1862
+ gap: var(--space-2);
1863
+ padding: var(--space-2) var(--space-3);
1864
+ flex-wrap: wrap;
1865
+ border-top: 1px solid var(--border-subtle);
1866
+ background: var(--surface-raised);
1867
+ }
1868
+ .attachment-chip {
1869
+ display: flex;
1870
+ align-items: center;
1871
+ gap: var(--space-2);
1872
+ background: var(--surface);
1873
+ border: 1px solid var(--border-subtle);
1874
+ border-radius: var(--radius-sm);
1875
+ padding: var(--space-1) var(--space-2);
1876
+ font-size: var(--text-xs);
1877
+ max-width: 200px;
1878
+ }
1879
+ .attachment-chip .chip-name {
1880
+ white-space: nowrap;
1881
+ overflow: hidden;
1882
+ text-overflow: ellipsis;
1883
+ flex: 1;
1884
+ color: var(--text);
1885
+ }
1886
+ .attachment-chip .chip-remove {
1887
+ background: none;
1888
+ border: none;
1889
+ color: var(--text-muted);
1890
+ cursor: pointer;
1891
+ font-size: var(--text-xs);
1892
+ padding: 0 2px;
1893
+ font-family: inherit;
1894
+ }
1895
+ .attachment-chip .chip-remove:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1896
+ @media (hover: hover) and (pointer: fine) {
1897
+ .attachment-chip .chip-remove:hover { color: var(--red); }
1898
+ }
1899
+
1900
+ /* File card in chat messages */
1901
+ .msg-file-card {
1902
+ display: inline-flex;
1903
+ align-items: center;
1904
+ gap: var(--space-2);
1905
+ background: var(--surface-raised);
1906
+ border: 1px solid var(--border-subtle);
1907
+ border-radius: var(--radius-md);
1908
+ padding: var(--space-2) var(--space-3);
1909
+ cursor: pointer;
1910
+ transition: all var(--transition-fast);
1911
+ text-decoration: none;
1912
+ color: var(--text);
1913
+ max-width: 100%;
1914
+ }
1915
+ .msg-file-card:focus-visible { outline: var(--focus-ring); outline-offset: var(--focus-offset); }
1916
+ @media (hover: hover) and (pointer: fine) {
1917
+ .msg-file-card:hover { border-color: var(--border); background: var(--bg); }
1918
+ }
1919
+ .msg-file-card .file-thumb-placeholder {
1920
+ width: 36px;
1921
+ height: 36px;
1922
+ border-radius: var(--radius-sm);
1923
+ background: var(--surface);
1924
+ display: flex;
1925
+ align-items: center;
1926
+ justify-content: center;
1927
+ font-size: 18px;
1928
+ flex-shrink: 0;
1929
+ }
1930
+ .msg-file-card .msg-file-info { min-width: 0; }
1931
+ .msg-file-card .msg-file-info .name {
1932
+ font-size: var(--text-sm);
1933
+ font-weight: var(--font-weight-medium);
1934
+ white-space: nowrap;
1935
+ overflow: hidden;
1936
+ text-overflow: ellipsis;
1937
+ }
1938
+ .msg-file-card .msg-file-info .meta { font-size: var(--text-xs); color: var(--text-muted); }
1939
+ </style>
1940
+ <link rel="stylesheet" href="/dashboard-animations.css">
1941
+ </head>
1942
+ <body>
1943
+
1944
+ <div class="header">
1945
+ <div class="header-left">
1946
+ <div class="header-logo">⚡ <span>reflectt</span>-node</div>
1947
+ </div>
1948
+ <div class="header-right">
1949
+ <span><span class="status-dot"></span>Running</span>
1950
+ <button class="focus-toggle" id="focus-toggle" onclick="toggleFocusMode()" title="Focus Mode: highlight active work, collapse noise">
1951
+ <span class="focus-icon">🎯</span> Focus
1952
+ </button>
1953
+ <span id="release-badge" class="release-badge" title="Deploy status">deploy: checking…</span>
1954
+ <span id="build-badge" class="release-badge" title="Build info">build: loading…</span>
1955
+ <span id="clock"></span>
1956
+ </div>
1957
+ </div>
1958
+ <div id="pause-banner" class="pause-banner" style="display:none">
1959
+ <span class="pause-icon">⏸️</span>
1960
+ <span id="pause-message">Team paused</span>
1961
+ <button onclick="resumeFromBanner()" class="pause-resume-btn">Resume</button>
1962
+ </div>
1963
+ <div id="intensity-control" class="intensity-control" role="radiogroup" aria-label="Team intensity">
1964
+ <span class="intensity-label">Intensity</span>
1965
+ <button role="radio" aria-checked="false" class="intensity-btn" data-preset="low" onclick="setIntensity('low')" tabindex="0">🐢 Low</button>
1966
+ <button role="radio" aria-checked="true" class="intensity-btn intensity-active" data-preset="normal" onclick="setIntensity('normal')" tabindex="-1">⚡ Normal</button>
1967
+ <button role="radio" aria-checked="false" class="intensity-btn" data-preset="high" onclick="setIntensity('high')" tabindex="-1">🔥 High</button>
1968
+ <span id="intensity-info" class="intensity-info"></span>
1969
+ <span class="intensity-sep">|</span>
1970
+ <button id="pause-toggle-btn" class="pause-toggle-btn" onclick="toggleTeamPause()" aria-label="Pause team" tabindex="0">⏸️ Pause</button>
1971
+ </div>
1972
+
1973
+ <div class="agent-strip-wrapper" id="agent-strip-wrapper"><div class="agent-strip" id="agent-strip"></div></div>
1974
+
1975
+ <button class="sidebar-toggle" id="sidebar-toggle" onclick="toggleSidebar()" aria-label="Toggle sidebar">☰</button>
1976
+ <div class="sidebar-overlay" id="sidebar-overlay" onclick="toggleSidebar()"></div>
1977
+
1978
+ <div class="app-layout">
1979
+ <nav class="sidebar" id="sidebar" aria-label="Dashboard navigation">
1980
+ <div class="sidebar-nav">
1981
+ <button class="sidebar-link active" data-page="overview" onclick="navigateTo('overview')">
1982
+ <span class="nav-icon">🧭</span><span class="nav-label">Overview</span>
1983
+ </button>
1984
+ <button class="sidebar-link" data-page="tasks" onclick="navigateTo('tasks')">
1985
+ <span class="nav-icon">📋</span><span class="nav-label">Tasks</span><span class="nav-badge" id="nav-task-count">0</span>
1986
+ </button>
1987
+ <button class="sidebar-link" data-page="chat" onclick="navigateTo('chat')">
1988
+ <span class="nav-icon">💬</span><span class="nav-label">Chat</span>
1989
+ </button>
1990
+ <button class="sidebar-link" data-page="reviews" onclick="navigateTo('reviews')">
1991
+ <span class="nav-icon">👀</span><span class="nav-label">Reviews</span><span class="nav-badge" id="nav-review-count">0</span>
1992
+ </button>
1993
+ <div class="sidebar-divider"></div>
1994
+ <div class="sidebar-section">Insights</div>
1995
+ <button class="sidebar-link" data-page="health" onclick="navigateTo('health')">
1996
+ <span class="nav-icon">🏥</span><span class="nav-label">Health</span>
1997
+ </button>
1998
+ <button class="sidebar-link" data-page="outcomes" onclick="navigateTo('outcomes')">
1999
+ <span class="nav-icon">🏁</span><span class="nav-label">Outcomes</span>
2000
+ </button>
2001
+ <button class="sidebar-link" data-page="research" onclick="navigateTo('research')">
2002
+ <span class="nav-icon">🔍</span><span class="nav-label">Research</span>
2003
+ </button>
2004
+ <div class="sidebar-divider"></div>
2005
+ <div class="sidebar-section">System</div>
2006
+ <button class="sidebar-link" data-page="artifacts" onclick="navigateTo('artifacts')">
2007
+ <span class="nav-icon">📚</span><span class="nav-label">Artifacts</span>
2008
+ </button>
2009
+ <a class="sidebar-link" href="/ui-kit" target="_blank">
2010
+ <span class="nav-icon">🎨</span><span class="nav-label">UI Kit</span>
2011
+ </a>
2012
+ <a class="sidebar-link" href="/health" target="_blank">
2013
+ <span class="nav-icon">🩺</span><span class="nav-label">Doctor</span>
2014
+ </a>
2015
+ </div>
2016
+ </nav>
2017
+
2018
+ <div class="main">
2019
+ <!-- ═══ PAGE: Overview ═══ -->
2020
+ <div class="page active" id="page-overview">
2021
+
2022
+ <!-- Getting Started panel — hidden when configured -->
2023
+ <div class="getting-started" id="getting-started">
2024
+ <div class="panel-header">
2025
+ 🚀 Getting Started
2026
+ <button class="dismiss-btn" onclick="dismissGettingStarted()" aria-label="Dismiss Getting Started panel">Dismiss ✕</button>
2027
+ </div>
2028
+ <div class="gs-steps" id="gs-steps">
2029
+ <div class="gs-step" id="gs-preflight">
2030
+ <div class="gs-icon">1</div>
2031
+ <div class="gs-content">
2032
+ <div class="gs-title">Run preflight checks</div>
2033
+ <div class="gs-desc">Verify your system is ready — checks connectivity, config, and dependencies.</div>
2034
+ <a class="gs-link" href="/health" target="_blank">Open /health →</a>
2035
+ </div>
2036
+ </div>
2037
+ <div class="gs-step" id="gs-connect">
2038
+ <div class="gs-icon">2</div>
2039
+ <div class="gs-content">
2040
+ <div class="gs-title">Connect OpenClaw gateway</div>
2041
+ <div class="gs-desc">Set <code style="background:var(--border);padding:1px 5px;border-radius:3px;font-size:11px">OPENCLAW_GATEWAY_URL</code> and <code style="background:var(--border);padding:1px 5px;border-radius:3px;font-size:11px">OPENCLAW_GATEWAY_TOKEN</code> env vars. Get your token: <code style="background:var(--border);padding:1px 5px;border-radius:3px;font-size:11px">openclaw gateway token</code></div>
2042
+ <a class="gs-link" href="https://reflectt.ai/bootstrap" target="_blank">Bootstrap guide →</a>
2043
+ </div>
2044
+ </div>
2045
+ <div class="gs-step" id="gs-task">
2046
+ <div class="gs-icon">3</div>
2047
+ <div class="gs-content">
2048
+ <div class="gs-title">Create your first task</div>
2049
+ <div class="gs-desc">Post a task or message — your agents will pick it up automatically.</div>
2050
+ <a class="gs-link" href="/docs" target="_blank">API docs →</a>
2051
+ </div>
2052
+ </div>
2053
+ </div>
2054
+ </div>
2055
+
2056
+ <div class="panel">
2057
+ <div class="panel-header">🧭 Runtime Truth Card <span class="count" id="truth-count">loading…</span></div>
2058
+ <div class="panel-body" id="truth-body"></div>
2059
+ </div>
2060
+
2061
+ </div><!-- /page-overview -->
2062
+
2063
+ <!-- ═══ PAGE: Tasks ═══ -->
2064
+ <div class="page" id="page-tasks">
2065
+
2066
+ <div class="panel">
2067
+ <div class="panel-header">📋 Task Board <span class="count" id="task-count"></span></div>
2068
+ <div style="display:flex;align-items:center;gap:8px;padding:10px 18px 0;border-bottom:1px solid var(--border);flex-wrap:wrap">
2069
+ <div class="project-tabs" id="project-tabs" style="border-bottom:none;padding:0;flex:1;min-width:0"></div>
2070
+ <div class="project-tabs" id="status-filter-tabs" style="border-bottom:none;padding:0"></div>
2071
+ </div>
2072
+ <div class="kanban" id="kanban"></div>
2073
+ </div>
2074
+
2075
+ <div class="panel">
2076
+ <div class="panel-header">🔎 Task Search <span class="count" id="search-count"></span></div>
2077
+ <div class="panel-body" style="max-height:280px;overflow-y:auto">
2078
+ <div style="display:flex;gap:8px;margin-bottom:10px">
2079
+ <input type="text" id="task-search-input" class="modal-input" placeholder="Search tasks (title, id, assignee)…" autocomplete="off" />
2080
+ <button class="modal-copy-btn" onclick="runTaskSearch()">Search</button>
2081
+ </div>
2082
+ <div id="task-search-results"><div class="empty" style="color:var(--text-muted)">Type a query and press Enter…</div></div>
2083
+ </div>
2084
+ </div>
2085
+
2086
+ <div class="panel" id="backlog-panel">
2087
+ <div class="panel-header">📦 Available Work <span class="count" id="backlog-count"></span></div>
2088
+ <div class="panel-body" id="backlog-body" style="max-height:300px;overflow-y:auto"></div>
2089
+ </div>
2090
+
2091
+ </div><!-- /page-tasks -->
2092
+
2093
+ <!-- ═══ PAGE: Reviews ═══ -->
2094
+ <div class="page" id="page-reviews">
2095
+
2096
+ <div class="panel" id="review-queue-panel">
2097
+ <div class="panel-header">👀 Review Queue <span class="count" id="review-queue-count"></span></div>
2098
+ <div class="panel-body" id="review-queue-body" style="max-height:350px;overflow-y:auto"></div>
2099
+ </div>
2100
+
2101
+ <div class="panel" id="approval-queue-panel">
2102
+ <div class="panel-header">🎯 Approval Queue <span class="count" id="approval-queue-count"></span>
2103
+ <button id="approval-policy-btn" onclick="toggleRoutingPolicy()" style="float:right;font-size:11px;background:none;border:1px solid var(--border);color:var(--text-muted);padding:2px 8px;border-radius:4px;cursor:pointer">⚙ Policy</button>
2104
+ </div>
2105
+ <div class="panel-body" id="approval-queue-body" style="max-height:400px;overflow-y:auto"></div>
2106
+ <div id="routing-policy-panel" style="display:none;border-top:1px solid var(--border-subtle);padding:12px;max-height:400px;overflow-y:auto"></div>
2107
+ </div>
2108
+
2109
+ </div><!-- /page-reviews -->
2110
+
2111
+ <!-- ═══ PAGE: Chat ═══ -->
2112
+ <div class="page" id="page-chat">
2113
+
2114
+ <div class="panel">
2115
+ <div class="panel-header">💬 Chat <span class="count" id="chat-count"></span></div>
2116
+ <div class="channel-tabs" id="channel-tabs"></div>
2117
+ <div class="panel-body" id="chat-body"></div>
2118
+ <div class="chat-input-bar">
2119
+ <select id="chat-channel">
2120
+ <option value="general">#general</option>
2121
+ <option value="decisions">#decisions</option>
2122
+ <option value="shipping">#shipping</option>
2123
+ <option value="reviews">#reviews</option>
2124
+ <option value="blockers">#blockers</option>
2125
+ <option value="problems">#problems</option>
2126
+ </select>
2127
+ <button class="attach-btn" id="chatAttachBtn" aria-label="Attach file" title="Attach file"
2128
+ onclick="document.getElementById('chatFileInput').click()">📎</button>
2129
+ <input type="file" id="chatFileInput" multiple accept=".pdf,.png,.jpg,.jpeg,.csv,.xlsx,.txt,.md"
2130
+ aria-label="Choose file to attach" style="display:none">
2131
+ <input type="text" id="chat-input" placeholder="Message as ryan…" autocomplete="off" />
2132
+ <button id="chat-send" onclick="sendChat()">Send</button>
2133
+ </div>
2134
+ </div>
2135
+
2136
+ <div class="panel">
2137
+ <div class="panel-header">⚡ Activity <span class="count" id="activity-count"></span></div>
2138
+ <div class="panel-body" id="activity-body"></div>
2139
+ </div>
2140
+
2141
+ <div class="panel">
2142
+ <div class="panel-header">💬 Feedback <span class="count" id="feedback-count"></span></div>
2143
+ <div class="panel-body" id="feedback-body" style="max-height:350px;overflow-y:auto"></div>
2144
+ </div>
2145
+
2146
+ <div class="panel" id="polls-panel">
2147
+ <div class="panel-header">🗳️ Team Polls <span class="count" id="polls-count"></span>
2148
+ <button onclick="showCreatePollForm()" class="poll-new-btn" aria-label="Create new poll">+ New Poll</button>
2149
+ </div>
2150
+ <div class="panel-body" id="polls-body" style="max-height:400px;overflow-y:auto"></div>
2151
+ <div id="create-poll-form" class="poll-create-form" style="display:none" role="form" aria-label="Create a poll">
2152
+ <label for="poll-question" class="poll-form-label">Question</label>
2153
+ <input type="text" id="poll-question" class="poll-input" placeholder="What should we do?" aria-required="true" />
2154
+ <label class="poll-form-label">Options</label>
2155
+ <div id="poll-options-inputs">
2156
+ <input type="text" class="poll-option-input poll-input" placeholder="Option 1" aria-label="Poll option 1" />
2157
+ <input type="text" class="poll-option-input poll-input" placeholder="Option 2" aria-label="Poll option 2" />
2158
+ </div>
2159
+ <div class="poll-form-row">
2160
+ <button onclick="addPollOption()" class="poll-btn-secondary" aria-label="Add another option">+ Option</button>
2161
+ <select id="poll-expiry" class="poll-select" aria-label="Poll expiry">
2162
+ <option value="">No expiry</option>
2163
+ <option value="60">1 hour</option>
2164
+ <option value="240">4 hours</option>
2165
+ <option value="1440" selected>24 hours</option>
2166
+ <option value="4320">3 days</option>
2167
+ </select>
2168
+ <label class="poll-anon-label"><input type="checkbox" id="poll-anonymous" /> Anonymous</label>
2169
+ </div>
2170
+ <div class="poll-form-row">
2171
+ <button onclick="submitPoll()" class="poll-btn-primary">Create Poll</button>
2172
+ <button onclick="hideCreatePollForm()" class="poll-btn-secondary">Cancel</button>
2173
+ </div>
2174
+ </div>
2175
+ </div>
2176
+
2177
+ </div><!-- /page-chat -->
2178
+
2179
+ <!-- ═══ PAGE: Health ═══ -->
2180
+ <div class="page" id="page-health">
2181
+
2182
+ <div class="panel">
2183
+ <div class="panel-header">🏥 Team Health <span class="count" id="health-count"></span></div>
2184
+ <div class="panel-body" id="health-body"></div>
2185
+ </div>
2186
+
2187
+ <div class="panel">
2188
+ <div class="panel-header">🛡️ Collaboration Compliance <span class="count" id="compliance-count"></span></div>
2189
+ <div class="panel-body" id="compliance-body"></div>
2190
+ </div>
2191
+
2192
+ </div><!-- /page-health -->
2193
+
2194
+ <!-- ═══ PAGE: Outcomes ═══ -->
2195
+ <div class="page" id="page-outcomes">
2196
+
2197
+ <div class="panel">
2198
+ <div class="panel-header">🏁 Outcome Feed <span class="count" id="outcome-count"></span></div>
2199
+ <div class="panel-body" id="outcome-body" style="max-height:none;overflow-y:auto"></div>
2200
+ </div>
2201
+
2202
+ <div class="panel">
2203
+ <div class="panel-header">🧭 Promotion SSOT <span class="count" id="ssot-count"></span></div>
2204
+ <div class="panel-body" id="ssot-body"></div>
2205
+ </div>
2206
+
2207
+ </div><!-- /page-outcomes -->
2208
+
2209
+ <!-- ═══ PAGE: Research ═══ -->
2210
+ <div class="page" id="page-research">
2211
+
2212
+ <div class="panel">
2213
+ <div class="panel-header">🔍 Research Intake <span class="count" id="research-count"></span></div>
2214
+ <div class="panel-body" id="research-body" style="max-height:none;overflow-y:auto"></div>
2215
+ </div>
2216
+
2217
+ </div><!-- /page-research -->
2218
+
2219
+ <!-- ═══ PAGE: Artifacts ═══ -->
2220
+ <div class="page" id="page-artifacts">
2221
+
2222
+ <!-- Upload Zone -->
2223
+ <div class="panel" style="margin-bottom:var(--space-4)">
2224
+ <div class="panel-header">📤 Upload Files</div>
2225
+ <div class="panel-body" style="max-height:none">
2226
+ <div class="drop-zone" id="dropZone" role="button" tabindex="0"
2227
+ aria-label="Upload files — drag and drop or click to browse">
2228
+ <div style="font-size:32px;opacity:0.6;pointer-events:none">📂</div>
2229
+ <div style="color:var(--text-muted);pointer-events:none">Drag files here or <strong style="color:var(--accent);font-weight:var(--font-weight-medium)">browse</strong></div>
2230
+ <div style="font-size:var(--text-xs);color:var(--text-muted);pointer-events:none">PDF, PNG, JPG, CSV, XLSX, TXT, MD — up to 50MB</div>
2231
+ <input type="file" id="fileInput" multiple accept=".pdf,.png,.jpg,.jpeg,.csv,.xlsx,.txt,.md" aria-label="Choose files to upload">
2232
+ </div>
2233
+ <div class="upload-queue" id="uploadQueue" role="log" aria-label="Upload progress" aria-live="polite" style="display:none"></div>
2234
+ </div>
2235
+ </div>
2236
+
2237
+ <!-- File Browser -->
2238
+ <div class="panel" style="margin-bottom:var(--space-4)">
2239
+ <div class="panel-header">📁 Files <span class="count" id="files-count"></span></div>
2240
+ <div class="panel-body" style="max-height:50vh;overflow-y:auto">
2241
+ <div class="file-toolbar">
2242
+ <input class="file-search" type="search" id="fileSearch" placeholder="Search files…"
2243
+ aria-label="Search files" oninput="filterFiles(this.value)">
2244
+ <div class="view-toggle" role="radiogroup" aria-label="View mode">
2245
+ <button class="active" id="viewGridBtn" role="radio" aria-checked="true"
2246
+ onclick="toggleFileView('grid')" aria-label="Grid view">▦</button>
2247
+ <button id="viewListBtn" role="radio" aria-checked="false"
2248
+ onclick="toggleFileView('list')" aria-label="List view">☰</button>
2249
+ </div>
2250
+ </div>
2251
+ <div id="files-grid" class="file-grid"></div>
2252
+ <div id="files-list" class="file-list" style="display:none"></div>
2253
+ <div id="files-empty" class="empty" style="display:none">No files yet. Drop some files above to get started.</div>
2254
+ </div>
2255
+ </div>
2256
+
2257
+ <!-- Shared Artifacts (existing) -->
2258
+ <div class="panel" id="shared-artifacts-panel">
2259
+ <div class="panel-header">📚 Shared Artifacts <span class="count" id="shared-artifacts-count">loading…</span></div>
2260
+ <div class="panel-body" id="shared-artifacts-body" style="max-height:60vh;overflow-y:auto"></div>
2261
+ </div>
2262
+
2263
+ </div><!-- /page-artifacts -->
2264
+
2265
+ </div><!-- /.main -->
2266
+ </div><!-- /.app-layout -->
2267
+
2268
+ <script src="/dashboard.js"></script>
2269
+
2270
+ <!-- Task Modal -->
2271
+ <div id="task-modal" class="modal-overlay" onclick="if(event.target===this) closeTaskModal()">
2272
+ <div class="modal">
2273
+ <div class="modal-header">
2274
+ <h2 id="modal-task-title"></h2>
2275
+ <button class="modal-close" onclick="closeTaskModal()">&times;</button>
2276
+ </div>
2277
+ <div class="modal-body">
2278
+ <div class="modal-section">
2279
+ <div class="modal-label">Description</div>
2280
+ <div class="modal-value" id="modal-task-desc"></div>
2281
+ </div>
2282
+
2283
+ <div class="modal-section">
2284
+ <div class="modal-label">Task ID</div>
2285
+ <div class="modal-inline-row">
2286
+ <div class="modal-value" id="modal-task-id"></div>
2287
+ <button class="modal-copy-btn" onclick="copyTaskId()">Copy full ID</button>
2288
+ </div>
2289
+ </div>
2290
+
2291
+ <div class="modal-section">
2292
+ <div class="modal-label">Status</div>
2293
+ <div class="status-buttons">
2294
+ <button class="status-btn" data-status="todo" onclick="updateTaskStatus('todo')">Todo</button>
2295
+ <button class="status-btn" data-status="doing" onclick="updateTaskStatus('doing')">Doing</button>
2296
+ <button class="status-btn" data-status="blocked" onclick="updateTaskStatus('blocked')">Blocked</button>
2297
+ <button class="status-btn" data-status="validating" onclick="updateTaskStatus('validating')">Validating</button>
2298
+ <button class="status-btn" data-status="done" onclick="updateTaskStatus('done')">Done</button>
2299
+ </div>
2300
+ </div>
2301
+
2302
+ <div class="modal-section">
2303
+ <div class="modal-label">Assignee</div>
2304
+ <input type="text" id="modal-task-assignee" class="modal-input"
2305
+ placeholder="Enter agent name (e.g., link, ryan)"
2306
+ onblur="updateTaskAssignee()">
2307
+ </div>
2308
+
2309
+ <div class="modal-section">
2310
+ <div class="modal-label">Priority</div>
2311
+ <div class="modal-value" id="modal-task-priority"></div>
2312
+ </div>
2313
+
2314
+ <div class="modal-section" id="modal-branch-section" style="display:none">
2315
+ <div class="modal-label">Branch</div>
2316
+ <div class="modal-value" id="modal-task-branch" style="font-family:monospace;font-size:12px;color:var(--accent)"></div>
2317
+ </div>
2318
+
2319
+ <div class="modal-section">
2320
+ <div class="modal-label">Created</div>
2321
+ <div class="modal-value" id="modal-task-created"></div>
2322
+ </div>
2323
+
2324
+ <div class="modal-section">
2325
+ <div class="modal-label">Blocked by</div>
2326
+ <div class="modal-value" id="modal-task-blockers"></div>
2327
+ </div>
2328
+
2329
+ <div class="modal-section">
2330
+ <div class="modal-label">Artifacts</div>
2331
+ <div id="modal-task-artifacts" class="artifact-list"><div class="empty" style="color:var(--text-muted)">No artifacts loaded</div></div>
2332
+ </div>
2333
+
2334
+ <!-- PR Review Quality Panel -->
2335
+ <div id="pr-review-panel" style="display:none">
2336
+ <div style="border-top:1px solid var(--border-subtle);margin-top:16px;padding-top:16px">
2337
+ <div id="pr-review-loading" style="color:var(--text-dim);font-size:12px">Loading PR review data…</div>
2338
+ <div id="pr-review-content" style="display:none"></div>
2339
+ </div>
2340
+ </div>
2341
+ </div>
2342
+ </div>
2343
+ </div>
2344
+
2345
+ </body>
2346
+ </html>`;
2347
+ }
2348
+ //# sourceMappingURL=dashboard.js.map