Module soitool.module_list
Includes functionality for displaying a prioritized list of modules.
Expand source code
"""Includes functionality for displaying a prioritized list of modules."""
from PySide2.QtCore import Qt
from PySide2.QtWidgets import (
QListWidget,
QListWidgetItem,
QAbstractItemView,
)
from soitool.dialog_wrappers import exec_warning_dialog
from soitool.soi import SOI
from soitool.enumerates import ModuleType
class ModuleList(QListWidget):
"""Contains module-names from soitool.SOI.
List elements are names of modules or attachment-modules from soitool.SOI.
List elements are editable, drag-and-droppable and unique (no duplicates).
Makes changes in soitool.SOI lists through its soi property.
Parameters
----------
module_type : int
Determines whether names are from modules or attachment-modules.
Is used with the Enum 'ModuleType' to know which SOI-list (modules or
attachments) to update when changes are made.
soi : soitool.soi.SOI
Reference to SOI-instance.
"""
def __init__(self, module_type, soi):
super().__init__()
if not isinstance(soi, SOI):
raise RuntimeError(
"Only soitool.SOI is "
"acceptable type for the soi property "
"in class ModuleList."
)
self.type = module_type
self.soi = soi
self.original_element_name = None
self.original_element_index = None
self.setup_list()
self.fill_list()
self.soi.add_reorganization_listener(self.update_list_order)
def setup_list(self):
"""Prepare list.
Make list drag-and-droppable and remove horizontal scrollbar.
"""
# Enable drag-and-drop
self.setDragEnabled(True)
self.viewport().setAcceptDrops(True)
self.setDragDropMode(QAbstractItemView.InternalMove)
# Remove horizontal scrollbar
self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
def fill_list(self):
"""Fill list with elements in order defined in SOI."""
# Get names of modules/attachments:
if ModuleType(self.type) == ModuleType.MAIN_MODULE:
names = [module["meta"]["name"] for module in self.soi.modules]
elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE:
names = [
attachment["meta"]["name"]
for attachment in self.soi.attachments
]
for i, name in enumerate(names):
item = QListWidgetItem(name)
item.setFlags(item.flags() | Qt.ItemIsEditable)
self.insertItem(i, item)
def update_list_order(self):
"""Update order of modules in list to respect order in SOI."""
self.clear()
self.fill_list()
def currentChanged(self, current, previous):
"""Save name and index of an element when it is selected.
Function is needed to remember original:
1: index of an element in case it's' drag-and-dropped (notify parent).
2: name of an element in case it's name changes (avoid duplicates).
https://doc.qt.io/qt-5/qlistview.html#currentChanged.
Parameters
----------
current : QModelIndex
Used to get index of element, is sent to super().
previous : QModelIndex
Is sent to super().
"""
super().currentChanged(current, previous)
# If an item is selected
if current.row() != -1:
self.original_element_name = self.item(current.row()).text()
self.original_element_index = current.row()
def dataChanged(self, index1, index2, roles):
"""Check for duplicate name and notify parent when an element changes.
https://doc.qt.io/qt-5/qabstractitemview.html#dataChanged.
Parameters
----------
index1 : QModelIndex
Used to get index of changed element, is sent to super().
index2 : QModelIndex
Is sent to super().
roles : QVector
Is sent to super().
"""
index = index1.row()
# Get all names and new name
names = [self.item(i).text() for i in range(self.count())]
new_name = names[index]
# Count occurrences of new name
occurrences = names.count(new_name)
# If new name already exists, replace with original name
if occurrences > 1:
self.item(index).setText(self.original_element_name)
# Name does not already exist, update list in soi
else:
name = self.item(index).text()
if ModuleType(self.type) == ModuleType.MAIN_MODULE:
self.soi.modules[index]["meta"]["name"] = name
elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE:
self.soi.attachments[index]["meta"]["name"] = name
super().dataChanged(index1, index2, roles)
def dropEvent(self, event):
"""Notify parent when an element is drag-and-dropped.
Note that if the SOI is not prepared for manual priorization an error
message will be displayed, and nothing else will be done. This only
applies to uses of this class with non-attachment modules.
https://doc.qt.io/qt-5/qabstractitemview.html#dropEvent.
Parameters
----------
event : QDropEvent
Is sent to super().
"""
if (
self.soi.algorithm_sort != "none"
and ModuleType(self.type) == ModuleType.MAIN_MODULE
):
exec_warning_dialog(
text="SOI er ikke innstilt for manuell prioritering av "
"moduler!",
informative_text="Enn så lenge vil manuell prioritering av "
"moduler bare fungere dersom SOI er innstilt til ikke å gjøre "
"sortering av moduler før pakking. I fremtiden vil det være "
"mulig å låse utvalgte moduler, men la resten optimalt "
"pakkes.",
)
else:
super().dropEvent(event)
# Get origin and destination index of module/attachment
origin = self.original_element_index
destination = self.currentRow()
# Update module/attachment priority (order in list):
if ModuleType(self.type) == ModuleType.MAIN_MODULE:
moving_module = self.soi.modules.pop(origin)
self.soi.modules.insert(destination, moving_module)
elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE:
moving_module = self.soi.attachments.pop(origin)
self.soi.attachments.insert(destination, moving_module)
self.soi.reorganize()
self.original_element_index = self.currentRow()
Classes
class ModuleList (module_type, soi)
-
Contains module-names from soitool.SOI.
List elements are names of modules or attachment-modules from soitool.SOI. List elements are editable, drag-and-droppable and unique (no duplicates). Makes changes in soitool.SOI lists through its soi property.
Parameters
module_type
:int
- Determines whether names are from modules or attachment-modules. Is used with the Enum 'ModuleType' to know which SOI-list (modules or attachments) to update when changes are made.
soi
:SOI
- Reference to SOI-instance.
Expand source code
class ModuleList(QListWidget): """Contains module-names from soitool.SOI. List elements are names of modules or attachment-modules from soitool.SOI. List elements are editable, drag-and-droppable and unique (no duplicates). Makes changes in soitool.SOI lists through its soi property. Parameters ---------- module_type : int Determines whether names are from modules or attachment-modules. Is used with the Enum 'ModuleType' to know which SOI-list (modules or attachments) to update when changes are made. soi : soitool.soi.SOI Reference to SOI-instance. """ def __init__(self, module_type, soi): super().__init__() if not isinstance(soi, SOI): raise RuntimeError( "Only soitool.SOI is " "acceptable type for the soi property " "in class ModuleList." ) self.type = module_type self.soi = soi self.original_element_name = None self.original_element_index = None self.setup_list() self.fill_list() self.soi.add_reorganization_listener(self.update_list_order) def setup_list(self): """Prepare list. Make list drag-and-droppable and remove horizontal scrollbar. """ # Enable drag-and-drop self.setDragEnabled(True) self.viewport().setAcceptDrops(True) self.setDragDropMode(QAbstractItemView.InternalMove) # Remove horizontal scrollbar self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff) def fill_list(self): """Fill list with elements in order defined in SOI.""" # Get names of modules/attachments: if ModuleType(self.type) == ModuleType.MAIN_MODULE: names = [module["meta"]["name"] for module in self.soi.modules] elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: names = [ attachment["meta"]["name"] for attachment in self.soi.attachments ] for i, name in enumerate(names): item = QListWidgetItem(name) item.setFlags(item.flags() | Qt.ItemIsEditable) self.insertItem(i, item) def update_list_order(self): """Update order of modules in list to respect order in SOI.""" self.clear() self.fill_list() def currentChanged(self, current, previous): """Save name and index of an element when it is selected. Function is needed to remember original: 1: index of an element in case it's' drag-and-dropped (notify parent). 2: name of an element in case it's name changes (avoid duplicates). https://doc.qt.io/qt-5/qlistview.html#currentChanged. Parameters ---------- current : QModelIndex Used to get index of element, is sent to super(). previous : QModelIndex Is sent to super(). """ super().currentChanged(current, previous) # If an item is selected if current.row() != -1: self.original_element_name = self.item(current.row()).text() self.original_element_index = current.row() def dataChanged(self, index1, index2, roles): """Check for duplicate name and notify parent when an element changes. https://doc.qt.io/qt-5/qabstractitemview.html#dataChanged. Parameters ---------- index1 : QModelIndex Used to get index of changed element, is sent to super(). index2 : QModelIndex Is sent to super(). roles : QVector Is sent to super(). """ index = index1.row() # Get all names and new name names = [self.item(i).text() for i in range(self.count())] new_name = names[index] # Count occurrences of new name occurrences = names.count(new_name) # If new name already exists, replace with original name if occurrences > 1: self.item(index).setText(self.original_element_name) # Name does not already exist, update list in soi else: name = self.item(index).text() if ModuleType(self.type) == ModuleType.MAIN_MODULE: self.soi.modules[index]["meta"]["name"] = name elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: self.soi.attachments[index]["meta"]["name"] = name super().dataChanged(index1, index2, roles) def dropEvent(self, event): """Notify parent when an element is drag-and-dropped. Note that if the SOI is not prepared for manual priorization an error message will be displayed, and nothing else will be done. This only applies to uses of this class with non-attachment modules. https://doc.qt.io/qt-5/qabstractitemview.html#dropEvent. Parameters ---------- event : QDropEvent Is sent to super(). """ if ( self.soi.algorithm_sort != "none" and ModuleType(self.type) == ModuleType.MAIN_MODULE ): exec_warning_dialog( text="SOI er ikke innstilt for manuell prioritering av " "moduler!", informative_text="Enn så lenge vil manuell prioritering av " "moduler bare fungere dersom SOI er innstilt til ikke å gjøre " "sortering av moduler før pakking. I fremtiden vil det være " "mulig å låse utvalgte moduler, men la resten optimalt " "pakkes.", ) else: super().dropEvent(event) # Get origin and destination index of module/attachment origin = self.original_element_index destination = self.currentRow() # Update module/attachment priority (order in list): if ModuleType(self.type) == ModuleType.MAIN_MODULE: moving_module = self.soi.modules.pop(origin) self.soi.modules.insert(destination, moving_module) elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: moving_module = self.soi.attachments.pop(origin) self.soi.attachments.insert(destination, moving_module) self.soi.reorganize() self.original_element_index = self.currentRow()
Ancestors
- PySide2.QtWidgets.QListWidget
- PySide2.QtWidgets.QListView
- PySide2.QtWidgets.QAbstractItemView
- PySide2.QtWidgets.QAbstractScrollArea
- PySide2.QtWidgets.QFrame
- PySide2.QtWidgets.QWidget
- PySide2.QtCore.QObject
- PySide2.QtGui.QPaintDevice
- Shiboken.Object
Class variables
var staticMetaObject
Methods
def currentChanged(self, current, previous)
-
Save name and index of an element when it is selected.
Function is needed to remember original: 1: index of an element in case it's' drag-and-dropped (notify parent). 2: name of an element in case it's name changes (avoid duplicates).
https://doc.qt.io/qt-5/qlistview.html#currentChanged.
Parameters
current
:QModelIndex
- Used to get index of element, is sent to super().
previous
:QModelIndex
- Is sent to super().
Expand source code
def currentChanged(self, current, previous): """Save name and index of an element when it is selected. Function is needed to remember original: 1: index of an element in case it's' drag-and-dropped (notify parent). 2: name of an element in case it's name changes (avoid duplicates). https://doc.qt.io/qt-5/qlistview.html#currentChanged. Parameters ---------- current : QModelIndex Used to get index of element, is sent to super(). previous : QModelIndex Is sent to super(). """ super().currentChanged(current, previous) # If an item is selected if current.row() != -1: self.original_element_name = self.item(current.row()).text() self.original_element_index = current.row()
def dataChanged(self, index1, index2, roles)
-
Check for duplicate name and notify parent when an element changes.
https://doc.qt.io/qt-5/qabstractitemview.html#dataChanged.
Parameters
index1
:QModelIndex
- Used to get index of changed element, is sent to super().
index2
:QModelIndex
- Is sent to super().
roles
:QVector
- Is sent to super().
Expand source code
def dataChanged(self, index1, index2, roles): """Check for duplicate name and notify parent when an element changes. https://doc.qt.io/qt-5/qabstractitemview.html#dataChanged. Parameters ---------- index1 : QModelIndex Used to get index of changed element, is sent to super(). index2 : QModelIndex Is sent to super(). roles : QVector Is sent to super(). """ index = index1.row() # Get all names and new name names = [self.item(i).text() for i in range(self.count())] new_name = names[index] # Count occurrences of new name occurrences = names.count(new_name) # If new name already exists, replace with original name if occurrences > 1: self.item(index).setText(self.original_element_name) # Name does not already exist, update list in soi else: name = self.item(index).text() if ModuleType(self.type) == ModuleType.MAIN_MODULE: self.soi.modules[index]["meta"]["name"] = name elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: self.soi.attachments[index]["meta"]["name"] = name super().dataChanged(index1, index2, roles)
def dropEvent(self, event)
-
Notify parent when an element is drag-and-dropped.
Note that if the SOI is not prepared for manual priorization an error message will be displayed, and nothing else will be done. This only applies to uses of this class with non-attachment modules.
https://doc.qt.io/qt-5/qabstractitemview.html#dropEvent.
Parameters
event
:QDropEvent
- Is sent to super().
Expand source code
def dropEvent(self, event): """Notify parent when an element is drag-and-dropped. Note that if the SOI is not prepared for manual priorization an error message will be displayed, and nothing else will be done. This only applies to uses of this class with non-attachment modules. https://doc.qt.io/qt-5/qabstractitemview.html#dropEvent. Parameters ---------- event : QDropEvent Is sent to super(). """ if ( self.soi.algorithm_sort != "none" and ModuleType(self.type) == ModuleType.MAIN_MODULE ): exec_warning_dialog( text="SOI er ikke innstilt for manuell prioritering av " "moduler!", informative_text="Enn så lenge vil manuell prioritering av " "moduler bare fungere dersom SOI er innstilt til ikke å gjøre " "sortering av moduler før pakking. I fremtiden vil det være " "mulig å låse utvalgte moduler, men la resten optimalt " "pakkes.", ) else: super().dropEvent(event) # Get origin and destination index of module/attachment origin = self.original_element_index destination = self.currentRow() # Update module/attachment priority (order in list): if ModuleType(self.type) == ModuleType.MAIN_MODULE: moving_module = self.soi.modules.pop(origin) self.soi.modules.insert(destination, moving_module) elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: moving_module = self.soi.attachments.pop(origin) self.soi.attachments.insert(destination, moving_module) self.soi.reorganize() self.original_element_index = self.currentRow()
def fill_list(self)
-
Fill list with elements in order defined in SOI.
Expand source code
def fill_list(self): """Fill list with elements in order defined in SOI.""" # Get names of modules/attachments: if ModuleType(self.type) == ModuleType.MAIN_MODULE: names = [module["meta"]["name"] for module in self.soi.modules] elif ModuleType(self.type) == ModuleType.ATTACHMENT_MODULE: names = [ attachment["meta"]["name"] for attachment in self.soi.attachments ] for i, name in enumerate(names): item = QListWidgetItem(name) item.setFlags(item.flags() | Qt.ItemIsEditable) self.insertItem(i, item)
def setup_list(self)
-
Prepare list.
Make list drag-and-droppable and remove horizontal scrollbar.
Expand source code
def setup_list(self): """Prepare list. Make list drag-and-droppable and remove horizontal scrollbar. """ # Enable drag-and-drop self.setDragEnabled(True) self.viewport().setAcceptDrops(True) self.setDragDropMode(QAbstractItemView.InternalMove) # Remove horizontal scrollbar self.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
def update_list_order(self)
-
Update order of modules in list to respect order in SOI.
Expand source code
def update_list_order(self): """Update order of modules in list to respect order in SOI.""" self.clear() self.fill_list()