Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions apps/www/next.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,14 @@ const nextConfig = async (phase: string) => {
destination: '/:path*?locale=cn', // Rewrite it to the corresponding path without /cn
source: '/cn/:path*', // Match any path under /cn
},
{
destination: '/?locale=pt-br',
source: '/pt-br',
},
{
destination: '/:path*?locale=pt-br', // Rewrite it to the corresponding path without /pt-br
source: '/pt-br/:path*', // Match any path under /pt-br
},
];
},

Expand Down
3 changes: 3 additions & 0 deletions apps/www/src/app/(app)/_components/announcement-button.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,9 @@ const i18n = {
en: {
description: 'MCP, AI, Upload, and more',
},
'pt-br': {
description: 'MCP, IA, Upload, e mais',
},
};

export function AnnouncementButton() {
Expand Down
7 changes: 7 additions & 0 deletions apps/www/src/app/(app)/_components/potion-lazy-block.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,13 @@ const i18n = {
github: 'GitHub',
potionDescription: 'A Notion-like AI template.',
},
'pt-br': {
buildYourRichTextEditor: 'Construa seu editor de texto',
description: 'Framework · Plugins · Componentes · Temas',
getStarted: 'Começar',
github: 'GitHub',
potionDescription: 'Um template de IA similar ao Notion.',
},
};

export function PotionLazyBlock() {
Expand Down
26 changes: 13 additions & 13 deletions apps/www/src/app/(app)/docs/[[...slug]]/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -43,23 +43,23 @@ async function getDocFromParams({ params, searchParams }: DocPageProps) {

let slug = slugParam?.join('/') || '';

// For Chinese docs, look for .cn.mdx files
if (locale === 'cn') {
// First try to find the Chinese version with .cn.mdx
const cnDoc = allDocs.find(
// For non-default locales (e.g. cn, pt-br), look for .locale.mdx files
if (locale) {
// First try to find the localized version with .locale.mdx
const localizedDoc = allDocs.find(
(doc) =>
doc.slugAsParams === `docs/${slug || 'index'}.cn` &&
doc._raw.sourceFileName?.endsWith('.cn.mdx')
doc.slugAsParams === `docs/${slug || 'index'}.${locale}` &&
doc._raw.sourceFileName?.endsWith(`.${locale}.mdx`)
);

if (cnDoc) {
if (localizedDoc) {
const path = slugParam?.join('/') || '';
cnDoc.slug = `/docs${path ? `/${path}` : ''}?locale=cn`;
return cnDoc;
localizedDoc.slug = `/docs${path ? `/${path}` : ''}?locale=${locale}`;
return localizedDoc;
}
}

// Default behavior for non-Chinese or fallback
// Default behavior for non-localized or fallback
slug = `docs${slug ? `/${slug}` : ''}`;
const doc = allDocs.find((doc) => doc.slugAsParams === slug);

Expand All @@ -70,9 +70,9 @@ async function getDocFromParams({ params, searchParams }: DocPageProps) {
const path = slugParam?.join('/') || '';
doc.slug = `/docs${path ? `/${path}` : ''}`;

// Only add locale param for Chinese
if (locale === 'cn') {
doc.slug += '?locale=cn';
// Only add locale param if present
if (locale) {
doc.slug += `?locale=${locale}`;
}

return doc;
Expand Down
5 changes: 5 additions & 0 deletions apps/www/src/app/(app)/editors/editor-description.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,11 @@ const i18n = {
description: 'Beautifully designed. Copy and paste into your apps.',
title: 'Building Editors for the Web',
},
'pt-br': {
browseEditors: 'Navegar por Editores',
description: 'Desenhado elegantemente. Copie e cole em suas aplicações.',
title: 'Construindo Editores para a Web',
},
};

export function EditorDescription() {
Expand Down
7 changes: 7 additions & 0 deletions apps/www/src/app/(app)/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,13 @@ const i18n = {
github: 'GitHub',
potionDescription: 'A Notion-like AI template.',
},
'pt-br': {
buildYourRichTextEditor: 'Construa seu editor de texto',
description: 'Framework · Plugins · Componentes · Temas',
getStarted: 'Começar',
github: 'GitHub',
potionDescription: 'Um template de IA similar ao Notion.',
},
};

const title = 'Build your rich-text editor';
Expand Down
39 changes: 26 additions & 13 deletions apps/www/src/components/languages-dropdown-menu.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,23 +16,26 @@ export function LanguagesDropdownMenu() {

const handleClick = (locale?: string) => {
const url = new URL(window.location.href);
const supportedLocales = ['cn', 'pt-br'];

if (locale) {
if (pathname?.includes(locale)) {
return;
}
if (!pathname) return;

const segments = pathname.split('/').filter((p) => !!p);
const currentLocale = supportedLocales.includes(segments[0])
? segments[0]
: undefined;

// If the target locale is the same as the current, do nothing
if (locale === currentLocale) return;

// Remove the current locale from the segments if it exists
const newSegments = currentLocale ? segments.slice(1) : segments;

url.pathname = `/${locale}${pathname}`;
if (locale) {
url.pathname = `/${locale}/${newSegments.join('/')}`;
url.searchParams.set('locale', locale);
} else {
if (!pathname?.includes('cn')) return;
if (pathname) {
const segments = pathname.split('/').filter((p) => !!p);
const newSegments = segments.filter((segment) => segment !== 'cn');
url.pathname =
newSegments.length > 0 ? `/${newSegments.join('/')}` : '/';
}

url.pathname = `/${newSegments.join('/')}`;
url.searchParams.delete('locale');
}

Expand Down Expand Up @@ -66,6 +69,16 @@ export function LanguagesDropdownMenu() {
中文
</button>
</DropdownMenuItem>
<DropdownMenuItem asChild>
<button
type="button"
className="w-full cursor-pointer"
onClick={() => handleClick('pt-br')}
>
Português
<span className="text-muted-foreground text-xs">Beta</span>
</button>
</DropdownMenuItem>
</DropdownMenuContent>
</DropdownMenu>
);
Expand Down
6 changes: 6 additions & 0 deletions apps/www/src/components/main-nav.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,12 @@ const i18n = {
editors: 'Editors',
templates: 'Templates',
},
'pt-br': {
components: 'Componentes',
docs: 'Documentação',
editors: 'Editores',
templates: 'Templates',
},
};

export function MainNav({
Expand Down
6 changes: 6 additions & 0 deletions apps/www/src/components/open-in-plus.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,12 @@ const i18n = {
getAccess: 'Get all-access',
productionReady: 'Production-ready AI template and reusable components.',
},
'pt-br': {
buildYourEditor: 'Construa seu editor',
getAccess: 'Obtenha acesso completo',
productionReady:
'Template de IA pronto para produção e componentes reutilizáveis.',
},
};

export function OpenInPlus({ className }: { className?: string }) {
Expand Down
3 changes: 3 additions & 0 deletions apps/www/src/components/playground-preview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,9 @@ const i18n = {
en: {
description: 'An AI editor',
},
'pt-br': {
description: 'Um editor de IA',
},
};

// TODO: sync
Expand Down
4 changes: 3 additions & 1 deletion apps/www/src/hooks/useLocale.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,4 +8,6 @@ export const useLocale = () => {
};

export const getLocalizedPath = (locale: string, href: string) =>
locale === 'cn' ? `/cn${href}?locale=cn` : href;
locale === 'cn' || locale === 'pt-br'
? `/${locale}${href}?locale=${locale}`
: href;
Loading