Smart language for the preview cards and preview line

This commit is contained in:
DrMint 2022-06-02 00:41:54 +02:00
parent 59283fa465
commit f2c572e576
6 changed files with 142 additions and 32 deletions

View File

@ -10,9 +10,11 @@ import {
prettyDuration, prettyDuration,
prettyPrice, prettyPrice,
prettyShortenNumber, prettyShortenNumber,
prettySlug,
} from "helpers/formatters"; } from "helpers/formatters";
import { ImageQuality } from "helpers/img"; import { ImageQuality } from "helpers/img";
import { Immutable } from "helpers/types"; import { Immutable } from "helpers/types";
import { useSmartLanguage } from "hooks/useSmartLanguage";
import Link from "next/link"; import Link from "next/link";
import { Chip } from "./Chip"; import { Chip } from "./Chip";
import { Ico, Icon } from "./Ico"; import { Ico, Icon } from "./Ico";
@ -260,3 +262,42 @@ export function PreviewCard(props: Immutable<Props>): JSX.Element {
</Link> </Link>
); );
} }
interface TranslatedProps
extends Omit<Props, "pre_title" | "subtitle" | "title"> {
translations:
| {
pre_title?: string | null | undefined;
title: string | null | undefined;
subtitle?: string | null | undefined;
language: string | undefined;
}[]
| undefined;
slug: string;
languages: AppStaticProps["languages"];
}
export function TranslatedPreviewCard(
props: Immutable<TranslatedProps>
): JSX.Element {
const {
translations = [{ title: props.slug, language: "default" }],
slug,
languages,
} = props;
const [selectedTranslation] = useSmartLanguage({
items: translations,
languages: languages,
languageExtractor: (item) => item.language,
});
return (
<PreviewCard
pre_title={selectedTranslation?.pre_title}
title={selectedTranslation?.title ?? prettySlug(slug)}
subtitle={selectedTranslation?.subtitle}
{...props}
/>
);
}

View File

@ -1,6 +1,9 @@
import { UploadImageFragment } from "graphql/generated"; import { UploadImageFragment } from "graphql/generated";
import { AppStaticProps } from "graphql/getAppStaticProps";
import { prettySlug } from "helpers/formatters";
import { ImageQuality } from "helpers/img"; import { ImageQuality } from "helpers/img";
import { Immutable } from "helpers/types"; import { Immutable } from "helpers/types";
import { useSmartLanguage } from "hooks/useSmartLanguage";
import Link from "next/link"; import Link from "next/link";
import { Chip } from "./Chip"; import { Chip } from "./Chip";
import { Img } from "./Img"; import { Img } from "./Img";
@ -71,3 +74,42 @@ export function PreviewLine(props: Immutable<Props>): JSX.Element {
</Link> </Link>
); );
} }
interface TranslatedProps
extends Omit<Props, "pre_title" | "subtitle" | "title"> {
translations:
| {
pre_title?: string | null | undefined;
title: string | null | undefined;
subtitle?: string | null | undefined;
language: string | undefined;
}[]
| undefined;
slug: string;
languages: AppStaticProps["languages"];
}
export function TranslatedPreviewLine(
props: Immutable<TranslatedProps>
): JSX.Element {
const {
translations = [{ title: props.slug, language: "default" }],
slug,
languages,
} = props;
const [selectedTranslation] = useSmartLanguage({
items: translations,
languages: languages,
languageExtractor: (item) => item.language,
});
return (
<PreviewLine
pre_title={selectedTranslation?.pre_title}
title={selectedTranslation?.title ?? prettySlug(slug)}
subtitle={selectedTranslation?.subtitle}
{...props}
/>
);
}

View File

