Commit a657e6bbb7adff3491de8f1fd79d8ad3df4bd9a7
1 parent
c614e7ac
Exists in
threshold_history
ENH: EditionHistory can be interlaced to ThresholdHistory
Showing
2 changed files
with
39 additions
and
16 deletions
Show diff stats
invesalius/data/mask.py
@@ -32,22 +32,33 @@ import imagedata_utils as iu | @@ -32,22 +32,33 @@ import imagedata_utils as iu | ||
32 | from wx.lib.pubsub import pub as Publisher | 32 | from wx.lib.pubsub import pub as Publisher |
33 | 33 | ||
34 | class ThresholdHistoryNode(object): | 34 | class ThresholdHistoryNode(object): |
35 | - def __init__(self, threshold): | ||
36 | - self.threshold = threshold | 35 | + def __init__(self, mask): |
36 | + self.threshold = mask.threshold_range | ||
37 | + | ||
38 | + if mask.was_edited: | ||
39 | + self.array_file = tempfile.mktemp() | ||
40 | + shutil.copyfile(mask.temp_file, self.array_file) | ||
41 | + else: | ||
42 | + self.array_file = '' | ||
37 | 43 | ||
38 | def commit_history(self, mask): | 44 | def commit_history(self, mask): |
39 | #Publisher.sendMessage('Changing threshold values', self.threshold) | 45 | #Publisher.sendMessage('Changing threshold values', self.threshold) |
40 | mask.threshold_range = self.threshold | 46 | mask.threshold_range = self.threshold |
41 | - Publisher.sendMessage('Set threshold values no history', self.threshold) | 47 | + if self.array_file: |
48 | + mask._open_mask(self.array_file, mask.matrix.shape) | ||
49 | + Publisher.sendMessage('Discard buffer masks') | ||
50 | + else: | ||
51 | + Publisher.sendMessage('Set threshold values no history', self.threshold) | ||
42 | Publisher.sendMessage('Reload actual slice') | 52 | Publisher.sendMessage('Reload actual slice') |
43 | 53 | ||
44 | 54 | ||
45 | class EditionHistoryNode(object): | 55 | class EditionHistoryNode(object): |
46 | - def __init__(self, index, orientation, array, clean=False): | 56 | + def __init__(self, index, orientation, array, clean=False, threshold=(0,0)): |
47 | self.index = index | 57 | self.index = index |
48 | self.orientation = orientation | 58 | self.orientation = orientation |
49 | self.filename = tempfile.mktemp(suffix='.npy') | 59 | self.filename = tempfile.mktemp(suffix='.npy') |
50 | self.clean = clean | 60 | self.clean = clean |
61 | + self.threshold = threshold | ||
51 | 62 | ||
52 | self._save_array(array) | 63 | self._save_array(array) |
53 | 64 | ||
@@ -71,6 +82,7 @@ class EditionHistoryNode(object): | @@ -71,6 +82,7 @@ class EditionHistoryNode(object): | ||
71 | if self.clean: | 82 | if self.clean: |
72 | mvolume[0, 0, self.index+1] = 1 | 83 | mvolume[0, 0, self.index+1] = 1 |
73 | 84 | ||
85 | + mask.threshold_range = self.threshold | ||
74 | print "applying to", self.orientation, "at slice", self.index | 86 | print "applying to", self.orientation, "at slice", self.index |
75 | 87 | ||
76 | def __del__(self): | 88 | def __del__(self): |
@@ -87,16 +99,17 @@ class EditionHistory(object): | @@ -87,16 +99,17 @@ class EditionHistory(object): | ||
87 | Publisher.sendMessage("Enable undo", False) | 99 | Publisher.sendMessage("Enable undo", False) |
88 | Publisher.sendMessage("Enable redo", False) | 100 | Publisher.sendMessage("Enable redo", False) |
89 | 101 | ||
90 | - def new_node(self, index, orientation, array, p_array, clean): | 102 | + def new_node(self, index, orientation, array, p_array, clean, threshold): |
91 | # Saving the previous state, used to undo/redo correctly. | 103 | # Saving the previous state, used to undo/redo correctly. |
92 | - p_node = EditionHistoryNode(index, orientation, p_array, clean) | 104 | + p_node = EditionHistoryNode(index, orientation, p_array, clean, |
105 | + threshold) | ||
93 | self.add(p_node) | 106 | self.add(p_node) |
94 | 107 | ||
95 | - node = EditionHistoryNode(index, orientation, array, clean) | 108 | + node = EditionHistoryNode(index, orientation, array, clean, threshold) |
96 | self.add(node) | 109 | self.add(node) |
97 | 110 | ||
98 | - def new_theshold_node(self, threshold): | ||
99 | - node = ThresholdHistoryNode(threshold) | 111 | + def new_theshold_node(self, mask): |
112 | + node = ThresholdHistoryNode(mask) | ||
100 | self.add(node) | 113 | self.add(node) |
101 | 114 | ||
102 | def add(self, node): | 115 | def add(self, node): |
@@ -116,7 +129,7 @@ class EditionHistory(object): | @@ -116,7 +129,7 @@ class EditionHistory(object): | ||
116 | def undo(self, mask, actual_slices=None): | 129 | def undo(self, mask, actual_slices=None): |
117 | h = self.history | 130 | h = self.history |
118 | if self.index > 0: | 131 | if self.index > 0: |
119 | - if isinstance(h[self.index], EditionHistoryNode): | 132 | + if isinstance(h[self.index - 1], EditionHistoryNode): |
120 | #if self.index > 0 and h[self.index].clean: | 133 | #if self.index > 0 and h[self.index].clean: |
121 | ##self.index -= 1 | 134 | ##self.index -= 1 |
122 | ##h[self.index].commit_history(mvolume) | 135 | ##h[self.index].commit_history(mvolume) |
@@ -126,7 +139,7 @@ class EditionHistory(object): | @@ -126,7 +139,7 @@ class EditionHistory(object): | ||
126 | else: | 139 | else: |
127 | self.index -= 1 | 140 | self.index -= 1 |
128 | h[self.index].commit_history(mask) | 141 | h[self.index].commit_history(mask) |
129 | - if actual_slices and self.index and actual_slices[h[self.index - 1].orientation] == h[self.index - 1].index: | 142 | + if actual_slices and self.index and isinstance(h[self.index - 1], EditionHistoryNode) and actual_slices[h[self.index - 1].orientation] == h[self.index - 1].index : |
130 | self.index -= 1 | 143 | self.index -= 1 |
131 | h[self.index].commit_history(mask) | 144 | h[self.index].commit_history(mask) |
132 | self._reload_slice(self.index) | 145 | self._reload_slice(self.index) |
@@ -143,7 +156,7 @@ class EditionHistory(object): | @@ -143,7 +156,7 @@ class EditionHistory(object): | ||
143 | def redo(self, mask, actual_slices=None): | 156 | def redo(self, mask, actual_slices=None): |
144 | h = self.history | 157 | h = self.history |
145 | if self.index < len(h) - 1: | 158 | if self.index < len(h) - 1: |
146 | - if isinstance(h[self.index], EditionHistoryNode): | 159 | + if isinstance(h[self.index + 1], EditionHistoryNode): |
147 | #if self.index < len(h) - 1 and h[self.index].clean: | 160 | #if self.index < len(h) - 1 and h[self.index].clean: |
148 | ##self.index += 1 | 161 | ##self.index += 1 |
149 | ##h[self.index].commit_history(mvolume) | 162 | ##h[self.index].commit_history(mvolume) |
@@ -154,7 +167,7 @@ class EditionHistory(object): | @@ -154,7 +167,7 @@ class EditionHistory(object): | ||
154 | else: | 167 | else: |
155 | self.index += 1 | 168 | self.index += 1 |
156 | h[self.index].commit_history(mask) | 169 | h[self.index].commit_history(mask) |
157 | - if actual_slices and self.index < len(h) - 1 and actual_slices[h[self.index + 1].orientation] == h[self.index + 1].index: | 170 | + if actual_slices and self.index < len(h) - 1 and isinstance(h[self.index + 1], EditionHistoryNode) and actual_slices[h[self.index + 1].orientation] == h[self.index + 1].index: |
158 | self.index += 1 | 171 | self.index += 1 |
159 | h[self.index].commit_history(mask) | 172 | h[self.index].commit_history(mask) |
160 | self._reload_slice(self.index) | 173 | self._reload_slice(self.index) |
@@ -217,10 +230,11 @@ class Mask(): | @@ -217,10 +230,11 @@ class Mask(): | ||
217 | Publisher.subscribe(self.OnSwapVolumeAxes, 'Swap volume axes') | 230 | Publisher.subscribe(self.OnSwapVolumeAxes, 'Swap volume axes') |
218 | 231 | ||
219 | def save_edition_history(self, index, orientation, array, p_array, clean=False): | 232 | def save_edition_history(self, index, orientation, array, p_array, clean=False): |
220 | - self.history.new_node(index, orientation, array, p_array, clean) | 233 | + self.history.new_node(index, orientation, array, p_array, clean, |
234 | + self.threshold_range) | ||
221 | 235 | ||
222 | def save_threshold_history(self, threshold): | 236 | def save_threshold_history(self, threshold): |
223 | - self.history.new_theshold_node(threshold) | 237 | + self.history.new_theshold_node(self) |
224 | 238 | ||
225 | def undo_history(self, actual_slices): | 239 | def undo_history(self, actual_slices): |
226 | self.history.undo(self, actual_slices) | 240 | self.history.undo(self, actual_slices) |
invesalius/data/slice_.py
@@ -117,6 +117,7 @@ class Slice(object): | @@ -117,6 +117,7 @@ class Slice(object): | ||
117 | 'Change mask colour') | 117 | 'Change mask colour') |
118 | Publisher.subscribe(self.__set_mask_name, 'Change mask name') | 118 | Publisher.subscribe(self.__set_mask_name, 'Change mask name') |
119 | Publisher.subscribe(self.__show_mask, 'Show mask') | 119 | Publisher.subscribe(self.__show_mask, 'Show mask') |
120 | + Publisher.subscribe(self.discard_buffer_mask, 'Discard buffer masks') | ||
120 | 121 | ||
121 | Publisher.subscribe(self.__set_current_mask_threshold_limits, | 122 | Publisher.subscribe(self.__set_current_mask_threshold_limits, |
122 | 'Update threshold limits') | 123 | 'Update threshold limits') |
@@ -259,7 +260,11 @@ class Slice(object): | @@ -259,7 +260,11 @@ class Slice(object): | ||
259 | threshold_range = evt_pubsub.data | 260 | threshold_range = evt_pubsub.data |
260 | index = self.current_mask.index | 261 | index = self.current_mask.index |
261 | self.num_gradient += 1 | 262 | self.num_gradient += 1 |
263 | + | ||
264 | + self.current_mask.save_threshold_history(threshold_range) | ||
265 | + | ||
262 | self.current_mask.matrix[:] = 0 | 266 | self.current_mask.matrix[:] = 0 |
267 | + | ||
263 | #self.current_mask.clear_history() | 268 | #self.current_mask.clear_history() |
264 | 269 | ||
265 | # TODO: merge this code with apply_slice_buffer_to_mask | 270 | # TODO: merge this code with apply_slice_buffer_to_mask |
@@ -278,7 +283,6 @@ class Slice(object): | @@ -278,7 +283,6 @@ class Slice(object): | ||
278 | self.current_mask.matrix[1:, 1:, n] = b_mask | 283 | self.current_mask.matrix[1:, 1:, n] = b_mask |
279 | self.current_mask.matrix[0, 0, n] = 1 | 284 | self.current_mask.matrix[0, 0, n] = 1 |
280 | 285 | ||
281 | - self.current_mask.save_threshold_history(threshold_range) | ||
282 | 286 | ||
283 | def __set_current_mask_threshold_no_history(self, evt_pubsub): | 287 | def __set_current_mask_threshold_no_history(self, evt_pubsub): |
284 | threshold_range = evt_pubsub.data | 288 | threshold_range = evt_pubsub.data |
@@ -952,6 +956,11 @@ class Slice(object): | @@ -952,6 +956,11 @@ class Slice(object): | ||
952 | self.buffer_slices[o].discard_vtk_mask() | 956 | self.buffer_slices[o].discard_vtk_mask() |
953 | Publisher.sendMessage('Reload actual slice') | 957 | Publisher.sendMessage('Reload actual slice') |
954 | 958 | ||
959 | + def discard_buffer_mask(self, pubsub_evt): | ||
960 | + for buffer_ in self.buffer_slices.values(): | ||
961 | + buffer_.discard_vtk_mask() | ||
962 | + buffer_.discard_mask() | ||
963 | + | ||
955 | def __undo_edition(self, pub_evt): | 964 | def __undo_edition(self, pub_evt): |
956 | buffer_slices = self.buffer_slices | 965 | buffer_slices = self.buffer_slices |
957 | actual_slices = {"AXIAL": buffer_slices["AXIAL"].index, | 966 | actual_slices = {"AXIAL": buffer_slices["AXIAL"].index, |