diff --git a/ATTRIBUTION.md b/ATTRIBUTION.md index dddd4eae..4f940140 100644 --- a/ATTRIBUTION.md +++ b/ATTRIBUTION.md @@ -64,5 +64,6 @@ Generated-in-code assets are original and have no file to list: | `crates/ui-egui/src/i18n/ru.tsv` | @pechnikov2026-star | Original Russian translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied | | `crates/ui-egui/src/i18n/fr.tsv` | @pechnikov2026-star | Original French translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied | | `crates/ui-egui/src/i18n/zh.tsv` | @mayloglog | Original Simplified Chinese translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied | +| `crates/ui-egui/src/i18n/sv.tsv` | Erik Holmbom (@holmbom) with Claude Code (AI-assisted) | Original Swedish translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied; terminology and the running app reviewed by a native speaker | | `crates/ui-egui/src/i18n/it.tsv` | Emanuele Bottelli (AI-assisted) | Original Italian translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied | | `crates/ui-egui/src/i18n/ko.tsv` | @huk082 (AI-assisted) | Original Korean translations of CADCraft English strings | MIT OR Apache-2.0 (`LICENSE-MIT`, `LICENSE-APACHE`) | No proprietary localization resources copied; no font assets added | diff --git a/README.md b/README.md index 56317a00..10d17964 100644 --- a/README.md +++ b/README.md @@ -111,7 +111,7 @@ numbers): | Layouts & plotting | Paper-space layouts, viewports (scale, lock, per-viewport layer freeze), MSPACE/PSPACE through viewports, page setups, PLOT and EXPORTPDF | | Parametric | Geometric and dimensional constraints, AUTOCONSTRAIN, PARAMETERS with expressions, conflict detection; constraints re-solve after every edit | | Grips | Hot grips with Space to cycle Stretch, Move, Rotate, Scale and Mirror | -| Interface languages | English, Ukrainian (Українська), Brazilian Portuguese (Português (Brasil)), German (Deutsch), Spanish (Español), Czech (Čeština), Russian (Русский), French (Français), Simplified Chinese (简体中文, with an installed CJK font), Italian (Italiano) and Korean (한국어, with an installed Hangul font), live switching and a remembered Auto/system-language choice; [details](docs/localization.md) | +| Interface languages | English, Ukrainian (Українська), Brazilian Portuguese (Português (Brasil)), German (Deutsch), Spanish (Español), Czech (Čeština), Russian (Русский), French (Français), Simplified Chinese (简体中文, with an installed CJK font), Italian (Italiano), Korean (한국어, with an installed Hangul font) and Swedish (Svenska), live switching and a remembered Auto/system-language choice; [details](docs/localization.md) | | Automation | MCP server, JSON control channel, `cadcraft-cli` (info, convert, run, commands, mcp) | ## Quick start diff --git a/contributors/people.toml b/contributors/people.toml index 17f56c2a..1b314041 100644 --- a/contributors/people.toml +++ b/contributors/people.toml @@ -52,6 +52,11 @@ sync_github_name = true [people.GJoe2] sync_github_name = true +[people.holmbom] +real_name = "Erik Holmbom" +display_name = "Erik Holmbom" +sync_github_name = false + [people.cyfung1031] real_name = "Chester Fung" display_name = "Chester Fung" diff --git a/crates/ui-egui/src/i18n/mod.rs b/crates/ui-egui/src/i18n/mod.rs index 35a5f1eb..4a94e75a 100644 --- a/crates/ui-egui/src/i18n/mod.rs +++ b/crates/ui-egui/src/i18n/mod.rs @@ -35,10 +35,12 @@ pub enum Preference { Italian, #[serde(rename = "ko")] Korean, + #[serde(rename = "sv")] + Swedish, } impl Preference { - pub const ALL: [Self; 12] = [ + pub const ALL: [Self; 13] = [ Self::Auto, Self::English, Self::Ukrainian, @@ -51,6 +53,7 @@ impl Preference { Self::Chinese, Self::Italian, Self::Korean, + Self::Swedish, ]; /// The codes a preference can be given as, for messages ("auto, en or uk"). @@ -76,6 +79,7 @@ impl Preference { Self::Chinese => "zh", Self::Italian => "it", Self::Korean => "ko", + Self::Swedish => "sv", } } @@ -99,6 +103,7 @@ impl Preference { "Korean" } } + Self::Swedish => "Svenska", } } @@ -124,6 +129,7 @@ impl Preference { Self::Chinese => "zh", Self::Italian => "it", Self::Korean => "ko", + Self::Swedish => "sv", Self::Auto => locales.iter().find_map(|s| locale_language(s)).unwrap_or("en"), } } @@ -140,7 +146,7 @@ pub struct Language { catalog: OnceLock>, } -pub static LANGUAGES: [Language; 11] = [ +pub static LANGUAGES: [Language; 12] = [ Language { code: "en", name: "English", source: "", plural: plural_en, plural_forms: 2, catalog: OnceLock::new() }, Language { code: "uk", name: "Українська", source: include_str!("uk.tsv"), plural: plural_uk, plural_forms: 3, catalog: OnceLock::new() @@ -169,6 +175,8 @@ pub static LANGUAGES: [Language; 11] = [ Language { code: "it", name: "Italiano", source: include_str!("it.tsv"), plural: plural_en, plural_forms: 2, catalog: OnceLock::new() }, // Korean has one integer plural form and needs a Hangul-capable interface font. Language { code: "ko", name: "한국어", source: include_str!("ko.tsv"), plural: plural_ko, plural_forms: 1, catalog: OnceLock::new() }, + // Swedish plurals follow the English rule: one (1), other. + Language { code: "sv", name: "Svenska", source: include_str!("sv.tsv"), plural: plural_en, plural_forms: 2, catalog: OnceLock::new() }, ]; /// BCP 47 and POSIX locale tags, including `uk-UA`, `uk_UA.UTF-8` and `pt_BR.UTF-8`. diff --git a/crates/ui-egui/src/i18n/sv.tsv b/crates/ui-egui/src/i18n/sv.tsv new file mode 100644 index 00000000..8a2e5ebd --- /dev/null +++ b/crates/ui-egui/src/i18n/sv.tsv @@ -0,0 +1,1247 @@ +# CADCraft Swedish interface catalog — original translations by the CADCraft contributors. +# License: MIT OR Apache-2.0 (the repository LICENSE-MIT and LICENSE-APACHE). +# Written from CADCraft's English strings; no proprietary translations were copied. +# Clean room: every entry is written from the plain meaning of the English label in ordinary +# computing vocabulary. No other product's Swedish interface, string table or terminology +# database was consulted, and no other catalog is used as a source. +# UTF-8: contextEnglish sourceSwedish translation. +# Empty context = ordinary label; @plural = one|other forms with {n}. +# Keep command IDs, keywords, technology/product names and user data unchanged. + + Cancel Avbryt + OK OK + or [ eller [ + % of all commits % av alla commits + * Wildcard Match * Jokerteckenmatchning + *VARIES* *VARIERAR* + + | Top | 2D Wireframe + | Ovanifrån | 2D-trådmodell + +Bin +Bin + +LOC +LOC + 1 Viewport 1 vyfönster + 2 Points 2 punkter + 2 Viewports 2 vyfönster + 2D Solid 2D-solid + 3 Points 3 punkter + 3 Viewports 3 vyfönster + 3D Face 3D-yta + 3D Operations 3D-operationer + 3D Polyline 3D-polylinje + 4 Viewports 4 vyfönster + < Less than < Mindre än + <> Not Equal <> Inte lika med + = Equals = Lika med + > Greater than > Större än + A drawing opened from a file keeps that file's format. En ritning som öppnats från en fil behåller filens format. + A variable name starts with a letter and has only letters, digits and _ Ett variabelnamn börjar med en bokstav och innehåller bara bokstäver, siffror och _ + About Om + About CADCraft Om CADCraft + Absolute Absolut + Add Current Scale Lägg till aktuell skala + Add Leader Lägg till hänvisningslinje + Add Vertex Lägg till hörnpunkt + Add/Delete Scales... Lägg till/ta bort skalor... + Additional angles Ytterligare vinklar + Align Justera + Align Text Justera text + Aligned Justerat + All Alla + All Annotation Objects Alla annoteringsobjekt + All Scales Alla skalor + All Used Layers Alla använda lager + All files Alla filer + An array that would create more objects than this is refused. Ett mönster som skulle skapa fler objekt än så avvisas. + Angle Vinkel + Angular Vinkelmått + Annotation Visibility Annoteringssynlighet + Annotation scale Annoteringsskala + Annotative Object Scale Annotativ objektskala + Annotative Update Annotativ uppdatering + Apparent Intersection Skenbar skärningspunkt + Append to current selection set Lägg till i aktuell markering + Apply Använd + Apply to: Använd på: + Apply true color Använd RGB-färg + Arc Båge + Arc Length Båglängd + Area Area + Arrange Panel Panelen Ordna + Array Mönster + Attach Koppla + Attach DWG... Koppla DWG... + Attribute Attribut + Attribute Definition Attributdefinition + Attribute Display Attributvisning + Audit Kontrollera + Auto (system language) Auto (systemspråk) + Auto Constrain Automatiska villkor + AutoConstrain Automatiska villkor + Automatic save every Spara automatiskt var + Automatic save file location Plats för automatiskt sparade filer + Axis, End Axel, slutpunkt + B F + Base Baspunkt + Baseline Baslinje + Batch Publish Publicera flera + Batch Publish... Publicera flera... + Binary assets added Tillagda binärfiler + Binary assets removed Borttagna binärfiler + Bind Bädda in + Bind... Bädda in... + Blend Mjuk övergång + Block Block + Block Attribute Manager... Hantera blockattribut... + Block Editor Blockredigerare + Block Reference Blockreferens + Block... Block... + Blocks Block + Blue Blå + Bold Fet + Boolean Boolesk + Boundary Gräns + Boundary... Gräns... + Box Låda + Break Bryt + Break At Point Bryt vid punkt + Bring Above Objects Flytta ovanför objekt + Bring Annotations to Front Flytta annoteringar längst fram + Bring to Front Flytta längst fram + Bulleted list Punktlista + ByBlock Enligt block + ByColor Enligt färg + ByLayer Enligt lager + CADCraft CADCraft + CADCraft Help Hjälp för CADCraft + CADCraft keeps these preferences, object snap modes and drafting toggles for your user account and restores them when it starts. CADCraft sparar de här inställningarna, objektfästena och ritlägena för ditt användarkonto och återställer dem när programmet startar. + Cancel Avbryt + Cartesian (x, y) Kartesisk (x, y) + Center Centrum + Center Line Centrumlinje + Center Mark Centrummarkering + Center X Centrum X + Center Y Centrum Y + Center Z Centrum Z + Center, Diameter Centrum, diameter + Center, Radius Centrum, radie + Center, Start, Angle Centrum, start, vinkel + Center, Start, End Centrum, start, slut + Center, Start, Length Centrum, start, längd + Chamfer Fasa + Change Space Byt rymd + Change to Current Layer Flytta till aktuellt lager + Changed: {n} Ändrade: {n} + Changes apply at once and are kept for next time. Ändringar gäller direkt och sparas till nästa gång. + Circle Cirkel + Circumference Omkrets + Clear Rensa + Clear Command History Rensa kommandohistoriken + Clear History Rensa historiken + Clip Beskär + Clip Viewport Beskär vyfönster + Clipboard Urklipp + Close Stäng + Close All Stäng alla + Close All Other Drawings Stäng alla andra ritningar + Close Array Editing Avsluta redigering av mönster + Close Comparison Stäng jämförelse + Closed Sluten + Coincident Sammanfallande + Collapse Palettes Fäll ihop paletter + Collapse Tool Sets Fäll ihop verktygsuppsättningar + Collinear Kolinjär + Color Färg + Color 8 Färg 8 + Color 9 Färg 9 + Color Index Färgindex + Color... Färg... + Command Aliases Kommandoalias + Command History Kommandohistorik + Command Line Kommandorad + Command Line History Lines Rader i kommandoradens historik + Command Reference Kommandoreferens + Command line history Kommandoradens historik + Commits Commits + Company Företag + Compare Drawings... Jämför ritningar... + Computer-aided design and drafting: an open-source, clean-room CAD application written in pure Rust. Datorstödd konstruktion och ritning: ett CAD-program med öppen källkod, skrivet från grunden i ren Rust. + Concentric Koncentrisk + Cone Kon + Constraint Bars Villkorsfält + Constraint Settings Villkorsinställningar + Construction Line Konstruktionslinje + Contents Innehåll + Continue Fortsätt + Contributors Bidragsgivare + Control Vertices Styrpunkter + Convert Konvertera + Convert to Arc Konvertera till båge + Convert to Line Konvertera till linje + Copy Kopiera + Copy Full File Path Kopiera fullständig sökväg + Copy History Kopiera historik + Copy Layout Kopiera layout + Copy Nested Objects Kopiera nästlade objekt + Copy Selection Kopiera markering + Copy as JSON Kopiera som JSON + Copy with Base Point Kopiera med baspunkt + Count Antal + Count List Antalslista + Count Table Antalstabell + Create Block Skapa block + Creates a user parameter Skapar en användarparameter + Crosshair size Hårkorsets storlek + Ctrl+Enter to finish Ctrl+Enter för att avsluta + Current Scale Only Bara aktuell skala + Current layer Aktuellt lager + Current selection Aktuell markering + Current: {color} Aktuell: {color} + Cut Klipp ut + Cyan Cyan + Cylinder Cylinder + DWG DWG + DWG Reference... DWG-referens... + DXF DXF + Dark Mörkt + Data Extraction... Dataextrahering... + Data Link... Datalänk... + Default Standard + Default Save Format Standardformat för att spara + Default Save Version Standardversion för att spara + Default save version Standardversion för att spara + Define Attributes Definiera attribut + Define Attributes... Definiera attribut... + Defined width Definierad bredd + Degree Grad + Degrees of Freedom Frihetsgrader + Degrees of freedom: {n} Frihetsgrader: {n} + Delete Ta bort + Delete Column Ta bort kolumn + Delete Constraints Ta bort villkor + Delete Current Scale Ta bort aktuell skala + Delete Dimension Style Ta bort måttstil + Delete Duplicate Objects Ta bort dubblettobjekt + Delete Layer Ta bort lager + Delete Layer State Ta bort lagertillstånd + Delete Layout Ta bort layout + Delete Row Ta bort rad + Delete Text Style Ta bort textstil + Delta X Delta X + Delta Y Delta Y + Description Beskrivning + Deselect All Avmarkera allt + Detach Koppla bort + Diameter Diameter + Dim style Måttstil + Dimension Mått + Dimension Break Måttbrytning + Dimension Edit Redigera mått + Dimension Objects Only Bara måttobjekt + Dimension Space Måttavstånd + Dimension Style Override Åsidosätt måttstil + Dimension Style... Måttstil... + Dimension Text Edit Redigera måttext + Dimension style Måttstil + Dimensional Constraint Måttvillkor + Dimensional Constraint Parameters Parametrar för måttvillkor + Dimensional Constraints Måttvillkor + Disassociate Dimensions Lösgör mått + Display Visning + Display name Visningsnamn + Distance Avstånd + Divide Dela in + Do not plot (click: plot) Plotta inte (klicka: plotta) + Donut Ring + Double-click to edit the description Dubbelklicka för att redigera beskrivningen + Down Ned + Drafting Ritning + Drafting Settings Ritinställningar + Drafting Settings... Ritinställningar... + Draw Rita + Draw Order Ritordning + Drawing (DWG) Ritning (DWG) + Drawing (DXF) Ritning (DXF) + Drawing Limits Ritningsgränser + Drawing Recovery Manager... Återställ ritningar... + Drawing Template (DWT) Ritningsmall (DWT) + Drawing Utilities Ritningsverktyg + Drawings (DWG, DXF) Ritningar (DWG, DXF) + Drawings with no file yet are saved in the default version. 0 minutes turns automatic save off. Ritningar som ännu saknar fil sparas i standardversionen. 0 minuter stänger av automatiskt sparande. + Dynamic Dynamisk + Dynamic Dimensions Dynamiska mått + Dynamic Input Dynamisk inmatning + Dynamic Input (F12) Dynamisk inmatning (F12) + E Ö + Edit Redigera + Edit Array Redigera mönster + Edit Attributes... Redigera attribut... + Edit Table Cell Redigera tabellcell + Edit Text... Redigera text... + Elevation Höjdläge + Ellipse Ellips + Elliptical Arc Elliptisk båge + Enable Dynamic Input (F12) Slå på dynamisk inmatning (F12) + End Object Isolation Avsluta isolering av objekt + End Width Slutbredd + End X Slut X + End Y Slut Y + End angle Slutvinkel + Endpoint Ändpunkt + Enter Enter + Enter Top, Zero or Bottom. Ange Top, Zero eller Bottom. + Enter a fit data option Ange ett alternativ för anpassningsdata + Enter a pattern name Ange ett mönsternamn + Enter a vertex editing option Ange ett alternativ för hörnpunktsredigering + Enter an option Ange ett alternativ + Enter angle of xline Ange konstruktionslinjens vinkel + Enter angle of xline (0) or Ange konstruktionslinjens vinkel (0) eller + Enter area of rectangle in current units Ange rektangelns area i aktuella enheter + Enter attribute prompt Ange attributets fråga + Enter attribute tag name Ange attributets taggnamn + Enter attribute value Ange attributvärde + Enter block name Ange blocknamn + Enter constraint type Ange villkorstyp + Enter continuity Ange kontinuitet + Enter default attribute value Ange attributets standardvärde + Enter degree of spline Ange splinens grad + Enter delta angle Ange vinkeländring + Enter delta length or Ange längdändring eller + Enter dimension text Ange måttext + Enter dimension text (<> = measurement) Ange måttext (<> = mätvärde) + Enter dimension value or [name=expression] Ange måttvärde eller [namn=uttryck] + Enter dimension variable name to override Ange namnet på måttvariabeln som ska åsidosättas + Enter justification type Ange justeringstyp + Enter leader text Ange text för hänvisningslinjen + Enter mline scale Ange skala för multilinje + Enter mode Ange läge + Enter name of block to insert Ange namnet på blocket som ska infogas + Enter new text Ange ny text + Enter next point Ange nästa punkt + Enter number of columns Ange antal kolumner + Enter number of data rows Ange antal datarader + Enter number of items Ange antal objekt + Enter number of items along path Ange antal objekt längs banan + Enter number of sides Ange antal sidor + Enter number of turns Ange antal varv + Enter percentage length Ange längd i procent + Enter rectangle length Ange rektangelns längd + Enter rectangle width Ange rektangelns bredd + Enter scale factor Ange skalfaktor + Enter text Ange text + Enter text (use \P for new paragraphs) Ange text (använd \P för nya stycken) + Enter the number of segments Ange antal segment + Enter twist direction of helix Ange spiralens vridriktning + Entire drawing Hela ritningen + Equal Lika + Erase Radera + Evaluate Beräkna + Exclude from new selection set Uteslut från ny markering + Explode Lös upp + Export Exportera + Export Table Exportera tabell + Export to PDF... Exportera till PDF... + Export... Exportera... + Expression Uttryck + Extend Förläng + Extension Förlängning + Extents Utsträckning + External Reference Extern referens + External References Externa referenser + Extrude Extrudera + File Arkiv + File Tab Filflik + Fillet Avrunda + Filter Filter + Filters Filter + Find and Replace Sök och ersätt + Find... Sök... + First Första + First commit Första commit + Fit Points Anpassningspunkter + Fix Fixera + Flatten Objects Platta till objekt + Format Format + Freehand Frihand + Freeze Frys + Freeze Layer Frys lager + Freeze in new viewports Frys i nya vyfönster + Freeze/Thaw Frys/tina + Freeze/Thaw in all viewports Frys/tina i alla vyfönster + Freeze/Thaw in the current viewport Frys/tina i aktuellt vyfönster + From Från + From Template... Från mall... + General Allmänt + Geometric Center Geometriskt centrum + Geometric Constraint Geometriskt villkor + Geometric Constraints Geometriska villkor + Geometry Geometri + Get Variable Hämta variabel + Get View Hämta vy + Get from the Drawing Hämta från ritningen + Global Global + Global width Global bredd + Grab bag Blandat + Gradient Toning + Gradient... Toning... + Green Grön + Grid (F7) Rutnät (F7) + Grid Display Visa rutnät + Grid On (F7) Rutnät på (F7) + Grid snap Fäst mot rutnät + Grid spacing Rutnätsavstånd + Grip Edit Redigera med grepp + Grip Mirror Spegla med grepp + Grip Option Greppalternativ + Grip Rotate Rotera med grepp + Grip Scale Skala med grepp + Grip Stretch Sträck med grepp + Grip size Greppstorlek + Group Gruppera + Group Edit Redigera grupp + Group Options Gruppalternativ + Group Selection Gruppmarkering + Hatch Skraffering + Hatch Edit Redigera skraffering + Hatch Patterns Skrafferingsmönster + Hatch... Skraffering... + Height Höjd + Height: {height} Höjd: {height} + Helix Spiral + Help Hjälp + Hide All Dölj alla + Hide All Constraint Bars Dölj alla villkorsfält + Hide All Dynamic Dimensions Dölj alla dynamiska mått + Hide Layer List Dölj lagerlistan + Hide Objects Dölj objekt + Hide Palette Dölj palett + Hide Palettes Dölj paletter + History Historik + Hold Shift to add to the selection Håll ned Shift för att lägga till i markeringen + Home Start + Horizontal Vågrät + HorizontalDistance Vågrätt avstånd + How to apply: Använd så här: + ID Point ID-punkt + Import Importera + Import... Importera... + In In + In-window Menu Bar Menyrad i fönstret + Include in new selection set Ta med i ny markering + Increment angle Vinkelsteg + Index Color Indexfärg + Index color: {index} Indexfärg: {index} + Infer Constraints Härled villkor + Inquiry Information + Insert Infoga + Insert Block Infoga block + Insert Column Infoga kolumn + Insert Row Infoga rad + Insert Table Formula Infoga tabellformel + Insert tab Fliken Infoga + Insert this block Infoga det här blocket + Insertion Insättningspunkt + Insertion X Insättning X + Insertion Y Insättning Y + Insertion Z Insättning Z + Inspect Constraints Granska villkor + Inspect Drawing Granska ritningen + Inspection Granskning + Interface Language Gränssnittsspråk + Interface Theme Gränssnittstema + Interface language Gränssnittsspråk + Interface theme Gränssnittstema + Intersect Snitt + Intersection Skärningspunkt + Isolate Isolera + Isolate Layer Isolera lager + Isolate Objects Isolera objekt + Isometric Drafting Isometrisk ritning + Isometric Plane Isometriskt plan + Isometric snap Isometriskt fäste + Jogged Bruten + Jogged Linear Brutet linjärt + Join Foga samman + Join the ArtCraft Discord… Gå med i ArtCrafts Discord… + Join us on Discord Gå med i ArtCrafts community på Discord + Keep the system cursor visible over the drawing area Visa systemets muspekare över ritytan + Language Språk + Largest array Största mönster + Last Senaste + Last commit Senaste commit + Layer Lager + Layer Delete Ta bort lager + Layer Match Matcha lager + Layer Merge Sammanfoga lager + Layer Off Stäng av lager + Layer Properties Lageregenskaper + Layer Properties Manager Hantera lageregenskaper + Layer Properties Manager — current viewport Hantera lageregenskaper – aktuellt vyfönster + Layer State Lagertillstånd + Layer States Manager... Hantera lagertillstånd... + Layer Tools Lagerverktyg + Layer contains objects (double-click to make current) Lagret innehåller objekt (dubbelklicka för att göra det aktuellt) + Layer is empty (double-click to make current) Lagret är tomt (dubbelklicka för att göra det aktuellt) + Layers Lager + Layers Palette Lagerpalett + Layers displayed: {shown} of {total}. Current layer: {layer} Visade lager: {shown} av {total}. Aktuellt lager: {layer} + Layout Layout + Layout list Layoutlista + Layout paper Layoutpapper + Leader Hänvisningslinje + Leaders Only Bara hänvisningslinjer + Left Vänster + Length Längd + Length X Längd X + Length Y Längd Y + Lengthen Ändra längd + Light Ljust + Line Linje + Line delta Radskillnad + Linear Linjärt + Lines +/− Rader +/− + Lines added Tillagda rader + Lines deleted Borttagna rader + Lines of Command History Rader i kommandohistoriken + Linetype Linjetyp + Linetype Scale Linjetypsskala + Linetype scale Linjetypsskala + Loaded Inläst + Lock viewport Lås vyfönster + Ltscale Linjetypsskala + Linetype... Linjetyp... + Lineweight Linjetjocklek + Lineweight... Linjetjocklek... + List Lista + List Blocks Lista block + List Dimension Styles Lista måttstilar + List Groups Lista grupper + List Layer States Lista lagertillstånd + List Layouts Lista layouter + List System Variables Lista systemvariabler + List Text Styles Lista textstilar + Load all Läs in alla + Load... Läs in... + Loaded linetypes Inlästa linjetyper + Lock Lås + Lock Layer Lås lager + Lock/Unlock Lås/lås upp + Loft Loft + MIT OR Apache-2.0. Not affiliated with Autodesk, Inc. MIT OR Apache-2.0. Inte knutet till Autodesk, Inc. + MODEL MODELL + MText MText + Magenta Magenta + Major line every Huvudlinje var + Make Current Gör aktuellt + Make Object's Layer Current Gör objektets lager aktuellt + Make it a block of this drawing, keeping its layer names Gör den till ett block i den här ritningen och behåll dess lagernamn + Make it a block of this drawing; its layers become NAME$0$LAYER Gör den till ett block i den här ritningen; dess lager blir NAME$0$LAYER + Make... Skapa... + Match Layer Matcha lager + Match Properties Matcha egenskaper + Measure Mät upp + Measure Distance Mät avstånd + Measure Geometry Mät geometri + Merge Cells Sammanfoga celler + Merged PRs Sammanslagna PR:er + Mid Between 2 Points Mitt mellan 2 punkter + Midpoint Mittpunkt + Mirror Spegla + Model Modell + Model Space (in viewport) Modellrymd (i vyfönster) + Model background Modellbakgrund + Modeling Modellering + Models Modeller + Modify Ändra + More toolbar commands Fler verktygsfältskommandon + Move Flytta + Multileader Multihänvisningslinje + Multileader Style... Multihänvisningsstil... + Multileader style Multihänvisningsstil + Multiline Multilinje + Multiline Style... Multilinjestil... + Multiline Text Flerradstext + Multiline Text... Flerradstext... + Multiline... Multilinje... + Multiple Flera + Multiple Point Flera punkter + My Mina + My properties: not available yet Mina egenskaper: inte tillgängligt än + N N + Name Namn + Name (A–Z) Namn (A–Ö) + Named Views... Namngivna vyer... + Nearest Närmaste + New Ny + New (metric) Ny (metrisk) + New Drawing Ny ritning + New Drawing (⌘N) Ny ritning (⌘N) + New Drawing... Ny ritning... + New Layer Nytt lager + New Layout Ny layout + New VP Freeze Frys i nya vyfönster + New Viewports... Nya vyfönster... + New from Template... Ny från mall... + New layout Ny layout + New state name Namn på nytt tillstånd + Next Change Nästa ändring + No Nej + No blocks defined in this drawing. Inga block är definierade i den här ritningen. + No contributor data was built into this copy. Den här kopian innehåller inga uppgifter om bidragsgivare. + No external references are attached. Inga externa referenser är kopplade. + No model credits were built into this copy. Den här kopian innehåller inga uppgifter om medverkande AI-modeller. + No saved layer states Inga sparade lagertillstånd + No selection Ingen markering + Node Nod + None Ingen + Not Found Hittades inte + Not available Inte tillgängligt + Not available yet Inte tillgängligt än + Not loaded Inte inläst + Numbered list Numrerad lista + OK OK + Object Objekt + Object Snap Objektfäste + Object Snap (F3) Objektfäste (F3) + Object Snap On (F3) Objektfäste på (F3) + Object Snap Tracking Objektfästesspårning + Object Snap Tracking (F11) Objektfästesspårning (F11) + Object Snap Tracking Settings Inställningar för objektfästesspårning + Object snap aperture Objektfästets sökområde + Object snap marker size Objektfästets markörstorlek + Object type: Objekttyp: + Oblique Sned + Off Av + Offset Förskjut + On På + On/Off På/av + One of the Crafting Apps by the ArtCraft team and community. En av Crafting Apps, gjord av ArtCraft-teamet och dess community. + Only in this drawing: {n} Bara i den här ritningen: {n} + Only in {name}: {n} Bara i {name}: {n} + Open Öppna + Open (⌘O) Öppna (⌘O) + Open Sample Drawing Öppna exempelritning + Open Xref Öppna extern referens + Open and Save Öppna och spara + Open sample drawing Öppna exempelritning + Open... Öppna... + Operator: Operator: + Options Alternativ + Options... Alternativ... + Orbit Kretsa + Ordinate Koordinatmått + Ortho (F8) Orto (F8) + Ortho Mode Ortoläge + Ortho Mode (F8) Ortoläge (F8) + Osnap Settings... Inställningar för objektfäste... + Out Ut + Over-constrained Överbestämd + Overlay Överlägg + Override Åsidosätt + PAPER PAPPER + Paste to Command Line Klistra in på kommandoraden + Percent Procent + Pickbox size Markeringsrutans storlek + Plotter Manager Hantera plottrar + Plotter Manager... Hantera plottrar... + Polar (distance < angle) Polär (avstånd < vinkel) + PRs PR:er + Page Setup Manager Hantera sidinställningar + Page Setup Manager... Hantera sidinställningar... + Pan Panorera + Pan Down Panorera nedåt + Pan Left Panorera åt vänster + Pan Right Panorera åt höger + Pan Up Panorera uppåt + Paper Space Pappersrymd + Parallel Parallell + Parameters Manager Hantera parametrar + Parametric Parametrisk + Paste Klistra in + Paste as Block Klistra in som block + Paste to Original Coordinates Klistra in på ursprungliga koordinater + Path Array Mönster längs bana + Pattern Mönster + Perpendicular Vinkelrät + Plot Plotta + Plot (click: do not plot) Plotta (klicka: plotta inte) + Plot Preview Förhandsgranska plott + Plot Window Plottfönster + Plot style Plottstil + Plot style attached to Plottstil kopplad till + Plot style table Plottstilstabell + Plot Style... Plottstil... + Plot Style Manager Hantera plottstilar + Plot Style Manager... Hantera plottstilar... + Plot Styles... Plottstilar... + New CTB Ny CTB + New STB Ny STB + New style Ny stil + Polar angle measurement Mätning av polär vinkel + Polar distance Polärt avstånd + PolarSnap Polärt fäste + Polygonal Viewport Polygonalt vyfönster + Polyline Edit Redigera polylinje + Previous Change Föregående ändring + Profiles Profiler + QuickCalc Pick Snabbkalkyl: välj punkt + Recalculate Table Formulas Beräkna tabellformler igen + Recent Commands Senaste kommandon + Recent Input Senaste inmatning + Rectangular snap Rektangulärt fäste + Reference Manager Referenshanterare + Reference Name Referensnamn + References: {n} Referenser: {n} + Reinitialize Initiera om + Relative to last segment Relativt sista segmentet + Reload Läs in igen + Reload All Läs in alla igen + Remove Vertex Ta bort hörnpunkt + Reset Panel Layout Återställ panellayout + Reset keeps the interface language. Återställningen behåller gränssnittsspråket. + Reset to Defaults Återställ standardvärden + SVG drawings (SVG, SVGZ) SVG-ritningar (SVG, SVGZ) + Save new drawings as Spara nya ritningar som + Saved Path Sparad sökväg + Scale List... Skallista... + Screen magnifiers, screen readers and recorders follow the system cursor. Skärmförstorare, skärmläsare och skärminspelare följer systemets muspekare. + Select Similar Markera liknande + Select objects first, then choose a command Markera objekt först och välj sedan ett kommando + Selection Markering + Send Hatches to Back Flytta skrafferingar längst bak + Send Under Objects Flytta under objekt + Set Current Viewport Gör vyfönster aktuellt + Set Table Cell Style Ange tabellcellstil + Settings... Inställningar... + Show Annotative Objects Visa annotativa objekt + Show Quick Properties for selected objects Visa snabbegenskaper för markerade objekt + Show and hide the tools of this category Visa och dölj verktygen i den här kategorin + Show command prompting near the crosshairs Visa kommandofrågor nära hårkorset + Show in Tool Sets Visa i verktygsuppsättningar + Snap Overrides Tillfälliga fästen + Snap type Fästtyp + Snap, grid, polar tracking and Dynamic Input: Fäst, rutnät, polär spårning och dynamisk inmatning: + Solid Editing Solidredigering + Spline Edit Redigera spline + Stretch Vertex Sträck hörnpunkt + Synchronize Multiple-scale Positions Synkronisera positioner för flera skalor + Table Breaks Tabellbrytningar + Table Cell Style Tabellcellstil + Temporary track point Tillfällig spårpunkt + Text Objects Only Bara textobjekt + Thaw Layer Tina lager + The aperture is how near the cursor must come to a point for an object snap to find it. Sökområdet anger hur nära en punkt markören måste komma för att objektfästet ska hitta den. + Time-sensitive right-click: a quick click is Enter, holding opens the menu Tidskänsligt högerklick: ett snabbt klick är Enter, att hålla ned öppnar menyn + To Till + Tolerance... Tolerans... + Track orthogonally only Spåra bara ortogonalt + Track using all polar angle settings Spåra med alla polära vinkelinställningar + Turn On Layer Slå på lager + Turned off, a right-click while a command runs always opens the shortcut menu. Om det är avstängt öppnar ett högerklick under ett kommando alltid snabbmenyn. + Units Conversion Enhetsomvandling + Unload Inaktivera + Unloaded Inaktiverad + Unlock viewport Lås upp vyfönster + Unreferenced Inte refererad + Unresolved Hittades inte + Update Data Links Uppdatera datalänkar + Use for this layout Använd för den här layouten + Display plot styles Visa plottstilar + No plot style tables. Inga plottstilstabeller. + A built-in table: editing it keeps an edited copy in the drawing. En inbyggd tabell: om du redigerar den sparas en redigerad kopia i ritningen. + Keep an editable copy of this table in the drawing Spara en redigerbar kopia av tabellen i ritningen + Layout {name}: {table} Layout {name}: {table} + Grayscale Gråskala + Screening Rastrering + Use object linetype Använd objektets linjetyp + Use object lineweight Använd objektets linjetjocklek + Remove Ta bort + Add Lägg till + Open a drawing first. Öppna en ritning först. + Plot table type Typ av plottstilstabell + Color-dependent Färgberoende + Named Namngiven + Plus/minus Plus/minus + Point Punkt + Point Filters Punktfilter + Point Style... Punktstil... + Polar Array Polärt mönster + Polar Tracking Polär spårning + Polar Tracking (F10) Polär spårning (F10) + Polar Tracking On (F10) Polär spårning på (F10) + Polar: {distance} < {angle}° Polär: {distance} < {angle}° + Polygon Polygon + Polygonal Polygonal + Polyline Polylinje + Position X Position X + Position Y Position Y + Position Z Position Z + Previous Föregående + Previous Layer Föregående lager + Primitives Grundformer + Print Skriv ut + Print... Skriv ut... + Properties Egenskaper + Properties Inspector Egenskapsinspektör + Properties: Egenskaper: + Proxy Proxy + Purge Rensa + Pyramid Pyramid + Quadrant Kvadrant + Query Entities Objektinformation + Quick Snabb + Quick Dimension Snabbmått + Quick Properties Snabbegenskaper + Quick Select Snabbmarkering + Quick Select Properties Egenskaper för snabbmarkering + Quick Select... Snabbmarkering... + QuickCalc Snabbkalkyl + Quit CADCraft Avsluta CADCraft + Radius Radie + Raster Image Rasterbild + Ray Stråle + Read-only Skrivskyddad + Real name Riktigt namn + Realtime Realtid + Reassociate Dimensions Återkoppla mått + Recent Senaste + Recover... Reparera... + Rectangle Rektangel + Rectangular Rektangulär + Rectangular Array Rektangulärt mönster + Red Röd + Redo Gör om + Redo (⇧⌘Z) Gör om (⇧⌘Z) + Redraw Rita om + Regen Regenerera + Regen All Regenerera alla + Region Region + Region/Mass Properties Region- och massegenskaper + Relative Relativ + Remove Leader Ta bort hänvisningslinje + Remove the viewport override Ta bort vyfönstrets åsidosättning + Rename Dimension Style Byt namn på måttstil + Rename Layer Byt namn på lager + Rename Layer State Byt namn på lagertillstånd + Rename Layout Byt namn på layout + Rename Text Style Byt namn på textstil + Rename... Byt namn... + Repeat {command} Upprepa {command} + Requires a point (x,y, @dx,dy or @d Ange andra punkten eller + Specify second source point Ange andra källpunkten + Specify side to offset Ange sida att förskjuta åt + Specify start angle Ange startvinkel + Specify start point Ange startpunkt + Specify start point of arc Ange bågens startpunkt + Specify start point of polyline Ange polylinjens startpunkt + Specify start point of text Ange textens startpunkt + Specify starting width Ange startbredd + Specify starting width for next segment Ange startbredd för nästa segment + Specify tangent direction for the start point of arc Ange tangentriktning för bågens startpunkt + Specify the elevation for rectangles Ange höjdläge för rektanglar + Specify thickness for rectangles Ange tjocklek för rektanglar + Specify third point on circle Ange tredje punkten på cirkeln + Specify third point on circle: _tan to Ange tredje punkten på cirkeln: _tan to + Specify third source point or Ange tredje källpunkten eller + Specify through point Ange genomgångspunkt + Specify top diameter Ange toppdiameter + Specify top radius or Ange toppradie eller + Specify total angle Ange total vinkel + Specify total length or Ange total längd eller + Specify width for rectangles Ange bredd för rektanglar + Sphere Sfär + Spline Spline + Stack (type 1/2 then select) Stapla (skriv 1/2 och markera sedan) + Standard Standard + Start Start + Start Width Startbredd + Start X Start X + Start Y Start Y + Start angle Startvinkel + Start, Center, Angle Start, centrum, vinkel + Start, Center, End Start, centrum, slut + Start, Center, Length Start, centrum, längd + Start, End, Angle Start, slut, vinkel + Start, End, Direction Start, slut, riktning + Start, End, Radius Start, slut, radie + Status Status + Status Bar Statusfält + Stretch Sträck + Style: Standard Stil: Standard + Subtract Subtrahera + Sweep Svep + Switch Drawing Byt ritning + Switch Layout Byt layout + Switch between model space in a viewport and paper space Växla mellan modellrymd i ett vyfönster och pappersrymd + Symmetric Symmetrisk + Synchronize Attributes Synkronisera attribut + Toggle PICKADD (off: each pick replaces the selection) Växla PICKADD (av: varje klick ersätter markeringen) + Toggle PICKADD (on: picks add to the selection) Växla PICKADD (på: klick läggs till i markeringen) + TOP OVAN + Table Tabell + Table Style... Tabellstil... + Table style Tabellstil + Table... Tabell... + Tan, Tan, Radius Tan, tan, radie + Tan, Tan, Tan Tan, tan, tan + Tangent Tangent + Text Text + Text Editor Textredigerare + Text Height Texthöjd + Text Style... Textstil... + Text height Texthöjd + Text override Åsidosatt text + Text style Textstil + Thaw All Layers Tina alla lager + There is nothing here yet. Här finns inget än. + Thickness Tjocklek + Time Tid + To get started, create or open a drawing. Kom igång genom att skapa eller öppna en ritning. + Tool Bar Verktygsfält + Tool Sets Verktygsuppsättningar + Tools Verktyg + Torus Torus + Trace Bred linje + Transparency Genomskinlighet + Trim Trimma + True Color RGB-färg + Turn All Layers On Slå på alla lager + Turn Off Layer Stäng av lager + Turn Quick Properties off (QPMODE) Stäng av snabbegenskaper (QPMODE) + Type Typ + Type a command Skriv ett kommando + Type text; Enter starts a new paragraph Skriv text; Enter börjar ett nytt stycke + UCS Icon UCS-ikon + Undo Ångra + Undo (⌘Z) Ångra (⌘Z) + Ungroup Dela upp grupp + Union Förena + Unisolate Layer Avsluta isolering av lager + Units... Enheter... + Unlock Layer Lås upp lager + Unmerge Cells Dela celler + Unsaved Layer State Osparat lagertillstånd + Up Upp + Update Uppdatera + Use System Setting Använd systeminställningen + User Användare + User Parameters Användarparametrar + User Preferences Användarinställningar + Username Användarnamn + VP Color Färg i vyfönster + VP Freeze Frys i vyfönster + Value Värde + Value: Värde: + Variables Variabler + Version Version + Version 2000 Version 2000 + Version 2004 Version 2004 + Version 2007 Version 2007 + Version 2010 Version 2010 + Version 2013 Version 2013 + Version 2018 Version 2018 + Version {version} Version {version} + Vertical Lodrät + VerticalDistance Lodrätt avstånd + View Visa + ViewCube ViewCube + Viewport Vyfönster + Viewport Layer Freeze Frys lager i vyfönster + Viewport Properties Vyfönsteregenskaper + Viewport is locked Vyfönstret är låst + Viewport scale Vyfönsterskala + Viewport {id} Vyfönster {id} + Viewports Vyfönster + Volume Volym + W V + WCS ⌄ WCS ⌄ + White Vit + Width factor Breddfaktor + Window Fönster + Wipeout Maskering + Workspace Switching Byt arbetsyta + Write Block Skriv block till fil + X X + Xline Konstruktionslinje + Y Y + Yellow Gul + Yes Ja + Zoom Zooma + Zoom All Zooma allt + Zoom Dynamic Zooma dynamiskt + Zoom Extents Zooma till utsträckning + Zoom In Zooma in + Zoom Object Zooma till objekt + Zoom Out Zooma ut + Zoom Previous Zooma till föregående + Zoom Realtime Zooma i realtid + Zoom Window Zooma fönster + error fel + min min + objects objekt + {contributors} · {commits} {contributors} · {commits} + {kind} (constraint {id}) {kind} (villkor {id}) + {kind} constraint {name} = {expression} (double-click to edit) Villkor {kind} {name} = {expression} (dubbelklicka för att redigera) + {name}: {distance} < {angle}° {name}: {distance} < {angle}° + ƒx New User Parameter ƒx Ny användarparameter + ΔLOC ΔLOC + −Bin −Bin + −LOC −LOC + ⌘↩ to finish ⌘↩ för att avsluta +@plural {n} commit {n} commit|{n} commits +@plural {n} contributor {n} bidragsgivare|{n} bidragsgivare + Drawing as bytes Ritningen som byte + Services Tjänster + Hide CADCraft Dölj CADCraft + Hide Others Dölj övriga + Accessibility Tillgänglighet + Show System Cursor Visa systemets muspekare + 3D Mouse... 3D-mus... + 3D Mouse 3D-mus + Calibrate 3D Mouse Kalibrera 3D-mus + 3D Mouse Navigation Navigering med 3D-mus + 3D mouse input is unavailable on this platform Inmatning med 3D-mus finns inte på den här plattformen + No supported 3D mouse found Ingen 3D-mus som stöds hittades + Release the 3D mouse to calibrate its resting position Släpp 3D-musen för att kalibrera dess viloläge + 3D mouse connected 3D-mus ansluten + 3D mouse busy, possibly 3DxWare or missing device permissions 3D-musen är upptagen, kanske av 3DxWare eller på grund av saknade behörigheter + 3D mouse disconnected 3D-mus frånkopplad + 3D mouse input could not be started Inmatning med 3D-mus kunde inte startas + Enable 3D mouse navigation Slå på navigering med 3D-mus + Pan sensitivity Känslighet för panorering + Zoom sensitivity Känslighet för zoom + Reverse zoom direction Vänd zoomriktningen + Calibrate Kalibrera + Move sideways to pan; push/pull or twist to zoom. Rör i sidled för att panorera; tryck, dra eller vrid för att zooma. + Left device button: zoom extents. Right device button: calibrate. Vänster knapp på enheten: zooma till utsträckning. Höger knapp: kalibrera. + Hatch Pattern Skrafferingsmönster + Search for pattern Sök efter mönster + +# Strings the Spanish catalog lacks: menu headings worded apart from their commands, and others. + Run Script... Kör skript... +menu View Visa +menu Draw Rita +menu Dimension Måttsättning +menu Modify Ändra diff --git a/crates/ui-egui/src/i18n/tests.rs b/crates/ui-egui/src/i18n/tests.rs index 71c2bff2..b2abbc1d 100644 --- a/crates/ui-egui/src/i18n/tests.rs +++ b/crates/ui-egui/src/i18n/tests.rs @@ -39,7 +39,7 @@ fn catalog_is_valid_and_preserves_placeholders_and_ellipses() { /// to English for what they don't cover yet; their gaps are reported, not enforced, so adding a /// command doesn't require a row in every language. const REQUIRED: &[&str] = &["uk"]; -const REPORTED: &[&str] = &["pt-BR", "de", "es", "cs", "ru", "fr", "zh", "it", "ko"]; +const REPORTED: &[&str] = &["pt-BR", "de", "es", "cs", "ru", "fr", "zh", "it", "ko", "sv"]; fn check(language: &str, what: &str, missing: Vec) { if REQUIRED.contains(&language) { @@ -779,3 +779,108 @@ fn korean_ui_fonts_cover_catalog_and_language_picker_in_both_families() { }); assert!(missing.is_empty(), "missing Korean UI glyphs: {}", missing.join(", ")); } + +#[test] +fn swedish_locales_preferences_and_plural_forms() { + for tag in ["sv", "sv-SE", "sv_SE.UTF-8", "SV-se", " sv-SE ", "sv-FI"] { + assert_eq!(locale_language(tag), Some("sv"), "{tag}"); + } + // `se` is Northern Sami and `swe` the three-letter code; neither picks Swedish. + for tag in ["se", "swe", "svenska"] { + assert_eq!(locale_language(tag), None, "{tag}"); + } + assert_eq!(Preference::parse("sv"), Some(Preference::Swedish)); + assert_eq!(Preference::Swedish.name(), "Svenska"); + assert_eq!(Preference::Swedish.resolve(&["en-US".into()]), "sv"); + assert_eq!(Preference::Auto.resolve(&["pl-PL".into(), "sv-SE".into(), "en-US".into()]), "sv"); + let mut app = CadApp::new(Session::new(), Services::default()); + app.ui.interface_language = Preference::Swedish; + let mut restored = CadApp::new(Session::new(), Services::default()); + restored.load_prefs(&app.prefs_json()); + assert_eq!(restored.ui.interface_language, Preference::Swedish); + with_language("sv", || { + for n in [0, 1, 2, 5, 21, u64::MAX] { + // `bidragsgivare` is the same in the singular and the plural; `commit` takes an -s. + assert_eq!(count(n, "{n} contributor", "{n} contributors"), format!("{n} bidragsgivare")); + let commit = if n == 1 { "commit" } else { "commits" }; + assert_eq!(count(n, "{n} commit", "{n} commits"), format!("{n} {commit}")); + } + assert_eq!(format("Current: {color}", &[("color", "{n} Open".into())]), "Aktuell: {n} Open"); + }); +} + +#[test] +fn swedish_menu_headings_keep_object_labels() { + with_language("sv", || { + assert_eq!(menu("Dimension"), "Måttsättning"); + assert_eq!(t("Dimension"), "Mått"); + assert_eq!(menu("View"), "Visa"); + assert_eq!(menu("Draw"), "Rita"); + assert_eq!(menu("Modify"), "Ändra"); + assert_eq!(menu("Edit"), "Redigera"); + assert_eq!(menu("File"), "Arkiv"); + }); +} + +#[test] +fn live_swedish_switch_preserves_drawing_command_and_saved_choice() { + let mut app = CadApp::new(Session::new(), Services::default()); + app.ui.in_window_menu = true; + app.session.state_mut().unwrap().title = "Open".into(); + let ctx = egui::Context::default(); + app.logic(&ctx); + assert!(render(&mut app, &ctx).contains("Properties")); + app.start("line"); + let prompt = crate::control::cmdline_state(&app); + let commands = crate::control::all_commands(&app); + app.run("ui.language", json!({"lang":"sv"})).unwrap(); + let text = render(&mut app, &ctx); + for label in ["Egenskaper", "Arkiv", "Visa", "Rita", "Måttsättning", "Ange första punkten"] { + assert!(text.contains(label), "missing {label}: {text}"); + } + assert_eq!(app.language(), "sv"); + assert_eq!(app.session.state().unwrap().title, "Open"); + assert_eq!(crate::control::cmdline_state(&app), prompt); + assert_eq!(crate::control::all_commands(&app), commands); + app.run("ui.language", json!({"lang":"en"})).unwrap(); + assert!(render(&mut app, &ctx).contains("Properties")); +} + +#[test] +fn swedish_dialogs_render_with_stable_ids() { + for (dialog, heading) in [ + ("dsettings", "Ritinställningar"), + ("about", "Om CADCraft"), + ("blocks", "Block"), + ("layers", "Hantera lageregenskaper"), + ("qselect", "Snabbmarkering"), + ("parameters", "Hantera parametrar"), + ("language", "Svenska"), + ("options:preferences", "Användarinställningar"), + ] { + let mut app = CadApp::new(Session::new(), Services::default()); + app.ui.interface_language = Preference::Swedish; + app.ui.dialog = Some(dialog.into()); + let ctx = egui::Context::default(); + app.logic(&ctx); + let text = render(&mut app, &ctx); + assert!(text.contains(heading), "{dialog}: {text}"); + assert_eq!(app.ui.dialog.as_deref(), Some(dialog)); + } +} + +#[test] +fn default_fonts_cover_swedish_letters_and_quotes() { + let ctx = egui::Context::default(); + let mut output = ctx.run_ui(Default::default(), |_| {}); + output.textures_delta.clear(); + let letters: BTreeSet<_> = "ÅÄÖÉåäöé”–".chars().collect(); + ctx.fonts_mut(|view| { + for family in [egui::FontFamily::Proportional, egui::FontFamily::Monospace] { + let mut font = view.fonts.font(&family); + for c in &letters { + assert!(font.characters().contains_key(c), "missing {c} in {family:?}"); + } + } + }); +} diff --git a/crates/ui-egui/src/options/mod.rs b/crates/ui-egui/src/options/mod.rs index ae5097fe..145a0dbc 100644 --- a/crates/ui-egui/src/options/mod.rs +++ b/crates/ui-egui/src/options/mod.rs @@ -10,7 +10,7 @@ //! |---|---| //! | `theme` | `"system"`, `"light"` or `"dark"` | //! | `animations` | `"system"`, `"on"` or `"off"`: dialog and menu fades and smoothed scrolling | -//! | `interfaceLanguage` | `"auto"`, `"en"`, `"uk"`, `"pt-BR"`, `"de"`, `"es"`, `"cs"`, `"ru"`, `"fr"`, `"zh"`, `"it"` or `"ko"` | +//! | `interfaceLanguage` | `"auto"`, `"en"`, `"uk"`, `"pt-BR"`, `"de"`, `"es"`, `"cs"`, `"ru"`, `"fr"`, `"zh"`, `"it"`, `"ko"` or `"sv"` | //! | `saveFormat` | `"dxf"` or `"dwg"`: the format Save As suggests for new drawings | //! | `saveVersion` | `"2000"` … `"2018"`: the version drawings with no file yet are saved in | //! | `SAVETIME` | minutes between automatic saves, 0–600 (0: off) | diff --git a/docs/control-protocol.md b/docs/control-protocol.md index 50c07d8a..13320d8d 100644 --- a/docs/control-protocol.md +++ b/docs/control-protocol.md @@ -152,7 +152,7 @@ Select a language with `engine.execute` and the UI command `ui.language`: {"id":1,"method":"engine.execute","params":{"command":"ui.language","params":{"lang":"uk"}}} ``` -Supported values are `auto`, `en`, `uk`, `pt-BR`, `de`, `es`, `cs`, `ru`, `fr`, `zh`, `it` and `ko`. +Supported values are `auto`, `en`, `uk`, `pt-BR`, `de`, `es`, `cs`, `ru`, `fr`, `zh`, `it`, `ko` and `sv`. Chinese needs an installed CJK font; Korean needs a font covering the Korean interface from the optional craft-fonts input or the operating system. Without a suitable font, the saved choice is retained and the result's `shown` is `en`. `ui.set` also accepts diff --git a/docs/localization-parity.md b/docs/localization-parity.md index 9fd23718..470b6f0d 100644 --- a/docs/localization-parity.md +++ b/docs/localization-parity.md @@ -1,6 +1,6 @@ # Localization parity -> **Last reviewed:** 2026-10-10 · **Last updated:** 2026-10-13 · **Change:** minor (complete current Korean catalog; locale/preferences/live-switch support and Hangul font coverage) · **Target:** Autodesk AutoCAD 2027 for Mac (26.0) +> **Last reviewed:** 2026-10-10 · **Last updated:** 2026-10-13 · **Change:** minor (Swedish catalog added: complete catalog, menu headings, native-speaker terminology review; previously: complete current Korean catalog with Hangul font coverage) · **Target:** Autodesk AutoCAD 2027 for Mac (26.0) How far CADCraft's interface and drawing text are from AutoCAD's languages. Summarised in [ROADMAP.md](../ROADMAP.md#languages); work items in [gaps.md](gaps.md#localization). @@ -66,10 +66,11 @@ plus native review by a human; extending the catalog to the remaining English-on | Vietnamese | vi | 0 (0%) | 0% | Latin with stacked diacritics: renders per code point, untested | no | none | 3–5 h | | Ukrainian | uk | 989 catalog rows (≈ 100% of the catalog; ≈ 80% of all UI strings, estimated: engine diagnostics and uncatalogued text stay English) | dialogs and tooltips yes; command reference searchable in Ukrainian | Cyrillic: yes (bundled egui fonts) | translated by a contributor; no second review | partial | 2–4 h | | Czech | cs | 1,202 catalog rows; reference catalog and marked UI literals covered | dialogs and tooltips yes; contextual menu headings; command reference searchable in Czech | Latin: yes (bundled egui proportional and monospace fonts; Czech letters and quotes tested) | AI-assisted by @Losminek; independent review pass; not yet proofread by a native speaker | complete current catalog; English-only interface gaps remain | native review + shared English-only UI work | +| Swedish | sv | 1,235 catalog rows; reference catalog, marked UI literals and menu headings covered (no gaps reported) | dialogs and tooltips yes; contextual menu headings; command reference searchable in Swedish | Latin: yes (bundled egui proportional and monospace fonts; å ä ö é and Swedish quotes tested) | AI-assisted (Claude Code) by @holmbom; terminology and the running app reviewed by a native speaker | complete current catalog; English-only interface gaps remain | line-by-line proofreading + shared English-only UI work | | Italian | it | 1,227 catalog rows; reference catalog and marked UI literals covered | dialogs and tooltips yes; contextual menu headings (Visualizza / Vista, Edita / Modifica); command reference searchable in Italian | Latin: yes (bundled egui fonts; accented letters tested) | AI-assisted by Emanuele Bottelli (Claude), written from the English strings with Italian desktop-CAD vocabulary; no native proofreading pass yet | complete current catalog; English-only interface gaps remain | native review + shared English-only UI work | -Other languages shipped: Ukrainian, Brazilian Portuguese, German, Czech, Russian, French, Italian and Korean. Czech and -Brazilian Portuguese cover the reference catalog and every marked UI literal; engine diagnostics and uncatalogued text +Other languages shipped: Ukrainian, Brazilian Portuguese, German, Czech, Russian, French, Italian, Korean and Swedish. +Czech, Swedish and Brazilian Portuguese cover the reference catalog and every marked UI literal; engine diagnostics and uncatalogued text remain English. AutoCAD for Mac ships 7 non-English languages (zh-Hans, es, fr, ja, de, ko, it); of those, CADCraft now ships German and Korean, and additionally Ukrainian, which AutoCAD for Mac doesn't ship. @@ -82,6 +83,7 @@ each language, which needs humans. Translations parallelise fully once the catal | Date | Change | Summary | |---|---|---| +| 2026-10-13 | minor | Swedish added: 1,235 rows, one/other plurals, menu headings, locale/preferences/menu/font/render tests; no gaps in the marked UI literals; terminology and the running app reviewed by a native speaker | | 2026-10-13 | minor | Korean added: full 1,235-row existing catalog union, single count form, locale/persistence/live-switch tests, and validated Hangul UI fonts; native review and platform verification pending | | 2026-10-12 | minor | Italian added: 1,227 rows, one/other plurals, two `menu` headings, locale/preference/plural/font tests; AI-assisted, native proofreading pending | | 2026-10-12 | minor | Brazilian Portuguese catalog completed by @RicSchonfelder: 238 rows added (1,231 total), now covering the reference catalog and every marked UI literal, gaps 0; bundled-font glyph test for the catalog's accented letters | diff --git a/docs/localization.md b/docs/localization.md index 4dc2e610..791adec2 100644 --- a/docs/localization.md +++ b/docs/localization.md @@ -1,7 +1,7 @@ # Interface languages Choose **Edit → Interface Language** and select **Auto (system language)**, **English**, -**Українська**, **Português (Brasil)**, **Deutsch**, **Español**, **Čeština** (Czech), **Русский**, **Français**, **简体中文**, **Italiano**, or **한국어** (Korean). +**Українська**, **Português (Brasil)**, **Deutsch**, **Español**, **Čeština** (Czech), **Русский**, **Français**, **简体中文**, **Italiano**, **한국어** (Korean), or **Svenska** (Swedish). The interface updates without restarting, including the native macOS menus. The choice is saved with the other interface preferences (`cadcraft.prefs`, beside the theme): eframe storage on the desktop, browser local storage on the web. Installations without a saved @@ -10,7 +10,8 @@ choice use Auto. Auto uses the first supported language in the operating system's preferred locales, or the browser's `navigator.languages` on the web. BCP 47 and POSIX tags select their primary language: `uk-UA` → `uk`, `de_AT.UTF-8` → `de`, `es-MX` → `es`, `pt_BR.UTF-8` → `pt-BR`, -`cs-CZ` and `cs_CZ.UTF-8` → `cs`, `it-IT` and `it_CH.UTF-8` → `it`, `ko-KR` and `ko_KR.UTF-8` → `ko`. Unsupported languages fall back to English. +`cs-CZ` and `cs_CZ.UTF-8` → `cs`, `it-IT` and `it_CH.UTF-8` → `it`, `ko-KR` and `ko_KR.UTF-8` → `ko`, +`sv-SE`, `sv-FI` and `sv_SE.UTF-8` → `sv`. Unsupported languages fall back to English. Set `CADCRAFT_LOCALE=cs-CZ` to override the desktop's locale for a launch. An explicit saved language choice takes precedence over that override. @@ -21,7 +22,7 @@ Automation can select the language through the existing control channel: ``` The `ui.set` method also accepts `{"interfaceLanguage":"cs"}`. Supported values are `auto`, -`en`, `uk`, `pt-BR`, `de`, `es`, `cs`, `ru`, `fr`, `zh`, `it`, and `ko`; invalid values are rejected without changing the current +`en`, `uk`, `pt-BR`, `de`, `es`, `cs`, `ru`, `fr`, `zh`, `it`, `ko`, and `sv`; invalid values are rejected without changing the current selection. Resetting palettes keeps the language choice. ## Translation coverage