Compare commits
3 commits
3f91f846f4
...
aab735bd39
Author | SHA1 | Date | |
---|---|---|---|
|
aab735bd39 | ||
|
a31ab6b8ea | ||
|
35a477bf07 |
6 changed files with 930 additions and 316 deletions
1
bookmarklet-uri.txt
Normal file
1
bookmarklet-uri.txt
Normal file
|
@ -0,0 +1 @@
|
|||
javascript:void%20function(){let%20a=JSON.parse(document.getElementById(%22trpc-dehydrated-state%22).innerText),b=a.queries.find(a=%3Ea.queryKey[0].includes(%22singlePost%22)).state.data.post,c=document.createElement(%22cohost-post%22);if(c.setAttribute(%22avatarSrc%22,b.postingProject.avatarURL),c.setAttribute(%22avatarShape%22,b.postingProject.avatarShape),c.setAttribute(%22displayName%22,b.postingProject.displayName),c.setAttribute(%22handle%22,b.postingProject.handle),c.setAttribute(%22permalink%22,b.singlePostPageUrl),c.setAttribute(%22publishedAt%22,b.publishedAt),b.headline%26%26c.setAttribute(%22singlePostHeadline%22,b.headline),c.setAttribute(%22tags%22,b.tags.join(%22,%22)),b.shareTree%26%26b.shareTree.length){c.setAttribute(%22sharedItems%22,%22%22);let%20a=b.shareTree[b.shareTree.length-1];c.setAttribute(%22sharedAvatarSrc%22,a.postingProject.avatarURL),c.setAttribute(%22sharedAvatarShape%22,a.postingProject.avatarShape),c.setAttribute(%22sharedDisplayName%22,a.postingProject.displayName),c.setAttribute(%22sharedHandle%22,a.postingProject.handle);let%20d=[...b.shareTree,b];for(sharedPost%20of%20d){if(null!==sharedPost.transparentShareOfPostId)continue;let%20a=document.createElement(%22cohost-shared-item%22);a.setAttribute(%22avatarSrc%22,sharedPost.postingProject.avatarURL),a.setAttribute(%22avatarShape%22,sharedPost.postingProject.avatarShape),a.setAttribute(%22displayName%22,sharedPost.postingProject.displayName),a.setAttribute(%22handle%22,sharedPost.postingProject.handle),sharedPost.headline%26%26a.setAttribute(%22headline%22,sharedPost.headline),a.setAttribute(%22permalink%22,sharedPost.singlePostPageUrl),a.setAttribute(%22publishedAt%22,sharedPost.publishedAt),a.setAttribute(%22tags%22,sharedPost.tags.join(%22,%22));let%20b=document.getElementById(`post-${sharedPost.postId}`);b%26%26(a.innerHTML=b.parentElement.querySelector(%22[data-post-body]%22).innerHTML),c.appendChild(a)}}else{let%20a=document.getElementById(`post-${b.postId}`);a%26%26(c.innerHTML=document.getElementById(`post-${b.postId}`).parentElement.querySelector(%22[data-post-body]%22).innerHTML)}let%20d=document.createElement(%22div%22);d.id=%22cohost-wc-bookmarklet-output%22,d.style=%22position:%20fixed;%20bottom:%200.5rem;%20left:%200.5rem;%20display:%20flex;%20flex-direction:%20column;%20gap:%200.25rem;%20font-size:%200.875rem;%20z-index:%20100%22;let%20e=document.createElement(%22textarea%22);e.value=c.outerHTML,e.rows=5,e.cols=20,e.style=%22font-size:%20inherit;%20line-height:%201.4%22,d.append(e);let%20f=document.createElement(%22button%22);f.innerText=%22dismiss%22,f.onclick=function(){d.remove()},d.append(f),document.body.append(d)}();
|
68
bookmarklet.cjs
Normal file
68
bookmarklet.cjs
Normal file
|
@ -0,0 +1,68 @@
|
|||
let trpcState = JSON.parse(document.getElementById("trpc-dehydrated-state").innerText);
|
||||
let postData = trpcState.queries.find((q) => q.queryKey[0].includes("singlePost")).state.data.post;
|
||||
let postElement = document.createElement("cohost-post");
|
||||
postElement.setAttribute("avatarSrc", postData.postingProject.avatarURL);
|
||||
postElement.setAttribute("avatarShape", postData.postingProject.avatarShape);
|
||||
postElement.setAttribute("displayName", postData.postingProject.displayName);
|
||||
postElement.setAttribute("handle", postData.postingProject.handle);
|
||||
postElement.setAttribute("permalink", postData.singlePostPageUrl);
|
||||
postElement.setAttribute("publishedAt", postData.publishedAt);
|
||||
if (postData.headline) {
|
||||
postElement.setAttribute("singlePostHeadline", postData.headline);
|
||||
}
|
||||
postElement.setAttribute("tags", postData.tags.join(","));
|
||||
|
||||
if (postData.shareTree && postData.shareTree.length) {
|
||||
postElement.setAttribute("sharedItems", "");
|
||||
let sharedFrom = postData.shareTree[postData.shareTree.length - 1];
|
||||
postElement.setAttribute("sharedAvatarSrc", sharedFrom.postingProject.avatarURL);
|
||||
postElement.setAttribute("sharedAvatarShape", sharedFrom.postingProject.avatarShape);
|
||||
postElement.setAttribute("sharedDisplayName", sharedFrom.postingProject.displayName);
|
||||
postElement.setAttribute("sharedHandle", sharedFrom.postingProject.handle);
|
||||
|
||||
let shareTree = [...postData.shareTree, postData];
|
||||
for (sharedPost of shareTree) {
|
||||
if (sharedPost.transparentShareOfPostId !== null) {
|
||||
continue;
|
||||
}
|
||||
let sharedElement = document.createElement("cohost-shared-item");
|
||||
sharedElement.setAttribute("avatarSrc", sharedPost.postingProject.avatarURL);
|
||||
sharedElement.setAttribute("avatarShape", sharedPost.postingProject.avatarShape);
|
||||
sharedElement.setAttribute("displayName", sharedPost.postingProject.displayName);
|
||||
sharedElement.setAttribute("handle", sharedPost.postingProject.handle);
|
||||
if (sharedPost.headline) {
|
||||
sharedElement.setAttribute("headline", sharedPost.headline);
|
||||
}
|
||||
sharedElement.setAttribute("permalink", sharedPost.singlePostPageUrl);
|
||||
sharedElement.setAttribute("publishedAt", sharedPost.publishedAt);
|
||||
sharedElement.setAttribute("tags", sharedPost.tags.join(","));
|
||||
let sharedIdElement = document.getElementById(`post-${sharedPost.postId}`);
|
||||
if (sharedIdElement) {
|
||||
sharedElement.innerHTML = sharedIdElement.parentElement.querySelector("[data-post-body]").innerHTML;
|
||||
}
|
||||
postElement.appendChild(sharedElement);
|
||||
}
|
||||
} else {
|
||||
let postIdElement = document.getElementById(`post-${postData.postId}`);
|
||||
if (postIdElement) {
|
||||
postElement.innerHTML = document.getElementById(`post-${postData.postId}`).parentElement.querySelector("[data-post-body]").innerHTML;
|
||||
}
|
||||
}
|
||||
|
||||
let outputContainer = document.createElement("div");
|
||||
outputContainer.id = "cohost-wc-bookmarklet-output"
|
||||
outputContainer.style = "position: fixed; bottom: 0.5rem; left: 0.5rem; display: flex; flex-direction: column; gap: 0.25rem; font-size: 0.875rem; z-index: 100";
|
||||
|
||||
let outputTextarea = document.createElement("textarea");
|
||||
outputTextarea.value = postElement.outerHTML;
|
||||
outputTextarea.rows = 5;
|
||||
outputTextarea.cols = 20;
|
||||
outputTextarea.style = "font-size: inherit; line-height: 1.4";
|
||||
outputContainer.append(outputTextarea);
|
||||
|
||||
let outputDismissButton = document.createElement("button");
|
||||
outputDismissButton.innerText = "dismiss";
|
||||
outputDismissButton.onclick = function() { outputContainer.remove(); }
|
||||
outputContainer.append(outputDismissButton);
|
||||
|
||||
document.body.append(outputContainer);
|
207
cohost-wc.css
207
cohost-wc.css
|
@ -1,42 +1,40 @@
|
|||
/* atkinson-hyperlegible-regular - latin_latin-ext */
|
||||
/* Atkinson Hyperlegible */
|
||||
|
||||
@font-face {
|
||||
font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
|
||||
font-display: swap;
|
||||
font-family: "Atkinson Hyperlegible";
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
src: url("../fonts/atkinson-hyperlegible-v11-latin_latin-ext-regular.woff2")
|
||||
format("woff2"); /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
|
||||
format("woff2");
|
||||
}
|
||||
|
||||
/* atkinson-hyperlegible-italic - latin_latin-ext */
|
||||
@font-face {
|
||||
font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
|
||||
font-display: swap;
|
||||
font-family: "Atkinson Hyperlegible";
|
||||
font-style: italic;
|
||||
font-weight: 400;
|
||||
src: url("../fonts/atkinson-hyperlegible-v11-latin_latin-ext-italic.woff2")
|
||||
format("woff2"); /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
|
||||
format("woff2");
|
||||
}
|
||||
|
||||
/* atkinson-hyperlegible-700 - latin_latin-ext */
|
||||
@font-face {
|
||||
font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
|
||||
font-display: swap;
|
||||
font-family: "Atkinson Hyperlegible";
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
src: url("../fonts/atkinson-hyperlegible-v11-latin_latin-ext-700.woff2")
|
||||
format("woff2"); /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
|
||||
format("woff2");
|
||||
}
|
||||
|
||||
/* atkinson-hyperlegible-700italic - latin_latin-ext */
|
||||
@font-face {
|
||||
font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
|
||||
font-display: swap;
|
||||
font-family: "Atkinson Hyperlegible";
|
||||
font-style: italic;
|
||||
font-weight: 700;
|
||||
src: url("./fonts/atkinson-hyperlegible-v11-latin_latin-ext-700italic.woff2")
|
||||
format("woff2"); /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
|
||||
format("woff2");
|
||||
}
|
||||
|
||||
/* Keyframes */
|
||||
|
||||
@keyframes bounce {
|
||||
0%,
|
||||
100% {
|
||||
|
@ -111,35 +109,37 @@
|
|||
}
|
||||
}
|
||||
|
||||
cohost-wc * {
|
||||
/* Cohost post content styling */
|
||||
|
||||
cohost-post * {
|
||||
box-sizing: border-box;
|
||||
border-width: 0;
|
||||
border-style: solid;
|
||||
border-color: #ded9d3;
|
||||
}
|
||||
cohost-wc a {
|
||||
cohost-post a {
|
||||
color: inherit;
|
||||
text-decoration: inherit;
|
||||
}
|
||||
|
||||
cohost-wc hr {
|
||||
cohost-post hr {
|
||||
height: 0;
|
||||
color: inherit;
|
||||
border-top-width: 1px;
|
||||
}
|
||||
cohost-wc blockquote,
|
||||
cohost-wc dl,
|
||||
cohost-wc dd,
|
||||
cohost-wc h1,
|
||||
cohost-wc h2,
|
||||
cohost-wc h3,
|
||||
cohost-wc h4,
|
||||
cohost-wc h5,
|
||||
cohost-wc h6,
|
||||
cohost-wc hr,
|
||||
cohost-wc figure,
|
||||
cohost-wc p,
|
||||
cohost-wc pre {
|
||||
cohost-post blockquote,
|
||||
cohost-post dl,
|
||||
cohost-post dd,
|
||||
cohost-post h1,
|
||||
cohost-post h2,
|
||||
cohost-post h3,
|
||||
cohost-post h4,
|
||||
cohost-post h5,
|
||||
cohost-post h6,
|
||||
cohost-post hr,
|
||||
cohost-post figure,
|
||||
cohost-post p,
|
||||
cohost-post pre {
|
||||
margin: 0;
|
||||
}
|
||||
.prose {
|
||||
|
@ -163,7 +163,9 @@ cohost-wc pre {
|
|||
font-size: 1em;
|
||||
line-height: 1.75;
|
||||
}
|
||||
.prose :where(h3):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
cohost-post
|
||||
.prose
|
||||
:where(h3):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
color: var(--tw-prose-headings);
|
||||
font-weight: 600;
|
||||
font-size: 1.25em;
|
||||
|
@ -171,15 +173,142 @@ cohost-wc pre {
|
|||
margin-bottom: 0.6em;
|
||||
line-height: 1.6;
|
||||
}
|
||||
.prose
|
||||
:where(.prose > :last-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.prose
|
||||
cohost-post
|
||||
.prose
|
||||
:where(.prose > :first-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-top: 0;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(p):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
margin-top: 1.25em;
|
||||
margin-bottom: 1.25em;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(hr):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
border-color: var(--tw-prose-hr);
|
||||
border-top-width: 1px;
|
||||
margin-top: 1em;
|
||||
margin-bottom: 1em;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(a):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
text-decoration: underline;
|
||||
font-weight: 500;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(ul):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
list-style-type: disc;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(ul > li):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
padding-inline-start: 0.375em;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(li):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
margin-top: 0.5em;
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(.prose > :last-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
cohost-post
|
||||
.prose
|
||||
:where(.prose > :first-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-top: 0;
|
||||
}
|
||||
cohost-post .co-embed {
|
||||
background-color: light-dark(rgb(255 241 223), rgb(25 25 25));
|
||||
}
|
||||
cohost-post .co-ui-text {
|
||||
color: light-dark(rgb(25 25 25), rgb(255 249 242));
|
||||
}
|
||||
|
||||
/* Hide interactive UI */
|
||||
cohost-post button.co-link-button {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/* Tailwind properties */
|
||||
|
||||
cohost-post .text-right {
|
||||
text-align: right;
|
||||
}
|
||||
cohost-post .p-3 {
|
||||
padding: 0.75rem;
|
||||
}
|
||||
cohost-post .mt-0 {
|
||||
margin-top: 0px;
|
||||
}
|
||||
cohost-post .my-4 {
|
||||
margin-top: 1rem;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
cohost-post .overflow-hidden {
|
||||
overflow: hidden;
|
||||
}
|
||||
cohost-post .break-words {
|
||||
overflow-wrap: break-word;
|
||||
}
|
||||
cohost-post .px-3 {
|
||||
padding-left: 0.75rem;
|
||||
padding-right: 0.75rem;
|
||||
}
|
||||
|
||||
/* TODO: light */
|
||||
@media (prefers-color-scheme: dark) {
|
||||
cohost-post {
|
||||
--color-notWhite: 255 249 242;
|
||||
--color-notBlack: 25 25 25;
|
||||
--color-cherry: 131 37 79;
|
||||
--color-strawberry: 229 107 111;
|
||||
--color-mango: 255 171 92;
|
||||
--color-longan: 255 216 168;
|
||||
--color-tertiary: var(--color-longan);
|
||||
--color-tertiary-200: 255 229 196;
|
||||
--color-tertiary-300: 255 216 168;
|
||||
--color-tertiary-400: 255 202 122;
|
||||
--color-tertiary-500: 183 133 61;
|
||||
--color-tertiary-600: 183 133 61;
|
||||
--color-tertiary-700: 132 94 38;
|
||||
--color-text: var(--color-notWhite);
|
||||
--color-bg-text: var(--color-notWhite);
|
||||
--color-foreground-100: 253 206 224;
|
||||
--color-foreground-200: 238 173 199;
|
||||
--color-foreground-300: 211 116 155;
|
||||
--color-foreground-400: 174 68 115;
|
||||
--color-foreground-500: 131 37 79;
|
||||
--color-foreground-600: 103 26 61;
|
||||
--color-foreground-700: 81 17 46;
|
||||
--color-foreground-800: 59 9 32;
|
||||
--color-foreground: var(--color-cherry);
|
||||
--color-secondary-200: 255 208 172;
|
||||
--color-secondary-300: 255 191 131;
|
||||
--color-secondary-400: 255 171 92;
|
||||
--color-secondary-600: 188 109 40;
|
||||
--color-secondary-700: 147 74 21;
|
||||
--color-secondary: var(--color-mango);
|
||||
--color-accent: var(--color-mango);
|
||||
--color-background: var(--color-notBlack);
|
||||
--color-sidebar-bg: var(--color-notBlack);
|
||||
--color-sidebar-text: var(--color-notWhite);
|
||||
--color-sidebar-accent: var(--color-mango);
|
||||
--color-compose-button: var(--color-foreground);
|
||||
--color-compose-button-400: var(--color-foreground-400);
|
||||
--color-compose-button-600: var(--color-foreground-600);
|
||||
--emoji-scale: 1.25em;
|
||||
}
|
||||
}
|
||||
|
|
127
package-lock.json
generated
127
package-lock.json
generated
|
@ -13,6 +13,7 @@
|
|||
"devDependencies": {
|
||||
"@web/dev-server": "^0.4.6",
|
||||
"@webcomponents/webcomponentsjs": "^2.8.0",
|
||||
"concurrently": "^9.0.1",
|
||||
"eslint": "^9.10.0",
|
||||
"lit-analyzer": "^2.0.3",
|
||||
"prettier": "^3.3.3",
|
||||
|
@ -1266,6 +1267,46 @@
|
|||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/concurrently": {
|
||||
"version": "9.0.1",
|
||||
"resolved": "https://registry.npmjs.org/concurrently/-/concurrently-9.0.1.tgz",
|
||||
"integrity": "sha512-wYKvCd/f54sTXJMSfV6Ln/B8UrfLBKOYa+lzc6CHay3Qek+LorVSBdMVfyewFhRbH0Rbabsk4D+3PL/VjQ5gzg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"chalk": "^4.1.2",
|
||||
"lodash": "^4.17.21",
|
||||
"rxjs": "^7.8.1",
|
||||
"shell-quote": "^1.8.1",
|
||||
"supports-color": "^8.1.1",
|
||||
"tree-kill": "^1.2.2",
|
||||
"yargs": "^17.7.2"
|
||||
},
|
||||
"bin": {
|
||||
"conc": "dist/bin/concurrently.js",
|
||||
"concurrently": "dist/bin/concurrently.js"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=18"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/open-cli-tools/concurrently?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/concurrently/node_modules/supports-color": {
|
||||
"version": "8.1.1",
|
||||
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz",
|
||||
"integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"has-flag": "^4.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/chalk/supports-color?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/content-disposition": {
|
||||
"version": "0.5.4",
|
||||
"resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz",
|
||||
|
@ -3159,6 +3200,15 @@
|
|||
"queue-microtask": "^1.2.2"
|
||||
}
|
||||
},
|
||||
"node_modules/rxjs": {
|
||||
"version": "7.8.1",
|
||||
"resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
|
||||
"integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"tslib": "^2.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/safe-buffer": {
|
||||
"version": "5.2.1",
|
||||
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
|
||||
|
@ -3206,6 +3256,15 @@
|
|||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/shell-quote": {
|
||||
"version": "1.8.1",
|
||||
"resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.8.1.tgz",
|
||||
"integrity": "sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==",
|
||||
"dev": true,
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/ljharb"
|
||||
}
|
||||
},
|
||||
"node_modules/signal-exit": {
|
||||
"version": "3.0.7",
|
||||
"resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz",
|
||||
|
@ -3353,12 +3412,27 @@
|
|||
"node": ">=18"
|
||||
}
|
||||
},
|
||||
"node_modules/tree-kill": {
|
||||
"version": "1.2.2",
|
||||
"resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz",
|
||||
"integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==",
|
||||
"dev": true,
|
||||
"bin": {
|
||||
"tree-kill": "cli.js"
|
||||
}
|
||||
},
|
||||
"node_modules/ts-simple-type": {
|
||||
"version": "2.0.0-next.0",
|
||||
"resolved": "https://registry.npmjs.org/ts-simple-type/-/ts-simple-type-2.0.0-next.0.tgz",
|
||||
"integrity": "sha512-A+hLX83gS+yH6DtzNAhzZbPfU+D9D8lHlTSd7GeoMRBjOt3GRylDqLTYbdmjA4biWvq2xSfpqfIDj2l0OA/BVg==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/tslib": {
|
||||
"version": "2.7.0",
|
||||
"resolved": "https://registry.npmjs.org/tslib/-/tslib-2.7.0.tgz",
|
||||
"integrity": "sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/tsscmp": {
|
||||
"version": "1.0.6",
|
||||
"resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.6.tgz",
|
||||
|
@ -4604,6 +4678,32 @@
|
|||
"integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==",
|
||||
"dev": true
|
||||
},
|
||||
"concurrently": {
|
||||
"version": "9.0.1",
|
||||
"resolved": "https://registry.npmjs.org/concurrently/-/concurrently-9.0.1.tgz",
|
||||
"integrity": "sha512-wYKvCd/f54sTXJMSfV6Ln/B8UrfLBKOYa+lzc6CHay3Qek+LorVSBdMVfyewFhRbH0Rbabsk4D+3PL/VjQ5gzg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"chalk": "^4.1.2",
|
||||
"lodash": "^4.17.21",
|
||||
"rxjs": "^7.8.1",
|
||||
"shell-quote": "^1.8.1",
|
||||
"supports-color": "^8.1.1",
|
||||
"tree-kill": "^1.2.2",
|
||||
"yargs": "^17.7.2"
|
||||
},
|
||||
"dependencies": {
|
||||
"supports-color": {
|
||||
"version": "8.1.1",
|
||||
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz",
|
||||
"integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"has-flag": "^4.0.0"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"content-disposition": {
|
||||
"version": "0.5.4",
|
||||
"resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz",
|
||||
|
@ -5997,6 +6097,15 @@
|
|||
"queue-microtask": "^1.2.2"
|
||||
}
|
||||
},
|
||||
"rxjs": {
|
||||
"version": "7.8.1",
|
||||
"resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.1.tgz",
|
||||
"integrity": "sha512-AA3TVj+0A2iuIoQkWEK/tqFjBq2j+6PO6Y0zJcvzLAFhEFIO3HL0vls9hWLncZbAAbK0mar7oZ4V079I/qPMxg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"tslib": "^2.1.0"
|
||||
}
|
||||
},
|
||||
"safe-buffer": {
|
||||
"version": "5.2.1",
|
||||
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
|
||||
|
@ -6024,6 +6133,12 @@
|
|||
"integrity": "sha512-7++dFhtcx3353uBaq8DDR4NuxBetBzC7ZQOhmTQInHEd6bSrXdiEyzCvG07Z44UYdLShWUyXt5M/yhz8ekcb1A==",
|
||||
"dev": true
|
||||
},
|
||||
"shell-quote": {
|
||||
"version": "1.8.1",
|
||||
"resolved": "https://registry.npmjs.org/shell-quote/-/shell-quote-1.8.1.tgz",
|
||||
"integrity": "sha512-6j1W9l1iAs/4xYBI1SYOVZyFcCis9b4KCLQ8fgAGG07QvzaRLVVRQvAy85yNmmZSjYjg4MWh4gNvlPujU/5LpA==",
|
||||
"dev": true
|
||||
},
|
||||
"signal-exit": {
|
||||
"version": "3.0.7",
|
||||
"resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz",
|
||||
|
@ -6131,12 +6246,24 @@
|
|||
"punycode": "^2.3.1"
|
||||
}
|
||||
},
|
||||
"tree-kill": {
|
||||
"version": "1.2.2",
|
||||
"resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.2.tgz",
|
||||
"integrity": "sha512-L0Orpi8qGpRG//Nd+H90vFB+3iHnue1zSSGmNOOCh1GLJ7rUKVwV2HvijphGQS2UmhUZewS9VgvxYIdgr+fG1A==",
|
||||
"dev": true
|
||||
},
|
||||
"ts-simple-type": {
|
||||
"version": "2.0.0-next.0",
|
||||
"resolved": "https://registry.npmjs.org/ts-simple-type/-/ts-simple-type-2.0.0-next.0.tgz",
|
||||
"integrity": "sha512-A+hLX83gS+yH6DtzNAhzZbPfU+D9D8lHlTSd7GeoMRBjOt3GRylDqLTYbdmjA4biWvq2xSfpqfIDj2l0OA/BVg==",
|
||||
"dev": true
|
||||
},
|
||||
"tslib": {
|
||||
"version": "2.7.0",
|
||||
"resolved": "https://registry.npmjs.org/tslib/-/tslib-2.7.0.tgz",
|
||||
"integrity": "sha512-gLXCKdN1/j47AiHiOkJN69hJmcbGTHI0ImLmbYLHykhgeN0jVGola9yVjFgzCUklsZQMW55o+dW7IXv3RCXDzA==",
|
||||
"dev": true
|
||||
},
|
||||
"tsscmp": {
|
||||
"version": "1.0.6",
|
||||
"resolved": "https://registry.npmjs.org/tsscmp/-/tsscmp-1.0.6.tgz",
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
"lint:eslint": "eslint 'src/**/*.ts'",
|
||||
"lint:lit-analyzer": "lit-analyzer",
|
||||
"format": "prettier \"**/*.{cjs,html,js,json,md,ts}\" --ignore-path ./.eslintignore --write",
|
||||
"serve": "wds --watch",
|
||||
"serve": "concurrently \"tsc --watch\" \"wds --watch\"",
|
||||
"serve:prod": "MODE=prod npm run serve"
|
||||
},
|
||||
"dependencies": {
|
||||
|
@ -22,6 +22,7 @@
|
|||
"devDependencies": {
|
||||
"@web/dev-server": "^0.4.6",
|
||||
"@webcomponents/webcomponentsjs": "^2.8.0",
|
||||
"concurrently": "^9.0.1",
|
||||
"eslint": "^9.10.0",
|
||||
"lit-analyzer": "^2.0.3",
|
||||
"prettier": "^3.3.3",
|
||||
|
|
840
src/cohost-wc.ts
840
src/cohost-wc.ts
|
@ -1,46 +1,251 @@
|
|||
import { LitElement, html, css } from "lit";
|
||||
import { customElement, property, state } from "lit/decorators.js";
|
||||
import { customElement, property } from "lit/decorators.js";
|
||||
import { when } from "lit/directives/when.js";
|
||||
import { ifDefined } from "lit/directives/if-defined.js";
|
||||
|
||||
@customElement("cohost-wc")
|
||||
export class CohostWebComponent extends LitElement {
|
||||
function formatRelativeTime(date: Date) {
|
||||
const millisecondsPerSecond = 1000;
|
||||
const secondsPerMinute = 60;
|
||||
const minutesPerHour = 60;
|
||||
const hoursPerDay = 24;
|
||||
const daysPerMonth = 30; // JS date handling moment
|
||||
const intervals = {
|
||||
month:
|
||||
millisecondsPerSecond *
|
||||
secondsPerMinute *
|
||||
minutesPerHour *
|
||||
hoursPerDay *
|
||||
daysPerMonth,
|
||||
day:
|
||||
millisecondsPerSecond * secondsPerMinute * minutesPerHour * hoursPerDay,
|
||||
hour: millisecondsPerSecond * secondsPerMinute * minutesPerHour,
|
||||
minute: millisecondsPerSecond * secondsPerMinute,
|
||||
second: millisecondsPerSecond,
|
||||
} as const;
|
||||
const relativeDateFormat = new Intl.RelativeTimeFormat("en", {
|
||||
style: "short",
|
||||
});
|
||||
const diff = date.getTime() - new Date().getTime();
|
||||
for (const interval in intervals) {
|
||||
const _interval = interval as keyof typeof intervals;
|
||||
if (intervals[_interval] <= Math.abs(diff)) {
|
||||
return relativeDateFormat.format(
|
||||
Math.trunc(diff / intervals[_interval]),
|
||||
_interval,
|
||||
);
|
||||
}
|
||||
}
|
||||
return relativeDateFormat.format(diff / 1000, "second");
|
||||
}
|
||||
|
||||
const COMMON_CSS = css`
|
||||
:host {
|
||||
color-scheme: light dark;
|
||||
font-family: "Atkinson Hyperlegible", ui-sans-serif, system-ui, sans-serif,
|
||||
"Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol",
|
||||
"Noto Color Emoji";
|
||||
}
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
border-width: 0;
|
||||
border-style: solid;
|
||||
border-color: #ded9d3;
|
||||
}
|
||||
a {
|
||||
color: inherit;
|
||||
text-decoration: inherit;
|
||||
}
|
||||
hr {
|
||||
height: 0;
|
||||
color: inherit;
|
||||
border-top-width: 1px;
|
||||
}
|
||||
blockquote,
|
||||
dl,
|
||||
dd,
|
||||
h1,
|
||||
h2,
|
||||
h3,
|
||||
h4,
|
||||
h5,
|
||||
h6,
|
||||
hr,
|
||||
figure,
|
||||
p,
|
||||
pre {
|
||||
margin: 0;
|
||||
}
|
||||
.post-anchor {
|
||||
position: relative;
|
||||
top: -5rem;
|
||||
}
|
||||
.co-avatar-container {
|
||||
width: 2rem;
|
||||
height: 2rem;
|
||||
aspect-ratio: 1 / 1;
|
||||
display: inline-block;
|
||||
position: relative;
|
||||
}
|
||||
.mask {
|
||||
-webkit-mask-size: contain;
|
||||
mask-size: contain;
|
||||
-webkit-mask-repeat: no-repeat;
|
||||
mask-repeat: no-repeat;
|
||||
-webkit-mask-position: center;
|
||||
mask-position: center;
|
||||
}
|
||||
.mask-squircle {
|
||||
-webkit-mask-image: url(data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJNMTAwIDBDMjAgMCAwIDIwIDAgMTAwczIwIDEwMCAxMDAgMTAwIDEwMC0yMCAxMDAtMTAwUzE4MCAwIDEwMCAweiIvPjwvc3ZnPg==);
|
||||
mask-image: url(data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJNMTAwIDBDMjAgMCAwIDIwIDAgMTAwczIwIDEwMCAxMDAgMTAwIDEwMC0yMCAxMDAtMTAwUzE4MCAwIDEwMCAweiIvPjwvc3ZnPg==);
|
||||
}
|
||||
.mask-roundrect {
|
||||
border-radius: 12.5%;
|
||||
}
|
||||
.mask-circle {
|
||||
border-radius: 9999px;
|
||||
}
|
||||
/* .mask-egg {
|
||||
-webkit-mask-image: url(/static/de7a6730ae8672a12406.svg);
|
||||
mask-image: url(/static/de7a6730ae8672a12406.svg);
|
||||
}
|
||||
.mask-capsule-big {
|
||||
-webkit-mask-image: url(/static/3e2b26f2f1e719024296.svg);
|
||||
mask-image: url(/static/3e2b26f2f1e719024296.svg);
|
||||
}
|
||||
.mask-capsule-small {
|
||||
-webkit-mask-image: url(/static/8ff201350af3c70fb5b8.svg);
|
||||
mask-image: url(/static/8ff201350af3c70fb5b8.svg);
|
||||
} */
|
||||
.co-avatar {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
-o-object-fit: cover;
|
||||
object-fit: cover;
|
||||
}
|
||||
.co-project-display-name {
|
||||
max-width: 100%;
|
||||
flex-shrink: 1;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
font-weight: 700;
|
||||
color: light-dark(rgb(25 25 25), rgb(255 249 242));
|
||||
}
|
||||
.co-project-display-name:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-project-handle {
|
||||
color: light-dark(rgb(74 72 71), rgb(222 217 211));
|
||||
}
|
||||
.co-project-handle:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-thread-header time,
|
||||
.co-post-header time {
|
||||
display: block;
|
||||
flex: none;
|
||||
font-size: 0.75rem;
|
||||
line-height: 1rem;
|
||||
font-variant-numeric: tabular-nums;
|
||||
color: rgb(130 127 124);
|
||||
}
|
||||
.co-thread-header time a:hover,
|
||||
.co-post-header time a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-hairline {
|
||||
border-color: light-dark(rgb(191 186 181), rgb(74 72 71));
|
||||
}
|
||||
.post-headline-container {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
width: 100%;
|
||||
padding: 0.75rem;
|
||||
}
|
||||
.post-headline-a {
|
||||
overflow-wrap: break-word;
|
||||
align-self: center;
|
||||
flex-grow: 1;
|
||||
}
|
||||
.post-headline-a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.prose {
|
||||
color: light-dark(#191919, #fff9f2);
|
||||
--tw-prose-body: light-dark(#374151, #fff9f2);
|
||||
--tw-prose-headings: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-lead: light-dark(#4b5563, #fff9f2);
|
||||
--tw-prose-links: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-bold: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-counters: light-dark(#6b7280, #fff9f2);
|
||||
--tw-prose-bullets: light-dark(#d1d5db, #fff9f2);
|
||||
--tw-prose-hr: light-dark(#e5e7eb, #bfbab5);
|
||||
--tw-prose-quotes: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-quote-borders: light-dark(#e5e7eb, #bfbab5);
|
||||
--tw-prose-captions: light-dark(#6b7280, #fff9f2);
|
||||
--tw-prose-code: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-pre-code: light-dark(#e5e7eb, #fff9f2);
|
||||
--tw-prose-pre-bg: light-dark(#1f2937, #191919);
|
||||
--tw-prose-th-borders: light-dark(#d1d5db, #bfbab5);
|
||||
--tw-prose-td-borders: light-dark(#e5e7eb, #bfbab5);
|
||||
font-size: 1em;
|
||||
line-height: 1.75;
|
||||
}
|
||||
.prose :where(h3):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
color: var(--tw-prose-headings);
|
||||
font-weight: 600;
|
||||
font-size: 1.25em;
|
||||
margin-top: 1.6em;
|
||||
margin-bottom: 0.6em;
|
||||
line-height: 1.6;
|
||||
}
|
||||
.prose
|
||||
:where(.prose > :last-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.prose
|
||||
:where(.prose > :first-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-top: 0;
|
||||
}
|
||||
.post-body {
|
||||
overflow: clip;
|
||||
contain: paint;
|
||||
overflow: hidden;
|
||||
isolation: isolate;
|
||||
position: relative;
|
||||
}
|
||||
.co-tags-container {
|
||||
width: 100%;
|
||||
max-width: 100%;
|
||||
padding: 0.75rem;
|
||||
}
|
||||
.co-tags {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
overflow-y: hidden;
|
||||
overflow-wrap: break-word;
|
||||
line-height: 1;
|
||||
color: light-dark(rgb(104 102 100), rgb(191 186 181));
|
||||
}
|
||||
.co-tags a {
|
||||
display: inline-block;
|
||||
margin-right: 0.5rem;
|
||||
font-size: 0.875rem;
|
||||
line-height: 1.25rem;
|
||||
}
|
||||
.co-tags a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
`;
|
||||
|
||||
@customElement("cohost-post")
|
||||
export class CohostPost extends LitElement {
|
||||
static override styles = css`
|
||||
:host {
|
||||
color-scheme: light dark;
|
||||
font-family: "Atkinson Hyperlegible", ui-sans-serif, system-ui, sans-serif,
|
||||
"Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol",
|
||||
"Noto Color Emoji";
|
||||
}
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
border-width: 0;
|
||||
border-style: solid;
|
||||
border-color: #ded9d3;
|
||||
}
|
||||
a {
|
||||
color: inherit;
|
||||
text-decoration: inherit;
|
||||
}
|
||||
hr {
|
||||
height: 0;
|
||||
color: inherit;
|
||||
border-top-width: 1px;
|
||||
}
|
||||
blockquote,
|
||||
dl,
|
||||
dd,
|
||||
h1,
|
||||
h2,
|
||||
h3,
|
||||
h4,
|
||||
h5,
|
||||
h6,
|
||||
hr,
|
||||
figure,
|
||||
p,
|
||||
pre {
|
||||
margin: 0;
|
||||
}
|
||||
${COMMON_CSS}
|
||||
.co-post-box {
|
||||
width: 100%;
|
||||
overflow-x: auto;
|
||||
|
@ -84,151 +289,9 @@ export class CohostWebComponent extends LitElement {
|
|||
min-width: 0px;
|
||||
display: flex;
|
||||
}
|
||||
.co-avatar-container {
|
||||
width: 2rem;
|
||||
height: 2rem;
|
||||
aspect-ratio: 1 / 1;
|
||||
display: inline-block;
|
||||
position: relative;
|
||||
}
|
||||
.mask {
|
||||
-webkit-mask-size: contain;
|
||||
mask-size: contain;
|
||||
-webkit-mask-repeat: no-repeat;
|
||||
mask-repeat: no-repeat;
|
||||
-webkit-mask-position: center;
|
||||
mask-position: center;
|
||||
}
|
||||
.mask-squircle {
|
||||
-webkit-mask-image: url(data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJNMTAwIDBDMjAgMCAwIDIwIDAgMTAwczIwIDEwMCAxMDAgMTAwIDEwMC0yMCAxMDAtMTAwUzE4MCAwIDEwMCAweiIvPjwvc3ZnPg==);
|
||||
mask-image: url(data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjAwIiBoZWlnaHQ9IjIwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48cGF0aCBkPSJNMTAwIDBDMjAgMCAwIDIwIDAgMTAwczIwIDEwMCAxMDAgMTAwIDEwMC0yMCAxMDAtMTAwUzE4MCAwIDEwMCAweiIvPjwvc3ZnPg==);
|
||||
}
|
||||
.mask-roundrect {
|
||||
border-radius: 12.5%;
|
||||
}
|
||||
.mask-circle {
|
||||
border-radius: 9999px;
|
||||
}
|
||||
/* .mask-egg {
|
||||
-webkit-mask-image: url(/static/de7a6730ae8672a12406.svg);
|
||||
mask-image: url(/static/de7a6730ae8672a12406.svg);
|
||||
}
|
||||
.mask-capsule-big {
|
||||
-webkit-mask-image: url(/static/3e2b26f2f1e719024296.svg);
|
||||
mask-image: url(/static/3e2b26f2f1e719024296.svg);
|
||||
}
|
||||
.mask-capsule-small {
|
||||
-webkit-mask-image: url(/static/8ff201350af3c70fb5b8.svg);
|
||||
mask-image: url(/static/8ff201350af3c70fb5b8.svg);
|
||||
} */
|
||||
.co-avatar {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
-o-object-fit: cover;
|
||||
object-fit: cover;
|
||||
}
|
||||
.co-project-display-name {
|
||||
max-width: 100%;
|
||||
flex-shrink: 1;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
font-weight: 700;
|
||||
color: light-dark(rgb(25 25 25), rgb(255 249 242));
|
||||
}
|
||||
.co-project-display-name:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-project-handle {
|
||||
color: light-dark(rgb(74 72 71), rgb(222 217 211));
|
||||
}
|
||||
.co-project-handle:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-thread-header time {
|
||||
display: block;
|
||||
flex: none;
|
||||
font-size: 0.75rem;
|
||||
line-height: 1rem;
|
||||
font-variant-numeric: tabular-nums;
|
||||
color: rgb(130 127 124);
|
||||
}
|
||||
.co-thread-header time a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.co-hairline {
|
||||
border-color: light-dark(rgb(191 186 181), rgb(74 72 71));
|
||||
}
|
||||
.post-title-container {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
width: 100%;
|
||||
padding: 0.75rem;
|
||||
}
|
||||
.post-title-a {
|
||||
overflow-wrap: break-word;
|
||||
align-self: center;
|
||||
flex-grow: 1;
|
||||
}
|
||||
.post-title-a:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.prose {
|
||||
color: light-dark(#191919, #fff9f2);
|
||||
--tw-prose-body: light-dark(#374151, #fff9f2);
|
||||
--tw-prose-headings: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-lead: light-dark(#4b5563, #fff9f2);
|
||||
--tw-prose-links: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-bold: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-counters: light-dark(#6b7280, #fff9f2);
|
||||
--tw-prose-bullets: light-dark(#d1d5db, #fff9f2);
|
||||
--tw-prose-hr: light-dark(#e5e7eb, #bfbab5);
|
||||
--tw-prose-quotes: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-quote-borders: light-dark(#e5e7eb, #bfbab5);
|
||||
--tw-prose-captions: light-dark(#6b7280, #fff9f2);
|
||||
--tw-prose-code: light-dark(#111827, #fff9f2);
|
||||
--tw-prose-pre-code: light-dark(#e5e7eb, #fff9f2);
|
||||
--tw-prose-pre-bg: light-dark(#1f2937, #191919);
|
||||
--tw-prose-th-borders: light-dark(#d1d5db, #bfbab5);
|
||||
--tw-prose-td-borders: light-dark(#e5e7eb, #bfbab5);
|
||||
font-size: 1em;
|
||||
line-height: 1.75;
|
||||
}
|
||||
.prose
|
||||
:where(h3):not(:where([class~="not-prose"], [class~="not-prose"] *)) {
|
||||
color: var(--tw-prose-headings);
|
||||
font-weight: 600;
|
||||
font-size: 1.25em;
|
||||
margin-top: 1.6em;
|
||||
margin-bottom: 0.6em;
|
||||
line-height: 1.6;
|
||||
}
|
||||
.prose
|
||||
:where(.prose > :last-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.prose
|
||||
:where(.prose > :first-child):not(
|
||||
:where([class~="not-prose"], [class~="not-prose"] *)
|
||||
) {
|
||||
margin-top: 0;
|
||||
}
|
||||
.post-body {
|
||||
overflow: clip;
|
||||
contain: paint;
|
||||
overflow: hidden;
|
||||
isolation: isolate;
|
||||
position: relative;
|
||||
}
|
||||
.post-body-section {
|
||||
padding-left: 0.75rem;
|
||||
padding-right: 0.75rem;
|
||||
overflow-wrap: break-word;
|
||||
overflow: hidden;
|
||||
margin-top: 1rem;
|
||||
margin-bottom: 1rem;
|
||||
.header-share-icon {
|
||||
width: 1.25rem;
|
||||
height: 1.25rem;
|
||||
}
|
||||
.co-thread-footer {
|
||||
width: 100%;
|
||||
|
@ -281,41 +344,50 @@ export class CohostWebComponent extends LitElement {
|
|||
displayName = "Display Name";
|
||||
|
||||
@property()
|
||||
username = "username";
|
||||
handle = "handle";
|
||||
|
||||
@property()
|
||||
iso8601Timestamp = "2022-06-28T18:03:00Z";
|
||||
publishedAt: string | undefined;
|
||||
|
||||
@property()
|
||||
permalink = "https://cohost.org/";
|
||||
permalink: string | undefined;
|
||||
|
||||
@property({ type: Boolean })
|
||||
sharedItems: boolean = false;
|
||||
|
||||
@property()
|
||||
postId: string | undefined = undefined;
|
||||
postId: string | undefined;
|
||||
|
||||
@property()
|
||||
postTitle: string | undefined = undefined;
|
||||
singlePostHeadline: string | undefined;
|
||||
|
||||
@property()
|
||||
sharedAvatarSrc: string | undefined = undefined;
|
||||
sharedAvatarSrc: string | undefined;
|
||||
|
||||
@property()
|
||||
sharedDisplayName: string | undefined = undefined;
|
||||
sharedAvatarShape: string | undefined;
|
||||
|
||||
@property()
|
||||
sharedUsername: string | undefined = undefined;
|
||||
sharedDisplayName: string | undefined;
|
||||
|
||||
@property()
|
||||
tags: string | undefined = undefined;
|
||||
sharedHandle: string | undefined;
|
||||
|
||||
@property()
|
||||
tags: string | undefined;
|
||||
|
||||
@property({ type: Number })
|
||||
comments = 0;
|
||||
|
||||
@state()
|
||||
protected _displayTimestamp = new Date(
|
||||
this.iso8601Timestamp,
|
||||
).toLocaleString();
|
||||
|
||||
override render() {
|
||||
let displayTimestamp = undefined;
|
||||
let relativeTimestamp = undefined;
|
||||
if (this.publishedAt) {
|
||||
let date = new Date(this.publishedAt);
|
||||
displayTimestamp = date.toLocaleString();
|
||||
relativeTimestamp = formatRelativeTime(date);
|
||||
}
|
||||
|
||||
return html`
|
||||
<article
|
||||
data-theme="both"
|
||||
|
@ -324,98 +396,186 @@ export class CohostWebComponent extends LitElement {
|
|||
>
|
||||
<header class="co-thread-header">
|
||||
<div class="co-thread-header-1">
|
||||
<div class="co-avatar-container mask">
|
||||
<img
|
||||
src="${this.avatarSrc}"
|
||||
class="co-avatar mask mask-${this.avatarShape}"
|
||||
alt="${this.displayName}"
|
||||
/>
|
||||
</div>
|
||||
<a
|
||||
rel="author"
|
||||
href="https://cohost.org/${this.username}"
|
||||
class="co-project-display-name"
|
||||
title="${this.displayName}"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>${this.displayName}</a
|
||||
><a
|
||||
href="https://cohost.org/${this.username}"
|
||||
class="co-project-handle"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>@${this.username}</a
|
||||
><time
|
||||
datetime="${this.iso8601Timestamp}"
|
||||
class="block flex-none text-xs tabular-nums text-gray-500"
|
||||
title="${this._displayTimestamp}"
|
||||
><a href="${this.permalink}" class="hover:underline"
|
||||
>${this._displayTimestamp}</a
|
||||
></time
|
||||
>
|
||||
${when(
|
||||
this.avatarSrc,
|
||||
() => html`
|
||||
<div class="co-avatar-container mask">
|
||||
<img
|
||||
src="${this.avatarSrc}"
|
||||
class="co-avatar mask mask-${this.avatarShape}"
|
||||
alt="${this.displayName}"
|
||||
/>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.displayName,
|
||||
() => html`
|
||||
<a
|
||||
rel="author"
|
||||
href="https://cohost.org/${this.handle}"
|
||||
class="co-project-display-name"
|
||||
title="${this.displayName}"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>${this.displayName}</a
|
||||
>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.handle,
|
||||
() =>
|
||||
html` <a
|
||||
href="https://cohost.org/${this.handle}"
|
||||
class="co-project-handle"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>@${this.handle}</a
|
||||
>`,
|
||||
)}
|
||||
${when(
|
||||
this.publishedAt,
|
||||
() => html`
|
||||
<time
|
||||
datetime="${ifDefined(this.publishedAt)}"
|
||||
title="${ifDefined(displayTimestamp)}"
|
||||
><a
|
||||
href="${ifDefined(this.permalink)}"
|
||||
class="hover:underline"
|
||||
>${relativeTimestamp}</a
|
||||
></time
|
||||
>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.sharedAvatarSrc ||
|
||||
this.sharedAvatarShape ||
|
||||
this.sharedDisplayName ||
|
||||
this.sharedHandle,
|
||||
() => html`
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 24 24"
|
||||
fill="currentColor"
|
||||
aria-hidden="true"
|
||||
class="co-project-display-name header-share-icon"
|
||||
>
|
||||
<path
|
||||
fill-rule="evenodd"
|
||||
d="M4.755 10.059a7.5 7.5 0 0112.548-3.364l1.903 1.903h-3.183a.75.75 0 100 1.5h4.992a.75.75 0 00.75-.75V4.356a.75.75 0 00-1.5 0v3.18l-1.9-1.9A9 9 0 003.306 9.67a.75.75 0 101.45.388zm15.408 3.352a.75.75 0 00-.919.53 7.5 7.5 0 01-12.548 3.364l-1.902-1.903h3.183a.75.75 0 000-1.5H2.984a.75.75 0 00-.75.75v4.992a.75.75 0 001.5 0v-3.18l1.9 1.9a9 9 0 0015.059-4.035.75.75 0 00-.53-.918z"
|
||||
clip-rule="evenodd"
|
||||
></path>
|
||||
</svg>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.sharedAvatarSrc,
|
||||
() => html`
|
||||
<div class="co-avatar-container mask">
|
||||
<img
|
||||
src="${ifDefined(this.sharedAvatarSrc)}"
|
||||
class="co-avatar mask mask-${this.sharedAvatarShape}"
|
||||
alt="${ifDefined(this.sharedDisplayName)}"
|
||||
/>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.sharedDisplayName,
|
||||
() => html`
|
||||
<a
|
||||
href="https://cohost.org/${this.sharedHandle}"
|
||||
class="co-project-display-name"
|
||||
title="${ifDefined(this.sharedDisplayName)}"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>${this.sharedDisplayName}</a
|
||||
>
|
||||
`,
|
||||
)}
|
||||
${when(
|
||||
this.sharedHandle,
|
||||
() =>
|
||||
html` <a
|
||||
href="https://cohost.org/${this.sharedHandle}"
|
||||
class="co-project-handle"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>@${this.sharedHandle}</a
|
||||
>`,
|
||||
)}
|
||||
</div>
|
||||
<!--<button
|
||||
id="headlessui-menu-button"
|
||||
type="button"
|
||||
aria-haspopup="menu"
|
||||
aria-expanded="false"
|
||||
data-headlessui-state=""
|
||||
>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
fill="none"
|
||||
viewBox="0 0 24 24"
|
||||
stroke-width="1.5"
|
||||
stroke="currentColor"
|
||||
aria-hidden="true"
|
||||
class="co-action-button h-6 w-6 transition-transform ui-open:rotate-90"
|
||||
>
|
||||
<path
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
d="M6.75 12a.75.75 0 11-1.5 0 .75.75 0 011.5 0zM12.75 12a.75.75 0 11-1.5 0 .75.75 0 011.5 0zM18.75 12a.75.75 0 11-1.5 0 .75.75 0 011.5 0z"
|
||||
></path>
|
||||
</svg>
|
||||
</button>-->
|
||||
</header>
|
||||
<hr class="co-hairline" />
|
||||
<div>
|
||||
${when(
|
||||
this.postId,
|
||||
() => html`
|
||||
<div id="post-${this.postId}" class="relative -top-20"></div>
|
||||
<div id="post-${this.postId}" class="post-anchor"></div>
|
||||
`,
|
||||
)}
|
||||
<div class="post-body-container">
|
||||
${when(
|
||||
this.postTitle,
|
||||
() => html`
|
||||
<div class="post-title-container flex w-full flex-row p-3">
|
||||
<a href="${this.permalink}" class="post-title-a prose"
|
||||
><h3>${this.postTitle}</h3></a
|
||||
>
|
||||
${when(
|
||||
this.sharedItems,
|
||||
() => html`<slot></slot>`,
|
||||
() => html`
|
||||
<div class="post-body-container">
|
||||
${when(
|
||||
this.singlePostHeadline,
|
||||
() => html`
|
||||
<div
|
||||
class="post-headline-container flex w-full flex-row p-3"
|
||||
>
|
||||
<a
|
||||
href="${ifDefined(this.permalink)}"
|
||||
class="post-headline-a prose"
|
||||
><h3>${this.singlePostHeadline}</h3></a
|
||||
>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
<div
|
||||
class="post-body"
|
||||
data-post-body="true"
|
||||
data-testid="post-body"
|
||||
>
|
||||
<slot></slot>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
<div
|
||||
class="post-body relative overflow-hidden supports-[overflow:clip]:overflow-clip isolate co-contain-paint"
|
||||
data-post-body="true"
|
||||
data-testid="post-body"
|
||||
>
|
||||
<div class="post-body-section prose">
|
||||
<slot></slot>
|
||||
${when(
|
||||
this.tags && this.tags.length,
|
||||
() => html`
|
||||
<div class="co-tags-container">
|
||||
<div
|
||||
class="co-tags relative w-full overflow-y-hidden break-words leading-none "
|
||||
>
|
||||
<div>
|
||||
${(this.tags || "")
|
||||
.split(",")
|
||||
.map(
|
||||
(tag) => html`
|
||||
<a href="https://cohost.org/tagged/${tag}"
|
||||
>#${tag}</a
|
||||
>
|
||||
`,
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
</div>
|
||||
<hr class="co-hairline" />
|
||||
<footer class="co-thread-footer">
|
||||
<div class="co-thread-footer-1">
|
||||
<div class="comments">
|
||||
<a
|
||||
href="${this.permalink}#comments"
|
||||
href="${ifDefined(this.permalink)}#comments"
|
||||
class="text-sm hover:underline"
|
||||
>${this.comments} comment${this.comments == 1 ? "" : "s"}</a
|
||||
>
|
||||
|
@ -458,8 +618,136 @@ export class CohostWebComponent extends LitElement {
|
|||
}
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
"cohost-wc": CohostWebComponent;
|
||||
@customElement("cohost-shared-item")
|
||||
export class CohostSharedItem extends LitElement {
|
||||
static override styles = css`
|
||||
${COMMON_CSS}
|
||||
|
||||
.co-post-header {
|
||||
display: flex;
|
||||
flex-direction: flex-row;
|
||||
flex-wrap: wrap;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
padding-left: 0.75rem;
|
||||
padding-right: 0.75rem;
|
||||
padding-top: 0.5rem;
|
||||
padding-bottom: 0.5rem;
|
||||
background-color: light-dark(rgb(255 249 242), rgb(25 25 25));
|
||||
}
|
||||
`;
|
||||
|
||||
@property()
|
||||
avatarSrc =
|
||||
"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAACuUlEQVRYR9WXPYwpURTHz3QbDdFJdqOxEWJXT7EVsgoRCRK6jSgUZCVb2ZJ2V7ONoBIfpVLUVBoiohAKQie7jejue+e+3HljPnzMWzbvVmbm3vv/nf85Z8bler0e0ev1cHV1BZcc2+0W1us1cNPplOAPk8kEWq32IgxfX18wmUwAA+eWyyXRaDT0xiUgmDhqbTabPwAGgwGED87lhFhjtVr9BUDvzwkht7cE4FwQSoHJAnw3xD5XFQG+C+JQSvcC/CvEIXHc/yCAWohjxI8GOBXiWPGTAI6FOEX8ZIBDEKeKqwJQglAjrhpADIHXar8jR3WB0ueRRY3P1X7E/l8AYc4vngK5grtYEe4TUgOxUwODwQDsdjtfc/1+H+7v7/lrOYHFYgE3Nzf8nM/PT74jdDodf79UKsHT05OkninA29sbeX5+Bo7jYD6fw/X1NbTbbXC73UAIoYuUorPZbFCtVilouVyGVqsFhUIBgsEgJBIJ8Pv9wCDFAfHvgVQqRfL5vIQOgXCR0WhU7HPcHIFxoIORSASGw6EEOBwOg8fjkbhAHajX6wQniAcCjEYjsFqt0Ol0wOFw0ClCp4RrXl9f6WU2m5W4Fo/HIRaLgcvl2pFRfA9gCpLJJFQqFcB/zGgpRoYiDw8POxsJ64ClkKlg6rrdLni9Xj69QgIKYDabyXg85u+zDWu1Gjw+PtKzAgIVi0U6p9FoSNxiKcAiFkNYLBYIhUKQTqcl5w4K8HsxYYuY+MfHB0Sj0Z0FrCaEnSEmwaJ8f3/nHcJrLMSXlxfZOpIAoIicOLMeuwVToTSEAFhXt7e3sjXBzh0UwOfzkWazCYFAAO7u7iRWYXXncjlqPaYC3cKeZm7JtS5rSXG6FA8ms9kMnE6nJDDscWwtYV4xMlbR4pcXm4dOikcmk6FuSI5mP344/enj+S+rBamTP+UGdwAAAABJRU5ErkJggg==";
|
||||
|
||||
@property()
|
||||
avatarShape = "squircle";
|
||||
|
||||
@property()
|
||||
displayName = "Display Name";
|
||||
|
||||
@property()
|
||||
handle = "handle";
|
||||
|
||||
@property()
|
||||
publishedAt: string | undefined;
|
||||
|
||||
@property()
|
||||
permalink: string | undefined;
|
||||
|
||||
@property({ type: Boolean })
|
||||
sharedItems: boolean = false;
|
||||
|
||||
@property()
|
||||
postId: string | undefined;
|
||||
|
||||
@property()
|
||||
headline: string | undefined;
|
||||
|
||||
@property()
|
||||
tags: string | undefined;
|
||||
|
||||
@property({ type: Number })
|
||||
comments = 0;
|
||||
|
||||
override render() {
|
||||
let displayTimestamp = undefined;
|
||||
let relativeTimestamp = undefined;
|
||||
if (this.publishedAt) {
|
||||
let date = new Date(this.publishedAt);
|
||||
displayTimestamp = date.toLocaleString();
|
||||
relativeTimestamp = formatRelativeTime(date);
|
||||
}
|
||||
|
||||
return html`
|
||||
${when(
|
||||
this.postId,
|
||||
() => html` <div id="post-${this.postId}" class="post-anchor"></div> `,
|
||||
)}
|
||||
<div class="co-post-header">
|
||||
<div class="co-avatar-container mask">
|
||||
<img
|
||||
src="${this.avatarSrc}"
|
||||
class="co-avatar mask mask-${this.avatarShape}"
|
||||
alt="${this.displayName}"
|
||||
/>
|
||||
</div>
|
||||
<a
|
||||
rel="author"
|
||||
href="https://cohost.org/${this.handle}"
|
||||
class="co-project-display-name"
|
||||
title="${this.displayName}"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>${this.displayName}</a
|
||||
><a
|
||||
rel="author"
|
||||
href="https://cohost.org/${this.handle}"
|
||||
class="co-project-handle"
|
||||
data-url-popovers=""
|
||||
style="user-select: none;"
|
||||
data-longpress-event="true"
|
||||
>@${this.handle}</a
|
||||
>${when(
|
||||
this.publishedAt,
|
||||
() =>
|
||||
html`<time
|
||||
datetime="${ifDefined(this.publishedAt)}"
|
||||
title="${ifDefined(displayTimestamp)}"
|
||||
><a href="${ifDefined(this.permalink)}"
|
||||
>${relativeTimestamp}</a
|
||||
></time
|
||||
>`,
|
||||
)}
|
||||
</div>
|
||||
<div class="post-body-container">
|
||||
${when(
|
||||
this.headline,
|
||||
() => html`
|
||||
<div class="post-headline-container flex w-full flex-row p-3">
|
||||
<a
|
||||
href="${ifDefined(this.permalink)}"
|
||||
class="post-headline-a prose"
|
||||
><h3>${this.headline}</h3></a
|
||||
>
|
||||
</div>
|
||||
`,
|
||||
)}
|
||||
<div class="post-body" data-post-body="true" data-testid="post-body">
|
||||
<div class="post-body-section">
|
||||
<slot></slot>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<hr class="co-hairline" />
|
||||
`;
|
||||
}
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
"cohost-post": CohostPost;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue