@rr0/ufoathome 0.18.0 → 0.19.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -332,6 +332,7 @@ interface SightingRecordingJson {
332
332
  weatherTrack?: { keyframes: Array<{ t: number, weather: Weather }> }
333
333
  weather?: Weather // legacy static fallback for recordings predating weatherTrack
334
334
  weatherSource?: { id: string, name: string, url: string } // the meteorological record weatherTrack was looked up from — see Weather is looked up, not remembered. Absent = the witness's own account
335
+ soundTrack?: { keyframes: Array<{ t: number, sound: { kind: "none" | "hum" | "whistle" | "rumble" | "crackle", volume: number, pitchHz: number, src?: string } }> } // what the witness heard — see What it sounded like
335
336
  decor?: DecorObject[] // buildings, trees, streetlights, vehicles, other witnesses — see src/engine/model/Decor.ts
336
337
  }
337
338
  ```
@@ -340,6 +341,30 @@ A shape left out of a later keyframe is **held** at its last recorded state, not
340
341
  keyframe is at `t=5000` is already painted, in that state, from `t=0` (hold-first/hold-last at both ends of a
341
342
  source's own range). To make something stop being visible, keyframe it with `transparency: 1`.
342
343
 
344
+ ### What it sounded like
345
+
346
+ Half of what makes these accounts strange is the sound — most often its absence. `soundTrack` records it on the
347
+ same clock as the shapes, because a sound rarely starts when the object does: a craft sitting silently on the
348
+ ground and heard only as it lifts off is two keyframes, `kind: "none"` at the start and a hum at the instant it
349
+ took off.
350
+
351
+ `volume` (0..1, how loud the witness could describe it, never a dB figure) and `pitchHz` blend between keyframes;
352
+ `kind` and `src` are **held**, like every other discrete field in this format — so the example above really is
353
+ silent right up to that second keyframe. To record a sound emerging gradually instead, give it two keyframes of
354
+ its own kind (hum at volume 0, then hum at full).
355
+
356
+ `kind: "none"` is a statement — the witness reported hearing nothing. A recording with no `soundTrack` at all is
357
+ the different, weaker case: nobody was asked. Both replay as silence, and neither invents a noise.
358
+
359
+ Sounds are **synthesized** from that description (a drone, a whistle, a rumble, a crackle — `pitchHz` is the tone
360
+ itself for the pitched ones and where the noise sits for the others), exactly as a described shape is drawn from
361
+ its description, and at no cost in bundled assets. A recording that actually captured the sound can point `src` at
362
+ the audio file, which then plays instead — at the price of an embed that is no longer self-contained, and a URL
363
+ that must be CORS-readable.
364
+
365
+ Sound plays during playback only, and only after a real click somewhere in the player: browsers refuse to start
366
+ audio without one.
367
+
343
368
  ### Naming a place
344
369
 
345
370
  Testimony names a place. It says "on the Valensole plateau", "near Socorro", "over Montgomery" —
@@ -1 +1 @@
1
- const e={oval:"Ovale",polygon:"Polygone",addVertex:"Ajouter un sommet",deleteVertex:"Supprimer le sommet",notAPolygon:"Sélectionnez une seule forme polygonale",tooFewVertices:"Une forme a besoin d'au moins 3 points",color:"Couleur",transparency:"Transparence",halo:"Halo",shape:"Forme",shapeTitle:"Nom",objectSize:"Taille réelle",objectDistance:"Distance",apparentSize:"soit {deg}° — {moons}× la Lune",utcOffset:"Fuseau horaire",utcOffsetPlaceholder:"d'après la longitude",objectSizePlaceholder:"largeur rapportée",objectDistancePlaceholder:"distance rapportée",addShape:"Ajouter une forme",deleteShape:"Supprimer la forme",play:"Lecture",pause:"Pause",noDuration:"Aucune durée d'observation",autoReplay:"Lecture automatique",group:"Grouper",ungroup:"Dégrouper",bringToFront:"Placer devant",sendToBack:"Placer derrière",contextMenuDelete:"Supprimer",confirmDeleteShape:"Supprimer {name} ? Cette action est irréversible.",confirmDeleteShapes:"Supprimer {count} formes ? Cette action est irréversible.",onlyOneShape:"Il n'y a qu'une seule forme",alreadyAtFront:"Cette forme est déjà la plus en avant",alreadyAtBack:"Cette forme est déjà la plus en arrière",needTwoShapesToGroup:"Sélectionnez au moins deux formes pour les grouper",notGrouped:"Cette forme ne fait pas partie d'un groupe",multipleShapesSelected:"Plusieurs formes sélectionnées — sélectionnez-en une seule pour modifier ceci",cloudBase:"Base des nuages",elevation:"Altitude",samplingRate:"Échantillonnage",duration:"Durée",durationPlaceholder:"durée de l'observation",durationImprecise:"Ces dates ne permettent pas de déterminer précisément une durée — saisissez-la manuellement.",export:"Exporter le JSON",importFile:"Charger un fichier JSON",importUrl:"Ou charger depuis une URL",importUrlPlaceholder:"https://…/sighting.json",importButton:"Charger",importError:"Impossible de charger cet enregistrement — vérifiez le fichier ou l'URL et réessayez.",record:"Enregistrer",stop:"Arrêter",according:"selon",sourceElevation:"Relief",sourceImagery:"Imagerie",placeName:"Lieu",placeNamePlaceholder:"Valensole, France",searchPlace:"Localiser",placeMatch:"Correspondances",placeSearching:"Recherche du lieu…",placeMatchFound:"lieu trouvé",placeMatchesFound:"lieux trouvés",placeNotFound:"Aucun lieu de ce nom",placeSearchFailed:"Recherche de lieu momentanément indisponible",utcOffsetImplausible:"Ce fuseau ne correspond pas à la longitude saisie, dont l'heure solaire est UTC{solar} — la scène et le relevé météo obéissent pourtant à ce qui est déclaré ici. Videz le champ pour le déduire de la longitude.",timeZoneManual:"décalage saisi",altitudeAboveSeaLevel:"Altitude du témoin au-dessus du niveau de la mer — le sol du lieu saisi en fixe le minimum : un témoin dans les Alpes n'est pas à 0 m.",groundAt:"sol à {m} m",latitude:"Latitude",longitude:"Longitude",heading:"Orientation",headingPlaceholder:"inconnu",pitch:"Inclinaison",observationTime:"Début de l'observation",observationEndTime:"Fin de l'observation",edtfInvalid:"Date/heure EDTF invalide (ex. 1965-07-01T05:00, 2025-06?, 2025~).",edtfPlaceholder:"AAAA-MM-JJThh:mm[?~%] ou hh:mm",observationTimeHint:"EDTF — ex. 1965-07-01T05:00, 2025-06? (incertain), 2025~ (approximatif), ou juste 05:00 si la date est inconnue",observationEndTimeHint:"EDTF — ex. 1965-07-01T05:10, 2025-06? (incertain), 2025~ (approximatif), ou juste 05:10 si la date est inconnue",presetsGroupLabel:"Forme de l'ovni",witnessId:"ID témoin",witnessDirName:"Répertoire du témoin",witnessTitle:"Titre du témoin",witnessLastName:"Nom de famille du témoin",witnessFirstNames:"Prénoms du témoin",caseId:"ID de l'affaire",description:"Description",tags:"Mots-clés",tagsPlaceholder:"séparés par des virgules",weather:"Météo",shapeGroup:"Forme",temporalGroup:"Date et heure",locationGroup:"Lieu",observationGroup:"Observation",witnessGroup:"Témoin",circumstancesGroup:"Circonstances",weatherInferred:"D'après les relevés",weatherInferredTitle:"La météo n'est pas un témoignage : c'est un fait mesurable, relevé pour la date, l'heure et le lieu de l'observation. Décochez pour saisir les conditions rapportées par le témoin, qui priment alors sur le relevé.",weatherFrom:"D'après",weatherLookingUp:"Recherche du relevé…",weatherNeedsDateAndPlace:"Date complète et lieu requis pour retrouver le relevé",weatherNoRecord:"Aucun relevé pour cette date et ce lieu",weatherLookupFailed:"Relevés météo momentanément inaccessibles",cloudCover:"Couverture nuageuse",cloudDarkness:"Obscurité des nuages",precipitationType:"Précipitations",precipitationNone:"Aucune",precipitationRain:"Pluie",precipitationSnow:"Neige",precipitationHail:"Grêle",precipitationIntensity:"Intensité",windDirection:"Direction du vent",windSpeed:"Force du vent",storm:"Orage",lensFlareBrightness:"Intensité lumineuse",cameraDevice:"Appareil photo/vidéo",decor:"Décor",decorBuilding:"Bâtiment",decorTree:"Arbre",decorStreetlight:"Lampadaire",decorVehicle:"Véhicule",decorWitness:"Autre témoin",addDecor:"Ajouter",deleteDecor:"Supprimer l'élément de décor",decorEast:"Distance à l'est",decorNorth:"Distance au nord",decorHeading:"Orientation",decorLit:"Allumé",decorTitle:"Nom",decorSightingUrl:"URL de l'enregistrement du témoin",viewTestimony:"Voir le témoignage",noWitnessRecording:"Aucune URL d'enregistrement définie pour ce témoin",masks:"Masque",addWitness:"Ajouter un témoin",decorFloors:"Étages",decorOccupiedFloor:"Étage occupé",decorWitnessSide:"Emplacement du témoin",decorWitnessSideNone:"Non présent",decorWindows:"Fenêtres",decorSideFront:"Avant",decorSideBehind:"Arrière",decorSideLeft:"Gauche",decorSideRight:"Droite",decorSideFrontLeft:"Avant-gauche",decorSideFrontRight:"Avant-droit",decorSideBehindLeft:"Arrière-gauche",decorSideBehindRight:"Arrière-droit"};export{e as ufoRecorderMessages_fr};
1
+ const e={oval:"Ovale",polygon:"Polygone",addVertex:"Ajouter un sommet",deleteVertex:"Supprimer le sommet",notAPolygon:"Sélectionnez une seule forme polygonale",tooFewVertices:"Une forme a besoin d'au moins 3 points",color:"Couleur",transparency:"Transparence",halo:"Halo",shape:"Forme",shapeTitle:"Nom",objectSize:"Taille réelle",objectDistance:"Distance",apparentSize:"soit {deg}° — {moons}× la Lune",utcOffset:"Fuseau horaire",utcOffsetPlaceholder:"d'après la longitude",objectSizePlaceholder:"largeur rapportée",objectDistancePlaceholder:"distance rapportée",addShape:"Ajouter une forme",deleteShape:"Supprimer la forme",play:"Lecture",pause:"Pause",noDuration:"Aucune durée d'observation",autoReplay:"Lecture automatique",group:"Grouper",ungroup:"Dégrouper",bringToFront:"Placer devant",sendToBack:"Placer derrière",contextMenuDelete:"Supprimer",confirmDeleteShape:"Supprimer {name} ? Cette action est irréversible.",confirmDeleteShapes:"Supprimer {count} formes ? Cette action est irréversible.",onlyOneShape:"Il n'y a qu'une seule forme",alreadyAtFront:"Cette forme est déjà la plus en avant",alreadyAtBack:"Cette forme est déjà la plus en arrière",needTwoShapesToGroup:"Sélectionnez au moins deux formes pour les grouper",notGrouped:"Cette forme ne fait pas partie d'un groupe",multipleShapesSelected:"Plusieurs formes sélectionnées — sélectionnez-en une seule pour modifier ceci",cloudBase:"Base des nuages",elevation:"Altitude",samplingRate:"Échantillonnage",duration:"Durée",durationPlaceholder:"durée de l'observation",durationImprecise:"Ces dates ne permettent pas de déterminer précisément une durée — saisissez-la manuellement.",export:"Exporter le JSON",importFile:"Charger un fichier JSON",importUrl:"Ou charger depuis une URL",importUrlPlaceholder:"https://…/sighting.json",importButton:"Charger",importError:"Impossible de charger cet enregistrement — vérifiez le fichier ou l'URL et réessayez.",record:"Enregistrer",stop:"Arrêter",according:"selon",sourceElevation:"Relief",sourceImagery:"Imagerie",placeName:"Lieu",placeNamePlaceholder:"Valensole, France",searchPlace:"Localiser",placeMatch:"Correspondances",placeSearching:"Recherche du lieu…",placeMatchFound:"lieu trouvé",placeMatchesFound:"lieux trouvés",placeNotFound:"Aucun lieu de ce nom",placeSearchFailed:"Recherche de lieu momentanément indisponible",utcOffsetImplausible:"Ce fuseau ne correspond pas à la longitude saisie, dont l'heure solaire est UTC{solar} — la scène et le relevé météo obéissent pourtant à ce qui est déclaré ici. Videz le champ pour le déduire de la longitude.",timeZoneManual:"décalage saisi",altitudeAboveSeaLevel:"Altitude du témoin au-dessus du niveau de la mer — le sol du lieu saisi en fixe le minimum : un témoin dans les Alpes n'est pas à 0 m.",groundAt:"sol à {m} m",latitude:"Latitude",longitude:"Longitude",heading:"Orientation",headingPlaceholder:"inconnu",pitch:"Inclinaison",observationTime:"Début de l'observation",observationEndTime:"Fin de l'observation",edtfInvalid:"Date/heure EDTF invalide (ex. 1965-07-01T05:00, 2025-06?, 2025~).",edtfPlaceholder:"AAAA-MM-JJThh:mm[?~%] ou hh:mm",observationTimeHint:"EDTF — ex. 1965-07-01T05:00, 2025-06? (incertain), 2025~ (approximatif), ou juste 05:00 si la date est inconnue",observationEndTimeHint:"EDTF — ex. 1965-07-01T05:10, 2025-06? (incertain), 2025~ (approximatif), ou juste 05:10 si la date est inconnue",presetsGroupLabel:"Forme de l'ovni",witnessId:"ID témoin",witnessDirName:"Répertoire du témoin",witnessTitle:"Titre du témoin",witnessLastName:"Nom de famille du témoin",witnessFirstNames:"Prénoms du témoin",caseId:"ID de l'affaire",description:"Description",tags:"Mots-clés",tagsPlaceholder:"séparés par des virgules",weather:"Météo",shapeGroup:"Forme",soundGroup:"Son",temporalGroup:"Date et heure",locationGroup:"Lieu",observationGroup:"Observation",witnessGroup:"Témoin",circumstancesGroup:"Circonstances",weatherInferred:"D'après les relevés",weatherInferredTitle:"La météo n'est pas un témoignage : c'est un fait mesurable, relevé pour la date, l'heure et le lieu de l'observation. Décochez pour saisir les conditions rapportées par le témoin, qui priment alors sur le relevé.",weatherFrom:"D'après",weatherLookingUp:"Recherche du relevé…",weatherNeedsDateAndPlace:"Date complète et lieu requis pour retrouver le relevé",weatherNoRecord:"Aucun relevé pour cette date et ce lieu",weatherLookupFailed:"Relevés météo momentanément inaccessibles",cloudCover:"Couverture nuageuse",cloudDarkness:"Obscurité des nuages",precipitationType:"Précipitations",precipitationNone:"Aucune",precipitationRain:"Pluie",precipitationSnow:"Neige",precipitationHail:"Grêle",precipitationIntensity:"Intensité",windDirection:"Direction du vent",windSpeed:"Force du vent",storm:"Orage",soundKind:"Son",soundNone:"Aucun (silencieux)",soundHum:"Bourdonnement",soundWhistle:"Sifflement",soundRumble:"Grondement",soundCrackle:"Crépitement",soundVolume:"Intensité sonore",soundPitch:"Hauteur",soundSrc:"Enregistrement",soundSrcPlaceholder:"URL d'un enregistrement réel",lensFlareBrightness:"Intensité lumineuse",cameraDevice:"Appareil photo/vidéo",decor:"Décor",decorBuilding:"Bâtiment",decorTree:"Arbre",decorStreetlight:"Lampadaire",decorVehicle:"Véhicule",decorWitness:"Autre témoin",addDecor:"Ajouter",deleteDecor:"Supprimer l'élément de décor",decorEast:"Distance à l'est",decorNorth:"Distance au nord",decorHeading:"Orientation",decorLit:"Allumé",decorTitle:"Nom",decorSightingUrl:"URL de l'enregistrement du témoin",viewTestimony:"Voir le témoignage",noWitnessRecording:"Aucune URL d'enregistrement définie pour ce témoin",masks:"Masque",addWitness:"Ajouter un témoin",decorFloors:"Étages",decorOccupiedFloor:"Étage occupé",decorWitnessSide:"Emplacement du témoin",decorWitnessSideNone:"Non présent",decorWindows:"Fenêtres",decorSideFront:"Avant",decorSideBehind:"Arrière",decorSideLeft:"Gauche",decorSideRight:"Droite",decorSideFrontLeft:"Avant-gauche",decorSideFrontRight:"Avant-droit",decorSideBehindLeft:"Arrière-gauche",decorSideBehindRight:"Arrière-droit"};export{e as ufoRecorderMessages_fr};