Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
96 changes: 55 additions & 41 deletions cellpose/gui/guiparts.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
"""
Copyright © 2025 Howard Hughes Medical Institute, Authored by Carsen Stringer , Michael Rariden and Marius Pachitariu.
"""
import logging
import traceback
from qtpy import QtGui, QtCore
from qtpy.QtGui import QPixmap, QDoubleValidator
from qtpy.QtWidgets import QWidget, QDialog, QGridLayout, QPushButton, QLabel, QLineEdit, QDialogButtonBox, QComboBox, QCheckBox, QVBoxLayout
Expand Down Expand Up @@ -135,6 +137,16 @@ def setup(self):

# return ChannelChoose, ChannelLabels

def unsilence_exceptions(func):
""" Wrapper to unsilence Qt exceptions and re-raise them """
def wrapper(*args, **kwargs):
try:
return func(*args, **kwargs)
except Exception as e:
logger = logging.getLogger(__name__)
logger.critical(f"Uncaught exception in {func.__name__}")
logger.debug(''.join(traceback.format_exception(type(e), e, e.__traceback__)))
return wrapper

class ModelButton(QPushButton):

Expand Down Expand Up @@ -582,6 +594,7 @@ def __init__(self, parent=None, border=None, lockAspect=False, enableMouse=True,
self.parent = parent
self.axHistoryPointer = -1

@unsilence_exceptions
def keyPressEvent(self, ev):
"""
This routine should capture key presses in the current view box.
Expand Down Expand Up @@ -629,58 +642,56 @@ def __init__(self, image=None, viewbox=None, parent=None, **kargs):
self.parent.current_stroke = []
self.parent.in_stroke = False

@unsilence_exceptions
def mouseClickEvent(self, ev):
if not (self.parent.masksOn or
self.parent.outlinesOn) and self.parent.removing_region:
return

try:
is_right_click = ev.button() == QtCore.Qt.RightButton
if self.parent.loaded \
and (is_right_click or ev.modifiers() & QtCore.Qt.ShiftModifier and not ev.double())\
and not self.parent.deleting_multiple:
if not self.parent.in_stroke:
ev.accept()
self.create_start(ev.pos())
self.parent.stroke_appended = False
self.parent.in_stroke = True
self.drawAt(ev.pos(), ev)
else:
ev.accept()
self.end_stroke()
self.parent.in_stroke = False
elif not self.parent.in_stroke:
y, x = int(ev.pos().y()), int(ev.pos().x())
if y >= 0 and y < self.parent.Ly and x >= 0 and x < self.parent.Lx:
if ev.button() == QtCore.Qt.LeftButton and not ev.double():
idx = self.parent.cellpix[self.parent.currentZ][y, x]
if idx > 0:
if ev.modifiers() & QtCore.Qt.ControlModifier:
# delete mask selected
self.parent.remove_cell(idx)
elif ev.modifiers() & QtCore.Qt.AltModifier:
self.parent.merge_cells(idx)
elif self.parent.masksOn and not self.parent.deleting_multiple:
self.parent.unselect_cell()
self.parent.select_cell(idx)
elif self.parent.deleting_multiple:
if idx in self.parent.removing_cells_list:
self.parent.unselect_cell_multi(idx)
self.parent.removing_cells_list.remove(idx)
else:
self.parent.select_cell_multi(idx)
self.parent.removing_cells_list.append(idx)
is_right_click = ev.button() == QtCore.Qt.RightButton
if self.parent.loaded \
and (is_right_click or ev.modifiers() & QtCore.Qt.ShiftModifier and not ev.double())\
and not self.parent.deleting_multiple:
if not self.parent.in_stroke:
ev.accept()
self.create_start(ev.pos())
self.parent.stroke_appended = False
self.parent.in_stroke = True
self.drawAt(ev.pos(), ev)
else:
ev.accept()
self.end_stroke()
self.parent.in_stroke = False
elif not self.parent.in_stroke:
y, x = int(ev.pos().y()), int(ev.pos().x())
if y >= 0 and y < self.parent.Ly and x >= 0 and x < self.parent.Lx:
if ev.button() == QtCore.Qt.LeftButton and not ev.double():
idx = self.parent.cellpix[self.parent.currentZ][y, x]
if idx > 0:
if ev.modifiers() & QtCore.Qt.ControlModifier:
# delete mask selected
self.parent.remove_cell(idx)
elif ev.modifiers() & QtCore.Qt.AltModifier:
self.parent.merge_cells(idx)
Comment on lines +651 to +675
Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just de-indented the code's try/catch to use the function decorator instead

elif self.parent.masksOn and not self.parent.deleting_multiple:
self.parent.unselect_cell()
except Exception as err:
print('Error encountered while drawing. Saving masks and exiting...')
_save_sets(self.parent)
raise(err)

self.parent.select_cell(idx)
elif self.parent.deleting_multiple:
if idx in self.parent.removing_cells_list:
self.parent.unselect_cell_multi(idx)
self.parent.removing_cells_list.remove(idx)
else:
self.parent.select_cell_multi(idx)
self.parent.removing_cells_list.append(idx)
elif self.parent.masksOn and not self.parent.deleting_multiple:
self.parent.unselect_cell()

@unsilence_exceptions
def mouseDragEvent(self, ev):
ev.ignore()
return

@unsilence_exceptions
def hoverEvent(self, ev):
if self.parent.in_stroke:
if self.parent.in_stroke:
Expand Down Expand Up @@ -739,9 +750,11 @@ def end_stroke(self):
self.parent.add_set()
self.parent.in_stroke = False

@unsilence_exceptions
def tabletEvent(self, ev):
pass

@unsilence_exceptions
def drawAt(self, pos, ev=None):
mask = self.strokemask
stroke = self.parent.current_stroke
Expand Down Expand Up @@ -786,6 +799,7 @@ def drawAt(self, pos, ev=None):
stroke.append([self.parent.currentZ, x, y, iscent])
self.updateImage()

@unsilence_exceptions
def setDrawKernel(self, kernel_size=3):
bs = kernel_size
kernel = np.ones((bs, bs), np.uint8)
Expand Down
2 changes: 1 addition & 1 deletion cellpose/io.py
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ def logger_setup(cp_path=".cellpose", logfile_name="run.log", stdout_file_replac
formatter = logging.Formatter("%(asctime)s [%(module)s %(levelname)s] %(message)s")
debug_formatter = logging.Formatter("%(asctime)s %(levelname)s [%(filename)s:%(lineno)d - %(funcName)20s()] %(message)s")
logger = logging.getLogger('cellpose')
logger.setLevel(logging.INFO)
logger.setLevel(logging.DEBUG)
logger.handlers.clear()

logfile_fh.setFormatter(debug_formatter)
Expand Down
Loading