add some french translations

This commit is contained in:
MathieuG-P
2022-12-11 02:20:25 +01:00
parent 55e7145ba2
commit d378312dbd
7 changed files with 141 additions and 49 deletions
+76
View File
@@ -15,6 +15,19 @@
"desktop": "Mode Bureau",
"debug": "Mode Debug"
},
"maps":{
"search-bar":{
"search-placeholder": "Rechercher une map",
"filters-btn":"Filtres",
"dropdown":{
"export-maps": "Exporter les maps",
"delete-maps": "Supprimer les maps"
}
},
"maps-panel":{
}
},
"mods":{
"loading-mods": "Chargement des mods...",
"buttons":{
@@ -392,6 +405,69 @@
}
}
},
"maps":{
"map-filter-panel":{
"duration": "Durée",
"tags": "tags",
"specificities": "général",
"requirements": "requis"
},
"map-types":{
"accuracy": "précision",
"balanced": "équilibrée",
"challenge": "challenge",
"dancestyle": "dance",
"fitness": "fitness",
"speed": "vitesse",
"tech": "tech"
},
"map-styles":{
"dance": "dance",
"swing": "swing",
"nightcore": "nightcore",
"folk": "Folk",
"family": "Famille",
"ambient": "ambiante",
"funk": "funk",
"jazz": "jazz",
"soul": "soul",
"speedcore": "speedcore",
"punk": "punk",
"rb": "r&b",
"holiday": "vacance",
"vocaloid": "vocaloid",
"jrock": "j-rock",
"trance": "trance",
"drumbass": "drum & bass",
"comedy": "comédie",
"instrumental": "instrumental",
"hardcore": "hardcore",
"kpop": "k-pop",
"indie": "indé",
"techno": "techno",
"house": "house",
"game": "jeu vidéo",
"film": "film",
"alt": "alternative",
"dubstep": "dubstep",
"metal": "metal",
"anime": "anime",
"hiphop": "hiphop",
"jpop": "j-pop",
"rock": "rock",
"pop": "pop",
"electronic": "éléctronique",
"classical-orchestral": "Classique & Orchestral"
},
"map-specificities":{
"automapper": "ia",
"ranked": "classée",
"curated": "recommandée",
"verified": "vérifiée",
"fullSpread": "panel complet"
}
},
"auto-update":{
"checking": "Vérification des mises à jour",
"downloading": "Téléchargement des mises à jour"
@@ -1,4 +1,4 @@
import { MapFilter, MapTag } from "shared/models/maps/beat-saver.model"
import { MapFilter, MapSpecificity, MapStyle, MapTag, MapType } from "shared/models/maps/beat-saver.model"
import {motion} from "framer-motion"
import { MutableRefObject} from "react"
import { MAP_TYPES } from "renderer/partials/maps/map-tags/map-types"
@@ -8,6 +8,9 @@ import { diffColors } from "./map-item.component"
import { min_to_s } from "renderer/helpers/time-utils"
import dateFormat from "dateformat"
import { BsmRange } from "../shared/bsm-range.component"
import { useTranslation } from "renderer/hooks/use-translation.hook"
import { MAP_SPECIFICITIES } from "renderer/partials/maps/map-general/map-specificity"
import { MAP_REQUIREMENTS } from "renderer/partials/maps/map-requirements/map-requirements"
export type Props = {
className?: string,
@@ -19,6 +22,8 @@ export type Props = {
export function FilterPanel({className, ref, playlist = false, filter, onChange}: Props) {
const t = useTranslation();
const MIN_NPS = 0;
const MAX_NPS = 17;
@@ -34,7 +39,7 @@ export function FilterPanel({className, ref, playlist = false, filter, onChange}
const renderDurationLabel = (sec: number): JSX.Element => {
const textValue = (() => {
if(sec === MIN_DURATION){ return "Durée"; } //TODO TRADUIRE
if(sec === MIN_DURATION){ return t("maps.map-filter-panel.duration"); }
if(sec === MAX_DURATION){ return "∞"; }
const date = new Date(0);
date.setSeconds(sec);
@@ -104,6 +109,18 @@ export function FilterPanel({className, ref, playlist = false, filter, onChange}
}
const translateMapType = (type: MapType): string => {
return t(`maps.map-types.${type}`);
}
const translateMapStyle = (style: MapStyle): string => {
return t(`maps.map-styles.${style}`)
}
const translateMapSpecificity = (specificity: MapSpecificity): string => {
return t(`maps.map-specificities.${specificity}`);
}
type BooleanKeys<T> = { [k in keyof T]: T[k] extends boolean ? k : never }[keyof T];
const handleCheckbox = (key: BooleanKeys<MapFilter>) => {
@@ -125,56 +142,34 @@ export function FilterPanel({className, ref, playlist = false, filter, onChange}
</div>
<div className="w-full h-full flex gap-x-2"> {/* TODO TRADUIRE */}
<section className="shrink-0">
<h2 className="mb-1 uppercase text-sm">general</h2>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("automapper")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.automapper} onChange={() => handleCheckbox("automapper")}/>
<span className="grow capitalize">AI</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("ranked")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.ranked} onChange={() => handleCheckbox("ranked")}/>
<span className="grow capitalize">Rancked</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("curated")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.curated} onChange={() => handleCheckbox("curated")}/>
<span className="grow capitalize">Curated</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("verified")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.verified} onChange={() => handleCheckbox("verified")}/>
<span className="grow capitalize">Verified Mapper</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("fullSpread")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.fullSpread} onChange={() => handleCheckbox("fullSpread")}/>
<span className="grow capitalize">Full Spread</span>
</div>
<h2 className="my-1 uppercase text-sm">requirements</h2>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("chroma")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.chroma} onChange={() => handleCheckbox("chroma")}/>
<span className="grow capitalize">Chroma</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("noodle")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.noodle} onChange={() => handleCheckbox("noodle")}/>
<span className="grow capitalize">Noodle</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("me")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.me} onChange={() => handleCheckbox("me")}/>
<span className="grow capitalize" title="Mapping Extensions">Me</span>
</div>
<div className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={e => handleCheckbox("cinema")}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.cinema} onChange={() => handleCheckbox("cinema")}/>
<span className="grow capitalize">Cinema</span>
</div>
<h2 className="mb-1 uppercase text-sm">{t("maps.map-filter-panel.specificities")}</h2>
{MAP_SPECIFICITIES.map(specificity => (
<div key={specificity} className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={() => handleCheckbox(specificity)}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.[specificity]} onChange={() => handleCheckbox(specificity)}/>
<span className="grow capitalize">{translateMapSpecificity(specificity)}</span>
</div>
))}
<h2 className="my-1 uppercase text-sm">{t("maps.map-filter-panel.requirements")}</h2>
{MAP_REQUIREMENTS.map(requirement => (
<div key={requirement} className="flex justify-start items-center h-[22px] z-20 relative py-0.5 cursor-pointer" onClick={() => handleCheckbox(requirement)}>
<BsmCheckbox className="h-full aspect-square relative bg-inherit mr-1" checked={filter?.[requirement]} onChange={() => handleCheckbox(requirement)}/>
<span className="grow capitalize">{requirement}</span>
</div>
))}
</section>
<section className="grow capitalize">
<h2 className="uppercase text-sm mb-1">TAGS</h2>
<h2 className="uppercase text-sm mb-1">{t("maps.map-filter-panel.tags")}</h2>
<div className="w-full flex flex-row flex-wrap items-start justify-start content-start gap-1 mb-2">
{MAP_TYPES.map(tag => (
<span key={tag} onClick={() => handleTagClick(tag)} className={`text-[12.5px] text-black rounded-md px-1 font-bold cursor-pointer ${(!isTagActivated(tag)) && "opacity-40 hover:opacity-90"}`} style={{backgroundColor: isTagExcluded(tag) ? diffColors.Expert : diffColors.Normal}}>{tag}</span>
<span key={tag} onClick={() => handleTagClick(tag)} className={`text-[12.5px] text-black rounded-md px-1 font-bold cursor-pointer ${(!isTagActivated(tag)) && "opacity-40 hover:opacity-90"}`} style={{backgroundColor: isTagExcluded(tag) ? diffColors.Expert : diffColors.Normal}}>{translateMapType(tag)}</span>
))}
</div>
<div className="w-full flex flex-row flex-wrap items-start justify-start content-start gap-1">
{MAP_STYLES.map(tag => (
<span key={tag} onClick={() => handleTagClick(tag)} className={`text-[12.5px] text-black rounded-md px-1 font-bold cursor-pointer ${(!isTagActivated(tag)) && "opacity-40 hover:opacity-90"}`} style={{backgroundColor: isTagExcluded(tag) ? diffColors.Expert : diffColors.Easy}}>{tag}</span>
<span key={tag} onClick={() => handleTagClick(tag)} className={`text-[12.5px] text-black rounded-md px-1 font-bold cursor-pointer ${(!isTagActivated(tag)) && "opacity-40 hover:opacity-90"}`} style={{backgroundColor: isTagExcluded(tag) ? diffColors.Expert : diffColors.Easy}}>{translateMapStyle(tag)}</span>
))}
</div>
@@ -15,6 +15,7 @@ import wipGif from "../../../../assets/images/gifs/wip.gif"
import { OsDiagnosticService } from "renderer/services/os-diagnostic.service"
import { useObservable } from "renderer/hooks/use-observable.hook"
import { BsmIcon } from "../svgs/bsm-icon.component"
import { useTranslation } from "renderer/hooks/use-translation.hook"
type Props = {
version?: BSVersion
@@ -33,6 +34,7 @@ export function MapsPlaylistsPanel({version}: Props) {
const [mapsLinked, setMapsLinked] = useState(false);
const isOnline = useObservable(osDiagnostic.isOnline$);
const color = useThemeColor("first-color");
const t = useTranslation();
const mapsRef = useRef<any>();
useEffect(() => {
@@ -110,8 +112,8 @@ export function MapsPlaylistsPanel({version}: Props) {
]
}
return [
{icon:"export", text: "Exporter les maps", onClick: () => mapsRef.current.exportMaps?.()},
{icon: "trash", text: "Supprimer les maps", onClick: () => mapsRef.current.deleteMaps?.()}
{icon:"export", text: "pages.version-viewer.maps.search-bar.dropdown.export-maps", onClick: () => mapsRef.current.exportMaps?.()},
{icon: "trash", text: "pages.version-viewer.maps.search-bar.dropdown.delete-maps", onClick: () => mapsRef.current.deleteMaps?.()}
]
})()
@@ -120,9 +122,9 @@ export function MapsPlaylistsPanel({version}: Props) {
<div className="w-full h-full flex flex-col items-center justify-center">
<nav className="w-full shrink-0 flex h-[35px] justify-center px-40 gap-2 mb-3">
<div className="h-full rounded-full bg-main-color-2 grow p-[6px]">
<input type="text" className="h-full w-full bg-main-color-1 rounded-full px-2" placeholder="Rechercher" value={tabIndex === 0 ? mapSearch : playlistSearch} onChange={e => handleSearch(e.target.value)}/>
<input type="text" className="h-full w-full bg-main-color-1 rounded-full px-2" placeholder={t("pages.version-viewer.maps.search-bar.search-placeholder")} value={tabIndex === 0 ? mapSearch : playlistSearch} onChange={e => handleSearch(e.target.value)}/>
</div>
<BsmDropdownButton className="h-full relative z-[1] flex justify-center" buttonClassName="flex items-center justify-center h-full rounded-full px-2 py-1" icon="search" text="Filtres" withBar={false}>
<BsmDropdownButton className="h-full relative z-[1] flex justify-center" buttonClassName="flex items-center justify-center h-full rounded-full px-2 py-1" icon="search" text="pages.version-viewer.maps.search-bar.filters-btn" withBar={false}>
<FilterPanel className="absolute top-[calc(100%+3px)] bg-main-color-3 origin-top w-[500px] h-fit p-2 rounded-md shadow-md shadow-black" filter={mapFilter} onChange={setMapFilter}/>
</BsmDropdownButton>
<BsmDropdownButton className="h-full flex aspect-square relative rounded-full z-[1] bg-main-color-3" buttonClassName="rounded-full h-full w-full p-[6px]" icon="three-dots" withBar={false} items={dropDownItems} menuTranslationY="6px" align="center"/>
@@ -0,0 +1,9 @@
import { MapSpecificity } from "shared/models/maps/beat-saver.model";
export const MAP_SPECIFICITIES: MapSpecificity[] = [
"automapper",
"ranked",
"curated",
"verified",
"fullSpread"
];
@@ -0,0 +1,8 @@
import { MapRequirement } from "shared/models/maps/beat-saver.model";
export const MAP_REQUIREMENTS: MapRequirement[] = [
"chroma",
"noodle",
"me",
"cinema"
];
@@ -9,7 +9,6 @@ export const MAP_STYLES: MapStyle[] = [
"ambient",
"funk",
"jazz",
"classical",
"soul",
"speedcore",
"punk",
+4 -1
View File
@@ -143,10 +143,13 @@ export interface BsvMapParitySummary {
export type BsvMapCharacteristic = ("Standard" | "OneSaber" | "NoArrows" | "90Degree" | "360Degree" | "Lightshow" | "Lawless")
export type BsvMapDifficultyType = ("Easy" | "Normal" | "Hard" | "Expert" | "ExpertPlus")
export type MapStyle = ("dance" | "swing" | "nightcore" | "folk" | "family" | "ambient" | "funk" | "jazz" | "classical" | "soul" | "speedcore" | "punk" | "rb" | "holiday" | "vocaloid" | "jrock" | "trance" | "drumbass" | "comedy" | "instrumental" | "hardcore" | "kpop" | "indie" | "techno" | "house" | "game" | "film" | "alt" | "dubstep" | "metal" | "anime" | "hiphop" | "jpop" | "rock" | "pop" | "electronic" | "classical-orchestral")
export type MapStyle = ("dance" | "swing" | "nightcore" | "folk" | "family" | "ambient" | "funk" | "jazz" | "soul" | "speedcore" | "punk" | "rb" | "holiday" | "vocaloid" | "jrock" | "trance" | "drumbass" | "comedy" | "instrumental" | "hardcore" | "kpop" | "indie" | "techno" | "house" | "game" | "film" | "alt" | "dubstep" | "metal" | "anime" | "hiphop" | "jpop" | "rock" | "pop" | "electronic" | "classical-orchestral")
export type MapType = ("accuracy" | "balanced" | "challenge" | "dancestyle" | "fitness" | "speed" | "tech")
export type MapTag = MapStyle | MapType
export type MapRequirement = ("chroma" | "noodle" | "me" | "cinema")
export type MapSpecificity = ("automapper" | "ranked" | "curated" | "verified" | "fullSpread")
export interface MapFilter {
automapper?: boolean,
chroma?: boolean,