HeshamAI commited on
Commit
49323b3
·
verified ·
1 Parent(s): 08c85ce

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +73 -70
app.py CHANGED
@@ -94,65 +94,6 @@ class DicomAnalyzer:
94
  self.zoom_factor = max(1.0, self.zoom_factor - 0.5)
95
  return self.update_display()
96
 
97
- def update_display(self):
98
- try:
99
- if self.original_display is None:
100
- return None
101
-
102
- # Calculate zoomed size
103
- height, width = self.original_display.shape[:2]
104
- new_height = int(height * self.zoom_factor)
105
- new_width = int(width * self.zoom_factor)
106
-
107
- # Create zoomed image
108
- zoomed = cv2.resize(self.original_display, (new_width, new_height),
109
- interpolation=cv2.INTER_CUBIC)
110
-
111
- # Draw marks with ImageJ-like yellow circle
112
- for x, y, diameter in self.marks:
113
- zoomed_x = int(x * self.zoom_factor)
114
- zoomed_y = int(y * self.zoom_factor)
115
- zoomed_diameter = int(diameter * self.zoom_factor)
116
-
117
- # Draw main circle like ImageJ
118
- cv2.circle(zoomed,
119
- (zoomed_x, zoomed_y),
120
- zoomed_diameter // 2,
121
- (0, 255, 255), # Yellow color
122
- 1, # Thinner line
123
- lineType=cv2.LINE_AA)
124
-
125
- # Add small points around circle perimeter (ImageJ style)
126
- num_points = 8
127
- for i in range(num_points):
128
- angle = 2 * np.pi * i / num_points
129
- point_x = int(zoomed_x + (zoomed_diameter/2) * np.cos(angle))
130
- point_y = int(zoomed_y + (zoomed_diameter/2) * np.sin(angle))
131
- cv2.circle(zoomed,
132
- (point_x, point_y),
133
- 1,
134
- (0, 255, 255),
135
- -1,
136
- lineType=cv2.LINE_AA)
137
-
138
- # Extract visible portion
139
- visible_height = min(height, new_height)
140
- visible_width = min(width, new_width)
141
-
142
- # Ensure pan values don't exceed bounds
143
- self.pan_x = min(self.pan_x, max(0, new_width - width))
144
- self.pan_y = min(self.pan_y, max(0, new_height - height))
145
-
146
- visible = zoomed[
147
- self.pan_y:self.pan_y + visible_height,
148
- self.pan_x:self.pan_x + visible_width
149
- ]
150
-
151
- return visible
152
- except Exception as e:
153
- print(f"Error updating display: {str(e)}")
154
- return self.original_display
155
-
156
  def handle_keyboard(self, key):
157
  try:
158
  print(f"Handling key press: {key}")
@@ -177,16 +118,14 @@ class DicomAnalyzer:
177
  if self.current_image is None:
178
  return None, "No image loaded"
179
 
180
- # Adjust coordinates to match ImageJ
 
 
 
 
181
  height, width = self.current_image.shape[:2]
182
- x = int(evt.index[0])
183
- y = int(evt.index[1])
184
-
185
- # Convert coordinates to match ImageJ system
186
- if hasattr(self.dicom_data, 'PixelSpacing'):
187
- pixel_spacing = float(self.dicom_data.PixelSpacing[0])
188
- x = int(x) # Keep original x coordinate
189
- y = int(y) # Keep original y coordinate
190
 
191
  mask = np.zeros_like(self.current_image, dtype=np.uint8)
192
  y_indices, x_indices = np.ogrid[:self.current_image.shape[0], :self.current_image.shape[1]]
@@ -223,7 +162,71 @@ class DicomAnalyzer:
223
  print(f"Error analyzing ROI: {str(e)}")
224
  return self.display_image, f"Error analyzing ROI: {str(e)}"
225
 
226
- def format_results(self):
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
227
  if not self.results:
228
  return "No measurements yet"
229
  df = pd.DataFrame(self.results)
@@ -420,4 +423,4 @@ if __name__ == "__main__":
420
  )
421
  except Exception as e:
422
  print(f"Error launching application: {str(e)}")
