bdb_parser/
models.rs

1//! This module contains the data structures and enums used to represent the parsed data.
2
3use serde::{Deserialize, Serialize};
4
5/// The identifier for a chunk in the file.
6#[derive(Debug, Serialize, Deserialize, Clone, Copy, PartialEq, Eq)]
7pub enum ChunkIdentifier {
8    FileHeader = 0xA1,
9    Region = 0xA2,
10    Track = 0xA3,
11    TrackName = 0xA4,
12    StartLine = 0xA5,
13    FinishLine = 0xA6,
14    ComboFlag = 0xA7,
15    FileFooter = 0xEE,
16}
17
18impl TryFrom<u8> for ChunkIdentifier {
19    type Error = ();
20
21    fn try_from(value: u8) -> Result<Self, Self::Error> {
22        match value {
23            0xA1 => Ok(ChunkIdentifier::FileHeader),
24            0xA2 => Ok(ChunkIdentifier::Region),
25            0xA3 => Ok(ChunkIdentifier::Track),
26            0xA4 => Ok(ChunkIdentifier::TrackName),
27            0xA5 => Ok(ChunkIdentifier::StartLine),
28            0xA6 => Ok(ChunkIdentifier::FinishLine),
29            0xA7 => Ok(ChunkIdentifier::ComboFlag),
30            0xEE => Ok(ChunkIdentifier::FileFooter),
31            _ => Err(()),
32        }
33    }
34}
35
36/// The latitude and longitude of a point.
37#[derive(Debug, Serialize, Deserialize, Clone, Copy)]
38pub struct LatLon {
39    pub lat: f64,
40    pub lon: f64,
41}
42
43/// The bounding box of a region or track.
44#[derive(Debug, Serialize, Deserialize, Clone, Copy)]
45pub struct BoundingBox {
46    pub corner_1: LatLon,
47    pub corner_2: LatLon,
48}
49
50/// A line segment between two points.
51#[derive(Debug, Serialize, Deserialize, Clone, Copy)]
52pub struct Line {
53    pub point_1: LatLon,
54    pub point_2: LatLon,
55}
56
57/// The start and finish of a track.
58#[derive(Debug, Serialize, Deserialize, Clone, Copy)]
59pub enum StartFinish {
60    /// A circuit track.
61    Circuit(Line),
62    /// A point-to-point track.
63    PointToPoint { start: Line, finish: Line },
64}
65
66/// All the data for a single track.
67#[derive(Debug, Serialize, Deserialize)]
68pub struct TrackChunk {
69    /// The name of the track.
70    pub track_name: String,
71    /// The bounding box of the track.
72    pub bounding_box: BoundingBox,
73    /// The start and finish of the track.
74    pub start_finish: StartFinish,
75    /// Whether the track is a combo track (Not sure exactly
76    ///  what this is but there is a flag set for every track
77    /// that has "combo" in the name.)
78    pub combo: bool,
79}
80
81/// The header of the file.
82#[derive(Debug, Serialize, Deserialize)]
83pub struct FileHeader {
84    pub year: u16,
85    pub month: u8,
86    pub day: u8,
87    /// Currently unknown data.
88    pub data: [u8; 8],
89}
90
91/// A geographic region as indicated in the file
92/// All tracks get grouped under a region. The region is defined by a bounding box.
93#[derive(Debug, Serialize, Deserialize)]
94pub struct Region {
95    /// The bounding box of the region.
96    pub bounding_box: BoundingBox,
97    /// The tracks in the region.
98    pub tracks: Vec<TrackChunk>,
99}
100
101/// The footer of the file.
102#[derive(Debug, Serialize, Deserialize)]
103pub struct Footer {
104    /// Currently unknown data.
105    pub data: [u8; 4],
106}
107
108/// The entire database of tracks as stored in the file.
109#[derive(Debug, Serialize, Deserialize)]
110pub struct TrackDatabase {
111    /// The header of the file.
112    pub hdr: FileHeader,
113    /// The regions in the file.
114    pub regions: Vec<Region>,
115    /// The footer of the file.
116    pub footer: Footer,
117}