@decentnetwork/beagle 0.1.113 → 0.1.115
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/desktop/app.js +266 -19
- package/package.json +2 -2
package/dist/desktop/app.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
window.__DK_UI_VERSION="0.1.
|
|
1
|
+
window.__DK_UI_VERSION="0.1.115";
|
|
2
2
|
"use strict";
|
|
3
3
|
(() => {
|
|
4
4
|
// packages/beagle-ui/dist/beagle-ui.js
|
|
@@ -114,6 +114,8 @@ window.__DK_UI_VERSION="0.1.113";
|
|
|
114
114
|
plug: '<path d="M9 2v6M15 2v6"/><path d="M7 8h10v3a5 5 0 0 1-10 0V8Z"/><path d="M12 16v6"/>',
|
|
115
115
|
// A form with a filled-in field: the glyph for "Fill with Beagle" and any
|
|
116
116
|
// other host app that puts your identity into someone else's page.
|
|
117
|
+
// A pane pinned to the right edge — "keep this beside the page".
|
|
118
|
+
dock: '<rect x="3" y="4" width="18" height="16" rx="2"/><path d="M14 4v16"/><path d="M17 9.5h1.5M17 13h1.5"/>',
|
|
117
119
|
form: '<rect x="4" y="3" width="16" height="18" rx="2"/><path d="M8 8h8M8 12h5"/><path d="M8 16h3"/><path d="m14.5 17.5 1.6 1.6 3.4-3.6"/>'
|
|
118
120
|
});
|
|
119
121
|
var H = {};
|
|
@@ -126,12 +128,16 @@ window.__DK_UI_VERSION="0.1.113";
|
|
|
126
128
|
var hostHideApps = null;
|
|
127
129
|
var hostApps = null;
|
|
128
130
|
var hostProfileSections = null;
|
|
131
|
+
var hostHeaderActions = null;
|
|
132
|
+
var hostIsProtocolMessage = null;
|
|
129
133
|
function setUiHost(host2) {
|
|
130
134
|
H = host2 || {};
|
|
131
135
|
hostTabs = Array.isArray(H.hostTabs) ? H.hostTabs : null;
|
|
132
136
|
hostHideApps = Array.isArray(H.hideApps) ? H.hideApps : null;
|
|
133
137
|
hostApps = Array.isArray(H.hostApps) ? H.hostApps : null;
|
|
134
138
|
hostProfileSections = Array.isArray(H.hostProfileSections) ? H.hostProfileSections : null;
|
|
139
|
+
hostHeaderActions = Array.isArray(H.hostHeaderActions) ? H.hostHeaderActions : null;
|
|
140
|
+
hostIsProtocolMessage = typeof H.isProtocolMessage === "function" ? H.isProtocolMessage : null;
|
|
135
141
|
hostNeedsWelcome = !!H.hostNeedsWelcome;
|
|
136
142
|
hostPrefersRtcFile = !!H.hostPrefersRtcFile;
|
|
137
143
|
hostHasKeyBackup = !!H.hostHasKeyBackup;
|
|
@@ -157,6 +163,140 @@ window.__DK_UI_VERSION="0.1.113";
|
|
|
157
163
|
function DkBrowserNotice(props) {
|
|
158
164
|
return H.DkBrowserNotice ? /* @__PURE__ */ React.createElement(H.DkBrowserNotice, { ...props }) : null;
|
|
159
165
|
}
|
|
166
|
+
function protocolTest(rule) {
|
|
167
|
+
if (typeof rule !== "function")
|
|
168
|
+
return () => false;
|
|
169
|
+
return (msg) => {
|
|
170
|
+
if (!msg)
|
|
171
|
+
return false;
|
|
172
|
+
try {
|
|
173
|
+
const v = rule(msg);
|
|
174
|
+
return typeof v === "string" ? v || true : !!v;
|
|
175
|
+
} catch (e) {
|
|
176
|
+
return false;
|
|
177
|
+
}
|
|
178
|
+
};
|
|
179
|
+
}
|
|
180
|
+
function stripOwnPrefix(text) {
|
|
181
|
+
return String(text == null ? "" : text).replace(/^you:\s*/i, "");
|
|
182
|
+
}
|
|
183
|
+
function lastMessageOf(peer) {
|
|
184
|
+
const raw = String(peer && peer.lastMsg || "");
|
|
185
|
+
return {
|
|
186
|
+
text: stripOwnPrefix(raw),
|
|
187
|
+
dir: peer && peer.lastDir || (/^you:\s*/i.test(raw) ? "out" : "in"),
|
|
188
|
+
ts: peer && peer.lastTs || 0
|
|
189
|
+
};
|
|
190
|
+
}
|
|
191
|
+
function lastIsProtocol(peer, isProto) {
|
|
192
|
+
const last = lastMessageOf(peer);
|
|
193
|
+
if (!last.text)
|
|
194
|
+
return false;
|
|
195
|
+
return isProto(last);
|
|
196
|
+
}
|
|
197
|
+
function newestHumanMessage(msgs, isProto) {
|
|
198
|
+
const arr = msgs || [];
|
|
199
|
+
for (let i = arr.length - 1; i >= 0; i--) {
|
|
200
|
+
const m = arr[i];
|
|
201
|
+
if (!m)
|
|
202
|
+
continue;
|
|
203
|
+
if (m.file)
|
|
204
|
+
return m;
|
|
205
|
+
if (!m.text)
|
|
206
|
+
continue;
|
|
207
|
+
if (isProto({ text: m.text, dir: m.dir, ts: m.ts }))
|
|
208
|
+
continue;
|
|
209
|
+
return m;
|
|
210
|
+
}
|
|
211
|
+
return null;
|
|
212
|
+
}
|
|
213
|
+
function humanUnread(msgs, unread, isProto) {
|
|
214
|
+
const want = Number(unread) || 0;
|
|
215
|
+
if (want <= 0)
|
|
216
|
+
return { count: 0, exact: true };
|
|
217
|
+
const arr = msgs || [];
|
|
218
|
+
const window2 = arr.slice(Math.max(0, arr.length - want));
|
|
219
|
+
let n = 0;
|
|
220
|
+
for (const m of window2) {
|
|
221
|
+
if (!m || m.dir !== "in")
|
|
222
|
+
continue;
|
|
223
|
+
if (m.text && !m.file && isProto({ text: m.text, dir: m.dir, ts: m.ts }))
|
|
224
|
+
continue;
|
|
225
|
+
n++;
|
|
226
|
+
}
|
|
227
|
+
return { count: n, exact: window2.length >= want };
|
|
228
|
+
}
|
|
229
|
+
function rosterRow(peer, isProto, fix) {
|
|
230
|
+
const hidden = lastIsProtocol(peer, isProto);
|
|
231
|
+
if (!hidden) {
|
|
232
|
+
return {
|
|
233
|
+
preview: peer && peer.lastMsg || "",
|
|
234
|
+
lastTime: peer && peer.lastTime || "",
|
|
235
|
+
unread: Number(peer && peer.unread || 0),
|
|
236
|
+
activityTs: Number(peer && peer.lastTs || 0),
|
|
237
|
+
hidden: false
|
|
238
|
+
};
|
|
239
|
+
}
|
|
240
|
+
return {
|
|
241
|
+
preview: fix && fix.preview || "",
|
|
242
|
+
lastTime: fix && fix.lastTime || "",
|
|
243
|
+
unread: fix && fix.unreadExact ? fix.unread : 0,
|
|
244
|
+
activityTs: fix && fix.ts || 0,
|
|
245
|
+
hidden: true,
|
|
246
|
+
pending: !fix
|
|
247
|
+
};
|
|
248
|
+
}
|
|
249
|
+
function rosterUnreadTotal(peers, isProto, fixes) {
|
|
250
|
+
return (peers || []).reduce((n, p) => n + rosterRow(p, isProto, fixes && fixes[p.id]).unread, 0);
|
|
251
|
+
}
|
|
252
|
+
function collapseProtocol(thread, isProto, lang) {
|
|
253
|
+
const out = [];
|
|
254
|
+
let run = null;
|
|
255
|
+
const flush = () => {
|
|
256
|
+
if (!run)
|
|
257
|
+
return;
|
|
258
|
+
out.push({
|
|
259
|
+
protocol: true,
|
|
260
|
+
id: `proto-${run.first.id || run.startIndex}`,
|
|
261
|
+
count: run.items.length,
|
|
262
|
+
label: run.label,
|
|
263
|
+
dir: run.first.from === "me" ? "out" : "in",
|
|
264
|
+
text: run.items.map((m) => m.text).join("\n"),
|
|
265
|
+
line: protocolLine(run, lang)
|
|
266
|
+
});
|
|
267
|
+
run = null;
|
|
268
|
+
};
|
|
269
|
+
(thread || []).forEach((m, i) => {
|
|
270
|
+
const hit = m && !m.day ? isProto({ text: m.text, dir: m && m.from === "me" ? "out" : "in", ts: m && m.ts }) : false;
|
|
271
|
+
if (!hit || m && m.file) {
|
|
272
|
+
flush();
|
|
273
|
+
out.push(m);
|
|
274
|
+
return;
|
|
275
|
+
}
|
|
276
|
+
if (!run)
|
|
277
|
+
run = { first: m, startIndex: i, items: [], label: typeof hit === "string" ? hit : "" };
|
|
278
|
+
if (!run.label && typeof hit === "string")
|
|
279
|
+
run.label = hit;
|
|
280
|
+
run.items.push(m);
|
|
281
|
+
});
|
|
282
|
+
flush();
|
|
283
|
+
return out;
|
|
284
|
+
}
|
|
285
|
+
function protocolLine(run, lang) {
|
|
286
|
+
const arrow = run.first.from === "me" ? "\u2192" : "\u2190";
|
|
287
|
+
const n = run.items.length;
|
|
288
|
+
if (run.label) {
|
|
289
|
+
return `\u2699 ${arrow} ${run.label}${n > 1 ? ` \xB7 ${n}` : ""}`;
|
|
290
|
+
}
|
|
291
|
+
if (n > 1) {
|
|
292
|
+
return lang === "zh" ? `\u2699 ${arrow} ${n} \u6761\u534F\u8BAE\u6D88\u606F` : `\u2699 ${arrow} ${n} protocol messages`;
|
|
293
|
+
}
|
|
294
|
+
return `\u2699 ${arrow} ${protocolSummary(run.first.text)}`;
|
|
295
|
+
}
|
|
296
|
+
function protocolSummary(text, max = 72) {
|
|
297
|
+
const s = String(text == null ? "" : text).replace(/\s+/g, " ").trim();
|
|
298
|
+
return s.length > max ? s.slice(0, max - 1) + "\u2026" : s;
|
|
299
|
+
}
|
|
160
300
|
function dkHash(s) {
|
|
161
301
|
let h = 2166136261;
|
|
162
302
|
for (let i = 0; i < s.length; i++) {
|
|
@@ -388,6 +528,48 @@ window.__DK_UI_VERSION="0.1.113";
|
|
|
388
528
|
components: m.components
|
|
389
529
|
};
|
|
390
530
|
}
|
|
531
|
+
var DK_TAIL_MIN = 30;
|
|
532
|
+
var DK_TAIL_MAX = 200;
|
|
533
|
+
function useProtocolTails(peers, isProtocol, enabled) {
|
|
534
|
+
const [fixes, setFixes] = React.useState({});
|
|
535
|
+
const cache = React.useRef(/* @__PURE__ */ new Map());
|
|
536
|
+
const inFlight = React.useRef(/* @__PURE__ */ new Set());
|
|
537
|
+
React.useEffect(() => {
|
|
538
|
+
if (!enabled)
|
|
539
|
+
return;
|
|
540
|
+
for (const p of peers || []) {
|
|
541
|
+
if (!p || !lastIsProtocol(p, isProtocol))
|
|
542
|
+
continue;
|
|
543
|
+
const unread = Number(p.unread) || 0;
|
|
544
|
+
const key = `${p.lastTs || 0}:${unread}`;
|
|
545
|
+
const had = cache.current.get(p.id);
|
|
546
|
+
if (had && had.key === key)
|
|
547
|
+
continue;
|
|
548
|
+
if (inFlight.current.has(p.id))
|
|
549
|
+
continue;
|
|
550
|
+
const limit = Math.min(DK_TAIL_MAX, Math.max(DK_TAIL_MIN, unread + 5));
|
|
551
|
+
inFlight.current.add(p.id);
|
|
552
|
+
dkGet("/api/chat-history?peer=" + encodeURIComponent(p.id) + "&limit=" + limit).then((d) => {
|
|
553
|
+
const msgs = d && d.chats && d.chats[p.id] || [];
|
|
554
|
+
const human = newestHumanMessage(msgs, isProtocol);
|
|
555
|
+
const count = humanUnread(msgs, unread, isProtocol);
|
|
556
|
+
const fix = {
|
|
557
|
+
preview: human ? (human.dir === "out" ? "you: " : "") + (human.file ? human.file.name : human.text || "") : "",
|
|
558
|
+
lastTime: human ? dkClock(human.ts) : "",
|
|
559
|
+
ts: human ? human.ts : 0,
|
|
560
|
+
unread: count.count,
|
|
561
|
+
unreadExact: count.exact
|
|
562
|
+
};
|
|
563
|
+
cache.current.set(p.id, { key, fix });
|
|
564
|
+
setFixes((f) => Object.assign({}, f, { [p.id]: fix }));
|
|
565
|
+
}).catch(() => {
|
|
566
|
+
}).finally(() => {
|
|
567
|
+
inFlight.current.delete(p.id);
|
|
568
|
+
});
|
|
569
|
+
}
|
|
570
|
+
}, [peers, isProtocol, enabled]);
|
|
571
|
+
return fixes;
|
|
572
|
+
}
|
|
391
573
|
function useDaemonData() {
|
|
392
574
|
const [snap, setSnap] = React.useState({
|
|
393
575
|
me: DK_ME_FALLBACK,
|
|
@@ -1547,8 +1729,9 @@ ${lines}`, { assistant: { kind: "adopt", rows: fresh } }));
|
|
|
1547
1729
|
paddingLeft: 8
|
|
1548
1730
|
} }, r.descr), failed[r.id] && /* @__PURE__ */ React.createElement("div", { style: { fontFamily: "var(--ui)", fontSize: 11, color: "var(--danger)" } }, failed[r.id]), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", gap: 6 } }, /* @__PURE__ */ React.createElement(Btn, { tone: "ok", icon: "check", size: "sm", onClick: () => act(r, "accept"), style: { flex: 1 } }, T.accept), /* @__PURE__ */ React.createElement(Btn, { tone: "danger", icon: "x", size: "sm", onClick: () => act(r, "reject"), style: { flex: 1 } }, T.reject))))));
|
|
1549
1731
|
}
|
|
1550
|
-
function PeerRow({ peer, T, active, onClick, muted }) {
|
|
1732
|
+
function PeerRow({ peer, T, active, onClick, muted, isProtocol, fix }) {
|
|
1551
1733
|
const name = peer.alias || peer.userId;
|
|
1734
|
+
const row = rosterRow(peer, isProtocol || (() => false), fix);
|
|
1552
1735
|
return /* @__PURE__ */ React.createElement("button", { onClick, style: {
|
|
1553
1736
|
display: "flex",
|
|
1554
1737
|
alignItems: "center",
|
|
@@ -1577,12 +1760,13 @@ ${lines}`, { assistant: { kind: "adopt", rows: fresh } }));
|
|
|
1577
1760
|
textOverflow: "ellipsis",
|
|
1578
1761
|
flex: 1,
|
|
1579
1762
|
minWidth: 0
|
|
1580
|
-
} }, dkRowPreview(
|
|
1763
|
+
} }, dkRowPreview(row.preview)))), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", flexDirection: "column", alignItems: "flex-end", gap: 4, flexShrink: 0 } }, /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 10.5, color: "var(--faint)" } }, row.lastTime), row.unread ? /* @__PURE__ */ React.createElement(Unread, { n: row.unread }) : peer.pending ? /* @__PURE__ */ React.createElement(Icon, { name: "clock", size: 11, stroke: 2.2, color: "var(--warn, #d29922)", title: "friend request pending" }) : /* @__PURE__ */ React.createElement(StatusDot, { online: peer.online })));
|
|
1581
1764
|
}
|
|
1582
|
-
function dkActivityTs(p) {
|
|
1583
|
-
|
|
1765
|
+
function dkActivityTs(p, isProtocol, fix) {
|
|
1766
|
+
const row = rosterRow(p, isProtocol || (() => false), fix);
|
|
1767
|
+
return Math.max(row.activityTs, p.acceptedAt || 0, p.requestedAt || 0);
|
|
1584
1768
|
}
|
|
1585
|
-
function PeerSidebar({ T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted, wide }) {
|
|
1769
|
+
function PeerSidebar({ T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted, wide, isProtocol, protocolFix }) {
|
|
1586
1770
|
const [q, setQ] = React.useState("");
|
|
1587
1771
|
const [addr, setAddr] = React.useState("");
|
|
1588
1772
|
const [addState, setAddState] = React.useState(null);
|
|
@@ -1627,7 +1811,8 @@ ${lines}`, { assistant: { kind: "adopt", rows: fresh } }));
|
|
|
1627
1811
|
}).slice().sort((a, b) => {
|
|
1628
1812
|
if (!!a.pinned !== !!b.pinned)
|
|
1629
1813
|
return a.pinned ? -1 : 1;
|
|
1630
|
-
const ta = dkActivityTs(a
|
|
1814
|
+
const ta = dkActivityTs(a, isProtocol, protocolFix && protocolFix[a.id]);
|
|
1815
|
+
const tb = dkActivityTs(b, isProtocol, protocolFix && protocolFix[b.id]);
|
|
1631
1816
|
if (ta !== tb)
|
|
1632
1817
|
return tb - ta;
|
|
1633
1818
|
return String(a.alias || a.userId || "").localeCompare(String(b.alias || b.userId || ""));
|
|
@@ -1666,7 +1851,7 @@ ${lines}`, { assistant: { kind: "adopt", rows: fresh } }));
|
|
|
1666
1851
|
fontSize: 11.5,
|
|
1667
1852
|
lineHeight: 1.35,
|
|
1668
1853
|
color: addState.kind === "err" ? "var(--bad, #e5484d)" : addState.kind === "ok" ? "var(--good, #46a758)" : "var(--faint)"
|
|
1669
|
-
} }, addState.msg), /* @__PURE__ */ React.createElement("div", { style: { position: "relative", display: "flex", alignItems: "center" } }, /* @__PURE__ */ React.createElement(Icon, { name: "search", size: 15, color: "var(--faint)", stroke: 2, style: { position: "absolute", left: 9 } }), /* @__PURE__ */ React.createElement("input", { value: q, onChange: (e) => setQ(e.target.value), placeholder: T.search, style: { ...inputStyle, paddingLeft: 30 } }))), /* @__PURE__ */ React.createElement("div", { style: { flex: 1, overflow: "auto", padding: "10px 8px 16px" } }, /* @__PURE__ */ React.createElement(RequestsBlock, { T, requests, onAct }), /* @__PURE__ */ React.createElement(Section, { label: T.peers, count: `${online}/${peers.length}`, style: { margin: "6px 4px 8px" } }), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", flexDirection: "column", gap: 2 } }, filtered.map((p) => /* @__PURE__ */ React.createElement(PeerRow, { key: p.id, peer: p, T, active: p.id === activeId, onClick: () => onSelect(p.id), muted: !!muted && muted.includes(p.id) })), !filtered.length && /* @__PURE__ */ React.createElement("div", { style: { padding: 16, textAlign: "center", fontFamily: "var(--mono)", fontSize: 12, color: "var(--faint)" } }, "no matches"))));
|
|
1854
|
+
} }, addState.msg), /* @__PURE__ */ React.createElement("div", { style: { position: "relative", display: "flex", alignItems: "center" } }, /* @__PURE__ */ React.createElement(Icon, { name: "search", size: 15, color: "var(--faint)", stroke: 2, style: { position: "absolute", left: 9 } }), /* @__PURE__ */ React.createElement("input", { value: q, onChange: (e) => setQ(e.target.value), placeholder: T.search, style: { ...inputStyle, paddingLeft: 30 } }))), /* @__PURE__ */ React.createElement("div", { style: { flex: 1, overflow: "auto", padding: "10px 8px 16px" } }, /* @__PURE__ */ React.createElement(RequestsBlock, { T, requests, onAct }), /* @__PURE__ */ React.createElement(Section, { label: T.peers, count: `${online}/${peers.length}`, style: { margin: "6px 4px 8px" } }), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", flexDirection: "column", gap: 2 } }, filtered.map((p) => /* @__PURE__ */ React.createElement(PeerRow, { key: p.id, peer: p, T, active: p.id === activeId, onClick: () => onSelect(p.id), muted: !!muted && muted.includes(p.id), isProtocol, fix: protocolFix && protocolFix[p.id] })), !filtered.length && /* @__PURE__ */ React.createElement("div", { style: { padding: 16, textAlign: "center", fontFamily: "var(--mono)", fontSize: 12, color: "var(--faint)" } }, "no matches"))));
|
|
1670
1855
|
}
|
|
1671
1856
|
var inputStyle = {
|
|
1672
1857
|
flex: 1,
|
|
@@ -2666,7 +2851,7 @@ ${lines}`, { assistant: { kind: "adopt", rows: fresh } }));
|
|
|
2666
2851
|
) : mine && m.via === "offline" && m.status !== "queued" && m.status !== "sending" ? /* @__PURE__ */ React.createElement(Icon, { name: "check", size: 12, stroke: 2.2, color: "#f59e0b", title: T.viaOutOffline || "posted to the offline relay \u2014 they get it when they come online" }) : mine && m.status === "sent" && m.confirmed === false ? /* @__PURE__ */ React.createElement(Icon, { name: "check", size: 12, stroke: 2.2, color: "var(--faint)", title: T.sentUnconfirmed || "sent \u2014 not confirmed by the peer" }) : mine && m.status && /* @__PURE__ */ React.createElement(Icon, { name: "checkCheck", size: 12, stroke: 2.2, color: m.status === "read" ? "var(--accent)" : "var(--faint)" })))
|
|
2667
2852
|
);
|
|
2668
2853
|
}
|
|
2669
|
-
function Conversation({ T, peer, lang, peers, onOpenChat, thread: threadProp, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, muted, onToggleMute, phone, onBack }) {
|
|
2854
|
+
function Conversation({ T, peer, lang, peers, onOpenChat, thread: threadProp, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, isProtocol, muted, onToggleMute, phone, onBack }) {
|
|
2670
2855
|
const scrollRef = React.useRef(null);
|
|
2671
2856
|
const prependRef = React.useRef(null);
|
|
2672
2857
|
const [earlierBusy, setEarlierBusy] = React.useState(false);
|
|
@@ -3088,7 +3273,15 @@ ${peer.address}`
|
|
|
3088
3273
|
fontSize: 12.5,
|
|
3089
3274
|
color: "var(--text)"
|
|
3090
3275
|
} }, /* @__PURE__ */ React.createElement(Icon, { name: "clock", size: 13, stroke: 2.2, color: "#d29922" }), /* @__PURE__ */ React.createElement("span", null, T.pendingFriend || "Waiting for them to accept your friend request \u2014 messages will queue and deliver once they do.")),
|
|
3091
|
-
/* @__PURE__ */ React.createElement("div", { ref: scrollRef, onScroll: updateFollowScroll, style: { flex: 1, overflow: "auto", padding: phone ? "12px 10px" : "18px 22px", WebkitOverflowScrolling: "touch" } }, /* @__PURE__ */ React.createElement("div", { style: { maxWidth: 1200, margin: "0 auto" } }, hasEarlier && /* @__PURE__ */ React.createElement("div", { style: { display: "flex", justifyContent: "center", margin: "4px 0 10px" } }, /* @__PURE__ */ React.createElement(Btn, { size: "sm", onClick: loadEarlier, disabled: earlierBusy }, earlierBusy ? T.loadingEarlier || "Loading\u2026" : T.loadEarlier || "Load earlier messages")), thread.filter((m) => m.day || !hidden.has(m.id)).map((m, i) => m.day ? /* @__PURE__ */ React.createElement("div", { key: i, style: { display: "flex", justifyContent: "center", margin: "14px 0" } }, /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 10.5, fontWeight: 600, color: "var(--faint)", background: "var(--chip)", padding: "3px 10px", borderRadius: 999 } }, m.day)) : /* @__PURE__ */ React.createElement(
|
|
3276
|
+
/* @__PURE__ */ React.createElement("div", { ref: scrollRef, onScroll: updateFollowScroll, style: { flex: 1, overflow: "auto", padding: phone ? "12px 10px" : "18px 22px", WebkitOverflowScrolling: "touch" } }, /* @__PURE__ */ React.createElement("div", { style: { maxWidth: 1200, margin: "0 auto" } }, hasEarlier && /* @__PURE__ */ React.createElement("div", { style: { display: "flex", justifyContent: "center", margin: "4px 0 10px" } }, /* @__PURE__ */ React.createElement(Btn, { size: "sm", onClick: loadEarlier, disabled: earlierBusy }, earlierBusy ? T.loadingEarlier || "Loading\u2026" : T.loadEarlier || "Load earlier messages")), collapseProtocol(thread, isProtocol || (() => false), lang).filter((m) => m.day || m.protocol || !hidden.has(m.id)).map((m, i) => m.day ? /* @__PURE__ */ React.createElement("div", { key: i, style: { display: "flex", justifyContent: "center", margin: "14px 0" } }, /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 10.5, fontWeight: 600, color: "var(--faint)", background: "var(--chip)", padding: "3px 10px", borderRadius: 999 } }, m.day)) : m.protocol ? /* @__PURE__ */ React.createElement("div", { key: m.id || i, style: { display: "flex", justifyContent: "center", margin: "4px 0" } }, /* @__PURE__ */ React.createElement("span", { title: m.text, style: {
|
|
3277
|
+
fontFamily: "var(--mono)",
|
|
3278
|
+
fontSize: 10.5,
|
|
3279
|
+
color: "var(--faint)",
|
|
3280
|
+
maxWidth: "86%",
|
|
3281
|
+
whiteSpace: "nowrap",
|
|
3282
|
+
overflow: "hidden",
|
|
3283
|
+
textOverflow: "ellipsis"
|
|
3284
|
+
} }, m.line)) : /* @__PURE__ */ React.createElement(
|
|
3092
3285
|
Msg,
|
|
3093
3286
|
{
|
|
3094
3287
|
key: m.id || i,
|
|
@@ -3259,12 +3452,12 @@ ${peer.address}`
|
|
|
3259
3452
|
function ChatEmpty({ T }) {
|
|
3260
3453
|
return /* @__PURE__ */ React.createElement("div", { style: { flex: 1, display: "flex", flexDirection: "column", alignItems: "center", justifyContent: "center", gap: 12, color: "var(--faint)", background: "var(--bg)" } }, /* @__PURE__ */ React.createElement(Icon, { name: "message", size: 40, stroke: 1.4, color: "var(--line)" }), /* @__PURE__ */ React.createElement("div", { style: { fontFamily: "var(--mono)", fontSize: 13 } }, T.pickPeer));
|
|
3261
3454
|
}
|
|
3262
|
-
function ChatTab({ T, lang, peers, requests, activeId, thread, onSelect, onAct, onAdd, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, prefillAddr, onPrefillConsumed, muted, onToggleMute, phone, onBack }) {
|
|
3455
|
+
function ChatTab({ T, lang, peers, requests, activeId, thread, isProtocol, protocolFix, onSelect, onAct, onAdd, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, prefillAddr, onPrefillConsumed, muted, onToggleMute, phone, onBack }) {
|
|
3263
3456
|
const peer = peers.find((p) => p.id === activeId);
|
|
3264
3457
|
if (phone) {
|
|
3265
|
-
return peer ? /* @__PURE__ */ React.createElement(Conversation, { T, peer, lang, peers, onOpenChat: onSelect, thread, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, muted: !!muted && muted.includes(peer.id), onToggleMute, phone: true, onBack }) : /* @__PURE__ */ React.createElement(PeerSidebar, { T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted, wide: true });
|
|
3458
|
+
return peer ? /* @__PURE__ */ React.createElement(Conversation, { T, peer, lang, peers, onOpenChat: onSelect, thread, isProtocol, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, muted: !!muted && muted.includes(peer.id), onToggleMute, phone: true, onBack }) : /* @__PURE__ */ React.createElement(PeerSidebar, { T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted, isProtocol, protocolFix, wide: true });
|
|
3266
3459
|
}
|
|
3267
|
-
return /* @__PURE__ */ React.createElement("div", { style: { flex: 1, display: "flex", minWidth: 0, minHeight: 0 } }, /* @__PURE__ */ React.createElement(PeerSidebar, { T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted }), peer ? /* @__PURE__ */ React.createElement(Conversation, { T, peer, lang, peers, onOpenChat: onSelect, thread, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, muted: !!muted && muted.includes(peer.id), onToggleMute }) : /* @__PURE__ */ React.createElement(ChatEmpty, { T }));
|
|
3460
|
+
return /* @__PURE__ */ React.createElement("div", { style: { flex: 1, display: "flex", minWidth: 0, minHeight: 0 } }, /* @__PURE__ */ React.createElement(PeerSidebar, { T, peers, requests, activeId, onSelect, onAct, onAdd, prefillAddr, onPrefillConsumed, muted, isProtocol, protocolFix }), peer ? /* @__PURE__ */ React.createElement(Conversation, { T, peer, lang, peers, onOpenChat: onSelect, thread, isProtocol, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread, hasEarlier, onLoadEarlier, onAssistantRemove, onAssistantAdopt, muted: !!muted && muted.includes(peer.id), onToggleMute }) : /* @__PURE__ */ React.createElement(ChatEmpty, { T }));
|
|
3268
3461
|
}
|
|
3269
3462
|
Object.assign(window, { ChatTab });
|
|
3270
3463
|
function CopyBtn({ value, copiedText = "Copied", copyFailedText = "Copy failed", copyTitle = "Copy" }) {
|
|
@@ -5888,7 +6081,7 @@ ${peer.address}`
|
|
|
5888
6081
|
function dkLooking() {
|
|
5889
6082
|
return document.visibilityState === "visible" && document.hasFocus();
|
|
5890
6083
|
}
|
|
5891
|
-
function useIncomingAlerts({ T, peers, requests, loaded, activeId, sound = true, flash = true, muted }) {
|
|
6084
|
+
function useIncomingAlerts({ T, peers, requests, loaded, activeId, sound = true, flash = true, muted, isProtocol }) {
|
|
5892
6085
|
const prev = React.useRef(null);
|
|
5893
6086
|
const mutedRef = React.useRef(/* @__PURE__ */ new Set());
|
|
5894
6087
|
mutedRef.current = new Set(muted || []);
|
|
@@ -5918,7 +6111,8 @@ ${peer.address}`
|
|
|
5918
6111
|
const byId = /* @__PURE__ */ new Map();
|
|
5919
6112
|
for (const p of peers || []) {
|
|
5920
6113
|
const dir = p.lastDir || (String(p.lastMsg || "").startsWith("you: ") ? "out" : "in");
|
|
5921
|
-
|
|
6114
|
+
const quiet = typeof isProtocol === "function" && lastIsProtocol(p, isProtocol);
|
|
6115
|
+
byId.set(p.id, { ts: p.lastTs || 0, dir, quiet });
|
|
5922
6116
|
}
|
|
5923
6117
|
const reqIds = new Set((requests || []).map((r) => r.id));
|
|
5924
6118
|
const was = prev.current;
|
|
@@ -5929,6 +6123,8 @@ ${peer.address}`
|
|
|
5929
6123
|
for (const [id, cur] of byId) {
|
|
5930
6124
|
if (cur.dir !== "in" || !cur.ts)
|
|
5931
6125
|
continue;
|
|
6126
|
+
if (cur.quiet)
|
|
6127
|
+
continue;
|
|
5932
6128
|
const old = was.byId.get(id);
|
|
5933
6129
|
if (old ? cur.ts <= old.ts : Date.now() - cur.ts > 3e4)
|
|
5934
6130
|
continue;
|
|
@@ -6772,6 +6968,8 @@ ${peer.address}`
|
|
|
6772
6968
|
const rowPad = t.density === "comfortable" ? "11px 12px" : "7px 10px";
|
|
6773
6969
|
const mutedIds = Array.isArray(t.alertMuted) ? t.alertMuted : [];
|
|
6774
6970
|
const onToggleMute = (id) => setTweak("alertMuted", mutedIds.includes(id) ? mutedIds.filter((x) => x !== id) : mutedIds.concat(id));
|
|
6971
|
+
const isProtocol = React.useMemo(() => protocolTest(hostIsProtocolMessage), []);
|
|
6972
|
+
const protocolFix = useProtocolTails(peers, isProtocol, !!hostIsProtocolMessage);
|
|
6775
6973
|
useIncomingAlerts({
|
|
6776
6974
|
T,
|
|
6777
6975
|
peers,
|
|
@@ -6780,7 +6978,8 @@ ${peer.address}`
|
|
|
6780
6978
|
activeId,
|
|
6781
6979
|
sound: t.alertSound !== false,
|
|
6782
6980
|
flash: t.alertFlash !== false,
|
|
6783
|
-
muted: mutedIds
|
|
6981
|
+
muted: mutedIds,
|
|
6982
|
+
isProtocol
|
|
6784
6983
|
});
|
|
6785
6984
|
const assistant = useAssistant({
|
|
6786
6985
|
lang: t.lang,
|
|
@@ -6814,6 +7013,54 @@ ${peer.address}`
|
|
|
6814
7013
|
});
|
|
6815
7014
|
const phone = useIsPhone();
|
|
6816
7015
|
const [sharing, setSharing] = React.useState(false);
|
|
7016
|
+
const headerActions = (hostHeaderActions || []).filter((a) => a && a.id && typeof a.onClick === "function");
|
|
7017
|
+
const headerActionBtns = headerActions.map((a) => {
|
|
7018
|
+
let on = false;
|
|
7019
|
+
try {
|
|
7020
|
+
on = typeof a.active === "function" ? !!a.active() : false;
|
|
7021
|
+
} catch (e) {
|
|
7022
|
+
on = false;
|
|
7023
|
+
}
|
|
7024
|
+
const label = pickText(a.label, t.lang, a.id);
|
|
7025
|
+
return /* @__PURE__ */ React.createElement(
|
|
7026
|
+
"button",
|
|
7027
|
+
{
|
|
7028
|
+
key: a.id,
|
|
7029
|
+
title: label,
|
|
7030
|
+
"aria-label": label,
|
|
7031
|
+
"aria-pressed": on,
|
|
7032
|
+
onClick: () => {
|
|
7033
|
+
try {
|
|
7034
|
+
a.onClick({ T, t, me, activeId, phone });
|
|
7035
|
+
} catch (e) {
|
|
7036
|
+
}
|
|
7037
|
+
},
|
|
7038
|
+
style: {
|
|
7039
|
+
width: 32,
|
|
7040
|
+
height: 32,
|
|
7041
|
+
flexShrink: 0,
|
|
7042
|
+
borderRadius: 8,
|
|
7043
|
+
cursor: "pointer",
|
|
7044
|
+
padding: 0,
|
|
7045
|
+
border: "1px solid " + (on ? "var(--accent)" : "var(--line)"),
|
|
7046
|
+
background: on ? "color-mix(in oklab, var(--accent), transparent 86%)" : "transparent",
|
|
7047
|
+
display: "flex",
|
|
7048
|
+
alignItems: "center",
|
|
7049
|
+
justifyContent: "center"
|
|
7050
|
+
}
|
|
7051
|
+
},
|
|
7052
|
+
/* @__PURE__ */ React.createElement(
|
|
7053
|
+
Icon,
|
|
7054
|
+
{
|
|
7055
|
+
name: typeof a.icon === "string" ? a.icon : void 0,
|
|
7056
|
+
svgPath: a.icon && typeof a.icon === "object" ? a.icon.svgPath : void 0,
|
|
7057
|
+
size: 16,
|
|
7058
|
+
stroke: 2,
|
|
7059
|
+
color: on ? "var(--accent)" : "var(--dim)"
|
|
7060
|
+
}
|
|
7061
|
+
)
|
|
7062
|
+
);
|
|
7063
|
+
});
|
|
6817
7064
|
const shareBtn = /* @__PURE__ */ React.createElement(
|
|
6818
7065
|
"button",
|
|
6819
7066
|
{
|
|
@@ -6984,7 +7231,7 @@ ${peer.address}`
|
|
|
6984
7231
|
const lastPeople = React.useRef("here");
|
|
6985
7232
|
if (peopleTab)
|
|
6986
7233
|
lastPeople.current = tab;
|
|
6987
|
-
const unreadTotal = (peers
|
|
7234
|
+
const unreadTotal = rosterUnreadTotal(peers, isProtocol, protocolFix) + (requests || []).length;
|
|
6988
7235
|
const NAV_FOR = {
|
|
6989
7236
|
chat: { icon: "message", label: T.chat, active: tab === "chat", badge: unreadTotal, go: () => setTab("chat") },
|
|
6990
7237
|
people: { icon: "users", label: T.people, active: peopleTab, go: () => setTab(lastPeople.current) },
|
|
@@ -7028,7 +7275,7 @@ ${peer.address}`
|
|
|
7028
7275
|
display: "flex",
|
|
7029
7276
|
border: "1px solid " + (tab === "profile" ? "var(--line)" : "transparent"),
|
|
7030
7277
|
background: tab === "profile" ? "var(--panel-2)" : "transparent"
|
|
7031
|
-
} }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 36, radius: 9 }))), /* @__PURE__ */ React.createElement("div", { style: { flex: 1, minWidth: 0, minHeight: 0, display: "flex", flexDirection: "column" } }, !inConversation && /* @__PURE__ */ React.createElement(DkBrowserNotice, { lang: t.lang }), !inConversation && /* @__PURE__ */ React.createElement("div", { style: { height: 46, boxSizing: "content-box", paddingTop: phone ? "env(safe-area-inset-top, 0px)" : 0, flexShrink: 0, borderBottom: "1px solid var(--line)", background: "var(--panel)", display: "flex", alignItems: "center", gap: phone ? 8 : 12, paddingLeft: phone ? 12 : 16, paddingRight: phone ? 12 : 16 } }, /* @__PURE__ */ React.createElement(Brand, { T, style: { gap: 12, flexShrink: 0 } }, /* @__PURE__ */ React.createElement("svg", { width: 20, height: 20, viewBox: "0 0 24 24", fill: "none", stroke: "var(--accent)", strokeWidth: 2.2, strokeLinecap: "round", strokeLinejoin: "round", style: { display: "block", flexShrink: 0 } }, /* @__PURE__ */ React.createElement("path", { d: "m4.5 17 6-6-6-6" }), /* @__PURE__ */ React.createElement("path", { d: "M12 18.5h7.5" })), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 14, fontWeight: 700, letterSpacing: -0.3, color: "var(--text)" } }, "beagle")), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 12, color: "var(--faint)", whiteSpace: "nowrap" } }, "\xB7 ", (nav.find((n) => n.id === tab) || { label: T.profile }).label.toLowerCase()), /* @__PURE__ */ React.createElement("div", { style: { flex: 1 } }), phone ? /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(StatusDot, { online: me.online }), shareBtn, /* @__PURE__ */ React.createElement("button", { onClick: () => setTab("profile"), title: T.profile, style: { padding: 0, border: "none", background: "transparent", cursor: "pointer", display: "flex" } }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 28, radius: 7, dot: false }))) : /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Tag, { tone: "accent" }, me.channel, " \xB7 lan ", me.lanVer), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", alignItems: "center", gap: 7, padding: "0 4px" } }, /* @__PURE__ */ React.createElement(StatusDot, { online: me.online }), /* @__PURE__ */ React.createElement(Mono, { size: 12.5, copy: me.ip }, me.ip)), /* @__PURE__ */ React.createElement("span", { style: { width: 1, height: 22, background: "var(--line)" } }), shareBtn, /* @__PURE__ */ React.createElement("div", { style: { display: "flex", alignItems: "center", gap: 8 } }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 26, radius: 7 }), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 12.5, fontWeight: 600, color: "var(--text)" } }, me.name)))), phone && peopleTab && /* @__PURE__ */ React.createElement("div", { style: { flexShrink: 0, display: "flex", gap: 6, padding: "8px 12px", borderBottom: "1px solid var(--line)", background: "var(--panel)", overflowX: "auto" } }, nav.filter((n) => DK_PEOPLE_TABS.includes(n.id)).map((n) => /* @__PURE__ */ React.createElement("button", { key: n.id, onClick: () => setTab(n.id), style: {
|
|
7278
|
+
} }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 36, radius: 9 }))), /* @__PURE__ */ React.createElement("div", { style: { flex: 1, minWidth: 0, minHeight: 0, display: "flex", flexDirection: "column" } }, !inConversation && /* @__PURE__ */ React.createElement(DkBrowserNotice, { lang: t.lang }), !inConversation && /* @__PURE__ */ React.createElement("div", { style: { height: 46, boxSizing: "content-box", paddingTop: phone ? "env(safe-area-inset-top, 0px)" : 0, flexShrink: 0, borderBottom: "1px solid var(--line)", background: "var(--panel)", display: "flex", alignItems: "center", gap: phone ? 8 : 12, paddingLeft: phone ? 12 : 16, paddingRight: phone ? 12 : 16 } }, /* @__PURE__ */ React.createElement(Brand, { T, style: { gap: 12, flexShrink: 0 } }, /* @__PURE__ */ React.createElement("svg", { width: 20, height: 20, viewBox: "0 0 24 24", fill: "none", stroke: "var(--accent)", strokeWidth: 2.2, strokeLinecap: "round", strokeLinejoin: "round", style: { display: "block", flexShrink: 0 } }, /* @__PURE__ */ React.createElement("path", { d: "m4.5 17 6-6-6-6" }), /* @__PURE__ */ React.createElement("path", { d: "M12 18.5h7.5" })), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 14, fontWeight: 700, letterSpacing: -0.3, color: "var(--text)" } }, "beagle")), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 12, color: "var(--faint)", whiteSpace: "nowrap" } }, "\xB7 ", (nav.find((n) => n.id === tab) || { label: T.profile }).label.toLowerCase()), /* @__PURE__ */ React.createElement("div", { style: { flex: 1 } }), phone ? /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(StatusDot, { online: me.online }), headerActionBtns, shareBtn, /* @__PURE__ */ React.createElement("button", { onClick: () => setTab("profile"), title: T.profile, style: { padding: 0, border: "none", background: "transparent", cursor: "pointer", display: "flex" } }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 28, radius: 7, dot: false }))) : /* @__PURE__ */ React.createElement(React.Fragment, null, /* @__PURE__ */ React.createElement(Tag, { tone: "accent" }, me.channel, " \xB7 lan ", me.lanVer), /* @__PURE__ */ React.createElement("div", { style: { display: "flex", alignItems: "center", gap: 7, padding: "0 4px" } }, /* @__PURE__ */ React.createElement(StatusDot, { online: me.online }), /* @__PURE__ */ React.createElement(Mono, { size: 12.5, copy: me.ip }, me.ip)), /* @__PURE__ */ React.createElement("span", { style: { width: 1, height: 22, background: "var(--line)" } }), headerActionBtns, shareBtn, /* @__PURE__ */ React.createElement("div", { style: { display: "flex", alignItems: "center", gap: 8 } }, /* @__PURE__ */ React.createElement(DkAvatar, { peer: { ...me, id: me.userId, agent: false }, size: 26, radius: 7 }), /* @__PURE__ */ React.createElement("span", { style: { fontFamily: "var(--mono)", fontSize: 12.5, fontWeight: 600, color: "var(--text)" } }, me.name)))), phone && peopleTab && /* @__PURE__ */ React.createElement("div", { style: { flexShrink: 0, display: "flex", gap: 6, padding: "8px 12px", borderBottom: "1px solid var(--line)", background: "var(--panel)", overflowX: "auto" } }, nav.filter((n) => DK_PEOPLE_TABS.includes(n.id)).map((n) => /* @__PURE__ */ React.createElement("button", { key: n.id, onClick: () => setTab(n.id), style: {
|
|
7032
7279
|
display: "inline-flex",
|
|
7033
7280
|
alignItems: "center",
|
|
7034
7281
|
gap: 6,
|
|
@@ -7042,7 +7289,7 @@ ${peer.address}`
|
|
|
7042
7289
|
fontWeight: 600,
|
|
7043
7290
|
background: tab === n.id ? "var(--accent)" : "transparent",
|
|
7044
7291
|
color: tab === n.id ? "#fff" : "var(--dim)"
|
|
7045
|
-
} }, /* @__PURE__ */ React.createElement(Icon, { name: n.icon, size: 14, stroke: 2, color: tab === n.id ? "#fff" : "var(--dim)" }), n.label))), tab === "chat" && /* @__PURE__ */ React.createElement(ChatTab, { T, lang: t.lang, phone, onBack: closeConversation, peers, requests, activeId, thread: activeId === ASSISTANT_ID ? assistant.thread : data.threads[activeId], onSelect, onAct, onAdd, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread: () => activeId && data.loadThread(activeId), hasEarlier: !!(activeId && activeId !== ASSISTANT_ID && data.earlier[activeId]), onAssistantRemove: activeId === ASSISTANT_ID ? assistant.removeFriends : null, onAssistantAdopt: activeId === ASSISTANT_ID ? assistant.adoptServicePeers : null, onLoadEarlier: () => activeId && data.loadEarlier(activeId), prefillAddr: pendingAddr, onPrefillConsumed: () => setPendingAddr(""), muted: mutedIds, onToggleMute }), tab === "here" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "bridge", peers, meId: me.userId, onAdd, onOpenChat }), tab === "recommended" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "recommended", peers, meId: me.userId, onAdd, onOpenChat }), tab === "registered" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "registered", peers, meId: me.userId, onAdd, onOpenChat }), tab === "network" && /* @__PURE__ */ React.createElement(NetworkTab, { T, me, peers, exits, activeExit, reqCount: requests.length, onSetExit, onOpenChat, backend, onArmLan: armLan, onCancelLan: cancelLan }), tab === "apps" && /* @__PURE__ */ React.createElement(AppsTab, { T, t, me, peers, phone, setTab }), tabs.map((x) => x.kind === "host" && tab === x.id ? /* @__PURE__ */ React.createElement(HostTabPane, { key: x.id, tab: x, props: { T, t, me, peers, phone, setTab }, lang: t.lang }) : null), tab === "profile" && /* @__PURE__ */ React.createElement(
|
|
7292
|
+
} }, /* @__PURE__ */ React.createElement(Icon, { name: n.icon, size: 14, stroke: 2, color: tab === n.id ? "#fff" : "var(--dim)" }), n.label))), tab === "chat" && /* @__PURE__ */ React.createElement(ChatTab, { T, lang: t.lang, phone, isProtocol, protocolFix, onBack: closeConversation, peers, requests, activeId, thread: activeId === ASSISTANT_ID ? assistant.thread : data.threads[activeId], onSelect, onAct, onAdd, onSend, onSendFile, onSendRtcFile, onAlias, onRemove, onOpenNet, onCall, onReloadThread: () => activeId && data.loadThread(activeId), hasEarlier: !!(activeId && activeId !== ASSISTANT_ID && data.earlier[activeId]), onAssistantRemove: activeId === ASSISTANT_ID ? assistant.removeFriends : null, onAssistantAdopt: activeId === ASSISTANT_ID ? assistant.adoptServicePeers : null, onLoadEarlier: () => activeId && data.loadEarlier(activeId), prefillAddr: pendingAddr, onPrefillConsumed: () => setPendingAddr(""), muted: mutedIds, onToggleMute }), tab === "here" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "bridge", peers, meId: me.userId, onAdd, onOpenChat }), tab === "recommended" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "recommended", peers, meId: me.userId, onAdd, onOpenChat }), tab === "registered" && /* @__PURE__ */ React.createElement(DiscoverTab, { T, kind: "registered", peers, meId: me.userId, onAdd, onOpenChat }), tab === "network" && /* @__PURE__ */ React.createElement(NetworkTab, { T, me, peers, exits, activeExit, reqCount: requests.length, onSetExit, onOpenChat, backend, onArmLan: armLan, onCancelLan: cancelLan }), tab === "apps" && /* @__PURE__ */ React.createElement(AppsTab, { T, t, me, peers, phone, setTab }), tabs.map((x) => x.kind === "host" && tab === x.id ? /* @__PURE__ */ React.createElement(HostTabPane, { key: x.id, tab: x, props: { T, t, me, peers, phone, setTab }, lang: t.lang }) : null), tab === "profile" && /* @__PURE__ */ React.createElement(
|
|
7046
7293
|
ProfileTab,
|
|
7047
7294
|
{
|
|
7048
7295
|
T,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@decentnetwork/beagle",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.115",
|
|
4
4
|
"description": "Beagle — P2P chat, file transfer and calls for regular users, on the Decent Network. No admin privilege required.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
"yargs": "^17.7.2"
|
|
36
36
|
},
|
|
37
37
|
"devDependencies": {
|
|
38
|
-
"@decentnetwork/beagle-ui": "^0.2.
|
|
38
|
+
"@decentnetwork/beagle-ui": "^0.2.29",
|
|
39
39
|
"@types/js-yaml": "^4.0.9",
|
|
40
40
|
"@types/node": "^20.11.0",
|
|
41
41
|
"@types/yargs": "^17.0.32",
|