Browse Source

interior manager: use cache for image computing

Bastien Sevajol 6 years ago
parent
commit
237f9555b7
1 changed files with 21 additions and 1 deletions
  1. 21 1
      opencombat/simulation/interior.py

+ 21 - 1
opencombat/simulation/interior.py View File

@@ -32,6 +32,7 @@ class InteriorManager(object):
32 32
         self.original_image = original_image
33 33
         self.configuration = configuration or InteriorMapConfiguration()
34 34
         self.interiors = self._compute_interiors()
35
+        self._cache = {}  # type: typing.Dict[str, PngImageFile]
35 36
 
36 37
     def _compute_interiors(self) -> typing.List[typing.List[typing.Tuple[int, int]]]:
37 38
         interiors = []
@@ -91,6 +92,20 @@ class InteriorManager(object):
91 92
                     interiors.append(interior)
92 93
         return interiors
93 94
 
95
+    def _get_interior_unique_key(
96
+        self,
97
+        interiors: typing.List[typing.List[typing.Tuple[int, int]]],
98
+    ) -> str:
99
+        """
100
+        Compute a key for given interior list. WARNING: For performance reasons,
101
+        actual unique key is interior list ID concatenation:
102
+        So, if same interior list is given, but in different python object, key will be
103
+        different !
104
+        :param interiors: Interior list to build unique key
105
+        :return: String or Int who id unique key of given interiors
106
+        """
107
+        return '.'.join([str(id(i)) for i in interiors])
108
+
94 109
     def update_image_for_interiors(
95 110
         self,
96 111
         interiors: typing.List[typing.List[typing.Tuple[int, int]]],
@@ -98,7 +113,11 @@ class InteriorManager(object):
98 113
         tile_height: int,
99 114
         invert_y: bool=True,
100 115
     ) -> PngImageFile:
101
-        # TODO BS 20171213: Optimization can be done: keep in cache modifications on image instead change it entirely
116
+        try:
117
+            return self._cache[self._get_interior_unique_key(interiors)]
118
+        except KeyError:
119
+            pass  # compute it
120
+
102 121
         image = self.original_image.copy()
103 122
         image_height = image.height
104 123
         pixels = image.load()
@@ -116,4 +135,5 @@ class InteriorManager(object):
116 135
 
117 136
                         pixels[x, real_y] = (0, 0, 0, 0)
118 137
 
138
+        self._cache[self._get_interior_unique_key(interiors)] = image
119 139
         return image