4

I am using QgsNewVectorLayerDialog for taking user input for creating a new shapefile. When the user clicks OK I am reading the inputs selected by the user using the following code.

dlg = QgsNewVectorFileDialog()
result = dlg.exec_()
if result == 1:
   crs = dlg.selectedCrsI()
   type = dlg.selectedType()
   attributes = []
   dlg.attributes(attributes)

All other parameters are coming fine. However attributes is returning an empty list. QgsNewVectorLayerDialog.attributes() shows that it needs an list of tuple of QString-QString. Whether I am passing correctly or not.

1

1 Answer 1

1

I think it is really a bug as Carrillo said.

But as a workaround, I implemented my own class OwnVectorLayerDialog inheriting QgsNewVectorLayerDialog and override the attributes() function. Therefore, I oriented on original c++ function from API: http://qgis.org/api/qgsnewvectorlayerdialog_8cpp_source.html#l00192

The only hack was to find QTreeWidget in dialog children - found a QGroupbox at index 9 and the tree at index 1 within that groupbox (maybe you have to find it yourself, if you are using other version, where indices might have changed)

My code looks like this:

from qgis.gui import QgsNewVectorLayerDialog
from PyQt4.QtCore import Qt
from PyQt4.QtGui import QTreeWidgetItemIterator


class OwnVectorLayerDialog(QgsNewVectorLayerDialog):
    def __init__(self, parent=None, flags=Qt.Window):
        super(OwnVectorLayerDialog, self).__init__(parent, flags)

    def attributes(self, att_list):
        # Find QTreeWidget:
        tree = self.children()[9].children()[1]

        # Iterate over items:
        it = QTreeWidgetItemIterator(tree)
        while it.value() is not None:
            item = it.value()
            item_type = "{0};{1};{2}".format(
                item.text(1), item.text(2), item.text(3))
            att_list.append((item.text(0), item_type))
            it += 1

dlg = OwnVectorLayerDialog()
result = dlg.exec_()
if result == 1:
    crs = dlg.selectedCrsId()
    types = dlg.selectedType()
    attributes = []
    dlg.attributes(attributes)

    print(crs)
    print(types)
    print(attributes)

And gives me output like this (for id field and added field new_field):

3452
1
[(u'id', 'Integer;10;'), (u'new_field', 'Real;10;3')]

Hope you can adapt and use my workaround!

1
  • Instead of overriding the attributes() function you could write your own function returning the fields as you want it, of course...
    – Henhuy
    Commented Nov 4, 2016 at 21:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.