@convokitapp/vue-ui 0.4.1 → 0.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.css CHANGED
@@ -11,6 +11,7 @@
11
11
  --ckui-incoming: #f4f4f5;
12
12
  --ckui-outgoing: #18181b;
13
13
  --ckui-outgoing-text: #fafafa;
14
+ --ckui-badge: #18181b;
14
15
  --ckui-radius: 10px;
15
16
  --ckui-avatar-size: 40px;
16
17
  --ckui-font:
@@ -32,6 +33,7 @@
32
33
  --ckui-incoming: inherit;
33
34
  --ckui-outgoing: inherit;
34
35
  --ckui-outgoing-text: inherit;
36
+ --ckui-badge: inherit;
35
37
  --ckui-radius: inherit;
36
38
  --ckui-avatar-size: inherit;
37
39
  --ckui-font: inherit;
@@ -100,7 +102,9 @@
100
102
  }
101
103
  .ckui-conversation-item {
102
104
  display: grid;
103
- grid-template-columns: auto minmax(0, 1fr) auto;
105
+ grid-template-columns: auto minmax(0, 1fr);
106
+ grid-auto-flow: column;
107
+ grid-auto-columns: auto;
104
108
  gap: 12px;
105
109
  align-items: center;
106
110
  width: 100%;
@@ -140,6 +144,38 @@
140
144
  color: var(--ckui-muted);
141
145
  font-size: 12px;
142
146
  }
