Skip to content

Commit d31556f

Browse files
committed
Fix serialisation of color dicts
1 parent 663a05c commit d31556f

File tree

3 files changed

+24
-10
lines changed

3 files changed

+24
-10
lines changed

CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
99

1010
### Added
1111

12+
* Added key conversion map to `compas.colors.ColorDict` to avoid serialisation problems with tuple keys when used in combination with edges.
13+
1214
### Changed
1315

1416
### Removed

src/compas/colors/colordict.py

Lines changed: 22 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -24,16 +24,23 @@ class ColorDict(Data):
2424
2525
"""
2626

27+
keymap = {
28+
int: lambda x: str(x),
29+
tuple: lambda x: ",".join(map(str, sorted(x))),
30+
list: lambda x: ",".join(map(str, sorted(x))),
31+
}
32+
2733
@property
2834
def __data__(self):
29-
return {"default": self.default, "dict": self._dict}
35+
return {
36+
"default": self.default,
37+
"dict": self._dict,
38+
}
3039

3140
@classmethod
3241
def __from_data__(cls, data):
3342
colordict = cls(data["default"])
34-
# note: this is specific to color dicts for vertices of meshes
35-
# perhaps the color dict needs to be subclassed per scene object type
36-
colordict.update({int(key): value for key, value in data["dict"].items()})
43+
colordict.update(data["dict"])
3744
return colordict
3845

3946
def __init__(self, default, name=None):
@@ -54,14 +61,19 @@ def default(self, default):
5461
default = Color.coerce(default)
5562
self._default = default
5663

64+
def keymapper(self, key):
65+
if key.__class__ in self.keymap:
66+
return self.keymap[key.__class__](key)
67+
return key
68+
5769
def __getitem__(self, key):
58-
return self._dict.get(key, self.default)
70+
return self._dict.get(self.keymapper(key), self.default)
5971

6072
def __setitem__(self, key, value):
61-
self._dict[key] = Color.coerce(value)
73+
self._dict[self.keymapper(key)] = Color.coerce(value)
6274

6375
def __delitem__(self, key):
64-
del self._dict[key]
76+
del self._dict[self.keymapper(key)]
6577

6678
def __iter__(self):
6779
return iter(self._dict)
@@ -70,7 +82,7 @@ def __len__(self):
7082
return len(self._dict)
7183

7284
def __contains__(self, key):
73-
return key in self._dict
85+
return self.keymapper(key) in self._dict
7486

7587
def items(self):
7688
return self._dict.items()
@@ -82,7 +94,7 @@ def values(self):
8294
return self._dict.values()
8395

8496
def get(self, key, default=None):
85-
return self._dict.get(key, default or self.default)
97+
return self._dict.get(self.keymapper(key), default or self.default)
8698

8799
def clear(self):
88100
"""Clear the previously stored items.
@@ -108,4 +120,4 @@ def update(self, other):
108120
109121
"""
110122
for key, value in other.items():
111-
self[key] = value
123+
self[self.keymapper(key)] = value

tests/compas/colors/test_colordict.py

Whitespace-only changes.

0 commit comments

Comments
 (0)