batoolset-gui 0.2.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (74) hide show
  1. batoolset/GUI/__init__.py +0 -0
  2. batoolset/GUI/customdialog.py +136 -0
  3. batoolset/GUI/exception_handler.py +74 -0
  4. batoolset/GUI/list_gui.py +514 -0
  5. batoolset/GUI/multi_image_display.py +1038 -0
  6. batoolset/GUI/open.py +325 -0
  7. batoolset/GUI/overlay_hints.py +45 -0
  8. batoolset/GUI/paint2.py +1369 -0
  9. batoolset/GUI/scrollablepaint.py +1165 -0
  10. batoolset/dialogs/__init__.py +0 -0
  11. batoolset/dialogs/opensave.py +228 -0
  12. batoolset/drawings/__init__.py +0 -0
  13. batoolset/drawings/math_text.py +294 -0
  14. batoolset/drawings/pdf_svg_renderer.py +376 -0
  15. batoolset/drawings/shapes/Position.py +183 -0
  16. batoolset/drawings/shapes/__init__.py +0 -0
  17. batoolset/drawings/shapes/automated_alignment_drawing_refactored.py +346 -0
  18. batoolset/drawings/shapes/circle2d.py +99 -0
  19. batoolset/drawings/shapes/compute_optimal_size_all_merged.py +328 -0
  20. batoolset/drawings/shapes/ellipse2d.py +336 -0
  21. batoolset/drawings/shapes/freehand2d.py +235 -0
  22. batoolset/drawings/shapes/group.py +1985 -0
  23. batoolset/drawings/shapes/image2d.py +3157 -0
  24. batoolset/drawings/shapes/line2d.py +579 -0
  25. batoolset/drawings/shapes/point2d.py +257 -0
  26. batoolset/drawings/shapes/polygon2d.py +357 -0
  27. batoolset/drawings/shapes/polyline2d.py +235 -0
  28. batoolset/drawings/shapes/rect2d.py +388 -0
  29. batoolset/drawings/shapes/rectangle2d.py +601 -0
  30. batoolset/drawings/shapes/scalebar.py +310 -0
  31. batoolset/drawings/shapes/serializablefont.py +133 -0
  32. batoolset/drawings/shapes/serializableguiparams.py +14 -0
  33. batoolset/drawings/shapes/square2d.py +102 -0
  34. batoolset/drawings/shapes/test_publication_style.py +220 -0
  35. batoolset/drawings/shapes/textorientation.py +45 -0
  36. batoolset/drawings/shapes/tools.py +467 -0
  37. batoolset/drawings/shapes/transform2D.py +350 -0
  38. batoolset/drawings/shapes/txt2d.py +615 -0
  39. batoolset/drawings/svg_clip_renderer.py +247 -0
  40. batoolset/drawings/svg_embed.py +165 -0
  41. batoolset/drawings/svg_text_renderer.py +183 -0
  42. batoolset/drawings/widgets/__init__.py +0 -0
  43. batoolset/drawings/widgets/col.py +343 -0
  44. batoolset/drawings/widgets/image_group.py +248 -0
  45. batoolset/drawings/widgets/image_organizer.py +96 -0
  46. batoolset/drawings/widgets/paint.py +184 -0
  47. batoolset/drawings/widgets/vectorial.py +256 -0
  48. batoolset/figure/__init__.py +0 -0
  49. batoolset/figure/alignment.py +822 -0
  50. batoolset/figure/column.py +1117 -0
  51. batoolset/figure/fig_tools.py +285 -0
  52. batoolset/figure/minimal_debugger_scale_etc.py +139 -0
  53. batoolset/figure/panel.py +697 -0
  54. batoolset/figure/row.py +852 -0
  55. batoolset/figure/user_selection.py +287 -0
  56. batoolset/icons/__init__.py +0 -0
  57. batoolset/icons/tools.py +248 -0
  58. batoolset/luts/__init__.py +0 -0
  59. batoolset/luts/lut_minimal_test.py +1308 -0
  60. batoolset/luts/lutcreatorfromformula.py +209 -0
  61. batoolset/luts/luteditor.py +243 -0
  62. batoolset/pyqts/__init__.py +0 -0
  63. batoolset/pyqts/pleasewaitdialog.py +14 -0
  64. batoolset/pyqts/tools.py +760 -0
  65. batoolset/serializations/__init__.py +0 -0
  66. batoolset/serializations/tools.py +1338 -0
  67. batoolset/theme.py +647 -0
  68. batoolset/uis/__init__.py +0 -0
  69. batoolset/uis/blinker.py +56 -0
  70. batoolset_gui-0.2.0.dist-info/METADATA +54 -0
  71. batoolset_gui-0.2.0.dist-info/RECORD +74 -0
  72. batoolset_gui-0.2.0.dist-info/WHEEL +5 -0
  73. batoolset_gui-0.2.0.dist-info/licenses/LICENSE +24 -0
  74. batoolset_gui-0.2.0.dist-info/top_level.txt +1 -0
