From efff30a9b6a6782c95874eb6070146060ad0800a Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Mon, 12 Oct 2026 14:06:40 +0000 Subject: [PATCH 1/2] feat: social share card meta (og/twitter) Add a 1200x630 paper/ink share image and site-wide Open Graph / Twitter tags so pasted links show a large preview card. Pages keep their own title and description. Co-authored-by: froQ --- docs/app/composables/useShareMeta.ts | 30 ++++++++++++++++++ docs/app/error.vue | 7 ++-- docs/app/pages/[...slug].vue | 7 ++-- docs/app/pages/changelog.vue | 6 ++-- .../app/pages/components/[concept]/[name].vue | 6 ++-- docs/app/pages/components/[concept]/index.vue | 5 ++- docs/app/pages/components/index.vue | 5 ++- docs/app/pages/docs/[...slug].vue | 7 ++-- docs/app/pages/index.vue | 6 ++-- docs/nuxt.config.ts | 22 ++++++++++++- docs/public/og.png | Bin 0 -> 28084 bytes docs/shared/site.ts | 20 ++++++++++++ 12 files changed, 106 insertions(+), 15 deletions(-) create mode 100644 docs/app/composables/useShareMeta.ts create mode 100644 docs/public/og.png create mode 100644 docs/shared/site.ts diff --git a/docs/app/composables/useShareMeta.ts b/docs/app/composables/useShareMeta.ts new file mode 100644 index 0000000..2bbd5e8 --- /dev/null +++ b/docs/app/composables/useShareMeta.ts @@ -0,0 +1,30 @@ +import type { MaybeRefOrGetter } from 'vue' +import { canonicalUrl, shareTitle } from '../../shared/site' + +/** Document title plus Open Graph / Twitter tags for the current route. */ +export function useShareMeta(input: { + title?: MaybeRefOrGetter + description?: MaybeRefOrGetter + type?: MaybeRefOrGetter<'website' | 'article' | undefined> +} = {}): void { + const route = useRoute() + const title = computed(() => shareTitle(toValue(input.title))) + const description = computed(() => { + const value = input.description == null ? undefined : toValue(input.description) + return value || undefined + }) + + useHead({ + title: () => input.title == null ? undefined : toValue(input.title) || undefined, + }) + + useSeoMeta({ + description, + ogTitle: title, + twitterTitle: title, + ogDescription: description, + twitterDescription: description, + ogUrl: () => canonicalUrl(route.path), + ogType: () => toValue(input.type) ?? 'website', + }) +} diff --git a/docs/app/error.vue b/docs/app/error.vue index 127a015..ac8476d 100644 --- a/docs/app/error.vue +++ b/docs/app/error.vue @@ -1,12 +1,15 @@