openvibers/openvibe.tools Commits
Share: one Share sheet on tool results and text output (#218)
Changes
@@@ -1132,7 +1132,7 @@}const actions = [kit.iconButton({ type: 'button', icon: 'copy', label: 'Copy result', attrs: { 'data-ovk-copy': `#${ANSWER_ID}` } }),-- kit.iconButton({ href: location.href, icon: 'link', label: 'Copy link', attrs: { 'data-ovk-share': 'Copy link' } }),++ kit.share({ title: o.title || document.title, url: `${location.origin}${location.pathname}?q=${encodeURIComponent((document.getElementById('search-input') || {}).value || '')}`, text: o.badge && o.badge.text ? String(o.badge.text) : '' }),...(o.actions || []),];out.innerHTML = kit.answer({ id: ANSWER_ID, title: o.title || '', badge: o.badge || null, rows: o.rows || [], body: o.body || '', next: o.next || [], tone: o.tone || '', actions });nnew file mode 100644@@@ -0,0 +1,23 @@++'use strict';++// The network's one Share sheet (openvibe-shared 4.114.0): a tool result that has a public link offers the one Share++// button (data-ov-share-sheet) with that link, and Text.OpenVibe's generated text is sent the same way. The old++// device-sheet/copy helpers are gone, so no page carries a second share path.++const assert = require('assert');++const fs = require('fs');++const path = require('path');++++const net = fs.readFileSync(path.join(__dirname, '..', 'public', 'net.html'), 'utf8');++assert.ok(net.includes("kit.share({ title: o.title || document.title, url: `${location.origin}${location.pathname}?q="), 'a result shares its own public link');++assert.ok(!net.includes('data-ovk-share'), 'the old kit menu item is gone');++++const zalgo = fs.readFileSync(path.join(__dirname, '..', '..', 'text', 'public', 'zalgo.html'), 'utf8');++assert.ok(zalgo.includes('data-ov-share-sheet'), 'Share is the one button');++assert.ok(zalgo.includes('class="ovk-btn ovk-btn--quiet"') && zalgo.includes('<span>Share</span>'), 'the shared kit button');++assert.ok(zalgo.includes("data-url=\"https://text.openvibe.tools/zalgo.html\""), 'the page address');++assert.ok(zalgo.includes('dataset.text = lastOutput'), 'the generated text goes with it');++assert.ok(!zalgo.includes('OpenVibeUI.shareText'), 'the old device sheet is gone');++++const shared = fs.readFileSync(path.join(__dirname, '..', '..', 'text', 'public', 'js', 'shared.js'), 'utf8');++assert.ok(!shared.includes('navigator.share') && !shared.includes('shareText'), 'no second share path in the text suite');++++console.log('share sheet ok');@@@ -204,6 +204,9 @@ img, canvas { max-width: 100%; height: auto; }font-weight: 500;}++/* The one Share sheet is same-origin markup (openvibe-shared/ov-share.css): a page-wide field rule must not redraw its++ link field (attribute selectors outrank .ov-share-linktext). */++.ov-share .ov-share-linktext { border: 0; background: none; padding: 0; }textarea, input[type="text"], input[type="number"], input[type="url"], select {width: 100%;padding: 14px 16px;@@@ -116,19 +116,6 @@ function downloadText(text, filename = 'openvibetext-output.txt') {URL.revokeObjectURL(url);}--// ── Share via Web Share API ──────────────────────────────────--async function shareText(text, title = 'Text.OpenVibe') {-- if (navigator.share) {-- try {-- await navigator.share({ title, text });-- } catch (e) {-- // User cancelled-- }-- } else {-- copyText(text);-- }--}--// ── Shared chrome: navbar + footer ───────────────────────────// Every page loads navbar.js / footer.js from openvibe.network; this is the one place that// boots them, so a page only needs a <div id="ov-footer" data-related="Name|url;…"> mount.@@@ -315,7 +302,6 @@ root.OpenVibeUI = {updateOutputCard,escapeHtml,downloadText,-- shareText,initPage,};@@@ -19,6 +19,7 @@</script><link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800;900&display=swap" rel="stylesheet"><link rel="stylesheet" href="/css/shared.css">++ <link rel="stylesheet" href="/shared/kit.css"><script src="/shared/theme-loader.js" defer></script></head><body>@@@ -59,7 +60,7 @@<div class="btn-row"><button class="btn btn-primary" onclick="copyOutput()"><i class="fas fa-copy"></i> Copy</button><button class="btn btn-secondary" onclick="regenerate()"><i class="fas fa-rotate"></i> Regenerate</button>-- <button class="btn btn-ghost" onclick="OpenVibeUI.shareText(lastOutput)"><i class="fas fa-arrow-up-from-bracket"></i> Share</button>++ <button class="ovk-btn ovk-btn--quiet" id="zalgo-share" type="button" data-ov-share-sheet data-title="Zalgo text on Text.OpenVibe" data-url="https://text.openvibe.tools/zalgo.html"><svg class="ovk-i" viewBox="0 0 24 24" aria-hidden="true" focusable="false"><path d="M12 20V9M7 14l5-5 5 5M5 4h14"/></svg><span>Share</span></button></div></div>@@@ -85,6 +86,8 @@OpenVibeUI.initPage();const intensityNames = ['low', 'medium', 'high', 'insane'];let lastOutput = '';++ // The one Share sheet (openvibe-shared 4.114.0) sends the generated text with the page's link.++ document.getElementById('zalgo-share').addEventListener('click', function () { this.dataset.text = lastOutput; });function getOpts() {return {
@@ -1132,7 +1132,7 @@
@@ -1132,7 +1132,7 @@
}
}
const actions = [
const actions = [
kit.iconButton({ type: 'button', icon: 'copy', label: 'Copy result', attrs: { 'data-ovk-copy': `#${ANSWER_ID}` } }),
kit.iconButton({ type: 'button', icon: 'copy', label: 'Copy result', attrs: { 'data-ovk-copy': `#${ANSWER_ID}` } }),
- kit.iconButton({ href: location.href, icon: 'link', label: 'Copy link', attrs: { 'data-ovk-share': 'Copy link' } }),
+ kit.share({ title: o.title || document.title, url: `${location.origin}${location.pathname}?q=${encodeURIComponent((document.getElementById('search-input') || {}).value || '')}`, text: o.badge && o.badge.text ? String(o.badge.text) : '' }),
...(o.actions || []),
...(o.actions || []),
];
];
out.innerHTML = kit.answer({ id: ANSWER_ID, title: o.title || '', badge: o.badge || null, rows: o.rows || [], body: o.body || '', next: o.next || [], tone: o.tone || '', actions });
out.innerHTML = kit.answer({ id: ANSWER_ID, title: o.title || '', badge: o.badge || null, rows: o.rows || [], body: o.body || '', next: o.next || [], tone: o.tone || '', actions });
new file mode 100644
new file mode 100644
@@ -0,0 +1,23 @@
@@ -0,0 +1,23 @@
+'use strict';
+// The network's one Share sheet (openvibe-shared 4.114.0): a tool result that has a public link offers the one Share
+// button (data-ov-share-sheet) with that link, and Text.OpenVibe's generated text is sent the same way. The old
+// device-sheet/copy helpers are gone, so no page carries a second share path.
+const assert = require('assert');
+const fs = require('fs');
+const path = require('path');
+
+const net = fs.readFileSync(path.join(__dirname, '..', 'public', 'net.html'), 'utf8');
+assert.ok(net.includes("kit.share({ title: o.title || document.title, url: `${location.origin}${location.pathname}?q="), 'a result shares its own public link');
+assert.ok(!net.includes('data-ovk-share'), 'the old kit menu item is gone');
+
+const zalgo = fs.readFileSync(path.join(__dirname, '..', '..', 'text', 'public', 'zalgo.html'), 'utf8');
+assert.ok(zalgo.includes('data-ov-share-sheet'), 'Share is the one button');
+assert.ok(zalgo.includes('class="ovk-btn ovk-btn--quiet"') && zalgo.includes('<span>Share</span>'), 'the shared kit button');
+assert.ok(zalgo.includes("data-url=\"https://text.openvibe.tools/zalgo.html\""), 'the page address');
+assert.ok(zalgo.includes('dataset.text = lastOutput'), 'the generated text goes with it');
+assert.ok(!zalgo.includes('OpenVibeUI.shareText'), 'the old device sheet is gone');
+
+const shared = fs.readFileSync(path.join(__dirname, '..', '..', 'text', 'public', 'js', 'shared.js'), 'utf8');
+assert.ok(!shared.includes('navigator.share') && !shared.includes('shareText'), 'no second share path in the text suite');
+
+console.log('share sheet ok');
@@ -204,6 +204,9 @@ img, canvas { max-width: 100%; height: auto; }
@@ -204,6 +204,9 @@ img, canvas { max-width: 100%; height: auto; }
font-weight: 500;
font-weight: 500;
}
}
+/* The one Share sheet is same-origin markup (openvibe-shared/ov-share.css): a page-wide field rule must not redraw its
+ link field (attribute selectors outrank .ov-share-linktext). */
+.ov-share .ov-share-linktext { border: 0; background: none; padding: 0; }
textarea, input[type="text"], input[type="number"], input[type="url"], select {
textarea, input[type="text"], input[type="number"], input[type="url"], select {
width: 100%;
width: 100%;
padding: 14px 16px;
padding: 14px 16px;
@@ -116,19 +116,6 @@ function downloadText(text, filename = 'openvibetext-output.txt') {
@@ -116,19 +116,6 @@ function downloadText(text, filename = 'openvibetext-output.txt') {
URL.revokeObjectURL(url);
URL.revokeObjectURL(url);
}
}
-// ── Share via Web Share API ──────────────────────────────────
-async function shareText(text, title = 'Text.OpenVibe') {
- if (navigator.share) {
- try {
- await navigator.share({ title, text });
- } catch (e) {
- // User cancelled
- }
- } else {
- copyText(text);
- }
-}
-
// ── Shared chrome: navbar + footer ───────────────────────────
// ── Shared chrome: navbar + footer ───────────────────────────
// Every page loads navbar.js / footer.js from openvibe.network; this is the one place that
// Every page loads navbar.js / footer.js from openvibe.network; this is the one place that
// boots them, so a page only needs a <div id="ov-footer" data-related="Name|url;…"> mount.
// boots them, so a page only needs a <div id="ov-footer" data-related="Name|url;…"> mount.
@@ -315,7 +302,6 @@ root.OpenVibeUI = {
@@ -315,7 +302,6 @@ root.OpenVibeUI = {
updateOutputCard,
updateOutputCard,
escapeHtml,
escapeHtml,
downloadText,
downloadText,
- shareText,
initPage,
initPage,
};
};
@@ -19,6 +19,7 @@
@@ -19,6 +19,7 @@
</script>
</script>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800;900&display=swap" rel="stylesheet">
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800;900&display=swap" rel="stylesheet">
<link rel="stylesheet" href="/css/shared.css">
<link rel="stylesheet" href="/css/shared.css">
+ <link rel="stylesheet" href="/shared/kit.css">
<script src="/shared/theme-loader.js" defer></script>
<script src="/shared/theme-loader.js" defer></script>
</head>
</head>
<body>
<body>
@@ -59,7 +60,7 @@
@@ -59,7 +60,7 @@
<div class="btn-row">
<div class="btn-row">
<button class="btn btn-primary" onclick="copyOutput()"><i class="fas fa-copy"></i> Copy</button>
<button class="btn btn-primary" onclick="copyOutput()"><i class="fas fa-copy"></i> Copy</button>
<button class="btn btn-secondary" onclick="regenerate()"><i class="fas fa-rotate"></i> Regenerate</button>
<button class="btn btn-secondary" onclick="regenerate()"><i class="fas fa-rotate"></i> Regenerate</button>
- <button class="btn btn-ghost" onclick="OpenVibeUI.shareText(lastOutput)"><i class="fas fa-arrow-up-from-bracket"></i> Share</button>
+ <button class="ovk-btn ovk-btn--quiet" id="zalgo-share" type="button" data-ov-share-sheet data-title="Zalgo text on Text.OpenVibe" data-url="https://text.openvibe.tools/zalgo.html"><svg class="ovk-i" viewBox="0 0 24 24" aria-hidden="true" focusable="false"><path d="M12 20V9M7 14l5-5 5 5M5 4h14"/></svg><span>Share</span></button>
</div>
</div>
</div>
</div>
@@ -85,6 +86,8 @@
@@ -85,6 +86,8 @@
OpenVibeUI.initPage();
OpenVibeUI.initPage();
const intensityNames = ['low', 'medium', 'high', 'insane'];
const intensityNames = ['low', 'medium', 'high', 'insane'];
let lastOutput = '';
let lastOutput = '';
+ // The one Share sheet (openvibe-shared 4.114.0) sends the generated text with the page's link.
+ document.getElementById('zalgo-share').addEventListener('click', function () { this.dataset.text = lastOutput; });
function getOpts() {
function getOpts() {
return {
return {