@@ -0,0 +1,514 @@
1
+ # support list for writing or not stuff
2
+ import os
3
+ from batoolset.settings.global_settings import set_UI # set the UI to qtpy
4
+ set_UI()
5
+ from qtpy import QtCore, QtWidgets
6
+ from qtpy.QtCore import Qt,Signal
7
+ from qtpy.QtWidgets import QWidget, QAbstractItemView, QListWidget, QVBoxLayout, QListWidgetItem, QToolBar, \
8
+ QToolButton, \
9
+ QLabel, QAction
10
+ import pyperclip as clip
11
+ from batoolset.dialogs.opensave import saveFileDialog
12
+ from batoolset.utils.loadlist import loadlist, save_list_to_file
13
+ import os
14
+ import platform
15
+ import subprocess
16
+ from batoolset.files.tools import smart_name_parser
17
+ import qtawesome as qta
18
+ from natsort import natsorted
19
+ from batoolset.icons.tools import get_icon
20
+ from batoolset.tools.logger import TA_logger
21
+ logger = TA_logger()
22
+
23
+
24
+ __DEBUG__ = True
25
+
26
+ IMAGES_2D = ['.tif', '.tiff', '.jpg', '.jpeg', '.png', '.tga', '.bmp']
27
+ STACKS = ['.tif', '.tiff', '.lif', '.czi', '.lif', '.lsm']
28
+ LISTS = ['.lst', '.txt']
29
+ FASTA = ['.fa','.fna','.fasta']
30
+ PYTA_DEFAULT = IMAGES_2D + LISTS
31
+
32
+ class CustomListWidget(QListWidget):
33
+ orderChanged = Signal()
34
+
35
+ def dropEvent(self, event):
36
+ super().dropEvent(event)
37
+ self.orderChanged.emit()
38
+
39
+ class ListGUI(QWidget):
40
+ orderChanged = Signal()
41
+ deletePressed = Signal() # can be used in parent to detect that this was called allowing some action to be taken (more elegant than the callback or the method overlaod in several aspects)!
42
+ # TODO define supported formats --> TODO
43
+ def __init__(self, parent=None, file_to_load=None, supported_files=None, custom_label='Please Drag and Drop files below:', default_double_click_behaviour='full_no_ext', enable_folder_DND=True, detect_list_order_change=False):
44
+ super().__init__(parent)
45
+ if detect_list_order_change:
46
+ self.list = CustomListWidget(self) # a list that contains files to read or play with
47
+ # self.list.orderChanged.connect(self.check_order_changed)
48
+ else:
49
+ self.list = QListWidget(self)
50
+ self.list.setSelectionMode(QAbstractItemView.ExtendedSelection)
51
+ # self.list.selectionModel().selectionChanged.connect(self.selectionChanged) # connect it to sel change
52
+
53
+ # self.list.selectionModel().selectionChanged.connect(self.listSelectionChanged)
54
+
55
+ self.list.itemDoubleClicked.connect(self.open_corresponding_folder)
56
+
57
+ self.enable_folder_DND = enable_folder_DND
58
+ self.default_double_click_behaviour = default_double_click_behaviour
59
+
60
+ layout = QVBoxLayout()
61
+ lab = QLabel(custom_label)
62
+ layout.addWidget(lab)
63
+ layout.addWidget(self.list)
64
+
65
+ self.setLayout(layout)
66
+ # allow support of DND
67
+ self.setAcceptDrops(True)
68
+ self.supported_files = supported_files
69
+
70
+ # status_bar = QStatusBar()
71
+ # layout.addWidget(status_bar)
72
+ # self.list_commands(**kwargs)
73
+ self.list_commands()
74
+
75
+ if file_to_load is not None:
76
+ self.load_list(file_to_load)
77
+ # if __DEBUG__:
78
+ # fake sel list
79
+ # pass
80
+
81
+ # allow move objects within the list
82
+ self.list.setDragDropMode(QAbstractItemView.InternalMove) # j'adore --> maybe put this as an option
83
+
84
+ # allows sorting of lists
85
+ # self.list.setSortingEnabled(True) # we don't want list to be sorted by default
86
+ # self.list.sortItems() # ascending by default
87
+ self.list.sortItems(QtCore.Qt.DescendingOrder) # todo MAKE it a sort button
88
+
89
+ # both lines below support objects handling directly from the list --> a gain of time
90
+ self.list.itemChanged.connect(self.item_changed)
91
+ self._object_dict = {} # dirty hack to store objects and allow for DND of objects
92
+
93
+ def item_changed(self, item):
94
+ obj = self._object_dict.get(str(item)) # Get the object from the dictionary
95
+ if obj is not None:
96
+ # Do something with the object
97
+ print("Object changed:", obj)
98
+ def check_order_changed(self):
99
+ # Implement your order changed logic here
100
+ print("Order changed!")
101
+ # self.setWindowTitle('test')
102
+
103
+ def open_corresponding_folder(self, double_clicked_item):
104
+ try:
105
+ self.open_folder(smart_name_parser(double_clicked_item.toolTip(), ordered_output=[self.default_double_click_behaviour])[0]) #'full_no_ext'
106
+ except:
107
+ # no big deal if it fails
108
+ pass
109
+
110
+ def open_folder(self, path):
111
+ if platform.system() == 'Darwin':
112
+ subprocess.Popen(['open', path])
113
+ elif platform.system() == 'Windows':
114
+ os.startfile(path)
115
+ elif platform.system() == 'Linux':
116
+ subprocess.Popen(["xdg-open", path])
117
+
118
+ def list_commands(self): #,**kwargs):
119
+
120
+ # buttons_to_hide = []
121
+ # if 'buttons_to_remove' in kwargs:
122
+ # buttons_to_hide = kwargs['buttons_to_remove']
123
+ # if isinstance(buttons_to_hide, str):
124
+ # buttons_to_hide = [buttons_to_hide]
125
+
126
+ # self.penSize = QSpinBox(objectName='penSize')
127
+ # self.penSize.setSingleStep(1)
128
+ # self.penSize.setRange(1, 256)
129
+ # self.penSize.setValue(3)
130
+ # self.penSize.valueChanged.connect(self.penSizechange)
131
+
132
+ # self.channels = QComboBox(objectName='channels')
133
+ # self.channels.addItem("merge")
134
+ # self.channels.addItem("0")
135
+ # self.channels.addItems(["1", "2", "3"])
136
+ # self.channels.currentIndexChanged.connect(self.channelChange)
137
+
138
+ self.tb = QToolBar()
139
+ #
140
+ toolButton = QToolButton()
141
+ # toolButton.setText('Draw')
142
+
143
+
144
+ save_action = QAction(get_icon('fa5.save'), 'Save image list', self)
145
+ save_action.triggered.connect(self.save_list)
146
+ # END KEEP
147
+ toolButton.setDefaultAction(save_action)
148
+ self.tb.addWidget(toolButton)
149
+ #
150
+ # toolButton2 = QToolButton()
151
+ # toolButton2.setText('Draw')
152
+ # toolButton2.setIcon(self.style().standardIcon(QStyle.SP_DialogApplyButton))
153
+ # tb.addWidget(toolButton2)
154
+ #
155
+ # toolButton3 = QToolButton()
156
+ # toolButton3.setText('Draw')
157
+ # toolButton3.setIcon(self.style().standardIcon(QStyle.SP_DialogCancelButton))
158
+ # tb.addWidget(toolButton3)
159
+ #
160
+ # toolButton4 = QToolButton()
161
+ # toolButton4.setText('Draw')
162
+ # toolButton4.setIcon(self.style().standardIcon(QStyle.SP_DialogCloseButton))
163
+ # tb.addWidget(toolButton4)
164
+
165
+ toolButton5 = QToolButton()
166
+ # toolButton5.setText("Delete")
167
+ # toolButton5.setIcon(self.style().standardIcon(QStyle.SP_TrashIcon))
168
+ # toolButton5.addAction(dqsdqsdq)
169
+ # pkoi marche pas
170
+ # KEEP
171
+
172
+ delete_sel_action = QAction(get_icon('mdi.delete-outline'), 'Delete selection', self)
173
+ # toolButton5.addAction(delete_sel_action) # this stuff adds a dropwdon that can be opened by pressing a long time on the button --> keep in mind cause can be useful
174
+ delete_sel_action.triggered.connect(self.removeSel)
175
+ # END KEEP
176
+ toolButton5.setDefaultAction(delete_sel_action)
177
+ self.tb.addWidget(toolButton5)
178
+
179
+ toolButton6 = QToolButton()
180
+ # toolButton6.setText("Copy")
181
+ # toolButton6.setIcon(get_icon('fa5.copy'))
182
+ copy_action = QAction(get_icon('fa5.copy'), 'Copy selection to the system clipboard', self)
183
+ copy_action.triggered.connect(self.sel_to_clipboard)
184
+ toolButton6.setDefaultAction(copy_action)
185
+ # toolButton6.ad#dAction(print('toto'))
186
+ self.tb.addWidget(toolButton6)
187
+
188
+ toolButton7 = QToolButton()
189
+ # toolButton7.setText("Paste")
190
+ # toolButton7.setIcon(get_icon('fa.paste'))
191
+ paste_action = QAction(get_icon('fa5s.paste'), 'Paste the system clipboard to the list', self)
192
+ paste_action.triggered.connect(self.paste_from_clipboard)
193
+ toolButton7.setDefaultAction(paste_action)
194
+ self.tb.addWidget(toolButton7)
195
+
196
+ toolButton8 = QToolButton()
197
+ sort_action = QAction(get_icon('mdi.sort-alphabetical-ascending'), 'Sort list (using the Natsort algorithm)', self)
198
+ sort_action.triggered.connect(self.natsort_list)
199
+ toolButton8.setDefaultAction(sort_action)
200
+ self.tb.addWidget(toolButton8)
201
+
202
+ # tb.addWidget(self.channels)
203
+
204
+ # tb.addAction("Save")
205
+ # tb.addAction("sq...")
206
+ # tb.addWidget(self.penSize)
207
+
208
+ # could have show and hide mask here --> see how I can do that --> but do not delete it in fact
209
+
210
+ self.layout().addWidget(self.tb)
211
+
212
+ # disable item internal move and list addition, just selection is kept
213
+ def freeze(self, bool):
214
+ self.tb.setEnabled(not bool)
215
+ # TODO disable DND of list component
216
+ # if bool:
217
+ # self.list.setDragDropMode(QAbstractItemView.InternalMove)
218
+ # self.setAcceptDrops(True)
219
+ # else:
220
+ # self.list.setDragDropMode(QAbstractItemView.InternalMove)
221
+ self.setAcceptDrops(not bool)
222
+ # how to disable item reorder
223
+ # QGraphicsItem.ItemIsMovable
224
+ # we also prevent internal drag --> it's a way to keep the list functional
225
+
226
+
227
+
228
+ # ça ne marche pas
229
+ # print(bool)
230
+ if bool:
231
+
232
+ # print('entering o,ne')
233
+
234
+ # disable item internal move
235
+ for iii in range(self.list.count()):
236
+ item = self.list.item(iii)
237
+
238
+ # is there a bug here
239
+ if item.flags() & Qt.ItemIsDragEnabled:
240
+ item.setFlags(item.flags() ^ Qt.ItemIsDragEnabled)
241
+ # item.setFlags(item.flags() ^ Qt.ItemIsDropEnabled)
242
+
243
+ # if iii == 0:
244
+ # if item.flags() & Qt.ItemIsDragEnabled:
245
+ # print( "ItemIsDragEnabled", item)
246
+ # else:
247
+ # print("not ItemIsDragEnabled", item)
248
+
249
+ else:
250
+ # allow item internal move
251
+ # print('entering two')
252
+ for iii in range(self.list.count()):
253
+ item = self.list.item(iii)
254
+ item.setFlags(item.flags() | Qt.ItemIsDragEnabled)
255
+ # item.setFlags(item.flags() | Qt.ItemIsDropEnabled)
256
+ # if iii == 0:
257
+ # if item.flags() & Qt.ItemIsDragEnabled:
258
+ # print("ItemIsDragEnabled", item)
259
+ # else:
260
+ # print("not ItemIsDragEnabled", item)
261
+
262
+
263
+ def load_list(self, file_to_load):
264
+ files = loadlist(file_to_load)
265
+ if files is not None:
266
+ # populate the list
267
+ for file in files:
268
+ self.add_file_to_list_if_supported(file)
269
+ else:
270
+ print('list could not be loaded/invalid list --> sorry')
271
+
272
+ # def selectionChanged(self):
273
+ # print('selection changed to override')
274
+
275
+ # allow DND
276
+ def dragEnterEvent(self, event):
277
+ if not self.acceptDrops():
278
+ logger.warning('Drag and drop not supported in "Preview" mode, please select another tab.')
279
+ event.ignore()
280
+ return
281
+ if event.mimeData().hasUrls():
282
+ event.accept()
283
+ else:
284
+ event.ignore()
285
+
286
+ def dragMoveEvent(self, event):
287
+ if not self.acceptDrops():
288
+ logger.warning('Drag and drop not supported in "Preview" mode, please select another tab.')
289
+ event.ignore()
290
+ return
291
+ if event.mimeData().hasUrls():
292
+ event.setDropAction(QtCore.Qt.CopyAction)
293
+ event.accept()
294
+ else:
295
+ event.ignore()
296
+
297
+ # handle DND on drop
298
+ def dropEvent(self, event):
299
+ super().dropEvent(event)
300
+ self.orderChanged.emit()
301
+
302
+ if not self.acceptDrops():
303
+ logger.warning('Drag and drop not supported in "Preview" mode, please select another tab.')
304
+ event.ignore()
305
+ return
306
+
307
+ if event.mimeData().hasUrls():
308
+ event.setDropAction(QtCore.Qt.CopyAction)
309
+ event.accept()
310
+ urls = []
311
+ for url in event.mimeData().urls():
312
+ urls.append(url.toLocalFile())
313
+ # add all dropped items to the list
314
+ for url in urls:
315
+ # item = QListWidgetItem(os.path.basename(url), self.list)
316
+ # item.setToolTip(url)
317
+ # self.list.addItem(item)
318
+ self.add_file_to_list_if_supported(url)
319
+ else:
320
+ event.ignore()
321
+
322
+ def is_file_supported(self, file):
323
+ if self.supported_files is None:
324
+ # accept all by default
325
+ return True
326
+ if smart_name_parser(file, ordered_output=['ext'])[0].lower() in self.supported_files:
327
+ return True
328
+ return False
329
+
330
+ def add_file_to_list_no_check(self, file):
331
+ item = QListWidgetItem(os.path.basename(file), self.list)
332
+ item.setToolTip(file)
333
+ self.list.addItem(item)
334
+
335
+ def add_object_to_list_no_check(self, obj): #added this to add non file objects to the list
336
+ item = QListWidgetItem(str(obj), self.list)
337
+ item.setToolTip(str(obj))
338
+ # item.setData(Qt.UserRole, obj)
339
+ # item.setData(Qt.UserRole, str(obj))
340
+ self._object_dict[str(item)] = obj # Store a reference to the object in the dictionary
341
+ self.list.addItem(item)
342
+
343
+ def add_to_list(self, files, check_if_supported=True):
344
+ if isinstance(files, str):
345
+ if check_if_supported:
346
+ self.add_file_to_list_if_supported(files)
347
+ else:
348
+ self.add_file_to_list_no_check(files)
349
+ elif isinstance(files, list):
350
+ for file in files:
351
+ if check_if_supported:
352
+ self.add_file_to_list_if_supported(file)
353
+ else:
354
+ self.add_file_to_list_no_check(file)
355
+ else:
356
+ print('Non supported, cannot be added to list', files)
357
+
358
+ def list_files_in_directory(self, directory_path):
359
+ files = [os.path.join(directory_path,f) for f in os.listdir(directory_path) if os.path.isfile(os.path.join(directory_path, f))]
360
+ # print(files)
361
+ return files
362
+
363
+ def add_file_to_list_if_supported(self, file):
364
+ # print('checking if supported', file)
365
+ if self.is_file_supported(file) and os.path.isfile(file):
366
+ ext = smart_name_parser(file, ordered_output=['ext'])[0].lower()
367
+ if ext in LISTS:
368
+ TA_list_of_files = loadlist(file)
369
+ return self.add_to_list(TA_list_of_files, check_if_supported=True)
370
+ else:
371
+ self.add_file_to_list_no_check(file)
372
+ elif self.enable_folder_DND and os.path.isdir(file):
373
+ files = self.list_files_in_directory(file)
374
+ for file in files:
375
+ self.add_file_to_list_if_supported(file)
376
+
377
+
378
+ def get_full_list(self):
379
+ # return the complete list of files
380
+ selected_items = []
381
+ for i in range(self.list.count()):
382
+ if str(self.list.item(i)) in self._object_dict:
383
+ selected_items.append(self._object_dict[str(self.list.item(i))])
384
+ else:
385
+ selected_items.append(self.list.item(i).toolTip())
386
+ return selected_items
387
+
388
+ def get_selection(self, mode='single'):
389
+ selected_items = self.list.selectedItems()
390
+ if selected_items:
391
+ if mode == 'single':
392
+ if str(selected_items[0]) in self._object_dict:
393
+ return self._object_dict[str(selected_items[0])]
394
+ # if selected_items[0].data(Qt.UserRole):
395
+ # return selected_items[0].data(Qt.UserRole)
396
+ return selected_items[0].toolTip()
397
+ else:
398
+ sel = []
399
+ for selec in selected_items:
400
+ if str(selec) in self._object_dict:
401
+ sel.append(self._object_dict[str(selec)])
402
+ # elif selec.data(Qt.UserRole):
403
+ # sel.append(selec.data(Qt.UserRole))
404
+ else:
405
+ sel.append(selec.toolTip())
406
+ return sel
407
+ else:
408
+ return None
409
+
410
+ def get_selection_index(self, mode='single'):
411
+ try:
412
+ # selected_items = self.list.selectedIndexes() # this is a weird model index object that is largely useless
413
+ selected_items = [s.row() for s in self.list.selectedIndexes()]
414
+ # print('selected_items',selected_items)
415
+ if selected_items:
416
+ if mode == 'single':
417
+ # print('sel', selected_items[0])
418
+ return selected_items[0]
419
+ else:
420
+ # sel = []
421
+ # for selec in selected_items:
422
+ # sel.append(selec.toolTip())
423
+ return selected_items
424
+ # else:
425
+ except:
426
+ pass
427
+ return None
428
+
429
+ def save_list(self):
430
+ # on va sauver la liste ici
431
+ lst = self.get_full_list()
432
+ if lst:
433
+ path = smart_name_parser(lst[0], ordered_output='parent')
434
+ path = os.path.join(path, 'list.lst')
435
+
436
+ output_file = saveFileDialog(parent_window=self, path=path,
437
+ extensions="Lists (*.lst);;Supported Files (*.lst *.txt);;All Files (*)",
438
+ default_ext='.lst')
439
+ if output_file is not None:
440
+ # now do save the list in the folder of the parent of the first file
441
+ save_list_to_file(lst, output_file)
442
+ # print(lst, output_file)
443
+
444
+ def removeSel(self):
445
+ selected_items = self.list.selectedItems()
446
+ self.list.clearSelection() # Clear selection # required to prevent selection from changing and the software to want to update display or anything alike
447
+ if not selected_items:
448
+ self.clearList()
449
+ self.deletePressed.emit() # send the delete action to the parent
450
+ return
451
+
452
+ # Remove selected items from the list
453
+ for item in selected_items:
454
+ # Remove the item from the dictionary
455
+ if str(item) in self._object_dict:
456
+ del self._object_dict[str(item)]
457
+ for item in selected_items:
458
+ # print('looping')
459
+ self.list.takeItem(self.list.row(item))
460
+ self.deletePressed.emit() # send the delete action to the parent
461
+
462
+ # faire une copie dans le clip de la selection
463
+ def sel_to_clipboard(self):
464
+ sel = self.get_selection(mode='all')
465
+ if sel is not None:
466
+ clip.copy('\n'.join(sel))
467
+
468
+ def paste_from_clipboard(self):
469
+ files = clip.paste()
470
+ # try add this to the list
471
+ try:
472
+ # print(files)
473
+ splitted_files = files.split('\n')
474
+ # print(splitted_files)
475
+ self.add_to_list(splitted_files, check_if_supported=True)
476
+ except:
477
+ # no big deal if fails
478
+ pass
479
+
480
+ # TODO maybe add sort by time as there is even an icon for that and can be useful for my leica files !!!
481
+ # TODO copy icons if they exist on natsort ok for now it's really a detail...
482
+ def natsort_list(self):
483
+ full_list = self.get_full_list()
484
+ if full_list is not None:
485
+ self.clearList()
486
+ self.add_to_list(natsorted(full_list), check_if_supported=False)
487
+
488
+ def clearList(self):
489
+ self.list.clear()
490
+ del self._object_dict
491
+ self._object_dict = {}
492
+
493
+
494
+ if __name__ == '__main__':
495
+ # TODO add a main method so it can be called directly
496
+ # maybe just show a canvas and give it interesting props --> TODO --> really need fix that too!!!
497
+ import sys
498
+ from qtpy.QtWidgets import QApplication
499
+
500
+ # should probably have his own scroll bar embedded somewhere
501
+
502
+ app = QApplication(sys.argv)
503
+
504
+ w = ListGUI(file_to_load='/E/Sample_images/sample_images_PA/mini/list.lst')
505
+
506
+ # w.freeze(False)
507
+ # w.freeze(True)
508
+
509
+ w.show()
510
+
511
+ print('get_full_list', w.get_full_list()) # very good and useful
512
+ print('sel', w.get_selection(mode='all'))
513
+
514
+ sys.exit(app.exec_())