I am developing a plugin for the GIS software, QGIS. The code below reads the number of layers in various groups (as shown in the image) and adds them to a QTableWidget:
For each group, I want to count the number of layers, divide 1 by this number and then add the result of this to each of the layers in each group in the table.
Taking "Group1" as an example:
- Count the number of layers (in this case 3).
- Calculate 1 / 3 = 0.33....
- Insert 0.33... to the first three layers in the table.
- Repeat for the remaining groups.
So the table looks like this:
However, there's a fair bit of list manipulation involved which seems unnecessary so was hoping to see if there's a way to reduce this.
Here is the code:
# Define QTableWidget
qTable = self.dockwidget.tableWidget
# Define group
root = QgsProject.instance().layerTreeRoot()
main_group = root.findGroup('Main group')
def refresh_table():
# Define parameters for QTableWidget
qTable.setRowCount(0)
# Define list to contain all layer names
layer_data = []
# Define list to contain the number of layers
layer_count = []
# Find all groups in main_group
for group in main_group.children():
# Define list to count number of layers in each group
layer_list = []
# Find all layers in each group
for child in group.children():
node = root.findLayer(child.layer().id())
try:
# If layer is visible, add them to lists
if node.isVisible() == Qt.Checked:
layer_data.append(child.layerName())
layer_list.append(child.layerName())
except AttributeError:
pass
# Insert the number of layers in each group to layer_count list
layer_count.append(len(layer_list))
# Get total number of layers
layer_data_count = len(layer_data)
try:
# Create new list for layer_count but ignore any zeros
new_layer_count = [x for x in layer_count if x != 0]
except ValueError:
pass
# List manipulation
# Calculate the number of layers in each group and divide 1 by this number
value_list = [1 / float(x) for x in new_layer_count]
# Format the list to one decimal place
formatted_value_list = ['%.1f' % elem for elem in value_list]
# Convert the values in list to float
formatted_value_list_to_float = [float(x) for x in formatted_value_list]
# Create final list containing each layer and the values of their group
final_value_list = [x for n,x in zip(new_layer_count,formatted_value_list_to_float) for _ in range(n)]
# Set number of rows/columns
nb_row = len(layer_data)
nb_col = 2
qTable.setRowCount(nb_row)
qTable.setColumnCount(nb_col)
# Hide row index number
qTable.verticalHeader().setVisible(False)
# Insert layer names and values
for row in range(layer_data_count):
for col in [0]:
item = QTableWidgetItem(str(layer_data[row]))
qTable.setItem(row,col,item)
# Make first column non-editable
item.setFlags(QtCore.Qt.ItemIsEnabled)
for col in [1]:
item = QTableWidgetItem(str(final_value_list[row]))
qTable.setItem(row,col,item)