Skip to content

Commit

Permalink
added 2 additional tracab meta file types and tests
Browse files Browse the repository at this point in the history
  • Loading branch information
Joris Bekkers committed Jul 10, 2024
1 parent c8cd1e3 commit 50aee17
Show file tree
Hide file tree
Showing 4 changed files with 170 additions and 3 deletions.
13 changes: 10 additions & 3 deletions kloppy/infra/serializers/tracking/tracab/tracab_dat.py
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ def _frame_from_line(cls, teams, period, line, frame_rate):
)

player = team.get_player_by_jersey_number(jersey_no)

if not player:
player = Player(
player_id=f"{team.ground}_{jersey_no}",
Expand Down Expand Up @@ -162,8 +163,12 @@ def deserialize(self, inputs: TRACABInputs) -> TrackingDataset:
meta_data = objectify.fromstring(inputs.meta_data.read())
match = meta_data.match
frame_rate = int(match.attrib["iFrameRateFps"])
pitch_size_width = float(match.attrib["fPitchXSizeMeters"])
pitch_size_height = float(match.attrib["fPitchYSizeMeters"])
pitch_size_width = float(
match.attrib["fPitchXSizeMeters"].replace(",", ".")
)
pitch_size_height = float(
match.attrib["fPitchYSizeMeters"].replace(",", ".")
)

periods = []
for period in match.iterchildren(tag="period"):
Expand All @@ -182,7 +187,9 @@ def deserialize(self, inputs: TRACABInputs) -> TrackingDataset:
)
)

if meta_data.get("HomeTeam") and meta_data.get("AwayTeam"):
if hasattr(meta_data, "HomeTeam") and hasattr(
meta_data, "AwayTeam"
):
home_team = self.create_team(
meta_data["HomeTeam"], Ground.HOME, start_frame_id
)
Expand Down
16 changes: 16 additions & 0 deletions kloppy/tests/files/tracab_meta_2.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
<?xml version="1.0"?>
<TracabMetaData sVersion="1.0">
<match
iId="1"
dtDate="2023-12-15 20:32:20"
iFrameRateFps="25"
fPitchXSizeMeters="105.00"
fPitchYSizeMeters="68.00"
fTrackingAreaXSizeMeters="unknown"
fTrackingAreaYSizeMeters="unknown">
<period iId="1" iStartFrame="1848508" iEndFrame="1916408"/>
<period iId="2" iStartFrame="1942114" iEndFrame="2017933"/>
<period iId="3" iStartFrame="0" iEndFrame="0"/>
<period iId="4" iStartFrame="0" iEndFrame="0"/>
</match>
</TracabMetaData>
12 changes: 12 additions & 0 deletions kloppy/tests/files/tracab_meta_3.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<OptaMetaData sVersion="1.2">
<match
iId="1"
dtDate="2023-12-15 20:32:20"
iFrameRateFps="25"
fPitchXSizeMeters="105,00"
fPitchYSizeMeters="68,00"
>
<period iId="1" iStartFrame="1848508" iEndFrame="1916408"/>
<period iId="2" iStartFrame="1942114" iEndFrame="2017933"/>
</match>
</OptaMetaData>
132 changes: 132 additions & 0 deletions kloppy/tests/test_tracab.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,16 @@ def xml_meta_data(base_dir: Path) -> Path:
return base_dir / "files" / "tracab_meta.xml"


@pytest.fixture(scope="session")
def xml_meta2_data(base_dir: Path) -> Path:
return base_dir / "files" / "tracab_meta_2.xml"


@pytest.fixture(scope="session")
def xml_meta3_data(base_dir: Path) -> Path:
return base_dir / "files" / "tracab_meta_3.xml"