147
+ .ckui-conversation-item[data-unread] .ckui-conversation-item__body strong {
148
+ font-weight: 700;
149
+ }
150
+ .ckui-conversation-item[data-unread] .ckui-conversation-item__body span {
151
+ color: var(--ckui-text);
152
+ }
153
+ .ckui-conversation-item__meta {
154
+ display: grid;
155
+ flex: 0 0 auto;
156
+ gap: 4px;
157
+ justify-items: end;
158
+ align-self: start;
159
+ padding-top: 2px;
160
+ }
161
+ .ckui-conversation-item__time {
162
+ color: var(--ckui-muted);
163
+ font-size: 11px;
164
+ white-space: nowrap;
165
+ }
166
+ .ckui-unread-badge {
167
+ display: inline-grid;
168
+ place-items: center;
169
+ min-width: 20px;
170
+ height: 20px;
171
+ padding: 0 6px;
172
+ border-radius: 999px;
173
+ background: var(--ckui-badge);
174
+ color: var(--ckui-outgoing-text);
175
+ font-size: 11px;
176
+ font-weight: 600;
177
+ line-height: 1;
178
+ }
143
179
  .ckui-avatar {
144
180
  display: inline-grid;
145
181
  flex: 0 0 auto;
@@ -427,6 +463,15 @@ button.ckui-media-card {
427
463
  --ckui-avatar-size: 30px;
428
464
  font-size: 10px;
429
465
  }
466
+ .ckui[data-density=compact] .ckui-conversation-item__meta {
467
+ align-self: center;
468
+ padding-top: 0;
469
+ }
470
+ .ckui[data-density=compact] .ckui-unread-badge {
471
+ min-width: 18px;
472
+ height: 18px;
473
+ font-size: 10px;
474
+ }
430
475
  .ckui[data-density=compact] .ckui-message-list {
431
476
  gap: 5px;
432
477
  padding: 10px 12px;
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/styles.css"],"sourcesContent":[".ckui-theme,\n.ckui {\n --ckui-background: #fafafa;\n --ckui-surface: #ffffff;\n --ckui-primary: #18181b;\n --ckui-text: #09090b;\n --ckui-muted: #71717a;\n --ckui-border: #e4e4e7;\n --ckui-error: #dc2626;\n --ckui-incoming: #f4f4f5;\n --ckui-outgoing: #18181b;\n --ckui-outgoing-text: #fafafa;\n --ckui-radius: 10px;\n --ckui-avatar-size: 40px;\n --ckui-font: ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, \"Segoe UI\", sans-serif;\n}\n\n.ckui-theme .ckui {\n --ckui-background: inherit;\n --ckui-surface: inherit;\n --ckui-primary: inherit;\n --ckui-text: inherit;\n --ckui-muted: inherit;\n --ckui-border: inherit;\n --ckui-error: inherit;\n --ckui-incoming: inherit;\n --ckui-outgoing: inherit;\n --ckui-outgoing-text: inherit;\n --ckui-radius: inherit;\n --ckui-avatar-size: inherit;\n --ckui-font: inherit;\n}\n\n.ckui,\n.ckui *,\n.ckui *::before,\n.ckui *::after { box-sizing: border-box; }\n\n.ckui { color: var(--ckui-text); font-family: var(--ckui-font); font-size: 14px; line-height: 1.45; }\n.ckui button, .ckui textarea { color: inherit; font: inherit; }\n.ckui button:focus-visible, .ckui textarea:focus-visible { outline: 2px solid color-mix(in srgb, var(--ckui-primary) 38%, white); outline-offset: 2px; }\n\n.ckui-conversation-list,\n.ckui-conversation {\n display: flex;\n min-width: 0;\n min-height: 0;\n height: 100%;\n overflow: hidden;\n flex-direction: column;\n border: 1px solid var(--ckui-border);\n border-radius: var(--ckui-radius);\n background: var(--ckui-surface);\n box-shadow: 0 1px 2px rgb(0 0 0 / 0.04);\n}\n\n.ckui-scroll-area, .ckui-message-list { min-height: 0; overflow: auto; overscroll-behavior: contain; scrollbar-gutter: stable; }\n.ckui-scroll-area { flex: 1; background: var(--ckui-surface); }\n\n.ckui-conversation-list__toolbar {\n display: flex;\n align-items: center;\n justify-content: space-between;\n min-height: 52px;\n padding: 8px 10px 8px 16px;\n border-bottom: 1px solid var(--ckui-border);\n background: var(--ckui-surface);\n color: var(--ckui-text);\n font-size: 14px;\n font-weight: 600;\n letter-spacing: -0.01em;\n}\n\n.ckui-conversation-list__items { display: grid; }\n.ckui-conversation-item {\n display: grid;\n grid-template-columns: auto minmax(0, 1fr) auto;\n gap: 12px;\n align-items: center;\n width: 100%;\n min-height: 68px;\n padding: 10px 14px;\n border: 0;\n border-bottom: 1px solid var(--ckui-border);\n border-radius: 0;\n background: var(--ckui-surface);\n cursor: pointer;\n text-align: left;\n transition: background-color 120ms ease;\n}\n.ckui-conversation-item:hover { background: color-mix(in srgb, var(--ckui-primary) 4%, var(--ckui-surface)); }\n.ckui-conversation-item[data-selected] { background: color-mix(in srgb, var(--ckui-primary) 7%, var(--ckui-surface)); }\n.ckui-conversation-item__body { display: grid; min-width: 0; gap: 2px; }\n.ckui-conversation-item__body strong, .ckui-conversation-item__body span { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-conversation-item__body strong { font-size: 14px; font-weight: 600; letter-spacing: -0.01em; }\n.ckui-conversation-item__body span { color: var(--ckui-muted); font-size: 12px; }\n\n.ckui-avatar {\n display: inline-grid;\n flex: 0 0 auto;\n width: var(--ckui-avatar-size);\n height: var(--ckui-avatar-size);\n overflow: hidden;\n place-items: center;\n border: 1px solid var(--ckui-border);\n border-radius: 999px;\n background: color-mix(in srgb, var(--ckui-primary) 6%, var(--ckui-surface));\n color: var(--ckui-text);\n font-size: 12px;\n font-weight: 600;\n}\n.ckui-avatar__image, .ckui-avatar__fallback { width: 100%; height: 100%; }\n.ckui-avatar__image { object-fit: cover; }\n.ckui-avatar__fallback { display: grid; place-items: center; }\n.ckui-separator { display: none; }\n\n.ckui-icon-button, .ckui-send-button, .ckui-link-button { border: 0; background: transparent; cursor: pointer; }\n.ckui-icon-button { display: inline-grid; flex: 0 0 auto; width: 34px; height: 34px; place-items: center; border-radius: 7px; color: var(--ckui-muted); }\n.ckui-icon-button:hover { background: color-mix(in srgb, var(--ckui-primary) 6%, transparent); color: var(--ckui-text); }\n.ckui-state, .ckui-inline-state { display: flex; align-items: center; justify-content: center; gap: 8px; min-height: 120px; padding: 20px; color: var(--ckui-muted); text-align: center; }\n.ckui-inline-state { min-height: 52px; font-size: 12px; }\n.ckui-state--error, .ckui-conversation-error { color: var(--ckui-error); }\n.ckui-link-button { color: currentColor; font-weight: 600; text-decoration: underline; text-underline-offset: 3px; }\n\n.ckui-conversation-header { display: flex; align-items: center; gap: 10px; min-height: 60px; padding: 8px 12px; border-bottom: 1px solid var(--ckui-border); background: var(--ckui-surface); }\n.ckui-conversation-header__body { display: grid; flex: 1; min-width: 0; gap: 1px; }\n.ckui-conversation-header__body strong { overflow: hidden; font-size: 14px; font-weight: 600; letter-spacing: -0.01em; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-conversation-header__body span { color: var(--ckui-muted); font-size: 12px; }\n.ckui-conversation-error { display: flex; align-items: center; justify-content: space-between; gap: 12px; padding: 8px 14px; border-bottom: 1px solid color-mix(in srgb, var(--ckui-error) 22%, var(--ckui-border)); background: color-mix(in srgb, var(--ckui-error) 5%, var(--ckui-surface)); font-size: 12px; }\n\n.ckui-message-list { display: flex; flex: 1; flex-direction: column; gap: 12px; padding: 18px; background: var(--ckui-background); }\n.ckui-message-row { display: flex; flex-direction: column; align-items: flex-start; }\n.ckui-message-row--outgoing { align-items: flex-end; }\n.ckui-message-bubble { max-width: min(74%, 560px); padding: 9px 12px 7px; border: 1px solid var(--ckui-border); border-radius: calc(var(--ckui-radius) + 2px); background: var(--ckui-incoming); }\n.ckui-message-row--outgoing .ckui-message-bubble { border-color: var(--ckui-outgoing); background: var(--ckui-outgoing); color: var(--ckui-outgoing-text); }\n.ckui-message-sender { display: block; margin-bottom: 3px; color: var(--ckui-muted); font-size: 11px; font-weight: 600; }\n.ckui-message-text { overflow-wrap: anywhere; white-space: pre-wrap; }\n.ckui-message-time { display: flex; align-items: center; justify-content: flex-end; gap: 3px; margin-top: 5px; color: color-mix(in srgb, currentColor 62%, transparent); font-size: 10px; }\n.ckui-read-receipt { min-height: 16px; padding-top: 3px; color: var(--ckui-muted); font-size: 10px; }\n\n.ckui-media { margin-top: 8px; }\n.ckui-media-card { display: flex; align-items: center; gap: 9px; width: 100%; min-width: 210px; padding: 9px; overflow: hidden; border: 1px solid color-mix(in srgb, currentColor 16%, transparent); border-radius: 8px; background: color-mix(in srgb, var(--ckui-surface) 94%, transparent); color: var(--ckui-text); text-align: left; }\nbutton.ckui-media-card { cursor: pointer; }\n.ckui-media-card > span { display: grid; flex: 1; min-width: 0; }\n.ckui-media-card strong, .ckui-media-card small { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-media-card small { color: var(--ckui-muted); }\n.ckui-media-card--image { display: grid; max-width: 330px; padding: 0; }\n.ckui-media-card--image img { display: block; width: 100%; max-height: 280px; object-fit: cover; }\n.ckui-media-name { padding: 0 10px 9px; font-size: 11px; }\n.ckui-media-placeholder { min-height: 120px; place-items: center; padding: 20px; }\n\n.ckui-typing { min-height: 26px; padding: 5px 16px; border-top: 1px solid var(--ckui-border); background: var(--ckui-surface); color: var(--ckui-muted); font-size: 11px; }\n.ckui-composer { display: flex; align-items: flex-end; gap: 8px; padding: 10px 12px; border-top: 1px solid var(--ckui-border); background: var(--ckui-surface); }\n.ckui-composer__input { flex: 1; min-width: 0; min-height: 38px; max-height: 132px; padding: 9px 11px; resize: none; border: 1px solid var(--ckui-border); border-radius: 8px; outline: 0; background: var(--ckui-surface); box-shadow: 0 1px 2px rgb(0 0 0 / 0.03); }\n.ckui-composer__input::placeholder { color: var(--ckui-muted); }\n.ckui-composer__input:focus { border-color: color-mix(in srgb, var(--ckui-primary) 45%, var(--ckui-border)); }\n.ckui-send-button { display: inline-grid; flex: 0 0 auto; width: 38px; height: 38px; place-items: center; border-radius: 8px; background: var(--ckui-primary); color: var(--ckui-outgoing-text); box-shadow: 0 1px 2px rgb(0 0 0 / 0.08); }\n.ckui-send-button:hover:not(:disabled) { opacity: 0.9; }\n.ckui-send-button:disabled, .ckui-icon-button:disabled { cursor: not-allowed; opacity: 0.45; }\n\n.ckui[data-density='compact'] { font-size: 12px; }\n.ckui[data-density='compact'] .ckui-conversation-list__toolbar { min-height: 44px; }\n.ckui[data-density='compact'] .ckui-conversation-item { min-height: 46px; padding: 6px 10px; }\n.ckui[data-density='compact'] .ckui-avatar { --ckui-avatar-size: 30px; font-size: 10px; }\n.ckui[data-density='compact'] .ckui-message-list { gap: 5px; padding: 10px 12px; }\n.ckui[data-density='compact'] .ckui-message-bubble { max-width: 88%; padding: 6px 9px; border-radius: 8px; }\n.ckui[data-density='compact'] .ckui-conversation-header { min-height: 48px; }\n.ckui[data-density='compact'] .ckui-typing { min-height: 22px; padding-block: 3px; }\n.ckui[data-density='compact'] .ckui-composer { padding: 6px 8px; }\n.ckui-spin { animation: ckui-spin 900ms linear infinite; }\n@keyframes ckui-spin { to { transform: rotate(360deg); } }\n@media (prefers-reduced-motion: reduce) { .ckui *, .ckui *::before, .ckui *::after { scroll-behavior: auto !important; transition-duration: .01ms !important; animation-duration: .01ms !important; animation-iteration-count: 1 !important; } }\n@media (max-width: 560px) { .ckui-message-bubble { max-width: 88%; } .ckui-message-list { padding-inline: 12px; } }\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../src/styles.css"],"sourcesContent":[".ckui-theme,\n.ckui {\n --ckui-background: #fafafa;\n --ckui-surface: #ffffff;\n --ckui-primary: #18181b;\n --ckui-text: #09090b;\n --ckui-muted: #71717a;\n --ckui-border: #e4e4e7;\n --ckui-error: #dc2626;\n --ckui-incoming: #f4f4f5;\n --ckui-outgoing: #18181b;\n --ckui-outgoing-text: #fafafa;\n --ckui-badge: #18181b;\n --ckui-radius: 10px;\n --ckui-avatar-size: 40px;\n --ckui-font: ui-sans-serif, system-ui, -apple-system, BlinkMacSystemFont, \"Segoe UI\", sans-serif;\n}\n\n.ckui-theme .ckui {\n --ckui-background: inherit;\n --ckui-surface: inherit;\n --ckui-primary: inherit;\n --ckui-text: inherit;\n --ckui-muted: inherit;\n --ckui-border: inherit;\n --ckui-error: inherit;\n --ckui-incoming: inherit;\n --ckui-outgoing: inherit;\n --ckui-outgoing-text: inherit;\n --ckui-badge: inherit;\n --ckui-radius: inherit;\n --ckui-avatar-size: inherit;\n --ckui-font: inherit;\n}\n\n.ckui,\n.ckui *,\n.ckui *::before,\n.ckui *::after { box-sizing: border-box; }\n\n.ckui { color: var(--ckui-text); font-family: var(--ckui-font); font-size: 14px; line-height: 1.45; }\n.ckui button, .ckui textarea { color: inherit; font: inherit; }\n.ckui button:focus-visible, .ckui textarea:focus-visible { outline: 2px solid color-mix(in srgb, var(--ckui-primary) 38%, white); outline-offset: 2px; }\n\n.ckui-conversation-list,\n.ckui-conversation {\n display: flex;\n min-width: 0;\n min-height: 0;\n height: 100%;\n overflow: hidden;\n flex-direction: column;\n border: 1px solid var(--ckui-border);\n border-radius: var(--ckui-radius);\n background: var(--ckui-surface);\n box-shadow: 0 1px 2px rgb(0 0 0 / 0.04);\n}\n\n.ckui-scroll-area, .ckui-message-list { min-height: 0; overflow: auto; overscroll-behavior: contain; scrollbar-gutter: stable; }\n.ckui-scroll-area { flex: 1; background: var(--ckui-surface); }\n\n.ckui-conversation-list__toolbar {\n display: flex;\n align-items: center;\n justify-content: space-between;\n min-height: 52px;\n padding: 8px 10px 8px 16px;\n border-bottom: 1px solid var(--ckui-border);\n background: var(--ckui-surface);\n color: var(--ckui-text);\n font-size: 14px;\n font-weight: 600;\n letter-spacing: -0.01em;\n}\n\n.ckui-conversation-list__items { display: grid; }\n.ckui-conversation-item {\n display: grid;\n grid-template-columns: auto minmax(0, 1fr);\n grid-auto-flow: column;\n grid-auto-columns: auto;\n gap: 12px;\n align-items: center;\n width: 100%;\n min-height: 68px;\n padding: 10px 14px;\n border: 0;\n border-bottom: 1px solid var(--ckui-border);\n border-radius: 0;\n background: var(--ckui-surface);\n cursor: pointer;\n text-align: left;\n transition: background-color 120ms ease;\n}\n.ckui-conversation-item:hover { background: color-mix(in srgb, var(--ckui-primary) 4%, var(--ckui-surface)); }\n.ckui-conversation-item[data-selected] { background: color-mix(in srgb, var(--ckui-primary) 7%, var(--ckui-surface)); }\n.ckui-conversation-item__body { display: grid; min-width: 0; gap: 2px; }\n.ckui-conversation-item__body strong, .ckui-conversation-item__body span { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-conversation-item__body strong { font-size: 14px; font-weight: 600; letter-spacing: -0.01em; }\n.ckui-conversation-item__body span { color: var(--ckui-muted); font-size: 12px; }\n.ckui-conversation-item[data-unread] .ckui-conversation-item__body strong { font-weight: 700; }\n.ckui-conversation-item[data-unread] .ckui-conversation-item__body span { color: var(--ckui-text); }\n.ckui-conversation-item__meta { display: grid; flex: 0 0 auto; gap: 4px; justify-items: end; align-self: start; padding-top: 2px; }\n.ckui-conversation-item__time { color: var(--ckui-muted); font-size: 11px; white-space: nowrap; }\n.ckui-unread-badge { display: inline-grid; place-items: center; min-width: 20px; height: 20px; padding: 0 6px; border-radius: 999px; background: var(--ckui-badge); color: var(--ckui-outgoing-text); font-size: 11px; font-weight: 600; line-height: 1; }\n\n.ckui-avatar {\n display: inline-grid;\n flex: 0 0 auto;\n width: var(--ckui-avatar-size);\n height: var(--ckui-avatar-size);\n overflow: hidden;\n place-items: center;\n border: 1px solid var(--ckui-border);\n border-radius: 999px;\n background: color-mix(in srgb, var(--ckui-primary) 6%, var(--ckui-surface));\n color: var(--ckui-text);\n font-size: 12px;\n font-weight: 600;\n}\n.ckui-avatar__image, .ckui-avatar__fallback { width: 100%; height: 100%; }\n.ckui-avatar__image { object-fit: cover; }\n.ckui-avatar__fallback { display: grid; place-items: center; }\n.ckui-separator { display: none; }\n\n.ckui-icon-button, .ckui-send-button, .ckui-link-button { border: 0; background: transparent; cursor: pointer; }\n.ckui-icon-button { display: inline-grid; flex: 0 0 auto; width: 34px; height: 34px; place-items: center; border-radius: 7px; color: var(--ckui-muted); }\n.ckui-icon-button:hover { background: color-mix(in srgb, var(--ckui-primary) 6%, transparent); color: var(--ckui-text); }\n.ckui-state, .ckui-inline-state { display: flex; align-items: center; justify-content: center; gap: 8px; min-height: 120px; padding: 20px; color: var(--ckui-muted); text-align: center; }\n.ckui-inline-state { min-height: 52px; font-size: 12px; }\n.ckui-state--error, .ckui-conversation-error { color: var(--ckui-error); }\n.ckui-link-button { color: currentColor; font-weight: 600; text-decoration: underline; text-underline-offset: 3px; }\n\n.ckui-conversation-header { display: flex; align-items: center; gap: 10px; min-height: 60px; padding: 8px 12px; border-bottom: 1px solid var(--ckui-border); background: var(--ckui-surface); }\n.ckui-conversation-header__body { display: grid; flex: 1; min-width: 0; gap: 1px; }\n.ckui-conversation-header__body strong { overflow: hidden; font-size: 14px; font-weight: 600; letter-spacing: -0.01em; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-conversation-header__body span { color: var(--ckui-muted); font-size: 12px; }\n.ckui-conversation-error { display: flex; align-items: center; justify-content: space-between; gap: 12px; padding: 8px 14px; border-bottom: 1px solid color-mix(in srgb, var(--ckui-error) 22%, var(--ckui-border)); background: color-mix(in srgb, var(--ckui-error) 5%, var(--ckui-surface)); font-size: 12px; }\n\n.ckui-message-list { display: flex; flex: 1; flex-direction: column; gap: 12px; padding: 18px; background: var(--ckui-background); }\n.ckui-message-row { display: flex; flex-direction: column; align-items: flex-start; }\n.ckui-message-row--outgoing { align-items: flex-end; }\n.ckui-message-bubble { max-width: min(74%, 560px); padding: 9px 12px 7px; border: 1px solid var(--ckui-border); border-radius: calc(var(--ckui-radius) + 2px); background: var(--ckui-incoming); }\n.ckui-message-row--outgoing .ckui-message-bubble { border-color: var(--ckui-outgoing); background: var(--ckui-outgoing); color: var(--ckui-outgoing-text); }\n.ckui-message-sender { display: block; margin-bottom: 3px; color: var(--ckui-muted); font-size: 11px; font-weight: 600; }\n.ckui-message-text { overflow-wrap: anywhere; white-space: pre-wrap; }\n.ckui-message-time { display: flex; align-items: center; justify-content: flex-end; gap: 3px; margin-top: 5px; color: color-mix(in srgb, currentColor 62%, transparent); font-size: 10px; }\n.ckui-read-receipt { min-height: 16px; padding-top: 3px; color: var(--ckui-muted); font-size: 10px; }\n\n.ckui-media { margin-top: 8px; }\n.ckui-media-card { display: flex; align-items: center; gap: 9px; width: 100%; min-width: 210px; padding: 9px; overflow: hidden; border: 1px solid color-mix(in srgb, currentColor 16%, transparent); border-radius: 8px; background: color-mix(in srgb, var(--ckui-surface) 94%, transparent); color: var(--ckui-text); text-align: left; }\nbutton.ckui-media-card { cursor: pointer; }\n.ckui-media-card > span { display: grid; flex: 1; min-width: 0; }\n.ckui-media-card strong, .ckui-media-card small { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }\n.ckui-media-card small { color: var(--ckui-muted); }\n.ckui-media-card--image { display: grid; max-width: 330px; padding: 0; }\n.ckui-media-card--image img { display: block; width: 100%; max-height: 280px; object-fit: cover; }\n.ckui-media-name { padding: 0 10px 9px; font-size: 11px; }\n.ckui-media-placeholder { min-height: 120px; place-items: center; padding: 20px; }\n\n.ckui-typing { min-height: 26px; padding: 5px 16px; border-top: 1px solid var(--ckui-border); background: var(--ckui-surface); color: var(--ckui-muted); font-size: 11px; }\n.ckui-composer { display: flex; align-items: flex-end; gap: 8px; padding: 10px 12px; border-top: 1px solid var(--ckui-border); background: var(--ckui-surface); }\n.ckui-composer__input { flex: 1; min-width: 0; min-height: 38px; max-height: 132px; padding: 9px 11px; resize: none; border: 1px solid var(--ckui-border); border-radius: 8px; outline: 0; background: var(--ckui-surface); box-shadow: 0 1px 2px rgb(0 0 0 / 0.03); }\n.ckui-composer__input::placeholder { color: var(--ckui-muted); }\n.ckui-composer__input:focus { border-color: color-mix(in srgb, var(--ckui-primary) 45%, var(--ckui-border)); }\n.ckui-send-button { display: inline-grid; flex: 0 0 auto; width: 38px; height: 38px; place-items: center; border-radius: 8px; background: var(--ckui-primary); color: var(--ckui-outgoing-text); box-shadow: 0 1px 2px rgb(0 0 0 / 0.08); }\n.ckui-send-button:hover:not(:disabled) { opacity: 0.9; }\n.ckui-send-button:disabled, .ckui-icon-button:disabled { cursor: not-allowed; opacity: 0.45; }\n\n.ckui[data-density='compact'] { font-size: 12px; }\n.ckui[data-density='compact'] .ckui-conversation-list__toolbar { min-height: 44px; }\n.ckui[data-density='compact'] .ckui-conversation-item { min-height: 46px; padding: 6px 10px; }\n.ckui[data-density='compact'] .ckui-avatar { --ckui-avatar-size: 30px; font-size: 10px; }\n.ckui[data-density='compact'] .ckui-conversation-item__meta { align-self: center; padding-top: 0; }\n.ckui[data-density='compact'] .ckui-unread-badge { min-width: 18px; height: 18px; font-size: 10px; }\n.ckui[data-density='compact'] .ckui-message-list { gap: 5px; padding: 10px 12px; }\n.ckui[data-density='compact'] .ckui-message-bubble { max-width: 88%; padding: 6px 9px; border-radius: 8px; }\n.ckui[data-density='compact'] .ckui-conversation-header { min-height: 48px; }\n.ckui[data-density='compact'] .ckui-typing { min-height: 22px; padding-block: 3px; }\n.ckui[data-density='compact'] .ckui-composer { padding: 6px 8px; }\n.ckui-spin { animation: ckui-spin 900ms linear infinite; }\n@keyframes ckui-spin { to { transform: rotate(360deg); } }\n@media (prefers-reduced-motion: reduce) { .ckui *, .ckui *::before, .ckui *::after { scroll-behavior: auto !important; transition-duration: .01ms !important; animation-duration: .01ms !important; animation-iteration-count: 1 !important; } }\n@media (max-width: 560px) { .ckui-message-bubble { max-width: 88%; } .ckui-message-list { padding-inline: 12px; } }\n"],"mappings":"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","names":[]}
package/dist/index.d.cts CHANGED
@@ -1,4 +1,4 @@
1
- import { Conversation as Conversation$1, MessageListOptions, Message, SendMessageInput, RealtimeConnectionHandlers, RealtimeSubscription, MessageEvent, MessageDeletedEvent, ReadEvent, TypingEvent, MessageMedia, ConvoKitClient } from '@convokitapp/sdk';
1
+ import { Conversation as Conversation$1, InboxPage, MessageListOptions, Message, SendMessageInput, MarkConversationReadOptions, RealtimeConnectionHandlers, RealtimeSubscription, MessageEvent, MessageDeletedEvent, ReadEvent, TypingEvent, ReadPosition, InboxSummary, MessageMedia, ConvoKitClient, InboxEntry } from '@convokitapp/sdk';
2
2
  import * as vue from 'vue';
3
3
  import { CSSProperties, HTMLAttributes, Ref, VNodeChild, PropType, MaybeRefOrGetter, TextareaHTMLAttributes } from 'vue';
4
4
 
@@ -11,13 +11,26 @@ interface ConvoKitUiClient {
11
11
  offset: number;
12
12
  archived: boolean;
13
13
  }): Promise<Conversation$1[]>;
14
+ /** Activity-ordered inbox pages with a preview, unread count and read state per row (core 0.6). Pass the previous
15
+ * `nextCursor` back as `cursor` (null for the head). Adapters without it, and custom page loaders, use the legacy
16
+ * `getConversations` path without summaries; a 404 from this endpoint falls back to that path for the store's life.
17
+ */
18
+ listInbox?(options: {
19
+ limit: number;
20
+ cursor: string | null;
21
+ archived: boolean;
22
+ }): Promise<InboxPage>;
14
23
  getConversation(conversationId: string): Promise<Conversation$1>;
15
24
  /** Newest first, with a paired value cursor; never derive an offset from rendered rows. */
16
25
  getMessages(options: MessageListOptions): Promise<Message[]>;
17
26
  /** Complete authorized message, including related media absent from raw row events. */
18
27
  getMessage(id: string): Promise<Message>;
19
28
  sendMessage(input: SendMessageInput): Promise<Message>;
20
- markConversationRead(conversationId: string): Promise<void>;
29
+ /** Acknowledge through `options.throughMessageId` (the newest rendered row). Custom adapters must forward it
30
+ * and reject a missing target with `code: 'MESSAGE_NOT_FOUND'` (or a 404 without a code); the UI never sends a
31
+ * request without a target. Membership failures keep their error code, if any, so they surface as errors.
32
+ */
33
+ markConversationRead(conversationId: string, options?: MarkConversationReadOptions): Promise<void>;
21
34
  sendTyping(input: {
22
35
  conversationId: string;
23
36
  isTyping: boolean;
@@ -25,6 +38,10 @@ interface ConvoKitUiClient {
25
38
  onConnectionEvent(handlers: RealtimeConnectionHandlers): RealtimeSubscription;
26
39
  /** Notify on inbox mutations AND on initial subscription/reconnect. No room data in the signal. */
27
40
  onInboxChanged(handler: () => void, onError?: (error: Error) => void): RealtimeSubscription;
41
+ /** Message inserts/edits and read-position advances in the caller's rooms; never fires on join/rejoin. The list
42
+ * store throttles these (`activityRefreshWindowMs`); room stores ignore them.
43
+ */
44
+ onInboxActivity?(handler: () => void, onError?: (error: Error) => void): RealtimeSubscription;
28
45
  onMessage(conversationId: string, handler: (event: MessageEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
29
46
  onMessageDeleted(conversationId: string, handler: (event: MessageDeletedEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
30
47
  onReadReceipt(conversationId: string, handler: (event: ReadEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
@@ -47,6 +64,10 @@ interface ConversationPageRequest {
47
64
  type ConversationPageLoader = (request: ConversationPageRequest) => Promise<Conversation$1[]>;
48
65
  interface ConversationListState {
49
66
  conversations: Readonly<Ref<Conversation$1[]>>;
67
+ /** Per-room preview, unread count and read state by conversation ID; empty on the legacy `getConversations` path. */
68
+ summaries: Readonly<Ref<ReadonlyMap<string, InboxSummary>>>;
69
+ /** The bound session's user; `''` without a session, on the legacy path and after disposal. */
70
+ currentUserId: Readonly<Ref<string>>;
50
71
  filter: Readonly<Ref<ConversationFilter>>;
51
72
  isInitialLoading: Readonly<Ref<boolean>>;
52
73
  isLoadingMore: Readonly<Ref<boolean>>;
@@ -58,7 +79,10 @@ interface ConversationState {
58
79
  conversation: Readonly<Ref<Conversation$1 | null>>;
59
80
  messages: Readonly<Ref<Message[]>>;
60
81
  typingUserIds: Readonly<Ref<ReadonlySet<string>>>;
82
+ /** Last acknowledgement time per user; kept for custom renderers. */
61
83
  readAtByUserId: Readonly<Ref<ReadonlyMap<string, Date>>>;
84
+ /** Monotonic read-through position per user; `readerIdsFor` prefers it over `readAtByUserId`. */
85
+ readPositionByUserId: Readonly<Ref<ReadonlyMap<string, ReadPosition>>>;
62
86
  isInitialLoading: Readonly<Ref<boolean>>;
63
87
  isLoadingOlder: Readonly<Ref<boolean>>;
64
88
  isReconciling: Readonly<Ref<boolean>>;
@@ -82,6 +106,10 @@ interface ConversationItemSlotProps {
82
106
  index: number;
83
107
  selected: boolean;
84
108
  select: () => void;
109
+ /** Present when the list carries an inbox summary for this row (0.6.0). */
110
+ summary?: InboxSummary;
111
+ /** Present when the list knows the viewer (0.6.0); compare with `summary.latestMessage.senderId`. */
112
+ currentUserId?: string;
85
113
  }
86
114
  interface MessageSlotProps {
87
115
  message: Message;
@@ -171,7 +199,10 @@ interface ConversationController extends ConversationState {
171
199
  text?: string;
172
200
  media?: MessageMedia[];
173
201
  }): Promise<Message | null>;
202
+ /** Acknowledge through the newest rendered message now; no request is sent while nothing is rendered. */
174
203
  markRead(): Promise<void>;
204
+ /** Automatic acknowledgements pause while hidden and resume when the view becomes visible again. */
205
+ setVisible(visible: boolean): void;
175
206
  updateTyping(isTyping: boolean): Promise<void>;
176
207
  dispose(): Promise<void>;
177
208
  }
@@ -185,6 +216,7 @@ interface ConversationViewProps extends ConvoKitAppearanceProps {
185
216
  onSendMessage: (text: string) => boolean | void | Promise<boolean | void>;
186
217
  typingUserIds?: ReadonlySet<string>;
187
218
  readAtByUserId?: ReadonlyMap<string, Date>;
219
+ readPositionByUserId?: ReadonlyMap<string, ReadPosition>;
188
220
  readersResolver?: (message: Message) => ReadonlySet<string>;
189
221
  onBack?: () => void;
190
222
  onRefresh?: () => void | Promise<void>;
@@ -239,6 +271,10 @@ declare const ConversationView: vue.DefineComponent<vue.ExtractPropTypes<{
239
271
  readonly type: PropType<ReadonlyMap<string, Date>>;
240
272
  readonly default: () => Map<any, any>;
241
273
  };
274
+ readonly readPositionByUserId: {
275
+ readonly type: PropType<ReadonlyMap<string, ReadPosition>>;
276
+ readonly default: () => Map<any, any>;
277
+ };
242
278
  readonly readersResolver: {
243
279
  readonly type: PropType<(message: Message) => ReadonlySet<string>>;
244
280
  readonly default: undefined;
@@ -382,6 +418,10 @@ declare const ConversationView: vue.DefineComponent<vue.ExtractPropTypes<{
382
418
  readonly type: PropType<ReadonlyMap<string, Date>>;
383
419
  readonly default: () => Map<any, any>;
384
420
  };
421
+ readonly readPositionByUserId: {
422
+ readonly type: PropType<ReadonlyMap<string, ReadPosition>>;
423
+ readonly default: () => Map<any, any>;
424
+ };
385
425
  readonly readersResolver: {
386
426
  readonly type: PropType<(message: Message) => ReadonlySet<string>>;
387
427
  readonly default: undefined;
@@ -510,6 +550,7 @@ declare const ConversationView: vue.DefineComponent<vue.ExtractPropTypes<{
510
550
  }>, {
511
551
  readonly typingUserIds: ReadonlySet<string>;
512
552
  readonly readAtByUserId: ReadonlyMap<string, Date>;
553
+ readonly readPositionByUserId: ReadonlyMap<string, ReadPosition>;
513
554
  readonly isInitialLoading: boolean;
514
555
  readonly isLoadingOlder: boolean;
515
556
  readonly isSending: boolean;
@@ -538,7 +579,7 @@ declare const ConversationView: vue.DefineComponent<vue.ExtractPropTypes<{
538
579
  readonly defaultDraft: string;
539
580
  readonly onDraftChange: (value: string) => void;
540
581
  }, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
541
- interface ConversationProps extends Omit<ConversationViewProps, 'conversation' | 'messages' | 'currentUserId' | 'onSendMessage' | 'typingUserIds' | 'readAtByUserId' | 'onRefresh' | 'onLoadOlder' | 'onTypingChange' | 'isInitialLoading' | 'isLoadingOlder' | 'isSending' | 'hasOlderMessages' | 'error'>, Omit<UseConversationOptions, 'client' | 'conversationId'> {
582
+ interface ConversationProps extends Omit<ConversationViewProps, 'conversation' | 'messages' | 'currentUserId' | 'onSendMessage' | 'typingUserIds' | 'readAtByUserId' | 'readPositionByUserId' | 'onRefresh' | 'onLoadOlder' | 'onTypingChange' | 'isInitialLoading' | 'isLoadingOlder' | 'isSending' | 'hasOlderMessages' | 'error'>, Omit<UseConversationOptions, 'client' | 'conversationId'> {
542
583
  client: ConvoKitUiClient;
543
584
  conversationId: string;
544
585
  onControllerChange?: (controller: ConversationController) => void;
@@ -601,6 +642,10 @@ declare const Conversation: vue.DefineComponent<vue.ExtractPropTypes<{
601
642
  readonly type: PropType<ReadonlyMap<string, Date>>;
602
643
  readonly default: () => Map<any, any>;
603
644
  };
645
+ readPositionByUserId: {
646
+ readonly type: PropType<ReadonlyMap<string, ReadPosition>>;
647
+ readonly default: () => Map<any, any>;
648
+ };
604
649
  readersResolver: {
605
650
  readonly type: PropType<(message: Message) => ReadonlySet<string>>;
606
651
  readonly default: undefined;
@@ -776,6 +821,10 @@ declare const Conversation: vue.DefineComponent<vue.ExtractPropTypes<{
776
821
  readonly type: PropType<ReadonlyMap<string, Date>>;
777
822
  readonly default: () => Map<any, any>;
778
823
  };
824
+ readPositionByUserId: {
825
+ readonly type: PropType<ReadonlyMap<string, ReadPosition>>;
826
+ readonly default: () => Map<any, any>;
827
+ };
779
828
  readersResolver: {
780
829
  readonly type: PropType<(message: Message) => ReadonlySet<string>>;
781
830
  readonly default: undefined;
@@ -907,6 +956,7 @@ declare const Conversation: vue.DefineComponent<vue.ExtractPropTypes<{
907
956
  conversation: Conversation$1;
908
957
  typingUserIds: ReadonlySet<string>;
909
958
  readAtByUserId: ReadonlyMap<string, Date>;
959
+ readPositionByUserId: ReadonlyMap<string, ReadPosition>;
910
960
  isInitialLoading: boolean;
911
961
  isLoadingOlder: boolean;
912
962
  isSending: boolean;
@@ -950,6 +1000,8 @@ interface UseConversationListOptions {
950
1000
  initialFilter?: ConversationFilter;
951
1001
  pageSize?: number;
952
1002
  autoLoad?: boolean;
1003
+ /** Max-wait window (ms) that coalesces `inbox_activity` signals into one refresh; default 500, 0 = immediate. */
1004
+ activityRefreshWindowMs?: number;
953
1005
  }
954
1006
  interface ConversationListController extends ConversationListState {
955
1007
  loadInitial(): Promise<void>;
@@ -963,6 +1015,10 @@ declare function useConversationList(options: UseConversationListOptions): Conve
963
1015
 
964
1016
  interface ConversationListViewProps extends ConvoKitAppearanceProps {
965
1017
  conversations: readonly Conversation$1[];
1018
+ /** Inbox summaries by conversation ID (0.6.0). Rows with one show a preview, time and unread badge. */
1019
+ summaries?: ReadonlyMap<string, InboxSummary>;
1020
+ /** The viewer; a preview from them reads `You: …`. Absent → no prefix. */
1021
+ currentUserId?: string;
966
1022
  selectedConversationId?: string;
967
1023
  onConversationSelect?: (conversation: Conversation$1) => void;
968
1024
  onRefresh?: () => void | Promise<void>;
@@ -983,6 +1039,14 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
983
1039
  readonly type: PropType<readonly Conversation$1[]>;
984
1040
  readonly required: true;
985
1041
  };
1042
+ readonly summaries: {
1043
+ readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
1044
+ readonly default: undefined;
1045
+ };
1046
+ readonly currentUserId: {
1047
+ readonly type: StringConstructor;
1048
+ readonly default: undefined;
1049
+ };
986
1050
  readonly selectedConversationId: {
987
1051
  readonly type: StringConstructor;
988
1052
  readonly default: undefined;
@@ -1054,6 +1118,14 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
1054
1118
  readonly type: PropType<readonly Conversation$1[]>;
1055
1119
  readonly required: true;
1056
1120
  };
1121
+ readonly summaries: {
1122
+ readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
1123
+ readonly default: undefined;
1124
+ };
1125
+ readonly currentUserId: {
1126
+ readonly type: StringConstructor;
1127
+ readonly default: undefined;
1128
+ };
1057
1129
  readonly selectedConversationId: {
1058
1130
  readonly type: StringConstructor;
1059
1131
  readonly default: undefined;
@@ -1120,6 +1192,7 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
1120
1192
  "onLoad-more"?: () => any;
1121
1193
  }>, {
1122
1194
  readonly isInitialLoading: boolean;
1195
+ readonly currentUserId: string;
1123
1196
  readonly scrollElement: Ref<HTMLElement | null, HTMLElement | null>;
1124
1197
  readonly paginationThreshold: number;
1125
1198
  readonly classNames: Partial<Record<ConvoKitUiPart, string>>;
@@ -1127,6 +1200,7 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
1127
1200
  readonly density: ConvoKitUiDensity;
1128
1201
  readonly unstyled: boolean;
1129
1202
  readonly onRefresh: () => void | Promise<void>;
1203
+ readonly summaries: ReadonlyMap<string, InboxSummary>;
1130
1204
  readonly isLoadingMore: boolean;
1131
1205
  readonly hasMore: boolean;
1132
1206
  readonly selectedConversationId: string;
@@ -1164,10 +1238,22 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
1164
1238
  type: BooleanConstructor;
1165
1239
  default: boolean;
1166
1240
  };
1241
+ activityRefreshWindowMs: {
1242
+ type: NumberConstructor;
1243
+ default: undefined;
1244
+ };
1167
1245
  onControllerChange: {
1168
1246
  type: PropType<(controller: ConversationListController) => void>;
1169
1247
  default: undefined;
1170
1248
  };
1249
+ summaries: {
1250
+ readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
1251
+ readonly default: undefined;
1252
+ };
1253
+ currentUserId: {
1254
+ readonly type: StringConstructor;
1255
+ readonly default: undefined;
1256
+ };
1171
1257
  selectedConversationId: {
1172
1258
  readonly type: StringConstructor;
1173
1259
  readonly default: undefined;
@@ -1255,10 +1341,22 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
1255
1341
  type: BooleanConstructor;
1256
1342
  default: boolean;
1257
1343
  };
1344
+ activityRefreshWindowMs: {
1345
+ type: NumberConstructor;
1346
+ default: undefined;
1347
+ };
1258
1348
  onControllerChange: {
1259
1349
  type: PropType<(controller: ConversationListController) => void>;
1260
1350
  default: undefined;
1261
1351
  };
1352
+ summaries: {
1353
+ readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
1354
+ readonly default: undefined;
1355
+ };
1356
+ currentUserId: {
1357
+ readonly type: StringConstructor;
1358
+ readonly default: undefined;
1359
+ };
1262
1360
  selectedConversationId: {
1263
1361
  readonly type: StringConstructor;
1264
1362
  readonly default: undefined;
@@ -1324,6 +1422,7 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
1324
1422
  "onConversation-select"?: (...args: any[]) => any;
1325
1423
  }>, {
1326
1424
  isInitialLoading: boolean;
1425
+ currentUserId: string;
1327
1426
  scrollElement: Ref<HTMLElement | null, HTMLElement | null>;
1328
1427
  paginationThreshold: number;
1329
1428
  classNames: Partial<Record<ConvoKitUiPart, string>>;
@@ -1334,6 +1433,7 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
1334
1433
  autoLoad: boolean;
1335
1434
  onControllerChange: (controller: ConversationListController) => void;
1336
1435
  conversations: readonly Conversation$1[];
1436
+ summaries: ReadonlyMap<string, InboxSummary>;
1337
1437
  isLoadingMore: boolean;
1338
1438
  hasMore: boolean;
1339
1439
  selectedConversationId: string;
@@ -1343,13 +1443,37 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
1343
1443
  pageLoader: ConversationPageLoader;
1344
1444
  initialFilter: ConversationFilter;
1345
1445
  pageSize: number;
1446
+ activityRefreshWindowMs: number;
1346
1447
  }, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
1347
1448
 
1449
+ /** Whether a message is an optimistic row awaiting server acknowledgement. */
1450
+ declare function isConvoKitPendingMessage(message: Message): boolean;
1451
+ declare function matchesConversation(conversation: Conversation$1, filter: ConversationFilter): boolean;
1452
+ declare function applyConversationFilter(conversations: readonly Conversation$1[], filter: ConversationFilter): Conversation$1[];
1453
+ declare function mergeConversations(current: readonly Conversation$1[], incoming: readonly Conversation$1[]): Conversation$1[];
1454
+ /** Merge inbox pages by conversation ID: a later entry replaces an earlier one (its room moved), and the result is
1455
+ * re-ordered by `(activityAt desc, id desc)`. Server order is authoritative within a page; this is the rule applied
1456
+ * whenever pages are combined (load more, refresh).
1457
+ */
1458
+ declare function mergeInboxEntries(current: readonly InboxEntry[], incoming: readonly InboxEntry[]): InboxEntry[];
1459
+ /** Device-zone clock time, shared by message rows and inbox rows. */
1460
+ declare function formatMessageTime(date: Date): string;
1461
+ declare function mergeMessages(current: readonly Message[], incoming: readonly Message[]): Message[];
1462
+ /** Readers of a message under the unified rule: a user's read position (createdAt, id) wins when present,
1463
+ * otherwise the acknowledgement time is compared with createdAt (legacy participants, empty-room acknowledgements).
1464
+ * The sender and pending rows never have readers.
1465
+ */
1466
+ declare function readerIdsFor(message: Message, readAtByUserId: ReadonlyMap<string, Date>, readPositionByUserId?: ReadonlyMap<string, ReadPosition>): ReadonlySet<string>;
1467
+ declare function formatFileSize(size: number | undefined): string | null;
1468
+
1348
1469
  interface MessageListViewProps extends ConvoKitAppearanceProps {
1349
1470
  conversation: Conversation$1;
1350
1471
  messages: readonly Message[];
1351
1472
  currentUserId: string;
1473
+ /** Acknowledgement times; the fallback for users without a read position. */
1352
1474
  readAtByUserId?: ReadonlyMap<string, Date>;
1475
+ /** Read-through positions; a user's position decides their receipts whenever one is present. */
1476
+ readPositionByUserId?: ReadonlyMap<string, ReadPosition>;
1353
1477
  readersResolver?: (message: Message) => ReadonlySet<string>;
1354
1478
  onLoadOlder?: () => void | Promise<void>;
1355
1479
  hasOlderMessages?: boolean;
@@ -1365,7 +1489,6 @@ interface MessageListViewProps extends ConvoKitAppearanceProps {
1365
1489
  class?: unknown;
1366
1490
  style?: unknown;
1367
1491
  }
1368
- declare function defaultFormatTime(date: Date): string;
1369
1492
  /** Controlled message history with read receipts, structured media, and older-page loading. */
1370
1493
  declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1371
1494
  conversation: {
@@ -1384,6 +1507,10 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1384
1507
  type: PropType<ReadonlyMap<string, Date>>;
1385
1508
  default: () => Map<any, any>;
1386
1509
  };
1510
+ readPositionByUserId: {
1511
+ type: PropType<ReadonlyMap<string, ReadPosition>>;
1512
+ default: () => Map<any, any>;
1513
+ };
1387
1514
  readersResolver: {
1388
1515
  type: PropType<(message: Message) => ReadonlySet<string>>;
1389
1516
  default: undefined;
@@ -1426,7 +1553,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1426
1553
  };
1427
1554
  formatTime: {
1428
1555
  type: PropType<(date: Date) => string>;
1429
- default: typeof defaultFormatTime;
1556
+ default: typeof formatMessageTime;
1430
1557
  };
1431
1558
  imageLoading: {
1432
1559
  type: PropType<"eager" | "lazy">;
@@ -1467,6 +1594,10 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1467
1594
  type: PropType<ReadonlyMap<string, Date>>;
1468
1595
  default: () => Map<any, any>;
1469
1596
  };
1597
+ readPositionByUserId: {
1598
+ type: PropType<ReadonlyMap<string, ReadPosition>>;
1599
+ default: () => Map<any, any>;
1600
+ };
1470
1601
  readersResolver: {
1471
1602
  type: PropType<(message: Message) => ReadonlySet<string>>;
1472
1603
  default: undefined;
@@ -1509,7 +1640,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1509
1640
  };
1510
1641
  formatTime: {
1511
1642
  type: PropType<(date: Date) => string>;
1512
- default: typeof defaultFormatTime;
1643
+ default: typeof formatMessageTime;
1513
1644
  };
1514
1645
  imageLoading: {
1515
1646
  type: PropType<"eager" | "lazy">;
@@ -1537,6 +1668,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1537
1668
  }>, {
1538
1669
  reverse: boolean;
1539
1670
  readAtByUserId: ReadonlyMap<string, Date>;
1671
+ readPositionByUserId: ReadonlyMap<string, ReadPosition>;
1540
1672
  isLoadingOlder: boolean;
1541
1673
  hasOlderMessages: boolean;
1542
1674
  readersResolver: (message: Message) => ReadonlySet<string>;
@@ -1552,7 +1684,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
1552
1684
  density: ConvoKitUiDensity;
1553
1685
  unstyled: boolean;
1554
1686
  }, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
1555
- declare function defaultReadersResolver(readAtByUserId: ReadonlyMap<string, Date>): (message: Message) => ReadonlySet<string>;
1687
+ declare function defaultReadersResolver(readAtByUserId: ReadonlyMap<string, Date>, readPositionByUserId?: ReadonlyMap<string, ReadPosition>): (message: Message) => ReadonlySet<string>;
1556
1688
 
1557
1689
  interface ConvoKitTheme {
1558
1690
  background: string;
@@ -1565,6 +1697,8 @@ interface ConvoKitTheme {
1565
1697
  incomingBubble: string;
1566
1698
  outgoingBubble: string;
1567
1699
  outgoingText: string;
1700
+ /** Unread badge background (0.6.0); its label uses `outgoingText`. Defaults to the primary color. */
1701
+ badge: string;
1568
1702
  radius: string;
1569
1703
  avatarSize: string;
1570
1704
  fontFamily: string;
@@ -1605,13 +1739,4 @@ declare const ConvoKitThemeProvider: vue.DefineComponent<vue.ExtractPropTypes<{
1605
1739
  }, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
1606
1740
  declare function useConvoKitTheme(): Readonly<Ref<ConvoKitTheme>>;
1607
1741
 
1608
- /** Whether a message is an optimistic row awaiting server acknowledgement. */
1609
- declare function isConvoKitPendingMessage(message: Message): boolean;
1610
- declare function matchesConversation(conversation: Conversation$1, filter: ConversationFilter): boolean;
1611
- declare function applyConversationFilter(conversations: readonly Conversation$1[], filter: ConversationFilter): Conversation$1[];
1612
- declare function mergeConversations(current: readonly Conversation$1[], incoming: readonly Conversation$1[]): Conversation$1[];
1613
- declare function mergeMessages(current: readonly Message[], incoming: readonly Message[]): Message[];
1614
- declare function readerIdsFor(message: Message, readAtByUserId: ReadonlyMap<string, Date>): ReadonlySet<string>;
1615
- declare function formatFileSize(size: number | undefined): string | null;
1616
-
1617
- export { type BaseViewProps, type ComposerSlotProps, Conversation, type ConversationController, type ConversationFilter, type ConversationItemSlotProps, ConversationList, type ConversationListController, type ConversationListProps, type ConversationListState, ConversationListView, type ConversationListViewProps, type ConversationPageLoader, type ConversationPageRequest, type ConversationProps, type ConversationState, ConversationView, type ConversationViewProps, type ConvoKitAppearanceProps, ConvoKitAvatar, type ConvoKitTheme, ConvoKitThemeProvider, type ConvoKitUiClient, type ConvoKitUiDensity, type ConvoKitUiPart, type ErrorSlot, type ErrorSlotProps, type MediaSlotProps, MessageListView, type MessageListViewProps, type MessageSlotProps, type ReadReceiptSlotProps, type ScrollOptions, type StateSlot, type TypingSlotProps, type UseConversationListOptions, type UseConversationOptions, applyConversationFilter, createConvoKitUiClient, defaultConvoKitTheme, defaultReadersResolver, formatFileSize, isConvoKitPendingMessage, matchesConversation, mergeConversations, mergeMessages, readerIdsFor, useConversation, useConversationList, useConvoKitTheme };
1742
+ export { type BaseViewProps, type ComposerSlotProps, Conversation, type ConversationController, type ConversationFilter, type ConversationItemSlotProps, ConversationList, type ConversationListController, type ConversationListProps, type ConversationListState, ConversationListView, type ConversationListViewProps, type ConversationPageLoader, type ConversationPageRequest, type ConversationProps, type ConversationState, ConversationView, type ConversationViewProps, type ConvoKitAppearanceProps, ConvoKitAvatar, type ConvoKitTheme, ConvoKitThemeProvider, type ConvoKitUiClient, type ConvoKitUiDensity, type ConvoKitUiPart, type ErrorSlot, type ErrorSlotProps, type MediaSlotProps, MessageListView, type MessageListViewProps, type MessageSlotProps, type ReadReceiptSlotProps, type ScrollOptions, type StateSlot, type TypingSlotProps, type UseConversationListOptions, type UseConversationOptions, applyConversationFilter, createConvoKitUiClient, defaultConvoKitTheme, defaultReadersResolver, formatFileSize, isConvoKitPendingMessage, matchesConversation, mergeConversations, mergeInboxEntries, mergeMessages, readerIdsFor, useConversation, useConversationList, useConvoKitTheme };