423
- raise e
 
94
  self.zoom_factor = max(1.0, self.zoom_factor - 0.5)
95
  return self.update_display()
96
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
97
  def handle_keyboard(self, key):
98
  try:
99
  print(f"Handling key press: {key}")
 
118
  if self.current_image is None:
119
  return None, "No image loaded"
120
 
121
+ # Convert clicked coordinates considering zoom and pan
122
+ x = int((evt.index[0] + self.pan_x) / self.zoom_factor)
123
+ y = int((evt.index[1] + self.pan_y) / self.zoom_factor)
124
+
125
+ # Ensure coordinates are within image bounds
126
  height, width = self.current_image.shape[:2]
127
+ x = max(0, min(x, width-1))
128
+ y = max(0, min(y, height-1))
 
 
 
 
 
 
129
 
130
  mask = np.zeros_like(self.current_image, dtype=np.uint8)
131
  y_indices, x_indices = np.ogrid[:self.current_image.shape[0], :self.current_image.shape[1]]
 
162
  print(f"Error analyzing ROI: {str(e)}")
163
  return self.display_image, f"Error analyzing ROI: {str(e)}"
164
 
165
+ def update_display(self):
166
+ try:
167
+ if self.original_display is None:
168
+ return None
169
+
170
+ # Calculate zoomed size
171
+ height, width = self.original_display.shape[:2]
172
+ new_height = int(height * self.zoom_factor)
173
+ new_width = int(width * self.zoom_factor)
174
+
175
+ # Create zoomed image
176
+ zoomed = cv2.resize(self.original_display, (new_width, new_height),
177
+ interpolation=cv2.INTER_CUBIC)
178
+
179
+ # Draw marks with ImageJ-like yellow circle
180
+ for x, y, diameter in self.marks:
181
+ # Calculate zoomed coordinates correctly
182
+ zoomed_x = int(x * self.zoom_factor)
183
+ zoomed_y = int(y * self.zoom_factor)
184
+ zoomed_diameter = int(diameter * self.zoom_factor)
185
+
186
+ # Draw main circle - Pure yellow
187
+ cv2.circle(zoomed,
188
+ (zoomed_x, zoomed_y),
189
+ zoomed_diameter // 2,
190
+ (0, 255, 255), # BGR: Pure yellow
191
+ 1, # Thin line
192
+ lineType=cv2.LINE_AA)
193
+
194
+ # Add small points around circle perimeter
195
+ num_points = 8
196
+ for i in range(num_points):
197
+ angle = 2 * np.pi * i / num_points
198
+ point_x = int(zoomed_x + (zoomed_diameter/2) * np.cos(angle))
199
+ point_y = int(zoomed_y + (zoomed_diameter/2) * np.sin(angle))
200
+ cv2.circle(zoomed,
201
+ (point_x, point_y),
202
+ 1,
203
+ (0, 255, 255), # BGR: Pure yellow
204
+ -1,
205
+ lineType=cv2.LINE_AA)
206
+
207
+ # Extract visible portion considering pan
208
+ visible_height = min(height, new_height)
209
+ visible_width = min(width, new_width)
210
+
211
+ # Calculate pan bounds
212
+ self.max_pan_x = max(0, new_width - width)
213
+ self.max_pan_y = max(0, new_height - height)
214
+
215
+ # Ensure pan values don't exceed bounds
216
+ self.pan_x = min(self.pan_x, self.max_pan_x)
217
+ self.pan_y = min(self.pan_y, self.max_pan_y)
218
+
219
+ # Extract correct portion of zoomed image
220
+ visible = zoomed[
221
+ self.pan_y:self.pan_y + visible_height,
222
+ self.pan_x:self.pan_x + visible_width
223
+ ]
224
+
225
+ return visible
226
+ except Exception as e:
227
+ print(f"Error updating display: {str(e)}")
228
+ return self.original_display
229
+ def format_results(self):
230
  if not self.results:
231
  return "No measurements yet"
232
  df = pd.DataFrame(self.results)
 
423
  )
424
  except Exception as e:
425
  print(f"Error launching application: {str(e)}")
426
+ raise e