@pytest.fixture(scope="session")
def dat_raw_data(base_dir: Path) -> Path:
return base_dir / "files" / "tracab_raw.dat"
Expand Down Expand Up @@ -223,3 +233,125 @@ def test_correct_normalized_deserialization(
assert dataset.records[0].players_data[
player_home_1
].coordinates == Point(x=1.0019047619047619, y=0.49602941176470583)


class TestTracabMeta2:
def test_correct_deserialization(
self, xml_meta2_data: Path, dat_raw_data: Path
):
dataset = tracab.load(
meta_data=xml_meta2_data,
raw_data=dat_raw_data,
coordinates="tracab",
only_alive=False,
)

# Check metadata
assert dataset.metadata.provider == Provider.TRACAB
assert dataset.dataset_type == DatasetType.TRACKING
assert len(dataset.records) == 7
assert len(dataset.metadata.periods) == 2
assert dataset.metadata.orientation == Orientation.AWAY_HOME
assert dataset.metadata.periods[0].id == 1
assert dataset.metadata.periods[0].start_timestamp == timedelta(
seconds=73940, microseconds=320000
)
assert dataset.metadata.periods[0].end_timestamp == timedelta(
seconds=76656, microseconds=320000
)
assert dataset.metadata.periods[1].id == 2
assert dataset.metadata.periods[1].start_timestamp == timedelta(
seconds=77684, microseconds=560000
)
assert dataset.metadata.periods[1].end_timestamp == timedelta(
seconds=80717, microseconds=320000
)

# No need to check frames, since we do that in TestTracabDATTracking
# The only difference in this test is the meta data file structure

# make sure player data is only in the frame when the player is at the pitch
assert "home_20" in [
player.player_id
for player in dataset.records[0].players_data.keys()
]
assert "home_20" not in [
player.player_id
for player in dataset.records[6].players_data.keys()
]

def test_correct_normalized_deserialization(
self, xml_meta2_data: Path, dat_raw_data: Path
):
dataset = tracab.load(
meta_data=xml_meta2_data, raw_data=dat_raw_data, only_alive=False
)

player_home_1 = dataset.metadata.teams[0].get_player_by_jersey_number(
1
)

assert dataset.records[0].players_data[
player_home_1
].coordinates == Point(x=1.0019047619047619, y=0.49602941176470583)


class TestTracabMeta3:
def test_correct_deserialization(
self, xml_meta3_data: Path, dat_raw_data: Path
):
dataset = tracab.load(
meta_data=xml_meta3_data,
raw_data=dat_raw_data,
coordinates="tracab",
only_alive=False,
)

# Check metadata
assert dataset.metadata.provider == Provider.TRACAB
assert dataset.dataset_type == DatasetType.TRACKING
assert len(dataset.records) == 7
assert len(dataset.metadata.periods) == 2
assert dataset.metadata.orientation == Orientation.AWAY_HOME
assert dataset.metadata.periods[0].id == 1
assert dataset.metadata.periods[0].start_timestamp == timedelta(
seconds=73940, microseconds=320000
)
assert dataset.metadata.periods[0].end_timestamp == timedelta(
seconds=76656, microseconds=320000
)
assert dataset.metadata.periods[1].id == 2
assert dataset.metadata.periods[1].start_timestamp == timedelta(
seconds=77684, microseconds=560000
)
assert dataset.metadata.periods[1].end_timestamp == timedelta(
seconds=80717, microseconds=320000
)

# No need to check frames, since we do that in TestTracabDATTracking
# The only difference in this test is the meta data file structure

# make sure player data is only in the frame when the player is at the pitch
assert "home_20" in [
player.player_id
for player in dataset.records[0].players_data.keys()
]
assert "home_20" not in [
player.player_id
for player in dataset.records[6].players_data.keys()
]

def test_correct_normalized_deserialization(
self, xml_meta3_data: Path, dat_raw_data: Path
):
dataset = tracab.load(
meta_data=xml_meta3_data, raw_data=dat_raw_data, only_alive=False
)

player_home_1 = dataset.metadata.teams[0].get_player_by_jersey_number(
1
)

assert dataset.records[0].players_data[
player_home_1
].coordinates == Point(x=1.0019047619047619, y=0.49602941176470583)

0 comments on commit 50aee17

Please sign in to comment.