aboutsummaryrefslogtreecommitdiff
path: root/src/i18n/present.ts
blob: d734efdd0a5adb08db67cdaf8cd9aaacb5dc1f51 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
import type { Choice, Experiment, ExperimentId, Measurement, Parameters, Slider, TestId } from '../experiments';
import { measurementLabel, word, getLanguage, type Language } from '../i18n';
import type { TestLesson } from '../test4';
import { danishLessons, danishTest } from './da';
import type { LessonText, TestCopy } from './lesson-text';
import { narrate } from './narrate';

interface Catalog {
  lessons: Record<ExperimentId, LessonText>;
  test: (id: TestId) => TestCopy;
  narrate: (id: TestId, p: Parameters) => string;
}

const catalogs: Record<Exclude<Language, 'en'>, Catalog> = {
  da: { lessons: danishLessons, test: danishTest, narrate },
};

function localizeMeasurements(measurements: Measurement[]): Measurement[] {
  return measurements.map(measurement => ({
    label: measurementLabel(measurement.label),
    value: word(measurement.value),
    unit: word(measurement.unit),
  }));
}

function localizeControls(experiment: Experiment, lessons: Record<ExperimentId, LessonText>): (Slider | Choice)[] {
  const copy = lessons[experiment.id].controls;
  return experiment.controls.map(control => {
    const text = copy[control.id];
    if (!text) return control;
    if (control.kind === 'range') return { ...control, label: text.label };
    return {
      ...control,
      label: text.label,
      options: control.options.map(option => ({ ...option, label: text.options?.[option.value] ?? option.label })),
    };
  });
}

export function presentLesson<T extends Experiment>(experiment: T): T {
  const measure = (p: Parameters) => localizeMeasurements(experiment.measure(p));
  const language = getLanguage();
  if (language === 'en') return { ...experiment, measure };
  const catalog = catalogs[language];
  const text = catalog.lessons[experiment.id];
  const localized = {
    ...experiment,
    title: text.title,
    shortTitle: text.shortTitle,
    description: text.description,
    explanation: text.explanation,
    challenge: text.challenge,
    limits: text.limits,
    sceneNote: text.sceneNote,
    legend: experiment.legend.map(([colour], index) => [colour, text.legend[index] ?? experiment.legend[index][1]] as [string, string]),
    source: { ...experiment.source, title: text.sourceTitle },
    controls: localizeControls(experiment, catalog.lessons),
    equations: text.equations ?? experiment.equations,
    measure,
  };
  if (!('questions' in experiment)) return localized as T;
  const lesson = experiment as unknown as TestLesson;
  const test = catalog.test(lesson.id);
  return {
    ...localized,
    questions: test.questions,
    prediction: test.prediction,
    predictionAnswer: test.predictionAnswer,
    answers: lesson.answers.map((part, index) => ({
      ...part,
      title: test.answers[index].title,
      steps: part.steps.map((step, stepIndex) => ({ ...step, why: test.answers[index].steps[stepIndex] })),
    })),
    observe: (p: Parameters) => catalog.narrate(lesson.id, p),
  } as T;
}