@pluno/product-agent-web 0.1.17 → 0.1.20

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.
@@ -1,7 +1,7 @@
1
- import { PlunoProductAgent as He } from "./product-agent-sdk.js";
2
- const Ue = "#7c3aed";
3
- function We(t) {
4
- const e = Ye(t);
1
+ import { PlunoProductAgent as dt } from "./product-agent-sdk.js";
2
+ const ct = "#7c3aed";
3
+ function ut(t) {
4
+ const e = wt(t);
5
5
  return `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1254 1254" role="img" aria-label="Pluno">
6
6
  <defs>
7
7
  <linearGradient id="boltFill" x1="420" y1="180" x2="790" y2="1040" gradientUnits="userSpaceOnUse">
@@ -75,23 +75,23 @@ function We(t) {
75
75
  </g>
76
76
  </svg>`;
77
77
  }
78
- function Ve(t) {
79
- return `data:image/svg+xml,${encodeURIComponent(We(t))}`;
78
+ function gt(t) {
79
+ return `data:image/svg+xml,${encodeURIComponent(ut(t))}`;
80
80
  }
81
- const M = "#2c2a1e", ue = [253, 250, 241], ge = 3.5;
82
- function Oe(t) {
83
- const e = Re(t);
84
- if (he(G(e), ue) >= ge)
81
+ const G = "#2c2a1e", ye = [253, 250, 241], ve = 3.5;
82
+ function Ve(t) {
83
+ const e = qe(t);
84
+ if (Ce(q(e), ye) >= ve)
85
85
  return e;
86
- let o = G(e);
87
- const a = G(M);
86
+ let o = q(e);
87
+ const a = q(G);
88
88
  for (let i = 0; i < 6; i += 1)
89
- if (o = Xe(o, a, 0.22), he(o, ue) >= ge)
90
- return ee(o);
91
- return ee(o);
89
+ if (o = bt(o, a, 0.22), Ce(o, ye) >= ve)
90
+ return de(o);
91
+ return de(o);
92
92
  }
93
- function Ke(t) {
94
- const e = Oe(t), n = "M547 151 C516 151 493 169 485 199 L382 606 C373 641 396 666 431 666 L523 666 C552 666 568 684 563 713 L491 1028 C486 1054 510 1067 527 1044 L894 487 C915 455 894 432 856 432 L815 432 C784 432 773 411 789 382 L904 205 C922 171 901 145 859 145 Z";
93
+ function ht(t) {
94
+ const e = Ve(t), n = "M547 151 C516 151 493 169 485 199 L382 606 C373 641 396 666 431 666 L523 666 C552 666 568 684 563 713 L491 1028 C486 1054 510 1067 527 1044 L894 487 C915 455 894 432 856 432 L815 432 C784 432 773 411 789 382 L904 205 C922 171 901 145 859 145 Z";
95
95
  return `<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1254 1254" role="img" aria-label="Pluno">
96
96
  <defs>
97
97
  <clipPath id="scribbleBoltClip">
@@ -104,35 +104,35 @@ function Ke(t) {
104
104
  </defs>
105
105
  <g filter="url(#scribbleBoltWobble)">
106
106
  <g clip-path="url(#scribbleBoltClip)">
107
- <path d="${qe()}" fill="none" stroke="${e}" stroke-width="56" stroke-linecap="round" stroke-linejoin="round" opacity="0.9" transform="rotate(-14 627 600)"/>
107
+ <path d="${ft()}" fill="none" stroke="${e}" stroke-width="56" stroke-linecap="round" stroke-linejoin="round" opacity="0.9" transform="rotate(-14 627 600)"/>
108
108
  </g>
109
- <path d="${n}" fill="none" stroke="${M}" stroke-width="18" stroke-linejoin="round"/>
109
+ <path d="${n}" fill="none" stroke="${G}" stroke-width="18" stroke-linejoin="round"/>
110
110
  <g transform="rotate(-2 528 463)">
111
- <ellipse cx="528" cy="463" rx="73" ry="80" fill="#ffffff" stroke="${M}" stroke-width="13"/>
112
- <ellipse cx="533" cy="473" rx="45" ry="53" fill="${M}"/>
111
+ <ellipse cx="528" cy="463" rx="73" ry="80" fill="#ffffff" stroke="${G}" stroke-width="13"/>
112
+ <ellipse cx="533" cy="473" rx="45" ry="53" fill="${G}"/>
113
113
  <circle cx="557" cy="447" r="16" fill="#ffffff"/>
114
114
  </g>
115
115
  <g transform="rotate(2 717 462)">
116
- <ellipse cx="717" cy="462" rx="73" ry="80" fill="#ffffff" stroke="${M}" stroke-width="13"/>
117
- <ellipse cx="712" cy="473" rx="45" ry="53" fill="${M}"/>
116
+ <ellipse cx="717" cy="462" rx="73" ry="80" fill="#ffffff" stroke="${G}" stroke-width="13"/>
117
+ <ellipse cx="712" cy="473" rx="45" ry="53" fill="${G}"/>
118
118
  <circle cx="728" cy="447" r="16" fill="#ffffff"/>
119
119
  </g>
120
120
  </g>
121
121
  </svg>`;
122
122
  }
123
- function je(t) {
124
- return `data:image/svg+xml,${encodeURIComponent(Ke(t))}`;
123
+ function mt(t) {
124
+ return `data:image/svg+xml,${encodeURIComponent(ht(t))}`;
125
125
  }
126
- function qe() {
126
+ function ft() {
127
127
  let n = "M 280 120", o = !1, a = 0;
128
128
  for (let i = 150; i <= 1170; i += 62) {
129
- const p = (a % 3 - 1) * 18, c = o ? 280 - p : 1020 + p;
130
- n += ` L ${c} ${i}`, o = !o, a += 1;
129
+ const l = (a % 3 - 1) * 18, s = o ? 280 - l : 1020 + l;
130
+ n += ` L ${s} ${i}`, o = !o, a += 1;
131
131
  }
132
132
  return n;
133
133
  }
134
- function Ye(t) {
135
- const e = Re(t), n = te(G(e));
134
+ function wt(t) {
135
+ const e = qe(t), n = ce(q(e));
136
136
  return n > 0.86 ? {
137
137
  top: "#ffffff",
138
138
  middle: "#f6f6f6",
@@ -156,81 +156,81 @@ function Ye(t) {
156
156
  inner: "#4b4b4b",
157
157
  shadow: "#000000"
158
158
  } : {
159
- top: C(e, 0.28, -0.03),
160
- middle: C(e, 0.08, 0.04),
161
- bottom: C(e, -0.1, 0.02),
162
- edgeStart: C(e, 0.08, 0.08),
163
- edgeMiddle: C(e, -0.08, 0.08),
164
- edgeEnd: C(e, -0.18, 0.05),
165
- glow: C(e, 0.32, -0.12),
166
- highlight: C(e, 0.38, -0.18),
167
- inner: C(e, 0.24, -0.1),
168
- shadow: C(e, -0.25, -0.08)
159
+ top: L(e, 0.28, -0.03),
160
+ middle: L(e, 0.08, 0.04),
161
+ bottom: L(e, -0.1, 0.02),
162
+ edgeStart: L(e, 0.08, 0.08),
163
+ edgeMiddle: L(e, -0.08, 0.08),
164
+ edgeEnd: L(e, -0.18, 0.05),
165
+ glow: L(e, 0.32, -0.12),
166
+ highlight: L(e, 0.38, -0.18),
167
+ inner: L(e, 0.24, -0.1),
168
+ shadow: L(e, -0.25, -0.08)
169
169
  };
170
170
  }
171
- function Re(t) {
171
+ function qe(t) {
172
172
  const e = t.trim();
173
- return /^#[0-9a-f]{6}$/i.test(e) ? e.toLowerCase() : /^#[0-9a-f]{3}$/i.test(e) ? `#${e.slice(1).split("").map((n) => n + n).join("").toLowerCase()}` : Ue;
173
+ return /^#[0-9a-f]{6}$/i.test(e) ? e.toLowerCase() : /^#[0-9a-f]{3}$/i.test(e) ? `#${e.slice(1).split("").map((n) => n + n).join("").toLowerCase()}` : ct;
174
174
  }
175
- function G(t) {
175
+ function q(t) {
176
176
  return [
177
177
  Number.parseInt(t.slice(1, 3), 16),
178
178
  Number.parseInt(t.slice(3, 5), 16),
179
179
  Number.parseInt(t.slice(5, 7), 16)
180
180
  ];
181
181
  }
182
- function ee([t, e, n]) {
182
+ function de([t, e, n]) {
183
183
  const o = (a) => Math.max(0, Math.min(255, Math.round(a))).toString(16).padStart(2, "0");
184
184
  return `#${o(t)}${o(e)}${o(n)}`;
185
185
  }
186
- function te([t, e, n]) {
186
+ function ce([t, e, n]) {
187
187
  const o = (a) => {
188
188
  const i = a / 255;
189
189
  return i <= 0.04045 ? i / 12.92 : ((i + 0.055) / 1.055) ** 2.4;
190
190
  };
191
191
  return 0.2126 * o(t) + 0.7152 * o(e) + 0.0722 * o(n);
192
192
  }
193
- function he(t, e) {
194
- const n = te(t), o = te(e), [a, i] = n > o ? [n, o] : [o, n];
193
+ function Ce(t, e) {
194
+ const n = ce(t), o = ce(e), [a, i] = n > o ? [n, o] : [o, n];
195
195
  return (a + 0.05) / (i + 0.05);
196
196
  }
197
- function Xe(t, e, n) {
198
- const o = ne(n);
197
+ function bt(t, e, n) {
198
+ const o = ue(n);
199
199
  return [
200
200
  t[0] + (e[0] - t[0]) * o,
201
201
  t[1] + (e[1] - t[1]) * o,
202
202
  t[2] + (e[2] - t[2]) * o
203
203
  ];
204
204
  }
205
- function C(t, e, n) {
206
- const [o, a, i] = Ze(G(t));
207
- return ee(Je(o, ne(a + n), ne(i + e)));
205
+ function L(t, e, n) {
206
+ const [o, a, i] = _t(q(t));
207
+ return de(xt(o, ue(a + n), ue(i + e)));
208
208
  }
209
- function Ze([t, e, n]) {
210
- const o = t / 255, a = e / 255, i = n / 255, p = Math.max(o, a, i), c = Math.min(o, a, i), d = (p + c) / 2;
211
- if (p === c)
212
- return [0, 0, d];
213
- const h = p - c, s = d > 0.5 ? h / (2 - p - c) : h / (p + c);
214
- return [(p === o ? (a - i) / h + (a < i ? 6 : 0) : p === a ? (i - o) / h + 2 : (o - a) / h + 4) / 6, s, d];
209
+ function _t([t, e, n]) {
210
+ const o = t / 255, a = e / 255, i = n / 255, l = Math.max(o, a, i), s = Math.min(o, a, i), u = (l + s) / 2;
211
+ if (l === s)
212
+ return [0, 0, u];
213
+ const h = l - s, c = u > 0.5 ? h / (2 - l - s) : h / (l + s);
214
+ return [(l === o ? (a - i) / h + (a < i ? 6 : 0) : l === a ? (i - o) / h + 2 : (o - a) / h + 4) / 6, c, u];
215
215
  }
216
- function Je(t, e, n) {
216
+ function xt(t, e, n) {
217
217
  if (e === 0)
218
218
  return [n * 255, n * 255, n * 255];
219
219
  const o = n < 0.5 ? n * (1 + e) : n + e - n * e, a = 2 * n - o;
220
220
  return [
221
- Z(a, o, t + 1 / 3) * 255,
222
- Z(a, o, t) * 255,
223
- Z(a, o, t - 1 / 3) * 255
221
+ re(a, o, t + 1 / 3) * 255,
222
+ re(a, o, t) * 255,
223
+ re(a, o, t - 1 / 3) * 255
224
224
  ];
225
225
  }
226
- function Z(t, e, n) {
226
+ function re(t, e, n) {
227
227
  let o = n;
228
228
  return o < 0 && (o += 1), o > 1 && (o -= 1), o < 1 / 6 ? t + (e - t) * 6 * o : o < 1 / 2 ? e : o < 2 / 3 ? t + (e - t) * (2 / 3 - o) * 6 : t;
229
229
  }
230
- function ne(t) {
230
+ function ue(t) {
231
231
  return Math.max(0, Math.min(1, t));
232
232
  }
233
- const Qe = "product-agent:sdk-preview-socket-connect", et = "product-agent:sdk-preview-socket-send", tt = "product-agent:sdk-preview-socket-close", nt = "product-agent:sdk-preview-socket-open", ot = "product-agent:sdk-preview-socket-message", at = "product-agent:sdk-preview-socket-error", it = "product-agent:sdk-preview-socket-closed", fe = "product-agent:sdk-preview-socket-id", rt = "product-agent:preview-diagnostic", A = {
233
+ const yt = "product-agent:sdk-preview-socket-connect", vt = "product-agent:sdk-preview-socket-send", Ct = "product-agent:sdk-preview-socket-close", Et = "product-agent:sdk-preview-socket-open", kt = "product-agent:sdk-preview-socket-message", St = "product-agent:sdk-preview-socket-error", Lt = "product-agent:sdk-preview-socket-closed", Ee = "product-agent:sdk-preview-socket-id", Pt = "product-agent:preview-diagnostic", ee = 10, At = 10 * 1024 * 1024, Tt = /* @__PURE__ */ new Set(["image/png", "image/jpeg", "image/webp", "image/gif", "application/pdf"]), D = {
234
234
  launcherLabel: "Ask for anything...",
235
235
  accentColor: "#7c3aed",
236
236
  colorScheme: "light",
@@ -238,26 +238,29 @@ const Qe = "product-agent:sdk-preview-socket-connect", et = "product-agent:sdk-p
238
238
  scribbleStyle: !1,
239
239
  position: "bottom-right",
240
240
  movableLauncher: !1
241
- }, be = 'data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 104 36"><g><ellipse cx="17.5" cy="24.5" rx="2.4" ry="3" fill="none" stroke="%232c2a1e" stroke-width="1.6" opacity="0.8"/><path d="M18.5 27 C20.5 12, 7.5 2.5, 6 18.5" fill="none" stroke="%232c2a1e" stroke-width="2.5" stroke-linecap="round"/></g><g transform="translate(26 0)"><ellipse cx="17.9" cy="24.1" rx="2.5" ry="2.8" fill="none" stroke="%232c2a1e" stroke-width="1.5" opacity="0.8"/><path d="M18.9 26.4 C21.2 13, 8.6 3.6, 6.9 17.4" fill="none" stroke="%232c2a1e" stroke-width="2.35" stroke-linecap="round"/></g><g transform="translate(52 0)"><ellipse cx="17.1" cy="24.9" rx="2.2" ry="3.1" fill="none" stroke="%232c2a1e" stroke-width="1.7" opacity="0.8"/><path d="M18.1 27.5 C19.9 10.4, 6.4 2, 5.6 19.2" fill="none" stroke="%232c2a1e" stroke-width="2.6" stroke-linecap="round"/></g><g transform="translate(78 0)"><ellipse cx="17.6" cy="24.4" rx="2.4" ry="2.9" fill="none" stroke="%232c2a1e" stroke-width="1.6" opacity="0.8"/><path d="M18.7 26.8 C21 11.2, 7.1 1.6, 6.3 18.1" fill="none" stroke="%232c2a1e" stroke-width="2.45" stroke-linecap="round"/></g></svg>', lt = '"Architects Daughter", "Bradley Hand", "Chalkboard SE", "Comic Sans MS", "Comic Sans", "Segoe Print", cursive', we = "pluno-pa-scribble-font", De = 190, Fe = 41, pt = 48, st = 420, ct = 680, k = 8, me = 50, dt = 11, ut = 13, gt = 4, ht = 10, ft = 40, bt = "movable-launcher-position-v2";
242
- function wt(t) {
243
- return (e) => new L(e, t);
241
+ }, ke = 'data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 104 36"><g><ellipse cx="17.5" cy="24.5" rx="2.4" ry="3" fill="none" stroke="%232c2a1e" stroke-width="1.6" opacity="0.8"/><path d="M18.5 27 C20.5 12, 7.5 2.5, 6 18.5" fill="none" stroke="%232c2a1e" stroke-width="2.5" stroke-linecap="round"/></g><g transform="translate(26 0)"><ellipse cx="17.9" cy="24.1" rx="2.5" ry="2.8" fill="none" stroke="%232c2a1e" stroke-width="1.5" opacity="0.8"/><path d="M18.9 26.4 C21.2 13, 8.6 3.6, 6.9 17.4" fill="none" stroke="%232c2a1e" stroke-width="2.35" stroke-linecap="round"/></g><g transform="translate(52 0)"><ellipse cx="17.1" cy="24.9" rx="2.2" ry="3.1" fill="none" stroke="%232c2a1e" stroke-width="1.7" opacity="0.8"/><path d="M18.1 27.5 C19.9 10.4, 6.4 2, 5.6 19.2" fill="none" stroke="%232c2a1e" stroke-width="2.6" stroke-linecap="round"/></g><g transform="translate(78 0)"><ellipse cx="17.6" cy="24.4" rx="2.4" ry="2.9" fill="none" stroke="%232c2a1e" stroke-width="1.6" opacity="0.8"/><path d="M18.7 26.8 C21 11.2, 7.1 1.6, 6.3 18.1" fill="none" stroke="%232c2a1e" stroke-width="2.45" stroke-linecap="round"/></g></svg>', Nt = '"Architects Daughter", "Bradley Hand", "Chalkboard SE", "Comic Sans MS", "Comic Sans", "Segoe Print", cursive', Se = "pluno-pa-scribble-font", Ke = 190, je = 41, It = 48, Rt = 420, Dt = 680, S = 8, Le = 50, Mt = "http://www.w3.org/2000/svg", Ot = 11, Ft = 13, Gt = 4, Bt = 10, $t = 40, zt = "movable-launcher-position-v2";
242
+ function Wt(t) {
243
+ return (e) => new I(e, t);
244
244
  }
245
- async function mt(t = {}) {
245
+ async function Ut(t = {}) {
246
246
  const e = {
247
- launcherLabel: t.launcherLabel ?? A.launcherLabel,
248
- accentColor: t.accentColor ?? A.accentColor,
249
- colorScheme: t.colorScheme ?? A.colorScheme,
250
- fontFamily: t.fontFamily ?? A.fontFamily,
251
- scribbleStyle: t.scribbleStyle ?? A.scribbleStyle,
252
- position: t.position ?? A.position,
253
- movableLauncher: t.movableLauncher ?? A.movableLauncher,
247
+ launcherLabel: t.launcherLabel ?? D.launcherLabel,
248
+ accentColor: t.accentColor ?? D.accentColor,
249
+ colorScheme: t.colorScheme ?? D.colorScheme,
250
+ fontFamily: t.fontFamily ?? D.fontFamily,
251
+ scribbleStyle: t.scribbleStyle ?? D.scribbleStyle,
252
+ position: t.position ?? D.position,
253
+ movableLauncher: t.movableLauncher ?? D.movableLauncher,
254
254
  token: t.token,
255
255
  tokenProvider: t.tokenProvider,
256
256
  tokenEndpoint: t.tokenEndpoint,
257
257
  backendUrl: t.backendUrl,
258
258
  metadata: t.metadata,
259
259
  initialStarterPrompts: t.initialStarterPrompts,
260
- webSocketFactory: t.webSocketFactory
260
+ webSocketFactory: t.webSocketFactory,
261
+ loginRequired: t.loginRequired === !0,
262
+ loginButtonLabel: t.loginButtonLabel ?? "Log in to Pluno",
263
+ onLoginClick: t.onLoginClick
261
264
  };
262
265
  O("web-sdk.widget", "Mounting widget with merged options", {
263
266
  accentColor: e.accentColor,
@@ -274,71 +277,10 @@ async function mt(t = {}) {
274
277
  n.className = "pluno-pa-widget-host";
275
278
  const o = n.attachShadow({ mode: "open" }), a = document.createElement("div");
276
279
  a.className = `pluno-pa-widget pluno-pa-widget--${e.position}`;
277
- let i = _e(e.accentColor, e.scribbleStyle);
278
- a.innerHTML = `
279
- <svg class="pluno-pa-widget__scribble-defs" aria-hidden="true" focusable="false" width="0" height="0">
280
- <defs>
281
- <filter id="pluno-pa-scribble-wobble" x="-8%" y="-8%" width="116%" height="116%">
282
- <feTurbulence type="fractalNoise" baseFrequency="0.012 0.028" numOctaves="3" seed="2" result="stroke-noise" />
283
- <feDisplacementMap in="SourceGraphic" in2="stroke-noise" scale="3.5" xChannelSelector="R" yChannelSelector="G" result="warped" />
284
- <feTurbulence type="fractalNoise" baseFrequency="0.7" numOctaves="1" seed="12" result="ink-noise" />
285
- <feDisplacementMap in="warped" in2="ink-noise" scale="0.9" xChannelSelector="R" yChannelSelector="G" />
286
- </filter>
287
- <filter id="pluno-pa-scribble-wobble-2" x="-8%" y="-8%" width="116%" height="116%">
288
- <feTurbulence type="fractalNoise" baseFrequency="0.012 0.028" numOctaves="3" seed="5" result="stroke-noise" />
289
- <feDisplacementMap in="SourceGraphic" in2="stroke-noise" scale="3.5" xChannelSelector="R" yChannelSelector="G" result="warped" />
290
- <feTurbulence type="fractalNoise" baseFrequency="0.7" numOctaves="1" seed="15" result="ink-noise" />
291
- <feDisplacementMap in="warped" in2="ink-noise" scale="0.9" xChannelSelector="R" yChannelSelector="G" />
292
- </filter>
293
- <filter id="pluno-pa-scribble-wobble-3" x="-8%" y="-8%" width="116%" height="116%">
294
- <feTurbulence type="fractalNoise" baseFrequency="0.012 0.028" numOctaves="3" seed="9" result="stroke-noise" />
295
- <feDisplacementMap in="SourceGraphic" in2="stroke-noise" scale="3.5" xChannelSelector="R" yChannelSelector="G" result="warped" />
296
- <feTurbulence type="fractalNoise" baseFrequency="0.7" numOctaves="1" seed="19" result="ink-noise" />
297
- <feDisplacementMap in="warped" in2="ink-noise" scale="0.9" xChannelSelector="R" yChannelSelector="G" />
298
- </filter>
299
- </defs>
300
- </svg>
301
- <form class="pluno-pa-widget__launcher">
302
- ${e.movableLauncher ? '<button type="button" class="pluno-pa-widget__launcher-drag-handle" aria-label="Move Product Agent launcher" title="Move Product Agent launcher"></button>' : ""}
303
- <img class="pluno-pa-widget__character pluno-pa-widget__character--launcher" src="${W(i)}" alt="" aria-hidden="true" />
304
- <input class="pluno-pa-widget__launcher-input" type="text" placeholder="${W(e.launcherLabel)}" aria-label="${W(e.launcherLabel)}" />
305
- </form>
306
- <button type="button" class="pluno-pa-widget__close" aria-label="Close" hidden>
307
- <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" stroke-width="2.25" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">
308
- <path d="m6 9 6 6 6-6" />
309
- </svg>
310
- </button>
311
- <section class="pluno-pa-widget__panel" hidden>
312
- <div class="pluno-pa-widget__timeline-wrap">
313
- <main class="pluno-pa-widget__timeline">
314
- <div class="pluno-pa-widget__empty-state">
315
- <img class="pluno-pa-widget__character pluno-pa-widget__character--empty" src="${W(i)}" alt="" aria-hidden="true" />
316
- <div class="pluno-pa-widget__empty">Hey there, I'm Pluno 👋<br />What do you want to do today?</div>
317
- </div>
318
- </main>
319
- <button type="button" class="pluno-pa-widget__new-chat" aria-label="New chat" title="New chat" hidden>
320
- <svg viewBox="0 0 24 24" width="17" height="17" fill="none" stroke="currentColor" stroke-width="2.25" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">
321
- <path d="M12 3H5a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7" />
322
- <path d="M18.4 2.6a2.1 2.1 0 0 1 3 3L12 15l-4 1 1-4Z" />
323
- </svg>
324
- </button>
325
- </div>
326
- <form class="pluno-pa-widget__composer">
327
- <div class="pluno-pa-widget__composer-inner">
328
- <textarea class="pluno-pa-widget__input" rows="1" placeholder="Ask for anything..."></textarea>
329
- <button type="button" class="pluno-pa-widget__send" aria-label="Send">
330
- <svg viewBox="0 0 24 24" width="14" height="14" fill="none" stroke="currentColor" stroke-width="2.75" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true">
331
- <line x1="12" y1="19" x2="12" y2="5" />
332
- <polyline points="5 12 12 5 19 12" />
333
- </svg>
334
- </button>
335
- </div>
336
- <a class="pluno-pa-widget__powered-by" href="https://pluno.ai" target="_blank" rel="noopener noreferrer">Powered by Pluno.ai</a>
337
- </form>
338
- </section>
339
- `, o.appendChild(a);
340
- const p = await Nt(), c = p.ownerDocument;
341
- p.appendChild(n), a.classList.add(`pluno-pa-widget--${e.colorScheme}`), Ne(o, e.accentColor), xe(a, i, {
280
+ let i = Pe(e.accentColor, e.scribbleStyle);
281
+ Zt(a, e.launcherLabel, i, e.movableLauncher), o.appendChild(a);
282
+ const l = await kn(), s = l.ownerDocument;
283
+ l.appendChild(n), a.classList.add(`pluno-pa-widget--${e.colorScheme}`), We(o, e.accentColor), Ae(a, i, {
342
284
  accentColor: e.accentColor,
343
285
  colorScheme: e.colorScheme,
344
286
  fontFamily: e.fontFamily,
@@ -349,15 +291,20 @@ async function mt(t = {}) {
349
291
  fontFamily: e.fontFamily,
350
292
  cssAccent: a.style.getPropertyValue("--pluno-pa-accent")
351
293
  });
352
- const d = a.querySelector(".pluno-pa-widget__launcher"), h = a.querySelector(".pluno-pa-widget__launcher-drag-handle"), s = a.querySelector(".pluno-pa-widget__launcher-input"), b = a.querySelector(".pluno-pa-widget__panel"), x = a.querySelector(".pluno-pa-widget__close"), v = a.querySelector(".pluno-pa-widget__composer"), u = a.querySelector(".pluno-pa-widget__input"), l = a.querySelector(".pluno-pa-widget__send"), g = a.querySelector(".pluno-pa-widget__new-chat"), f = a.querySelector(".pluno-pa-widget__timeline");
353
- if (!d || !s || !b || !x || !v || !u || !l || !g || !f)
354
- throw new Error("Failed to mount Product Agent widget");
294
+ const u = a.querySelector(".pluno-pa-widget__launcher"), h = a.querySelector(".pluno-pa-widget__launcher-drag-handle"), c = a.querySelector(".pluno-pa-widget__launcher-input"), f = a.querySelector(".pluno-pa-widget__panel"), y = a.querySelector(".pluno-pa-widget__close"), k = a.querySelector(".pluno-pa-widget__composer"), v = a.querySelector(".pluno-pa-widget__attachment-error"), d = a.querySelector(".pluno-pa-widget__attachments"), p = a.querySelector(".pluno-pa-widget__input"), m = a.querySelector(".pluno-pa-widget__send"), b = a.querySelector(".pluno-pa-widget__new-chat"), w = a.querySelector(".pluno-pa-widget__timeline");
295
+ if (!u || !c || !f || !y || !k || !v || !d || !p || !m || !b || !w)
296
+ throw new Error("Failed to mount Pluno widget");
355
297
  if (e.movableLauncher && !h)
356
- throw new Error("Failed to mount Product Agent widget drag handle");
357
- Ee(s), Ee(u);
358
- const _ = e.token || e.webSocketFactory ? void 0 : e.tokenProvider ?? (async () => {
298
+ throw new Error("Failed to mount Pluno widget drag handle");
299
+ De(c), De(p);
300
+ let x = [], P = null;
301
+ const F = () => {
302
+ sn(d, x, (r) => {
303
+ x = x.filter((g, E) => E !== r), F(), N();
304
+ });
305
+ }, ot = e.loginRequired || e.token || e.webSocketFactory ? void 0 : e.tokenProvider ?? (async () => {
359
306
  if (!e.tokenEndpoint)
360
- throw new Error("Product Agent widget requires token or tokenEndpoint");
307
+ throw new Error("Pluno widget requires token or tokenEndpoint");
361
308
  const r = await fetch(e.tokenEndpoint, {
362
309
  method: "POST",
363
310
  credentials: "include",
@@ -365,48 +312,49 @@ async function mt(t = {}) {
365
312
  body: JSON.stringify({ origin: location.origin, url: location.href })
366
313
  });
367
314
  if (!r.ok)
368
- throw new Error("Failed to load Product Agent token");
369
- const w = await r.json();
370
- if (!w.token)
371
- throw new Error("Product Agent token endpoint did not return a token");
372
- return w.token;
315
+ throw new Error("Failed to load Pluno token");
316
+ const g = await r.json();
317
+ if (!g.token)
318
+ throw new Error("Pluno token endpoint did not return a token");
319
+ return g.token;
373
320
  });
374
- let m;
375
- m = await He.init({
321
+ let C;
322
+ C = await dt.init({
376
323
  token: e.token,
377
- tokenProvider: _,
324
+ tokenProvider: ot,
378
325
  backendUrl: e.backendUrl,
379
326
  metadata: () => ({
380
327
  ...e.metadata ?? {},
381
- ...!m.getState().sessionId && e.scribbleStyle ? { scribbleStyleStarted: !0 } : {}
328
+ ...!C.getState().sessionId && e.scribbleStyle ? { scribbleStyleStarted: !0 } : {}
382
329
  }),
383
330
  initialStarterPrompts: e.initialStarterPrompts,
384
- webSocketFactory: e.webSocketFactory
331
+ webSocketFactory: e.webSocketFactory,
332
+ autoConnect: e.loginRequired ? !1 : void 0
385
333
  });
386
- const y = It(e), B = new Set(y.openToolGroupKeys);
387
- let E = e.movableLauncher ? y.launcherPosition : null, ae = E !== null, P = null, ie = !1;
388
- const Be = () => {
389
- ie || typeof document > "u" || (Ne(o, e.accentColor), n.isConnected || c.body?.appendChild(n));
390
- }, re = new MutationObserver(Be);
391
- re.observe(c.documentElement, { childList: !0, subtree: !0 });
392
- const j = (r = !0) => {
393
- const w = ye(a, r);
394
- return ve(
334
+ const z = Sn(e), K = new Set(z.openToolGroupKeys);
335
+ let A = e.movableLauncher ? z.launcherPosition : null, he = A !== null, R = null, me = !1;
336
+ const at = () => {
337
+ me || typeof document > "u" || (We(o, e.accentColor), n.isConnected || s.body?.appendChild(n));
338
+ }, fe = new MutationObserver(at);
339
+ fe.observe(s.documentElement, { childList: !0, subtree: !0 });
340
+ const ne = (r = !0) => {
341
+ const g = Te(a, r);
342
+ return Ne(
395
343
  a,
396
- E ?? vt(a, e.position, w),
397
- w
344
+ A ?? Kt(a, e.position, g),
345
+ g
398
346
  );
399
- }, S = () => {
400
- Mt(e, {
347
+ }, T = () => {
348
+ Ln(e, {
401
349
  isOpen: a.classList.contains("pluno-pa-widget--open"),
402
- composerValue: u.value,
403
- openToolGroupKeys: [...B],
404
- launcherPosition: ae ? E : null
350
+ composerValue: p.value,
351
+ openToolGroupKeys: [...K],
352
+ launcherPosition: he ? A : null
405
353
  });
406
- }, N = (r, w = {}) => {
407
- Et(r, {
408
- debugVersion: bt,
409
- launcherPosition: E,
354
+ }, M = (r, g = {}) => {
355
+ Xt(r, {
356
+ debugVersion: zt,
357
+ launcherPosition: A,
410
358
  rootClasses: a.className,
411
359
  rootStyle: {
412
360
  left: a.style.left,
@@ -414,160 +362,206 @@ async function mt(t = {}) {
414
362
  right: a.style.right,
415
363
  bottom: a.style.bottom
416
364
  },
417
- rootRect: J(a),
418
- launcherRect: J(d),
419
- panelRect: J(b),
420
- viewport: R(),
421
- panelHidden: b.hidden,
422
- closeHidden: x.hidden,
423
- ...w
365
+ rootRect: le(a),
366
+ launcherRect: le(u),
367
+ panelRect: le(f),
368
+ viewport: B(),
369
+ panelHidden: f.hidden,
370
+ closeHidden: y.hidden,
371
+ ...g
424
372
  });
425
- }, z = (r = !0) => {
426
- if (!E)
427
- return H(a, null), j(r);
428
- const w = j(r);
429
- return H(a, w), N("Applied stored closed launcher position", { visibleLauncherPosition: w }), w;
430
- }, le = (r, w) => {
431
- if (!r || !w) {
432
- Ce(a);
373
+ }, j = (r = !0) => {
374
+ if (!A)
375
+ return X(a, null), ne(r);
376
+ const g = ne(r);
377
+ return X(a, g), M("Applied stored closed launcher position", { visibleLauncherPosition: g }), g;
378
+ }, we = (r, g) => {
379
+ if (!r || !g) {
380
+ Re(a);
433
381
  return;
434
382
  }
435
- Ct(a, {
436
- x: r.x - w.x,
437
- y: r.y - w.y
383
+ Yt(a, {
384
+ x: r.x - g.x,
385
+ y: r.y - g.y
438
386
  });
439
- }, pe = () => {
440
- const r = z();
387
+ }, be = () => {
388
+ const r = j();
441
389
  if (a.classList.contains("pluno-pa-widget--open") || a.classList.contains("pluno-pa-widget--closing")) {
442
- const w = ke(r);
443
- le(w, r), N("Applied open panel position after viewport resize", { openPanelPosition: w });
444
- } else E && N("Applied visible launcher position after viewport resize", { visibleLauncherPosition: r });
390
+ const g = Ie(r);
391
+ we(g, r), M("Applied open panel position after viewport resize", { openPanelPosition: g });
392
+ } else A && M("Applied visible launcher position after viewport resize", { visibleLauncherPosition: r });
445
393
  };
446
- let se = () => {
394
+ let _e = () => {
447
395
  };
448
- e.movableLauncher && h ? (z(), window.addEventListener("resize", pe), se = xt({
396
+ e.movableLauncher && h ? (j(), window.addEventListener("resize", be), _e = Vt({
449
397
  root: a,
450
398
  launcherDragHandle: h,
451
- getPosition: () => j(),
399
+ getPosition: () => ne(),
452
400
  setPosition: (r) => {
453
- const w = r;
454
- E = ve(a, r, ye(a)), H(a, E), N("Dragging closed launcher", { requestedPosition: w });
401
+ const g = r;
402
+ A = Ne(a, r, Te(a)), X(a, A), M("Dragging closed launcher", { requestedPosition: g });
455
403
  },
456
404
  persist: () => {
457
- ae = !0, S(), N("Persisted closed launcher drag position");
405
+ he = !0, T(), M("Persisted closed launcher drag position");
458
406
  }
459
- })) : H(a, null);
460
- const D = (r = "", w = !0) => {
461
- if (P !== null && (window.clearTimeout(P), P = null), b.hidden = !1, x.hidden = !1, a.classList.remove("pluno-pa-widget--closing"), e.movableLauncher) {
462
- const T = z(), F = ke(T);
463
- le(F, T), N("Opening launcher at clamped open panel position", { openPanelPosition: F, visibleLauncherPosition: T });
407
+ })) : X(a, null);
408
+ const W = (r = "", g = !0) => {
409
+ if (R !== null && (window.clearTimeout(R), R = null), f.hidden = !1, y.hidden = !1, a.classList.remove("pluno-pa-widget--closing"), e.movableLauncher) {
410
+ const E = j(), H = Ie(E);
411
+ we(H, E), M("Opening launcher at clamped open panel position", { openPanelPosition: H, visibleLauncherPosition: E });
464
412
  } else
465
- Ce(a);
466
- if (!w) {
467
- a.classList.add("pluno-pa-widget--open"), d.hidden = !0, r && (u.value = r, $(u)), f.scrollTop = f.scrollHeight, u.focus(), u.setSelectionRange(u.value.length, u.value.length), S();
413
+ Re(a);
414
+ if (!g) {
415
+ a.classList.add("pluno-pa-widget--open"), u.hidden = !0, r && (p.value = r, V(p)), w.scrollTop = w.scrollHeight, p.focus(), p.setSelectionRange(p.value.length, p.value.length), T();
468
416
  return;
469
417
  }
470
418
  window.requestAnimationFrame(() => {
471
- a.classList.add("pluno-pa-widget--open"), r && (u.value = r, $(u)), f.scrollTop = f.scrollHeight, u.focus(), u.setSelectionRange(u.value.length, u.value.length), S(), P = window.setTimeout(() => {
472
- d.hidden = !0, f.scrollTop = f.scrollHeight;
419
+ a.classList.add("pluno-pa-widget--open"), r && (p.value = r, V(p)), w.scrollTop = w.scrollHeight, p.focus(), p.setSelectionRange(p.value.length, p.value.length), T(), R = window.setTimeout(() => {
420
+ u.hidden = !0, w.scrollTop = w.scrollHeight;
473
421
  }, 220);
474
422
  });
475
- }, ze = () => {
476
- P !== null && (window.clearTimeout(P), P = null), d.hidden = !1, E && (z(!1), N("Closing launcher at stored position")), a.classList.remove("pluno-pa-widget--open"), a.classList.add("pluno-pa-widget--closing"), S(), P = window.setTimeout(() => {
477
- b.hidden = !0, x.hidden = !0, a.classList.remove("pluno-pa-widget--closing");
423
+ }, it = () => {
424
+ R !== null && (window.clearTimeout(R), R = null), u.hidden = !1, A && (j(!1), M("Closing launcher at stored position")), a.classList.remove("pluno-pa-widget--open"), a.classList.add("pluno-pa-widget--closing"), T(), R = window.setTimeout(() => {
425
+ f.hidden = !0, y.hidden = !0, a.classList.remove("pluno-pa-widget--closing");
478
426
  }, 220);
479
427
  };
480
- d.addEventListener("submit", (r) => {
481
- r.preventDefault(), D(s.value), s.value = "";
428
+ u.addEventListener("submit", (r) => {
429
+ r.preventDefault(), W(c.value), c.value = "";
482
430
  }), h?.addEventListener("click", (r) => {
483
431
  r.preventDefault(), r.stopPropagation();
484
- }), d.addEventListener("click", (r) => {
485
- r.target !== s && (D(s.value), s.value = "");
486
- }), s.addEventListener("focus", () => {
487
- D(s.value), s.value = "";
488
- }), s.addEventListener("input", () => {
489
- if (!s.value)
432
+ }), u.addEventListener("click", (r) => {
433
+ r.target !== c && (W(c.value), c.value = "");
434
+ }), c.addEventListener("focus", () => {
435
+ W(c.value), c.value = "";
436
+ }), c.addEventListener("input", () => {
437
+ if (!c.value)
438
+ return;
439
+ const r = c.value;
440
+ W(r), c.value = "";
441
+ }), y.addEventListener("click", it);
442
+ const N = () => {
443
+ m.disabled = !C.getState().isThinking && p.value.trim().length === 0 && x.length === 0;
444
+ };
445
+ e.loginRequired && (c.readOnly = !0, c.placeholder = e.loginButtonLabel, p.placeholder = e.loginButtonLabel, k.hidden = !0), k.addEventListener("submit", (r) => {
446
+ if (r.preventDefault(), e.loginRequired) {
447
+ e.onLoginClick?.();
448
+ return;
449
+ }
450
+ x = pe(C, p, x), F(), N();
451
+ });
452
+ let U = 0;
453
+ const rt = () => {
454
+ U = 0, a.classList.remove("pluno-pa-widget--drag-over");
455
+ }, lt = (r) => {
456
+ P !== null && window.clearTimeout(P), v.textContent = r, v.hidden = !1, P = window.setTimeout(() => {
457
+ v.textContent = "", v.hidden = !0, P = null;
458
+ }, 3e3);
459
+ }, pt = () => {
460
+ P !== null && (window.clearTimeout(P), P = null), v.textContent = "", v.hidden = !0;
461
+ }, st = async (r) => {
462
+ if (r.length === 0)
490
463
  return;
491
- const r = s.value;
492
- D(r), s.value = "";
493
- }), x.addEventListener("click", ze);
494
- const I = () => {
495
- l.disabled = !m.getState().isThinking && u.value.trim().length === 0;
464
+ const g = await gn(r);
465
+ if (x.length + g.length > ee)
466
+ throw new Error(`Attach up to ${ee} files per message.`);
467
+ x = [...x, ...g], F(), pt(), N();
496
468
  };
497
- v.addEventListener("submit", (r) => {
498
- r.preventDefault(), Q(m, u), I();
499
- }), l.addEventListener("click", () => {
500
- if (m.getState().isThinking) {
501
- m.stop();
469
+ a.addEventListener("dragenter", (r) => {
470
+ !Z(r.dataTransfer) || e.loginRequired || (r.preventDefault(), r.stopPropagation(), U += 1, a.classList.add("pluno-pa-widget--drag-over"));
471
+ }), a.addEventListener("dragover", (r) => {
472
+ const g = r.dataTransfer;
473
+ !Z(g) || e.loginRequired || (r.preventDefault(), r.stopPropagation(), g.dropEffect = "copy");
474
+ }), a.addEventListener("dragleave", (r) => {
475
+ Z(r.dataTransfer) && (r.stopPropagation(), U = Math.max(0, U - 1), U === 0 && a.classList.remove("pluno-pa-widget--drag-over"));
476
+ }), a.addEventListener("drop", (r) => {
477
+ const g = r.dataTransfer;
478
+ !Z(g) || e.loginRequired || (r.preventDefault(), r.stopPropagation(), rt(), st(g.files).catch((E) => {
479
+ lt(E instanceof Error ? E.message : "Failed to attach file"), O("web-sdk.widget", "Attachment failed", {
480
+ message: E instanceof Error ? E.message : String(E)
481
+ });
482
+ }));
483
+ }), m.addEventListener("click", () => {
484
+ if (e.loginRequired) {
485
+ e.onLoginClick?.();
502
486
  return;
503
487
  }
504
- Q(m, u), I();
505
- }), g.addEventListener("click", () => {
506
- m.startNewSession(), B.clear(), u.value = "", $(u), S(), I(), u.focus();
507
- }), u.addEventListener("input", () => {
508
- $(u), S(), I();
509
- }), u.addEventListener("keydown", (r) => {
510
- r.key !== "Enter" || r.shiftKey || (r.preventDefault(), Q(m, u), I());
488
+ if (C.getState().isThinking) {
489
+ C.stop();
490
+ return;
491
+ }
492
+ x = pe(C, p, x), F(), N();
493
+ }), b.addEventListener("click", () => {
494
+ C.startNewSession(), K.clear(), p.value = "", x = [], F(), V(p), T(), N(), p.focus();
495
+ }), p.addEventListener("input", () => {
496
+ V(p), T(), N();
497
+ }), p.addEventListener("keydown", (r) => {
498
+ if (!(r.key !== "Enter" || r.shiftKey)) {
499
+ if (r.preventDefault(), e.loginRequired) {
500
+ e.onLoginClick?.();
501
+ return;
502
+ }
503
+ x = pe(C, p, x), F(), N();
504
+ }
511
505
  }), a.addEventListener("click", (r) => {
512
- (r.target instanceof Element ? r.target : null)?.closest("a[href]") && S();
513
- }), y.composerValue && (u.value = y.composerValue, $(u)), y.isOpen && D(u.value, !1);
514
- const ce = () => i;
515
- let q = m.getState().appearance !== null;
516
- return m.on("state", (r) => {
517
- r.appearance ? (q = !0, O("web-sdk.widget", "Agent state supplied appearance", {
506
+ (r.target instanceof Element ? r.target : null)?.closest("a[href]") && T();
507
+ }), z.composerValue && (p.value = z.composerValue, V(p)), z.isOpen && W(p.value, !1);
508
+ const Y = () => i;
509
+ let oe = C.getState().appearance !== null;
510
+ return C.on("state", (r) => {
511
+ r.appearance ? (oe = !0, O("web-sdk.widget", "Agent state supplied appearance", {
518
512
  appearance: r.appearance
519
- }), Y(r.appearance, "agent.state.appearance")) : q && (q = !1, O("web-sdk.widget", "Agent state cleared appearance; reverting to configured widget options", {
513
+ }), ae(r.appearance, "agent.state.appearance")) : oe && (oe = !1, O("web-sdk.widget", "Agent state cleared appearance; reverting to configured widget options", {
520
514
  fallbackAccentColor: e.accentColor,
521
515
  fallbackColorScheme: e.colorScheme,
522
516
  fallbackFontFamily: e.fontFamily
523
- }), Y({}, "agent.state.appearance-cleared")), Se(f, l, g, r, B, S, ce, (w) => {
524
- m.sendMessage(w);
525
- }), I();
526
- }), Se(f, l, g, m.getState(), B, S, ce, (r) => {
527
- m.sendMessage(r);
528
- }), I(), {
529
- agent: m,
517
+ }), ae({}, "agent.state.appearance-cleared")), e.loginRequired ? Fe(w, m, b, Y, e.loginButtonLabel, e.onLoginClick) : Oe(w, m, b, r, K, T, Y, (g) => {
518
+ C.sendMessage(g);
519
+ }), N();
520
+ }), e.loginRequired ? Fe(w, m, b, Y, e.loginButtonLabel, e.onLoginClick) : Oe(w, m, b, C.getState(), K, T, Y, (r) => {
521
+ C.sendMessage(r);
522
+ }), N(), {
523
+ agent: C,
530
524
  updateAppearance: (r) => {
531
- r.scribbleStyle !== void 0 && (e.scribbleStyle = r.scribbleStyle), Y(r, "widgetHandle.updateAppearance");
525
+ r.scribbleStyle !== void 0 && (e.scribbleStyle = r.scribbleStyle), ae(r, "widgetHandle.updateAppearance");
532
526
  },
533
527
  destroy: () => {
534
- ie = !0, re.disconnect(), e.movableLauncher && window.removeEventListener("resize", pe), se(), m.destroy(), n.remove();
528
+ me = !0, fe.disconnect(), e.movableLauncher && window.removeEventListener("resize", be), _e(), P !== null && window.clearTimeout(P), C.destroy(), n.remove();
535
529
  }
536
530
  };
537
- function Y(r, w) {
538
- const T = r.accentColor ?? e.accentColor, F = r.colorScheme ?? e.colorScheme, de = r.fontFamily ?? e.fontFamily, X = r.scribbleStyle ?? e.scribbleStyle;
539
- i = _e(T, X), xe(a, i, {
540
- accentColor: T,
541
- colorScheme: F,
542
- fontFamily: de,
543
- scribbleStyle: X
531
+ function ae(r, g) {
532
+ const E = r.accentColor ?? e.accentColor, H = r.colorScheme ?? e.colorScheme, xe = r.fontFamily ?? e.fontFamily, ie = r.scribbleStyle ?? e.scribbleStyle;
533
+ i = Pe(E, ie), Ae(a, i, {
534
+ accentColor: E,
535
+ colorScheme: H,
536
+ fontFamily: xe,
537
+ scribbleStyle: ie
544
538
  }), O("web-sdk.widget", "Updated widget appearance", {
545
- source: w,
539
+ source: g,
546
540
  inputAppearance: r,
547
- appliedAccentColor: T,
548
- appliedColorScheme: F,
549
- appliedFontFamily: de,
550
- appliedScribbleStyle: X,
541
+ appliedAccentColor: E,
542
+ appliedColorScheme: H,
543
+ appliedFontFamily: xe,
544
+ appliedScribbleStyle: ie,
551
545
  cssAccent: a.style.getPropertyValue("--pluno-pa-accent")
552
546
  });
553
547
  }
554
548
  }
555
- function _e(t, e) {
556
- return e ? je(t) : Ve(t);
549
+ function Pe(t, e) {
550
+ return e ? mt(t) : gt(t);
557
551
  }
558
- function xe(t, e, n) {
552
+ function Ae(t, e, n) {
559
553
  t.classList.toggle("pluno-pa-widget--dark", n.colorScheme === "dark"), t.classList.toggle("pluno-pa-widget--light", n.colorScheme !== "dark"), t.classList.toggle("pluno-pa-widget--scribble", n.scribbleStyle);
560
- const o = n.scribbleStyle ? Oe(n.accentColor) : n.accentColor;
561
- t.style.setProperty("--pluno-pa-accent", o), t.style.fontFamily = n.scribbleStyle ? lt : n.fontFamily, n.scribbleStyle && _t(t.ownerDocument);
554
+ const o = n.scribbleStyle ? Ve(n.accentColor) : n.accentColor;
555
+ t.style.setProperty("--pluno-pa-accent", o), t.style.fontFamily = n.scribbleStyle ? Nt : n.fontFamily, n.scribbleStyle && Ht(t.ownerDocument);
562
556
  const a = Array.from(t.querySelectorAll(".pluno-pa-widget__character"));
563
557
  for (const i of a)
564
558
  i.src = e;
565
559
  }
566
- function _t(t) {
567
- if (t.getElementById(we))
560
+ function Ht(t) {
561
+ if (t.getElementById(Se))
568
562
  return;
569
563
  const e = t.createElement("style");
570
- e.id = we, e.textContent = `@font-face {
564
+ e.id = Se, e.textContent = `@font-face {
571
565
  font-family: "Architects Daughter";
572
566
  font-style: normal;
573
567
  font-weight: 400;
@@ -575,107 +569,107 @@ function _t(t) {
575
569
  src: url("https://fonts.gstatic.com/s/architectsdaughter/v20/KtkxAKiDZI_td1Lkx62xHZHDtgO_Y-bvTYlg4-7jA-U.woff2") format("woff2");
576
570
  }`, t.head.appendChild(e), t.fonts?.load('16px "Architects Daughter"');
577
571
  }
578
- function xt({
572
+ function Vt({
579
573
  root: t,
580
574
  launcherDragHandle: e,
581
575
  getPosition: n,
582
576
  setPosition: o,
583
577
  persist: a
584
578
  }) {
585
- let i = null, p = null, c = null, d = !1;
579
+ let i = null, l = null, s = null, u = !1;
586
580
  const h = () => {
587
- i = null, p = null, c = null, d = !1, t.classList.remove("pluno-pa-widget--dragging");
588
- }, s = (l) => {
589
- t.classList.contains("pluno-pa-widget--open") || t.classList.contains("pluno-pa-widget--closing") || (l.preventDefault(), l.stopPropagation(), i = l.pointerId, p = { x: l.clientX, y: l.clientY }, c = n(), d = !1, e.setPointerCapture?.(l.pointerId));
590
- }, b = (l) => {
591
- if (i !== l.pointerId || !p || !c)
581
+ i = null, l = null, s = null, u = !1, t.classList.remove("pluno-pa-widget--dragging");
582
+ }, c = (d) => {
583
+ t.classList.contains("pluno-pa-widget--open") || t.classList.contains("pluno-pa-widget--closing") || (d.preventDefault(), d.stopPropagation(), i = d.pointerId, l = { x: d.clientX, y: d.clientY }, s = n(), u = !1, e.setPointerCapture?.(d.pointerId));
584
+ }, f = (d) => {
585
+ if (i !== d.pointerId || !l || !s)
592
586
  return;
593
- l.preventDefault();
594
- const g = l.clientX - p.x, f = l.clientY - p.y;
595
- !d && Math.hypot(g, f) < gt || (d = !0, t.classList.add("pluno-pa-widget--dragging"), o({ x: c.x + g, y: c.y + f }));
596
- }, x = (l) => {
597
- i === l.pointerId && (l.preventDefault(), l.stopPropagation(), d && a(), h());
598
- }, v = (l) => {
599
- i === l.pointerId && (l.preventDefault(), h());
600
- }, u = (l) => {
587
+ d.preventDefault();
588
+ const p = d.clientX - l.x, m = d.clientY - l.y;
589
+ !u && Math.hypot(p, m) < Gt || (u = !0, t.classList.add("pluno-pa-widget--dragging"), o({ x: s.x + p, y: s.y + m }));
590
+ }, y = (d) => {
591
+ i === d.pointerId && (d.preventDefault(), d.stopPropagation(), u && a(), h());
592
+ }, k = (d) => {
593
+ i === d.pointerId && (d.preventDefault(), h());
594
+ }, v = (d) => {
601
595
  if (t.classList.contains("pluno-pa-widget--open") || t.classList.contains("pluno-pa-widget--closing"))
602
596
  return;
603
- const g = l.shiftKey ? ft : ht, f = n();
604
- let _ = null;
605
- l.key === "ArrowUp" ? _ = { x: f.x, y: f.y - g } : l.key === "ArrowDown" ? _ = { x: f.x, y: f.y + g } : l.key === "ArrowLeft" ? _ = { x: f.x - g, y: f.y } : l.key === "ArrowRight" && (_ = { x: f.x + g, y: f.y }), _ && (l.preventDefault(), l.stopPropagation(), o(_), a());
597
+ const p = d.shiftKey ? $t : Bt, m = n();
598
+ let b = null;
599
+ d.key === "ArrowUp" ? b = { x: m.x, y: m.y - p } : d.key === "ArrowDown" ? b = { x: m.x, y: m.y + p } : d.key === "ArrowLeft" ? b = { x: m.x - p, y: m.y } : d.key === "ArrowRight" && (b = { x: m.x + p, y: m.y }), b && (d.preventDefault(), d.stopPropagation(), o(b), a());
606
600
  };
607
- return e.addEventListener("pointerdown", s), e.addEventListener("pointermove", b), e.addEventListener("pointerup", x), e.addEventListener("pointercancel", v), e.addEventListener("keydown", u), () => {
608
- e.removeEventListener("pointerdown", s), e.removeEventListener("pointermove", b), e.removeEventListener("pointerup", x), e.removeEventListener("pointercancel", v), e.removeEventListener("keydown", u);
601
+ return e.addEventListener("pointerdown", c), e.addEventListener("pointermove", f), e.addEventListener("pointerup", y), e.addEventListener("pointercancel", k), e.addEventListener("keydown", v), () => {
602
+ e.removeEventListener("pointerdown", c), e.removeEventListener("pointermove", f), e.removeEventListener("pointerup", y), e.removeEventListener("pointercancel", k), e.removeEventListener("keydown", v);
609
603
  };
610
604
  }
611
- function ye(t, e = !0) {
612
- const n = R(), o = t.getBoundingClientRect(), a = !t.classList.contains("pluno-pa-widget--open") && !t.classList.contains("pluno-pa-widget--closing");
605
+ function Te(t, e = !0) {
606
+ const n = B(), o = t.getBoundingClientRect(), a = !t.classList.contains("pluno-pa-widget--open") && !t.classList.contains("pluno-pa-widget--closing");
613
607
  return {
614
- width: e && a && o.width > 0 ? o.width : Math.min(De, n.width - 36),
615
- height: e && a && o.height > 0 ? o.height : t.classList.contains("pluno-pa-widget--scribble") ? pt : Fe
608
+ width: e && a && o.width > 0 ? o.width : Math.min(Ke, n.width - 36),
609
+ height: e && a && o.height > 0 ? o.height : t.classList.contains("pluno-pa-widget--scribble") ? It : je
616
610
  };
617
611
  }
618
- function yt() {
619
- const t = R();
612
+ function qt() {
613
+ const t = B();
620
614
  return {
621
- width: Math.min(st, t.width - 28),
622
- height: Math.min(ct, t.height - 28)
615
+ width: Math.min(Rt, t.width - 28),
616
+ height: Math.min(Dt, t.height - 28)
623
617
  };
624
618
  }
625
- function vt(t, e, n) {
619
+ function Kt(t, e, n) {
626
620
  const o = Number.parseFloat(t.style.left), a = Number.parseFloat(t.style.top);
627
621
  if (Number.isFinite(o) && Number.isFinite(a))
628
622
  return { x: o, y: a };
629
623
  const i = t.getBoundingClientRect();
630
624
  if (i.width > 0 || i.height > 0)
631
625
  return { x: i.left, y: i.top };
632
- const p = R();
626
+ const l = B();
633
627
  return {
634
- x: e === "bottom-left" ? 26 : p.width - 26 - n.width,
635
- y: p.height - 24 - n.height
628
+ x: e === "bottom-left" ? 26 : l.width - 26 - n.width,
629
+ y: l.height - 24 - n.height
636
630
  };
637
631
  }
638
- function ve(t, e, n) {
639
- const o = R(), a = k + kt(t);
632
+ function Ne(t, e, n) {
633
+ const o = B(), a = S + jt(t);
640
634
  return {
641
- x: K(e.x, k, Math.max(k, o.width - n.width - k)),
642
- y: K(e.y, a, Math.max(a, o.height - n.height - k))
635
+ x: te(e.x, S, Math.max(S, o.width - n.width - S)),
636
+ y: te(e.y, a, Math.max(a, o.height - n.height - S))
643
637
  };
644
638
  }
645
- function kt(t) {
646
- return t.classList.contains("pluno-pa-widget--scribble") ? ut : dt;
639
+ function jt(t) {
640
+ return t.classList.contains("pluno-pa-widget--scribble") ? Ft : Ot;
647
641
  }
648
- function ke(t) {
649
- const e = R(), n = yt();
642
+ function Ie(t) {
643
+ const e = B(), n = qt();
650
644
  return {
651
- x: K(t.x, k, Math.max(k, e.width - n.width - k)),
652
- y: K(
645
+ x: te(t.x, S, Math.max(S, e.width - n.width - S)),
646
+ y: te(
653
647
  t.y,
654
- me,
655
- Math.max(me, e.height - n.height - k)
648
+ Le,
649
+ Math.max(Le, e.height - n.height - S)
656
650
  )
657
651
  };
658
652
  }
659
- function H(t, e) {
653
+ function X(t, e) {
660
654
  if (t.classList.toggle("pluno-pa-widget--custom-position", e !== null), !e) {
661
655
  t.style.removeProperty("left"), t.style.removeProperty("top"), t.style.removeProperty("right"), t.style.removeProperty("bottom");
662
656
  return;
663
657
  }
664
658
  t.style.left = `${e.x}px`, t.style.top = `${e.y}px`, t.style.right = "auto", t.style.bottom = "auto";
665
659
  }
666
- function Ct(t, e) {
660
+ function Yt(t, e) {
667
661
  t.style.setProperty("--pluno-pa-panel-offset-x", `${e.x}px`), t.style.setProperty("--pluno-pa-panel-offset-y", `${e.y}px`);
668
662
  }
669
- function Ce(t) {
663
+ function Re(t) {
670
664
  t.style.removeProperty("--pluno-pa-panel-offset-x"), t.style.removeProperty("--pluno-pa-panel-offset-y");
671
665
  }
672
- function R() {
666
+ function B() {
673
667
  return {
674
- width: window.innerWidth || document.documentElement.clientWidth || De + k * 2,
675
- height: window.innerHeight || document.documentElement.clientHeight || Fe + k * 2
668
+ width: window.innerWidth || document.documentElement.clientWidth || Ke + S * 2,
669
+ height: window.innerHeight || document.documentElement.clientHeight || je + S * 2
676
670
  };
677
671
  }
678
- function J(t) {
672
+ function le(t) {
679
673
  const e = t.getBoundingClientRect();
680
674
  return {
681
675
  x: Math.round(e.x),
@@ -684,7 +678,7 @@ function J(t) {
684
678
  height: Math.round(e.height)
685
679
  };
686
680
  }
687
- function K(t, e, n) {
681
+ function te(t, e, n) {
688
682
  return Math.min(Math.max(t, e), n);
689
683
  }
690
684
  function O(t, e, n) {
@@ -696,139 +690,444 @@ function O(t, e, n) {
696
690
  message: e,
697
691
  details: n
698
692
  }, i = o.__plunoProductAgentDiagnostics__ ?? [];
699
- i.push(a), i.length > 120 && i.splice(0, i.length - 120), o.__plunoProductAgentDiagnostics__ = i, o.__PLUNO_PRODUCT_AGENT_DIAGNOSTICS__ = () => [...i], window.dispatchEvent(new CustomEvent(rt, { detail: a }));
693
+ i.push(a), i.length > 120 && i.splice(0, i.length - 120), o.__plunoProductAgentDiagnostics__ = i, o.__PLUNO_PRODUCT_AGENT_DIAGNOSTICS__ = () => [...i], window.dispatchEvent(new CustomEvent(Pt, { detail: a }));
700
694
  }
701
- function Et(t, e) {
695
+ function Xt(t, e) {
702
696
  O("web-sdk.widget.position", t, e);
703
697
  }
704
- function Q(t, e) {
705
- const n = e.value.trim();
706
- n && (e.value = "", e.style.height = "22px", e.style.overflowY = "hidden", t.sendMessage(n), e.dispatchEvent(new Event("input", { bubbles: !0 })));
698
+ function pe(t, e, n) {
699
+ const o = e.value.trim();
700
+ return !o && n.length === 0 ? n : (e.value = "", e.style.height = "22px", e.style.overflowY = "hidden", t.sendMessage(o, { attachments: n.length > 0 ? n : void 0 }), e.dispatchEvent(new Event("input", { bubbles: !0 })), []);
707
701
  }
708
- function $(t) {
702
+ function V(t) {
709
703
  t.style.height = "0px";
710
704
  const e = Math.max(22, Math.min(t.scrollHeight, 140));
711
705
  t.style.height = `${e}px`, t.style.overflowY = t.scrollHeight > 140 ? "auto" : "hidden";
712
706
  }
713
- function Ee(t) {
707
+ function Zt(t, e, n, o) {
708
+ t.appendChild(nn()), t.appendChild(Jt(e, n, o)), t.appendChild(Ze("pluno-pa-widget__close", "Close", on(16), !0)), t.appendChild(Qt(n));
709
+ }
710
+ function Jt(t, e, n) {
711
+ const o = document.createElement("form");
712
+ if (o.className = "pluno-pa-widget__launcher", n) {
713
+ const i = document.createElement("button");
714
+ i.type = "button", i.className = "pluno-pa-widget__launcher-drag-handle", i.setAttribute("aria-label", "Move Pluno launcher"), i.title = "Move Pluno launcher", o.appendChild(i);
715
+ }
716
+ o.appendChild(Xe("pluno-pa-widget__character--launcher", e));
717
+ const a = document.createElement("input");
718
+ return a.className = "pluno-pa-widget__launcher-input", a.type = "text", a.placeholder = t, a.setAttribute("aria-label", t), o.appendChild(a), o;
719
+ }
720
+ function Qt(t) {
721
+ const e = document.createElement("section");
722
+ e.className = "pluno-pa-widget__panel", e.hidden = !0;
723
+ const n = document.createElement("div");
724
+ n.className = "pluno-pa-widget__timeline-wrap";
725
+ const o = document.createElement("main");
726
+ return o.className = "pluno-pa-widget__timeline", o.appendChild(tn(t)), n.appendChild(o), n.appendChild(Ze("pluno-pa-widget__new-chat", "New chat", an(), !0)), e.appendChild(n), e.appendChild(en()), e;
727
+ }
728
+ function en() {
729
+ const t = document.createElement("form");
730
+ t.className = "pluno-pa-widget__composer";
731
+ const e = document.createElement("div");
732
+ e.className = "pluno-pa-widget__attachment-error", e.hidden = !0, t.appendChild(e);
733
+ const n = document.createElement("div");
734
+ n.className = "pluno-pa-widget__attachments", n.hidden = !0, t.appendChild(n);
735
+ const o = document.createElement("div");
736
+ o.className = "pluno-pa-widget__composer-inner";
737
+ const a = document.createElement("textarea");
738
+ a.className = "pluno-pa-widget__input", a.rows = 1, a.placeholder = "Ask for anything...", o.appendChild(a);
739
+ const i = document.createElement("button");
740
+ i.type = "button", i.className = "pluno-pa-widget__send", i.setAttribute("aria-label", "Send"), i.appendChild(Je()), o.appendChild(i), t.appendChild(o);
741
+ const l = document.createElement("div");
742
+ l.className = "pluno-pa-widget__composer-meta";
743
+ const s = document.createElement("a");
744
+ s.className = "pluno-pa-widget__powered-by", s.href = "https://pluno.ai", s.target = "_blank", s.rel = "noopener noreferrer", s.textContent = "Powered by Pluno.ai", l.appendChild(s);
745
+ const u = document.createElement("span");
746
+ return u.className = "pluno-pa-widget__ai-disclaimer", u.textContent = "AI can make mistakes", l.appendChild(u), t.appendChild(l), t;
747
+ }
748
+ function tn(t) {
749
+ const e = document.createElement("div");
750
+ return e.className = "pluno-pa-widget__empty-state", e.appendChild(Xe("pluno-pa-widget__character--empty", t)), e.appendChild(Ye()), e;
751
+ }
752
+ function Ye() {
753
+ const t = document.createElement("div");
754
+ return t.className = "pluno-pa-widget__empty", t.appendChild(document.createTextNode("Hey there, I'm Pluno 👋")), t.appendChild(document.createElement("br")), t.appendChild(document.createTextNode("What do you want to do today?")), t;
755
+ }
756
+ function Xe(t, e) {
757
+ const n = document.createElement("img");
758
+ return n.className = `pluno-pa-widget__character ${t}`, n.src = e, n.alt = "", n.setAttribute("aria-hidden", "true"), n;
759
+ }
760
+ function Ze(t, e, n, o) {
761
+ const a = document.createElement("button");
762
+ return a.type = "button", a.className = t, a.setAttribute("aria-label", e), a.title = e, a.hidden = o, a.appendChild(n), a;
763
+ }
764
+ function nn() {
765
+ const t = _("svg", {
766
+ class: "pluno-pa-widget__scribble-defs",
767
+ "aria-hidden": "true",
768
+ focusable: "false",
769
+ width: "0",
770
+ height: "0"
771
+ }), e = _("defs");
772
+ return e.appendChild(se("pluno-pa-scribble-wobble", "2", "12")), e.appendChild(se("pluno-pa-scribble-wobble-2", "5", "15")), e.appendChild(se("pluno-pa-scribble-wobble-3", "9", "19")), t.appendChild(e), t;
773
+ }
774
+ function se(t, e, n) {
775
+ const o = _("filter", { id: t, x: "-8%", y: "-8%", width: "116%", height: "116%" });
776
+ return o.appendChild(
777
+ _("feTurbulence", {
778
+ type: "fractalNoise",
779
+ baseFrequency: "0.012 0.028",
780
+ numOctaves: "3",
781
+ seed: e,
782
+ result: "stroke-noise"
783
+ })
784
+ ), o.appendChild(
785
+ _("feDisplacementMap", {
786
+ in: "SourceGraphic",
787
+ in2: "stroke-noise",
788
+ scale: "3.5",
789
+ xChannelSelector: "R",
790
+ yChannelSelector: "G",
791
+ result: "warped"
792
+ })
793
+ ), o.appendChild(
794
+ _("feTurbulence", {
795
+ type: "fractalNoise",
796
+ baseFrequency: "0.7",
797
+ numOctaves: "1",
798
+ seed: n,
799
+ result: "ink-noise"
800
+ })
801
+ ), o.appendChild(
802
+ _("feDisplacementMap", {
803
+ in: "warped",
804
+ in2: "ink-noise",
805
+ scale: "0.9",
806
+ xChannelSelector: "R",
807
+ yChannelSelector: "G"
808
+ })
809
+ ), o;
810
+ }
811
+ function on(t) {
812
+ const e = $("0 0 24 24", t, t, "none", "currentColor", "2.25");
813
+ return e.appendChild(_("path", { d: "m6 9 6 6 6-6" })), e;
814
+ }
815
+ function an() {
816
+ const t = $("0 0 24 24", 17, 17, "none", "currentColor", "2.25");
817
+ return t.appendChild(_("path", { d: "M12 3H5a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7" })), t.appendChild(_("path", { d: "M18.4 2.6a2.1 2.1 0 0 1 3 3L12 15l-4 1 1-4Z" })), t;
818
+ }
819
+ function Je() {
820
+ const t = $("0 0 24 24", 14, 14, "none", "currentColor", "2.75");
821
+ return t.appendChild(_("line", { x1: "12", y1: "19", x2: "12", y2: "5" })), t.appendChild(_("polyline", { points: "5 12 12 5 19 12" })), t;
822
+ }
823
+ function rn() {
824
+ const t = $("0 0 24 24", 18, 18, "currentColor");
825
+ return t.appendChild(_("rect", { x: "6", y: "6", width: "12", height: "12", rx: "2" })), t;
826
+ }
827
+ function ln() {
828
+ const t = $("0 0 24 24", 12, 12, "none", "currentColor", "2.4");
829
+ return t.appendChild(_("path", { d: "M18 6 6 18" })), t.appendChild(_("path", { d: "m6 6 12 12" })), t;
830
+ }
831
+ function pn() {
832
+ const t = $("0 0 24 24", 13, 13, "none", "currentColor", "2.25");
833
+ return t.appendChild(_("rect", { width: "14", height: "14", x: "8", y: "8", rx: "2", ry: "2" })), t.appendChild(_("path", { d: "M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2" })), t;
834
+ }
835
+ function $(t, e, n, o, a, i) {
836
+ const l = {
837
+ viewBox: t,
838
+ width: String(e),
839
+ height: String(n),
840
+ fill: o,
841
+ "aria-hidden": "true"
842
+ };
843
+ return a && (l.stroke = a, l["stroke-linecap"] = "round", l["stroke-linejoin"] = "round"), i && (l["stroke-width"] = i), _("svg", l);
844
+ }
845
+ function _(t, e = {}) {
846
+ const n = document.createElementNS(Mt, t);
847
+ for (const [o, a] of Object.entries(e))
848
+ n.setAttribute(o, a);
849
+ return n;
850
+ }
851
+ function De(t) {
714
852
  for (const e of ["keydown", "keypress", "keyup"])
715
853
  t.addEventListener(e, (n) => {
716
854
  n.stopPropagation();
717
855
  });
718
856
  }
719
- function Se(t, e, n, o, a, i, p, c) {
720
- const d = [...o.messages];
721
- t.innerHTML = "", Tt(e, o.isThinking);
722
- const h = d.length > 0 || !!o.assistantDraft || o.isThinking;
723
- if (n.hidden = !h, d.length === 0 && !o.assistantDraft && !o.lastError && !o.isThinking) {
724
- const l = document.createElement("div");
725
- l.className = "pluno-pa-widget__empty-state pluno-pa-widget__empty-state--starter";
726
- const g = document.createElement("img");
727
- g.className = "pluno-pa-widget__character pluno-pa-widget__character--empty", g.src = p(), g.alt = "", g.setAttribute("aria-hidden", "true"), l.appendChild(g);
728
- const f = document.createElement("div");
729
- f.className = "pluno-pa-widget__empty", f.innerHTML = "Hey there, I'm Pluno 👋<br />What do you want to do today?", l.appendChild(f);
730
- const _ = document.createElement("div");
731
- _.className = o.starterPrompts.length > 0 ? "pluno-pa-widget__starter-prompts" : "pluno-pa-widget__starter-prompts pluno-pa-widget__starter-prompts--empty", o.starterPrompts.length === 0 && _.setAttribute("aria-hidden", "true");
732
- for (const m of o.starterPrompts) {
733
- const y = document.createElement("button");
734
- y.type = "button", y.className = "pluno-pa-widget__starter-prompt", y.textContent = `"${m}"`, y.addEventListener("click", () => {
735
- c(m);
736
- }), _.appendChild(y);
737
- }
738
- l.appendChild(_), t.appendChild(l);
857
+ function sn(t, e, n) {
858
+ t.replaceChildren(), t.hidden = e.length === 0;
859
+ for (const [o, a] of e.entries()) {
860
+ const i = document.createElement("div");
861
+ i.className = "pluno-pa-widget__attachment", i.appendChild(dn(a));
862
+ const l = document.createElement("span");
863
+ l.textContent = a.name, i.appendChild(l);
864
+ const s = document.createElement("button");
865
+ s.type = "button", s.setAttribute("aria-label", `Remove ${a.name}`), s.appendChild(ln()), s.addEventListener("click", () => n(o)), i.appendChild(s), t.appendChild(i);
866
+ }
867
+ }
868
+ function dn(t) {
869
+ if (Qe(t)) {
870
+ const n = document.createElement("img");
871
+ return n.src = t.dataUrl, n.alt = "", n.setAttribute("aria-hidden", "true"), n;
872
+ }
873
+ const e = document.createElement("span");
874
+ return e.className = "pluno-pa-widget__attachment-file", e.textContent = "PDF", e;
875
+ }
876
+ function cn(t) {
877
+ if (Qe(t)) {
878
+ const a = document.createElement("img");
879
+ return a.src = t.dataUrl, a.alt = t.name, a;
880
+ }
881
+ const e = document.createElement("div");
882
+ e.className = "pluno-pa-widget__message-attachment-file";
883
+ const n = document.createElement("span");
884
+ n.textContent = "PDF";
885
+ const o = document.createElement("strong");
886
+ return o.textContent = t.name, e.append(n, o), e;
887
+ }
888
+ function Qe(t) {
889
+ return t.mimeType.startsWith("image/");
890
+ }
891
+ function un(t) {
892
+ return t === "application/pdf" ? "document.pdf" : "image";
893
+ }
894
+ async function gn(t) {
895
+ if (!t)
896
+ return [];
897
+ const e = Array.from(t);
898
+ if (e.length > ee)
899
+ throw new Error(`Attach up to ${ee} files per message.`);
900
+ return Promise.all(
901
+ e.map(async (n) => {
902
+ const o = hn(n);
903
+ if (!o)
904
+ throw new Error("Pluno supports PNG, JPEG, WebP, non-animated GIF, and PDF files.");
905
+ if (n.size > At)
906
+ throw new Error("Each Pluno attachment can be up to 10 MB.");
907
+ if (o === "image/gif") {
908
+ const a = new Uint8Array(await bn(n));
909
+ if (fn(a))
910
+ throw new Error("Pluno supports non-animated GIF images.");
911
+ }
912
+ return {
913
+ name: n.name || un(o),
914
+ mimeType: o,
915
+ sizeBytes: n.size,
916
+ dataUrl: mn(await _n(n), o)
917
+ };
918
+ })
919
+ );
920
+ }
921
+ function hn(t) {
922
+ if (Tt.has(t.type))
923
+ return t.type;
924
+ const e = t.name.toLowerCase();
925
+ return e.endsWith(".png") ? "image/png" : e.endsWith(".jpg") || e.endsWith(".jpeg") ? "image/jpeg" : e.endsWith(".webp") ? "image/webp" : e.endsWith(".gif") ? "image/gif" : e.endsWith(".pdf") ? "application/pdf" : null;
926
+ }
927
+ function mn(t, e) {
928
+ const n = `data:${e};base64,`;
929
+ return t.startsWith(n) ? t : t.replace(/^data:[^;]*;base64,/, n);
930
+ }
931
+ function fn(t) {
932
+ if (t.length < 14 || !wn(t))
933
+ return !1;
934
+ const e = t[10];
935
+ let n = 13;
936
+ e & 128 && (n += 3 * 2 ** ((e & 7) + 1));
937
+ let o = 0;
938
+ for (; n < t.length; ) {
939
+ const a = t[n];
940
+ if (n += 1, a === 59)
941
+ return !1;
942
+ if (a === 33) {
943
+ n += 1, n = Me(t, n);
944
+ continue;
945
+ }
946
+ if (a !== 44)
947
+ return !1;
948
+ if (o += 1, o > 1)
949
+ return !0;
950
+ if (n + 9 >= t.length)
951
+ return !1;
952
+ const i = t[n + 8];
953
+ if (n += 9, i & 128 && (n += 3 * 2 ** ((i & 7) + 1)), n >= t.length)
954
+ return !1;
955
+ n += 1, n = Me(t, n);
956
+ }
957
+ return !1;
958
+ }
959
+ function wn(t) {
960
+ return t[0] === 71 && t[1] === 73 && t[2] === 70 && t[3] === 56 && (t[4] === 55 || t[4] === 57) && t[5] === 97;
961
+ }
962
+ function Me(t, e) {
963
+ for (; e < t.length; ) {
964
+ const n = t[e];
965
+ if (e += 1, n === 0)
966
+ return e;
967
+ e += n;
968
+ }
969
+ return e;
970
+ }
971
+ function Z(t) {
972
+ return !!(t && Array.from(t.types).includes("Files"));
973
+ }
974
+ function bn(t) {
975
+ return new Promise((e, n) => {
976
+ const o = new FileReader();
977
+ o.addEventListener("load", () => {
978
+ if (o.result instanceof ArrayBuffer) {
979
+ e(o.result);
980
+ return;
981
+ }
982
+ n(new Error("Failed to read file"));
983
+ }), o.addEventListener("error", () => {
984
+ n(o.error ?? new Error("Failed to read file"));
985
+ }), o.readAsArrayBuffer(t);
986
+ });
987
+ }
988
+ function _n(t) {
989
+ return new Promise((e, n) => {
990
+ const o = new FileReader();
991
+ o.addEventListener("load", () => {
992
+ if (typeof o.result == "string") {
993
+ e(o.result);
994
+ return;
995
+ }
996
+ n(new Error("Failed to read file"));
997
+ }), o.addEventListener("error", () => {
998
+ n(o.error ?? new Error("Failed to read file"));
999
+ }), o.readAsDataURL(t);
1000
+ });
1001
+ }
1002
+ function Oe(t, e, n, o, a, i, l, s) {
1003
+ const u = [...o.messages];
1004
+ t.replaceChildren(), tt(e, o.isThinking);
1005
+ const h = u.length > 0 || !!o.assistantDraft || o.isThinking;
1006
+ if (n.hidden = !h, u.length === 0 && !o.assistantDraft && !o.lastError && !o.isThinking) {
1007
+ const d = document.createElement("div");
1008
+ d.className = "pluno-pa-widget__empty-state pluno-pa-widget__empty-state--starter";
1009
+ const p = document.createElement("img");
1010
+ p.className = "pluno-pa-widget__character pluno-pa-widget__character--empty", p.src = l(), p.alt = "", p.setAttribute("aria-hidden", "true"), d.appendChild(p), d.appendChild(Ye());
1011
+ const m = document.createElement("div");
1012
+ m.className = o.starterPrompts.length > 0 ? "pluno-pa-widget__starter-prompts" : "pluno-pa-widget__starter-prompts pluno-pa-widget__starter-prompts--empty", o.starterPrompts.length === 0 && m.setAttribute("aria-hidden", "true");
1013
+ for (const b of o.starterPrompts) {
1014
+ const w = document.createElement("button");
1015
+ w.type = "button", w.className = "pluno-pa-widget__starter-prompt", w.textContent = `"${b}"`, w.addEventListener("click", () => {
1016
+ s(b);
1017
+ }), m.appendChild(w);
1018
+ }
1019
+ d.appendChild(m), t.appendChild(d);
739
1020
  return;
740
1021
  }
741
- let s = null, b = null, x = [];
742
- const v = () => {
743
- if (x.length === 0)
1022
+ let c = null, f = null, y = [];
1023
+ const k = () => {
1024
+ if (y.length === 0)
744
1025
  return !1;
745
- const l = St(x, a, i, p());
746
- return t.appendChild(l), s = null, b = l, x = [], !0;
1026
+ const d = yn(y, a, i, l());
1027
+ return t.appendChild(d), c = null, f = d, y = [], !0;
747
1028
  };
748
- for (let l = 0; l < d.length; l += 1) {
749
- const g = d[l];
750
- if (g.role === "tool") {
751
- x.push(g);
1029
+ for (let d = 0; d < u.length; d += 1) {
1030
+ const p = u[d];
1031
+ if (p.role === "tool") {
1032
+ y.push(p);
752
1033
  continue;
753
1034
  }
754
- if (g.role === "system")
1035
+ if (p.role === "system")
755
1036
  continue;
756
- const f = v(), _ = Pe(g.content);
757
- if (g.role === "assistant" && !f) {
758
- const y = oe(p());
759
- t.appendChild(y), s = null, b = y;
1037
+ const m = k(), b = Be(p.content);
1038
+ if (p.role === "assistant" && !m) {
1039
+ const x = ge(l());
1040
+ t.appendChild(x), c = null, f = x;
760
1041
  }
761
- const m = document.createElement("div");
762
- m.className = `pluno-pa-widget__message pluno-pa-widget__message--${g.role}`, g.role === "assistant" ? Ae(m, _) : m.textContent = _, m.appendChild(Le(_)), t.appendChild(m), s = m, b = null;
1042
+ const w = document.createElement("div");
1043
+ w.className = `pluno-pa-widget__message pluno-pa-widget__message--${p.role}`, p.role === "assistant" ? ze(w, b) : w.textContent = b, p.role === "user" && p.attachments?.length && w.appendChild(xn(p.attachments)), w.appendChild(Ge(b)), t.appendChild(w), c = w, f = null;
763
1044
  }
764
- const u = v();
1045
+ const v = k();
765
1046
  if (o.assistantDraft) {
766
- if (!u) {
767
- const f = oe(p());
768
- t.appendChild(f), s = null, b = f;
1047
+ if (!v) {
1048
+ const m = ge(l());
1049
+ t.appendChild(m), c = null, f = m;
769
1050
  }
770
- const l = Pe(o.assistantDraft), g = document.createElement("div");
771
- g.className = "pluno-pa-widget__message pluno-pa-widget__message--assistant", Ae(g, l), g.appendChild(Le(l)), t.appendChild(g), s = g, b = null;
1051
+ const d = Be(o.assistantDraft), p = document.createElement("div");
1052
+ p.className = "pluno-pa-widget__message pluno-pa-widget__message--assistant", ze(p, d), p.appendChild(Ge(d)), t.appendChild(p), c = p, f = null;
772
1053
  }
773
1054
  if (o.isThinking && !o.assistantDraft)
774
- if (u) {
775
- const l = $e();
776
- t.appendChild(l), s = null, b = l;
1055
+ if (v) {
1056
+ const d = et();
1057
+ t.appendChild(d), c = null, f = d;
777
1058
  } else {
778
- const l = Lt(p());
779
- t.appendChild(l), s = null, b = l;
1059
+ const d = vn(l());
1060
+ t.appendChild(d), c = null, f = d;
780
1061
  }
781
1062
  if (o.lastError) {
782
- const l = document.createElement("div");
783
- l.className = "pluno-pa-widget__error", l.textContent = o.lastError, t.appendChild(l), s = l, b = null;
1063
+ const d = document.createElement("div");
1064
+ d.className = "pluno-pa-widget__error", d.textContent = o.lastError, t.appendChild(d), c = d, f = null;
784
1065
  }
785
- s?.classList.add("pluno-pa-widget__message--bottom-reserve"), b?.classList.add("pluno-pa-widget__bottom-reserve-compact"), t.scrollTop = t.scrollHeight;
1066
+ c?.classList.add("pluno-pa-widget__message--bottom-reserve"), f?.classList.add("pluno-pa-widget__bottom-reserve-compact"), t.scrollTop = t.scrollHeight;
1067
+ }
1068
+ function Fe(t, e, n, o, a, i) {
1069
+ t.replaceChildren(), tt(e, !1), e.disabled = !0, n.hidden = !0;
1070
+ const l = document.createElement("div");
1071
+ l.className = "pluno-pa-widget__empty-state pluno-pa-widget__empty-state--starter";
1072
+ const s = document.createElement("img");
1073
+ s.className = "pluno-pa-widget__character pluno-pa-widget__character--empty", s.src = o(), s.alt = "", s.setAttribute("aria-hidden", "true"), l.appendChild(s);
1074
+ const u = document.createElement("div");
1075
+ u.className = "pluno-pa-widget__empty", u.textContent = "Log in to use Pluno on this page.", l.appendChild(u);
1076
+ const h = document.createElement("button");
1077
+ h.type = "button", h.className = "pluno-pa-widget__login", h.textContent = a, h.addEventListener("click", () => i?.()), l.appendChild(h), t.appendChild(l);
1078
+ }
1079
+ function xn(t) {
1080
+ const e = document.createElement("div");
1081
+ e.className = "pluno-pa-widget__message-attachments";
1082
+ for (const n of t)
1083
+ e.appendChild(cn(n));
1084
+ return e;
786
1085
  }
787
- function Le(t) {
1086
+ function Ge(t) {
788
1087
  const e = document.createElement("button");
789
- return e.type = "button", e.className = "pluno-pa-widget__message-copy", e.setAttribute("aria-label", "Copy message"), e.title = "Copy message", e.innerHTML = '<svg viewBox="0 0 24 24" width="13" height="13" fill="none" stroke="currentColor" stroke-width="2.25" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><rect width="14" height="14" x="8" y="8" rx="2" ry="2"></rect><path d="M4 16c-1.1 0-2-.9-2-2V4c0-1.1.9-2 2-2h10c1.1 0 2 .9 2 2"></path></svg>', e.addEventListener("click", (n) => {
1088
+ return e.type = "button", e.className = "pluno-pa-widget__message-copy", e.setAttribute("aria-label", "Copy message"), e.title = "Copy message", e.appendChild(pn()), e.addEventListener("click", (n) => {
790
1089
  n.preventDefault(), n.stopPropagation(), navigator.clipboard.writeText(t);
791
1090
  }), e;
792
1091
  }
793
- function Pe(t) {
1092
+ function Be(t) {
794
1093
  return t.replace(/\uE200[^\uE201]*(?:\uE201|$)/g, "");
795
1094
  }
796
- function St(t, e, n, o) {
1095
+ function yn(t, e, n, o) {
797
1096
  const a = document.createElement("article");
798
1097
  a.className = "pluno-pa-widget__tool-group", a.title = new Date(t[t.length - 1].createdAt).toLocaleString();
799
1098
  const i = document.createElement("img");
800
1099
  i.className = "pluno-pa-widget__character pluno-pa-widget__character--tool-group", i.src = o, i.alt = "", i.setAttribute("aria-hidden", "true"), a.appendChild(i);
801
- const p = document.createElement("details"), c = Pt(t);
802
- p.open = e.has(c), p.addEventListener("toggle", () => {
803
- p.open ? e.add(c) : e.delete(c), n();
1100
+ const l = document.createElement("details"), s = Cn(t);
1101
+ l.open = e.has(s), l.addEventListener("toggle", () => {
1102
+ l.open ? e.add(s) : e.delete(s), n();
804
1103
  });
805
- const d = document.createElement("summary");
806
- d.className = "pluno-pa-widget__tool-summary", t.some((b) => b.loading) && d.appendChild(Te());
807
- const s = document.createElement("span");
808
- if (s.className = "pluno-pa-widget__tool-summary-title", s.textContent = t[t.length - 1].content || "Run tool", d.appendChild(s), p.appendChild(d), t.length > 0) {
809
- const b = document.createElement("div");
810
- b.className = "pluno-pa-widget__tool-lines";
811
- for (const x of t) {
812
- const v = document.createElement("div");
813
- v.className = "pluno-pa-widget__tool-line", x.loading && v.appendChild(Te());
814
- const u = document.createElement("span");
815
- u.textContent = x.content || "Run tool", v.appendChild(u), b.appendChild(v);
816
- }
817
- p.appendChild(b);
1104
+ const u = document.createElement("summary");
1105
+ u.className = "pluno-pa-widget__tool-summary", t.some((f) => f.loading) && u.appendChild($e());
1106
+ const c = document.createElement("span");
1107
+ if (c.className = "pluno-pa-widget__tool-summary-title", c.textContent = t[t.length - 1].content || "Run tool", u.appendChild(c), l.appendChild(u), t.length > 0) {
1108
+ const f = document.createElement("div");
1109
+ f.className = "pluno-pa-widget__tool-lines";
1110
+ for (const y of t) {
1111
+ const k = document.createElement("div");
1112
+ k.className = "pluno-pa-widget__tool-line", y.loading && k.appendChild($e());
1113
+ const v = document.createElement("span");
1114
+ v.textContent = y.content || "Run tool", k.appendChild(v), f.appendChild(k);
1115
+ }
1116
+ l.appendChild(f);
818
1117
  }
819
- return a.appendChild(p), a;
1118
+ return a.appendChild(l), a;
820
1119
  }
821
- function oe(t) {
1120
+ function ge(t) {
822
1121
  const e = document.createElement("article");
823
1122
  e.className = "pluno-pa-widget__tool-group pluno-pa-widget__assistant-marker";
824
1123
  const n = document.createElement("img");
825
1124
  return n.className = "pluno-pa-widget__character pluno-pa-widget__character--tool-group", n.src = t, n.alt = "", n.setAttribute("aria-hidden", "true"), e.appendChild(n), e;
826
1125
  }
827
- function Lt(t) {
828
- const e = oe(t);
829
- return e.classList.add("pluno-pa-widget__thinking-marker"), e.appendChild($e()), e;
1126
+ function vn(t) {
1127
+ const e = ge(t);
1128
+ return e.classList.add("pluno-pa-widget__thinking-marker"), e.appendChild(et()), e;
830
1129
  }
831
- function $e() {
1130
+ function et() {
832
1131
  const t = document.createElement("div");
833
1132
  t.className = "pluno-pa-widget__status";
834
1133
  const e = document.createElement("span");
@@ -836,17 +1135,17 @@ function $e() {
836
1135
  const n = document.createElement("span");
837
1136
  return n.textContent = "Thinking...", t.appendChild(n), t;
838
1137
  }
839
- function Pt(t) {
1138
+ function Cn(t) {
840
1139
  return `tools:${t.map((e) => e.id).join("|")}`;
841
1140
  }
842
- function Te() {
1141
+ function $e() {
843
1142
  const t = document.createElement("span");
844
1143
  return t.className = "pluno-pa-widget__spinner", t.setAttribute("aria-hidden", "true"), t;
845
1144
  }
846
- function Tt(t, e) {
847
- t.setAttribute("aria-label", e ? "Stop" : "Send"), t.classList.toggle("pluno-pa-widget__send--stop", e), t.innerHTML = e ? '<svg viewBox="0 0 24 24" width="18" height="18" fill="currentColor" aria-hidden="true"><rect x="6" y="6" width="12" height="12" rx="2" /></svg>' : '<svg viewBox="0 0 24 24" width="14" height="14" fill="none" stroke="currentColor" stroke-width="2.75" stroke-linecap="round" stroke-linejoin="round" aria-hidden="true"><line x1="12" y1="19" x2="12" y2="5" /><polyline points="5 12 12 5 19 12" /></svg>';
1145
+ function tt(t, e) {
1146
+ t.setAttribute("aria-label", e ? "Stop" : "Send"), t.classList.toggle("pluno-pa-widget__send--stop", e), t.replaceChildren(e ? rn() : Je());
848
1147
  }
849
- function Ae(t, e) {
1148
+ function ze(t, e) {
850
1149
  const n = e.replace(/\r\n/g, `
851
1150
  `).split(`
852
1151
  `);
@@ -862,22 +1161,22 @@ function Ae(t, e) {
862
1161
  for (o += 1; o < n.length && !/^```\s*$/.test(n[o]); )
863
1162
  h.push(n[o]), o += 1;
864
1163
  o += o < n.length ? 1 : 0;
865
- const s = document.createElement("pre"), b = document.createElement("code");
866
- b.textContent = h.join(`
867
- `), s.appendChild(b), t.appendChild(s);
1164
+ const c = document.createElement("pre"), f = document.createElement("code");
1165
+ f.textContent = h.join(`
1166
+ `), c.appendChild(f), t.appendChild(c);
868
1167
  continue;
869
1168
  }
870
- const p = a.match(/^(#{1,3})\s+(.+)$/);
871
- if (p) {
872
- const h = document.createElement(`h${p[1].length + 2}`);
873
- U(h, p[2]), t.appendChild(h), o += 1;
1169
+ const l = a.match(/^(#{1,3})\s+(.+)$/);
1170
+ if (l) {
1171
+ const h = document.createElement(`h${l[1].length + 2}`);
1172
+ J(h, l[2]), t.appendChild(h), o += 1;
874
1173
  continue;
875
1174
  }
876
1175
  if (/^\s*[-*+]\s+/.test(a)) {
877
1176
  const h = document.createElement("ul");
878
1177
  for (; o < n.length && /^\s*[-*+]\s+/.test(n[o]); ) {
879
- const s = document.createElement("li");
880
- U(s, n[o].replace(/^\s*[-*+]\s+/, "")), h.appendChild(s), o += 1;
1178
+ const c = document.createElement("li");
1179
+ J(c, n[o].replace(/^\s*[-*+]\s+/, "")), h.appendChild(c), o += 1;
881
1180
  }
882
1181
  t.appendChild(h);
883
1182
  continue;
@@ -885,50 +1184,50 @@ function Ae(t, e) {
885
1184
  if (/^\s*\d+\.\s+/.test(a)) {
886
1185
  const h = document.createElement("ol");
887
1186
  for (; o < n.length && /^\s*\d+\.\s+/.test(n[o]); ) {
888
- const s = document.createElement("li");
889
- U(s, n[o].replace(/^\s*\d+\.\s+/, "")), h.appendChild(s), o += 1;
1187
+ const c = document.createElement("li");
1188
+ J(c, n[o].replace(/^\s*\d+\.\s+/, "")), h.appendChild(c), o += 1;
890
1189
  }
891
1190
  t.appendChild(h);
892
1191
  continue;
893
1192
  }
894
- const c = [a];
1193
+ const s = [a];
895
1194
  for (o += 1; o < n.length && n[o].trim() && !/^```/.test(n[o]) && !/^(#{1,3})\s+/.test(n[o]) && !/^\s*[-*+]\s+/.test(n[o]) && !/^\s*\d+\.\s+/.test(n[o]); )
896
- c.push(n[o]), o += 1;
897
- const d = document.createElement("p");
898
- c.forEach((h, s) => {
899
- s > 0 && d.appendChild(document.createElement("br")), U(d, h);
900
- }), t.appendChild(d);
1195
+ s.push(n[o]), o += 1;
1196
+ const u = document.createElement("p");
1197
+ s.forEach((h, c) => {
1198
+ c > 0 && u.appendChild(document.createElement("br")), J(u, h);
1199
+ }), t.appendChild(u);
901
1200
  }
902
1201
  }
903
- function U(t, e) {
1202
+ function J(t, e) {
904
1203
  const n = /(`[^`]+`|\*\*[^*]+\*\*|\*[^*]+\*|\[[^\]]+\]\(([^)\s]+)\))/g;
905
1204
  let o = 0;
906
1205
  for (const a of e.matchAll(n)) {
907
1206
  const i = a.index ?? 0;
908
1207
  i > o && t.appendChild(document.createTextNode(e.slice(o, i)));
909
- const p = a[0];
910
- if (p.startsWith("`")) {
911
- const c = document.createElement("code");
912
- c.textContent = p.slice(1, -1), t.appendChild(c);
913
- } else if (p.startsWith("**")) {
914
- const c = document.createElement("strong");
915
- c.textContent = p.slice(2, -2), t.appendChild(c);
916
- } else if (p.startsWith("*")) {
917
- const c = document.createElement("em");
918
- c.textContent = p.slice(1, -1), t.appendChild(c);
1208
+ const l = a[0];
1209
+ if (l.startsWith("`")) {
1210
+ const s = document.createElement("code");
1211
+ s.textContent = l.slice(1, -1), t.appendChild(s);
1212
+ } else if (l.startsWith("**")) {
1213
+ const s = document.createElement("strong");
1214
+ s.textContent = l.slice(2, -2), t.appendChild(s);
1215
+ } else if (l.startsWith("*")) {
1216
+ const s = document.createElement("em");
1217
+ s.textContent = l.slice(1, -1), t.appendChild(s);
919
1218
  } else {
920
- const c = p.match(/^\[([^\]]+)\]\(([^)\s]+)\)$/);
921
- if (c && At(c[2])) {
922
- const d = document.createElement("a");
923
- d.href = c[2], d.target = "_top", d.rel = "noreferrer", d.textContent = c[1], t.appendChild(d);
1219
+ const s = l.match(/^\[([^\]]+)\]\(([^)\s]+)\)$/);
1220
+ if (s && En(s[2])) {
1221
+ const u = document.createElement("a");
1222
+ u.href = s[2], u.target = "_top", u.rel = "noreferrer", u.textContent = s[1], t.appendChild(u);
924
1223
  } else
925
- t.appendChild(document.createTextNode(p));
1224
+ t.appendChild(document.createTextNode(l));
926
1225
  }
927
- o = i + p.length;
1226
+ o = i + l.length;
928
1227
  }
929
1228
  o < e.length && t.appendChild(document.createTextNode(e.slice(o)));
930
1229
  }
931
- function At(t) {
1230
+ function En(t) {
932
1231
  if (t.startsWith("/") || t.startsWith("#"))
933
1232
  return !0;
934
1233
  try {
@@ -938,7 +1237,7 @@ function At(t) {
938
1237
  return !1;
939
1238
  }
940
1239
  }
941
- function Ne(t, e) {
1240
+ function We(t, e) {
942
1241
  if (t.getElementById("pluno-pa-widget-styles"))
943
1242
  return;
944
1243
  const n = t.ownerDocument.createElement("style");
@@ -993,7 +1292,7 @@ function Ne(t, e) {
993
1292
  --pluno-pa-accent-contrast: #fafafa;
994
1293
  position: fixed;
995
1294
  z-index: 2147483645;
996
- font-family: ${A.fontFamily};
1295
+ font-family: ${D.fontFamily};
997
1296
  font-size: 14px;
998
1297
  color: var(--pluno-pa-text);
999
1298
  width: var(--pluno-pa-launcher-width);
@@ -1014,6 +1313,31 @@ function Ne(t, e) {
1014
1313
  .pluno-pa-widget [hidden] {
1015
1314
  display: none !important;
1016
1315
  }
1316
+ .pluno-pa-widget--drag-over::after {
1317
+ content: "Drop files to attach";
1318
+ position: absolute;
1319
+ inset: -8px;
1320
+ z-index: 12;
1321
+ display: grid;
1322
+ place-items: center;
1323
+ border: 2px dashed var(--pluno-pa-accent);
1324
+ border-radius: 20px;
1325
+ background: color-mix(in srgb, var(--pluno-pa-bg) 82%, transparent);
1326
+ box-shadow: 0 0 0 999px rgba(24, 24, 27, 0.12);
1327
+ color: var(--pluno-pa-text);
1328
+ font-size: 14px;
1329
+ font-weight: 650;
1330
+ pointer-events: none;
1331
+ }
1332
+ .pluno-pa-widget--open.pluno-pa-widget--drag-over::after,
1333
+ .pluno-pa-widget--closing.pluno-pa-widget--drag-over::after {
1334
+ inset: auto;
1335
+ left: calc(var(--pluno-pa-panel-offset-x) - 8px);
1336
+ top: calc(var(--pluno-pa-panel-offset-y) - 8px);
1337
+ width: calc(var(--pluno-pa-panel-width) + 16px);
1338
+ height: calc(var(--pluno-pa-panel-height) + 16px);
1339
+ border-radius: 18px;
1340
+ }
1017
1341
  .pluno-pa-widget--bottom-right { right: 26px; bottom: 24px; }
1018
1342
  .pluno-pa-widget--bottom-left { left: 26px; bottom: 24px; }
1019
1343
  .pluno-pa-widget--bottom-left {
@@ -1296,6 +1620,50 @@ function Ne(t, e) {
1296
1620
  border-radius: 16px 16px 4px 16px;
1297
1621
  padding: 8px 12px;
1298
1622
  }
1623
+ .pluno-pa-widget__message-attachments {
1624
+ display: grid;
1625
+ grid-template-columns: repeat(auto-fill, minmax(72px, 1fr));
1626
+ gap: 6px;
1627
+ margin-top: 8px;
1628
+ max-width: 220px;
1629
+ }
1630
+ .pluno-pa-widget__message-attachments img {
1631
+ width: 100%;
1632
+ aspect-ratio: 1;
1633
+ border-radius: 8px;
1634
+ object-fit: cover;
1635
+ border: 1px solid var(--pluno-pa-divider);
1636
+ }
1637
+ .pluno-pa-widget__message-attachment-file {
1638
+ min-width: 0;
1639
+ aspect-ratio: 1;
1640
+ display: grid;
1641
+ align-content: center;
1642
+ gap: 5px;
1643
+ border: 1px solid var(--pluno-pa-divider);
1644
+ border-radius: 8px;
1645
+ background: var(--pluno-pa-surface);
1646
+ padding: 8px;
1647
+ color: var(--pluno-pa-text);
1648
+ }
1649
+ .pluno-pa-widget__message-attachment-file span {
1650
+ width: fit-content;
1651
+ border-radius: 4px;
1652
+ background: var(--pluno-pa-accent-soft);
1653
+ color: var(--pluno-pa-accent);
1654
+ padding: 2px 5px;
1655
+ font-size: 10px;
1656
+ font-weight: 700;
1657
+ line-height: 1;
1658
+ }
1659
+ .pluno-pa-widget__message-attachment-file strong {
1660
+ min-width: 0;
1661
+ overflow: hidden;
1662
+ text-overflow: ellipsis;
1663
+ white-space: nowrap;
1664
+ font-size: 11px;
1665
+ font-weight: 600;
1666
+ }
1299
1667
  .pluno-pa-widget__message--assistant {
1300
1668
  align-self: stretch;
1301
1669
  padding: 0 2px;
@@ -1506,6 +1874,85 @@ function Ne(t, e) {
1506
1874
  background: var(--pluno-pa-bg);
1507
1875
  border-top: 1px solid var(--pluno-pa-divider);
1508
1876
  }
1877
+ .pluno-pa-widget__attachment-error {
1878
+ margin: 0 0 8px;
1879
+ padding: 6px 9px;
1880
+ border-radius: 8px;
1881
+ background: rgba(239, 68, 68, 0.12);
1882
+ color: #dc2626;
1883
+ font-size: 12px;
1884
+ line-height: 1.35;
1885
+ }
1886
+ .pluno-pa-widget__attachment-error[hidden] {
1887
+ display: none;
1888
+ }
1889
+ .pluno-pa-widget__attachments {
1890
+ display: flex;
1891
+ flex-wrap: wrap;
1892
+ gap: 6px;
1893
+ margin: 0 0 8px;
1894
+ }
1895
+ .pluno-pa-widget__attachments[hidden] {
1896
+ display: none;
1897
+ }
1898
+ .pluno-pa-widget__attachment {
1899
+ min-width: 0;
1900
+ max-width: 100%;
1901
+ height: 30px;
1902
+ display: inline-flex;
1903
+ align-items: center;
1904
+ gap: 7px;
1905
+ border: 1px solid var(--pluno-pa-divider);
1906
+ border-radius: 8px;
1907
+ background: var(--pluno-pa-surface);
1908
+ color: var(--pluno-pa-muted);
1909
+ padding: 3px 5px 3px 3px;
1910
+ font-size: 12px;
1911
+ }
1912
+ .pluno-pa-widget__attachment img {
1913
+ width: 22px;
1914
+ height: 22px;
1915
+ border-radius: 5px;
1916
+ object-fit: cover;
1917
+ flex: 0 0 auto;
1918
+ }
1919
+ .pluno-pa-widget__attachment-file {
1920
+ width: 28px;
1921
+ height: 22px;
1922
+ flex: 0 0 auto;
1923
+ display: inline-grid;
1924
+ place-items: center;
1925
+ border-radius: 5px;
1926
+ background: var(--pluno-pa-accent-soft);
1927
+ color: var(--pluno-pa-accent);
1928
+ font-size: 9px;
1929
+ font-weight: 700;
1930
+ line-height: 1;
1931
+ }
1932
+ .pluno-pa-widget__attachment span {
1933
+ overflow: hidden;
1934
+ text-overflow: ellipsis;
1935
+ white-space: nowrap;
1936
+ }
1937
+ .pluno-pa-widget__attachment button {
1938
+ border: 0;
1939
+ background: transparent;
1940
+ color: inherit;
1941
+ padding: 0;
1942
+ cursor: pointer;
1943
+ }
1944
+ .pluno-pa-widget__attachment button {
1945
+ width: 18px;
1946
+ height: 18px;
1947
+ display: inline-flex;
1948
+ align-items: center;
1949
+ justify-content: center;
1950
+ border-radius: 999px;
1951
+ flex: 0 0 auto;
1952
+ }
1953
+ .pluno-pa-widget__attachment button:hover:not(:disabled) {
1954
+ background: var(--pluno-pa-bubble);
1955
+ }
1509
1956
  .pluno-pa-widget__composer-inner {
1510
1957
  position: relative;
1511
1958
  display: flex;
@@ -1515,11 +1962,16 @@ function Ne(t, e) {
1515
1962
  border: 1px solid var(--pluno-pa-divider);
1516
1963
  border-radius: 14px;
1517
1964
  padding: 8px 44px 8px 12px;
1518
- transition: border-color 150ms ease;
1965
+ transition: border-color 150ms ease, background-color 150ms ease, box-shadow 150ms ease;
1519
1966
  }
1520
1967
  .pluno-pa-widget__composer-inner:focus-within {
1521
1968
  border-color: var(--pluno-pa-accent);
1522
1969
  }
1970
+ .pluno-pa-widget--drag-over .pluno-pa-widget__composer-inner {
1971
+ border-color: var(--pluno-pa-accent);
1972
+ background: var(--pluno-pa-accent-soft);
1973
+ box-shadow: 0 0 0 3px var(--pluno-pa-accent-soft);
1974
+ }
1523
1975
  .pluno-pa-widget__input {
1524
1976
  flex: 1;
1525
1977
  width: 100%;
@@ -1575,20 +2027,30 @@ function Ne(t, e) {
1575
2027
  color: var(--pluno-pa-faint);
1576
2028
  cursor: not-allowed;
1577
2029
  }
1578
- .pluno-pa-widget__powered-by {
1579
- display: block;
1580
- width: fit-content;
1581
- margin: 8px auto 0;
2030
+ .pluno-pa-widget__composer-meta {
2031
+ display: flex;
2032
+ align-items: center;
2033
+ justify-content: space-between;
2034
+ gap: 10px;
2035
+ margin-top: 8px;
1582
2036
  color: var(--pluno-pa-faint);
1583
2037
  font: inherit;
1584
2038
  font-size: 11px;
1585
2039
  line-height: 1.2;
2040
+ }
2041
+ .pluno-pa-widget__powered-by {
2042
+ color: inherit;
1586
2043
  text-decoration: none;
1587
2044
  transition: color 120ms ease;
1588
2045
  }
1589
2046
  .pluno-pa-widget__powered-by:hover {
1590
2047
  color: var(--pluno-pa-muted);
1591
2048
  }
2049
+ .pluno-pa-widget__ai-disclaimer {
2050
+ color: inherit;
2051
+ text-align: right;
2052
+ white-space: nowrap;
2053
+ }
1592
2054
  .pluno-pa-widget__empty,
1593
2055
  .pluno-pa-widget__status,
1594
2056
  .pluno-pa-widget__error {
@@ -1660,6 +2122,20 @@ function Ne(t, e) {
1660
2122
  color: var(--pluno-pa-text);
1661
2123
  background: transparent;
1662
2124
  }
2125
+ .pluno-pa-widget__login {
2126
+ border: 0;
2127
+ border-radius: 8px;
2128
+ background: #09090b;
2129
+ color: #ffffff;
2130
+ min-height: 38px;
2131
+ padding: 0 14px;
2132
+ font: 650 13px/1 var(--pluno-pa-font);
2133
+ cursor: pointer;
2134
+ box-shadow: 0 8px 18px rgba(9, 9, 11, 0.16);
2135
+ }
2136
+ .pluno-pa-widget__login:hover {
2137
+ background: #18181b;
2138
+ }
1663
2139
  .pluno-pa-widget__status {
1664
2140
  display: inline-flex;
1665
2141
  align-items: center;
@@ -1757,7 +2233,7 @@ function Ne(t, e) {
1757
2233
  right: 16px;
1758
2234
  height: 36px;
1759
2235
  z-index: 3;
1760
- background-image: url('${be}');
2236
+ background-image: url('${ke}');
1761
2237
  background-repeat: repeat-x;
1762
2238
  background-size: 104px 36px;
1763
2239
  filter: url(#pluno-pa-scribble-wobble-2);
@@ -1961,7 +2437,7 @@ function Ne(t, e) {
1961
2437
  right: 12px;
1962
2438
  height: 22px;
1963
2439
  z-index: 1;
1964
- background-image: url('${be}');
2440
+ background-image: url('${ke}');
1965
2441
  background-repeat: repeat-x;
1966
2442
  background-size: 62px 21.5px;
1967
2443
  filter: url(#pluno-pa-scribble-wobble-2);
@@ -1975,7 +2451,7 @@ function Ne(t, e) {
1975
2451
  }
1976
2452
  `, t.appendChild(n);
1977
2453
  }
1978
- async function Nt() {
2454
+ async function kn() {
1979
2455
  return document.body ? document.body : await new Promise((t) => {
1980
2456
  const e = new MutationObserver(() => {
1981
2457
  document.body && (e.disconnect(), t(document.body));
@@ -1983,16 +2459,12 @@ async function Nt() {
1983
2459
  e.observe(document.documentElement, { childList: !0 });
1984
2460
  });
1985
2461
  }
1986
- function W(t) {
1987
- const e = document.createElement("span");
1988
- return e.textContent = t, e.innerHTML;
1989
- }
1990
- function Ge(t) {
2462
+ function nt(t) {
1991
2463
  return `pluno.productAgent.widgetState.${location.origin}.${t.backendUrl ?? ""}.${t.tokenEndpoint ?? ""}.${t.position ?? ""}`;
1992
2464
  }
1993
- function It(t) {
2465
+ function Sn(t) {
1994
2466
  try {
1995
- const e = window.localStorage.getItem(Ge(t));
2467
+ const e = window.localStorage.getItem(nt(t));
1996
2468
  if (!e)
1997
2469
  return { isOpen: !1, composerValue: "", openToolGroupKeys: [], launcherPosition: null };
1998
2470
  const n = JSON.parse(e);
@@ -2000,49 +2472,49 @@ function It(t) {
2000
2472
  isOpen: n.isOpen === !0,
2001
2473
  composerValue: typeof n.composerValue == "string" ? n.composerValue : "",
2002
2474
  openToolGroupKeys: Array.isArray(n.openToolGroupKeys) ? n.openToolGroupKeys.filter((o) => typeof o == "string") : [],
2003
- launcherPosition: Ot(n.launcherPosition) ? n.launcherPosition : null
2475
+ launcherPosition: Pn(n.launcherPosition) ? n.launcherPosition : null
2004
2476
  };
2005
2477
  } catch {
2006
2478
  return { isOpen: !1, composerValue: "", openToolGroupKeys: [], launcherPosition: null };
2007
2479
  }
2008
2480
  }
2009
- function Mt(t, e) {
2481
+ function Ln(t, e) {
2010
2482
  try {
2011
- window.localStorage.setItem(Ge(t), JSON.stringify(e));
2483
+ window.localStorage.setItem(nt(t), JSON.stringify(e));
2012
2484
  } catch {
2013
2485
  return;
2014
2486
  }
2015
2487
  }
2016
- function Ot(t) {
2488
+ function Pn(t) {
2017
2489
  if (!t || typeof t != "object")
2018
2490
  return !1;
2019
2491
  const e = t;
2020
2492
  return Number.isFinite(e.x) && Number.isFinite(e.y);
2021
2493
  }
2022
- const Ie = /* @__PURE__ */ new WeakSet();
2023
- function Rt(t) {
2494
+ const Ue = /* @__PURE__ */ new WeakSet();
2495
+ function An(t) {
2024
2496
  return Object.keys(t.dataset).some((e) => e.startsWith("pluno"));
2025
2497
  }
2026
- function Me(t) {
2498
+ function He(t) {
2027
2499
  const e = t.pathname.split("/");
2028
2500
  return e[e.length - 1] ?? "";
2029
2501
  }
2030
- function Dt(t, e) {
2502
+ function Tn(t, e) {
2031
2503
  const n = new URL(t.src, document.baseURI);
2032
- return n.href === e.href || n.pathname === e.pathname ? !0 : Me(n) === Me(e);
2504
+ return n.href === e.href || n.pathname === e.pathname ? !0 : He(n) === He(e);
2033
2505
  }
2034
- class L extends EventTarget {
2506
+ class I extends EventTarget {
2035
2507
  constructor(e, n) {
2036
- super(), this.channelId = n, this.url = e, this.addPreviewListener(nt, () => {
2037
- this.readyState = L.OPEN, this.dispatchEvent(new Event("open"));
2038
- }), this.addPreviewListener(ot, (o) => {
2508
+ super(), this.channelId = n, this.url = e, this.addPreviewListener(Et, () => {
2509
+ this.readyState = I.OPEN, this.dispatchEvent(new Event("open"));
2510
+ }), this.addPreviewListener(kt, (o) => {
2039
2511
  const a = o;
2040
2512
  this.dispatchEvent(new MessageEvent("message", { data: a.detail?.data ?? "" }));
2041
- }), this.addPreviewListener(at, () => {
2042
- this.readyState = L.CLOSED, this.dispatchEvent(new Event("error")), this.cleanup();
2043
- }), this.addPreviewListener(it, (o) => {
2513
+ }), this.addPreviewListener(St, () => {
2514
+ this.readyState = I.CLOSED, this.dispatchEvent(new Event("error")), this.cleanup();
2515
+ }), this.addPreviewListener(Lt, (o) => {
2044
2516
  const a = o;
2045
- this.readyState = L.CLOSED, this.dispatchEvent(
2517
+ this.readyState = I.CLOSED, this.dispatchEvent(
2046
2518
  new CloseEvent("close", {
2047
2519
  code: a.detail?.code ?? 1e3,
2048
2520
  reason: a.detail?.reason ?? "",
@@ -2050,7 +2522,7 @@ class L extends EventTarget {
2050
2522
  })
2051
2523
  ), this.cleanup();
2052
2524
  }), window.dispatchEvent(
2053
- new CustomEvent(V(Qe, this.channelId), {
2525
+ new CustomEvent(Q(yt, this.channelId), {
2054
2526
  detail: { socketId: this.socketId, url: e }
2055
2527
  })
2056
2528
  );
@@ -2065,27 +2537,27 @@ class L extends EventTarget {
2065
2537
  extensions = "";
2066
2538
  binaryType = "blob";
2067
2539
  bufferedAmount = 0;
2068
- readyState = L.CONNECTING;
2069
- socketId = Ft();
2540
+ readyState = I.CONNECTING;
2541
+ socketId = Nn();
2070
2542
  listeners = /* @__PURE__ */ new Map();
2071
2543
  send(e) {
2072
- if (this.readyState !== L.OPEN)
2073
- throw new DOMException("Product Agent preview websocket is not open", "InvalidStateError");
2544
+ if (this.readyState !== I.OPEN)
2545
+ throw new DOMException("Pluno preview websocket is not open", "InvalidStateError");
2074
2546
  window.dispatchEvent(
2075
- new CustomEvent(V(et, this.channelId), {
2547
+ new CustomEvent(Q(vt, this.channelId), {
2076
2548
  detail: { socketId: this.socketId, data: typeof e == "string" ? e : String(e) }
2077
2549
  })
2078
2550
  );
2079
2551
  }
2080
2552
  close(e, n) {
2081
- this.readyState !== L.CLOSED && (this.readyState = L.CLOSING, window.dispatchEvent(
2082
- new CustomEvent(V(tt, this.channelId), {
2553
+ this.readyState !== I.CLOSED && (this.readyState = I.CLOSING, window.dispatchEvent(
2554
+ new CustomEvent(Q(Ct, this.channelId), {
2083
2555
  detail: { socketId: this.socketId, code: e, reason: n }
2084
2556
  })
2085
2557
  ), this.cleanup());
2086
2558
  }
2087
2559
  addPreviewListener(e, n) {
2088
- const o = V(e, this.channelId), a = (i) => {
2560
+ const o = Q(e, this.channelId), a = (i) => {
2089
2561
  i.detail?.socketId === this.socketId && n(i);
2090
2562
  };
2091
2563
  this.listeners.set(o, a), window.addEventListener(o, a);
@@ -2096,36 +2568,36 @@ class L extends EventTarget {
2096
2568
  this.listeners.clear();
2097
2569
  }
2098
2570
  }
2099
- function Ft() {
2100
- const t = window.sessionStorage.getItem(fe);
2571
+ function Nn() {
2572
+ const t = window.sessionStorage.getItem(Ee);
2101
2573
  if (t)
2102
2574
  return t;
2103
2575
  const e = crypto.randomUUID();
2104
- return window.sessionStorage.setItem(fe, e), e;
2576
+ return window.sessionStorage.setItem(Ee, e), e;
2105
2577
  }
2106
- function V(t, e) {
2578
+ function Q(t, e) {
2107
2579
  return `${t}:${e}`;
2108
2580
  }
2109
- function $t(t) {
2581
+ function In(t) {
2110
2582
  const e = document.currentScript;
2111
2583
  if (e instanceof HTMLScriptElement)
2112
2584
  return [e];
2113
2585
  const n = new URL(t, document.baseURI).href, o = new URL(n);
2114
2586
  return Array.from(document.querySelectorAll("script[type='module'][src]")).filter(
2115
- (a) => a instanceof HTMLScriptElement && Rt(a) && Dt(a, o)
2587
+ (a) => a instanceof HTMLScriptElement && An(a) && Tn(a, o)
2116
2588
  );
2117
2589
  }
2118
- function Gt(t) {
2119
- for (const e of $t(t)) {
2120
- if (Ie.has(e) || e.dataset.plunoAutoMount === "false")
2590
+ function Rn(t) {
2591
+ for (const e of In(t)) {
2592
+ if (Ue.has(e) || e.dataset.plunoAutoMount === "false")
2121
2593
  continue;
2122
- Ie.add(e);
2594
+ Ue.add(e);
2123
2595
  const n = e.dataset.plunoPreviewChannel;
2124
- mt({
2596
+ Ut({
2125
2597
  token: e.dataset.plunoToken,
2126
2598
  tokenEndpoint: e.dataset.plunoTokenEndpoint,
2127
2599
  backendUrl: e.dataset.plunoBackendUrl,
2128
- webSocketFactory: n ? wt(n) : void 0,
2600
+ webSocketFactory: n ? Wt(n) : void 0,
2129
2601
  launcherLabel: e.dataset.plunoLauncherLabel,
2130
2602
  accentColor: e.dataset.plunoAccentColor,
2131
2603
  colorScheme: e.dataset.plunoColorScheme === "dark" ? "dark" : "light",
@@ -2133,12 +2605,12 @@ function Gt(t) {
2133
2605
  scribbleStyle: e.dataset.plunoScribbleStyle === "true",
2134
2606
  position: e.dataset.plunoPosition === "bottom-left" ? "bottom-left" : "bottom-right"
2135
2607
  }).catch((o) => {
2136
- console.error("Failed to mount Pluno Product Agent widget", o);
2608
+ console.error("Failed to mount Pluno widget", o);
2137
2609
  });
2138
2610
  }
2139
2611
  }
2140
- Gt(import.meta.url);
2612
+ Rn(import.meta.url);
2141
2613
  export {
2142
- wt as createProductAgentPreviewBridgeWebSocketFactory,
2143
- mt as mountPlunoProductAgentWidget
2614
+ Wt as createProductAgentPreviewBridgeWebSocketFactory,
2615
+ Ut as mountPlunoProductAgentWidget
2144
2616
  };