@ -119,6 +119,13 @@ query getContentText($slug: String, $language_code: String) {
pre_title pre_title
title title
subtitle subtitle
language {
data {
attributes {
code
}
}
}
} }
categories { categories {
data { data {

View File

@ -8,6 +8,13 @@ query getContents($language_code: String) {
pre_title pre_title
title title
subtitle subtitle
language {
data {
attributes {
code
}
}
}
} }
categories { categories {
data { data {

View File

@ -9,7 +9,7 @@ import {
} from "components/PanelComponents/ReturnButton"; } from "components/PanelComponents/ReturnButton";
import { ContentPanel } from "components/Panels/ContentPanel"; import { ContentPanel } from "components/Panels/ContentPanel";
import { SubPanel } from "components/Panels/SubPanel"; import { SubPanel } from "components/Panels/SubPanel";
import { PreviewLine } from "components/PreviewLine"; import { PreviewLine, TranslatedPreviewLine } from "components/PreviewLine";
import { RecorderChip } from "components/RecorderChip"; import { RecorderChip } from "components/RecorderChip";
import { ThumbnailHeader } from "components/ThumbnailHeader"; import { ThumbnailHeader } from "components/ThumbnailHeader";
import { ToolTip } from "components/ToolTip"; import { ToolTip } from "components/ToolTip";
@ -227,16 +227,18 @@ export default function Content(props: Immutable<Props>): JSX.Element {
<h2 className="mb-4 text-center text-2xl"> <h2 className="mb-4 text-center text-2xl">
{langui.previous_content} {langui.previous_content}
</h2> </h2>
<PreviewLine <TranslatedPreviewLine
href={`/contents/${previousContent.attributes.slug}`} href={`/contents/${previousContent.attributes.slug}`}
pre_title={ translations={previousContent.attributes.translations?.map(
previousContent.attributes.translations?.[0]?.pre_title (translation) => ({
} pre_title: translation?.pre_title,
title={ title: translation?.title,
previousContent.attributes.translations?.[0]?.title ?? subtitle: translation?.subtitle,
prettySlug(previousContent.attributes.slug) language: translation?.language?.data?.attributes?.code,
} })
subtitle={previousContent.attributes.translations?.[0]?.subtitle} )}
slug={previousContent.attributes.slug}
languages={languages}
thumbnail={previousContent.attributes.thumbnail?.data?.attributes} thumbnail={previousContent.attributes.thumbnail?.data?.attributes}
thumbnailAspectRatio="3/2" thumbnailAspectRatio="3/2"
topChips={ topChips={
@ -275,14 +277,18 @@ export default function Content(props: Immutable<Props>): JSX.Element {
<h2 className="mb-4 text-center text-2xl"> <h2 className="mb-4 text-center text-2xl">
{langui.followup_content} {langui.followup_content}
</h2> </h2>
<PreviewLine <TranslatedPreviewLine
href={`/contents/${nextContent.attributes.slug}`} href={`/contents/${nextContent.attributes.slug}`}
pre_title={nextContent.attributes.translations?.[0]?.pre_title} translations={nextContent.attributes.translations?.map(
title={ (translation) => ({
nextContent.attributes.translations?.[0]?.title ?? pre_title: translation?.pre_title,
prettySlug(nextContent.attributes.slug) title: translation?.title,
} subtitle: translation?.subtitle,
subtitle={nextContent.attributes.translations?.[0]?.subtitle} language: translation?.language?.data?.attributes?.code,
})
)}
slug={nextContent.attributes.slug}
languages={languages}
thumbnail={nextContent.attributes.thumbnail?.data?.attributes} thumbnail={nextContent.attributes.thumbnail?.data?.attributes}
thumbnailAspectRatio="3/2" thumbnailAspectRatio="3/2"
topChips={ topChips={

View File

@ -8,7 +8,7 @@ import {
ContentPanelWidthSizes, ContentPanelWidthSizes,
} from "components/Panels/ContentPanel"; } from "components/Panels/ContentPanel";
import { SubPanel } from "components/Panels/SubPanel"; import { SubPanel } from "components/Panels/SubPanel";
import { PreviewCard } from "components/PreviewCard"; import { PreviewCard, TranslatedPreviewCard } from "components/PreviewCard";
import { GetContentsQuery } from "graphql/generated"; import { GetContentsQuery } from "graphql/generated";
import { AppStaticProps, getAppStaticProps } from "graphql/getAppStaticProps"; import { AppStaticProps, getAppStaticProps } from "graphql/getAppStaticProps";
import { getReadySdk } from "graphql/sdk"; import { getReadySdk } from "graphql/sdk";
@ -35,7 +35,7 @@ const defaultFiltersState = {
}; };
export default function Contents(props: Immutable<Props>): JSX.Element { export default function Contents(props: Immutable<Props>): JSX.Element {
const { langui, contents } = props; const { langui, contents, languages } = props;
const [groupingMethod, setGroupingMethod] = useState<number>( const [groupingMethod, setGroupingMethod] = useState<number>(
defaultFiltersState.groupingMethod defaultFiltersState.groupingMethod
@ -176,14 +176,19 @@ export default function Contents(props: Immutable<Props>): JSX.Element {
{items.map((item) => ( {items.map((item) => (
<Fragment key={item.id}> <Fragment key={item.id}>
{item.attributes && ( {item.attributes && (
<PreviewCard <TranslatedPreviewCard
href={`/contents/${item.attributes.slug}`} href={`/contents/${item.attributes.slug}`}
pre_title={item.attributes.translations?.[0]?.pre_title} translations={item.attributes.translations?.map(
title={ (translation) => ({
item.attributes.translations?.[0]?.title ?? pre_title: translation?.pre_title,
prettySlug(item.attributes.slug) title: translation?.title,
} subtitle: translation?.subtitle,
subtitle={item.attributes.translations?.[0]?.subtitle} language:
translation?.language?.data?.attributes?.code,
})
)}
slug={item.attributes.slug}
languages={languages}
thumbnail={item.attributes.thumbnail?.data?.attributes} thumbnail={item.attributes.thumbnail?.data?.attributes}
thumbnailAspectRatio="3/2" thumbnailAspectRatio="3/2"
stackNumber={ stackNumber={
@ -343,13 +348,15 @@ function filterContents(
} }
if (searchName.length > 1) { if (searchName.length > 1) {
if ( if (
prettyinlineTitle( content.attributes?.translations?.find((translation) =>
content.attributes?.translations?.[0]?.pre_title, prettyinlineTitle(
content.attributes?.translations?.[0]?.title, translation?.pre_title,
content.attributes?.translations?.[0]?.subtitle translation?.title,
translation?.subtitle
)
.toLowerCase()
.includes(searchName.toLowerCase())
) )
.toLowerCase()
.includes(searchName.toLowerCase())
) { ) {
return true; return true;
} }