34
34
import os
35
35
from functools import cmp_to_key
36
36
37
- from qgis .core import QgsCoordinateReferenceSystem , QgsVectorLayer , QgsApplication
38
- from qgis .PyQt .QtWidgets import QCheckBox , QComboBox , QLineEdit , QPlainTextEdit , QWidget , QHBoxLayout , QToolButton
37
+ from qgis .core import QgsCoordinateReferenceSystem , QgsVectorLayer , QgsApplication , QgsWkbTypes , QgsMapLayerProxyModel
38
+ from qgis .PyQt .QtWidgets import QCheckBox , QComboBox , QLineEdit , QPlainTextEdit , QWidget , QHBoxLayout , QToolButton , QFileDialog
39
39
from qgis .gui import (QgsFieldExpressionWidget ,
40
40
QgsExpressionLineEdit ,
41
41
QgsProjectionSelectionWidget ,
42
42
QgsGenericProjectionSelector ,
43
43
QgsFieldComboBox ,
44
- QgsFieldProxyModel )
45
- from qgis .PyQt .QtCore import pyqtSignal , QObject , QVariant
44
+ QgsFieldProxyModel ,
45
+ QgsMapLayerComboBox
46
+ )
47
+ from qgis .PyQt .QtCore import pyqtSignal , QObject , QVariant , QSettings
46
48
47
49
from processing .gui .NumberInputPanel import NumberInputPanel , ModellerNumberInputPanel
48
50
from processing .gui .InputLayerSelectorPanel import InputLayerSelectorPanel
@@ -156,6 +158,26 @@ def postInitialize(self, wrappers):
156
158
def refresh (self ):
157
159
pass
158
160
161
+ def getFileName (self , initial_value = '' ):
162
+ """Shows a file open dialog"""
163
+ settings = QSettings ()
164
+ if os .path .isdir (initial_value ):
165
+ path = initial_value
166
+ elif os .path .isdir (os .path .dirname (initial_value )):
167
+ path = os .path .dirname (initial_value )
168
+ elif settings .contains ('/Processing/LastInputPath' ):
169
+ path = str (settings .value ('/Processing/LastInputPath' ))
170
+ else :
171
+ path = ''
172
+
173
+ filename , selected_filter = QFileDialog .getOpenFileName (self .widget , self .tr ('Select file' ),
174
+ path , self .tr (
175
+ 'All files (*.*);;' ) + self .param .getFileFilter ())
176
+ if filename :
177
+ settings .setValue ('/Processing/LastInputPath' ,
178
+ os .path .dirname (str (filename )))
179
+ return filename , selected_filter
180
+
159
181
160
182
class BasicWidgetWrapper (WidgetWrapper ):
161
183
@@ -534,13 +556,31 @@ class RasterWidgetWrapper(WidgetWrapper):
534
556
535
557
def createWidget (self ):
536
558
if self .dialogType == DIALOG_STANDARD :
537
- layers = dataobjects .getRasterLayers ()
538
- items = []
559
+ widget = QWidget ()
560
+ layout = QHBoxLayout ()
561
+ layout .setMargin (0 )
562
+ layout .setContentsMargins (0 , 0 , 0 , 0 )
563
+ layout .setSpacing (2 )
564
+ self .combo = QgsMapLayerComboBox ()
565
+ layout .addWidget (self .combo )
566
+ btn = QToolButton ()
567
+ btn .setText ('...' )
568
+ btn .setToolTip (self .tr ("Select file" ))
569
+ btn .clicked .connect (self .selectFile )
570
+ layout .addWidget (btn )
571
+
572
+ widget .setLayout (layout )
539
573
if self .param .optional :
540
- items .append ((self .NOT_SELECTED , None ))
541
- for layer in layers :
542
- items .append ((getExtendedLayerName (layer ), layer ))
543
- return InputLayerSelectorPanel (items , self .param )
574
+ self .combo .setAllowEmptyLayer (True )
575
+ if ProcessingConfig .getSetting (ProcessingConfig .SHOW_CRS_DEF ):
576
+ self .combo .setShowCrs (True )
577
+
578
+ self .combo .setFilters (QgsMapLayerProxyModel .RasterLayer )
579
+ self .combo .setExcludedProviders (['grass' ])
580
+
581
+ self .combo .currentIndexChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
582
+ self .combo .currentTextChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
583
+ return widget
544
584
elif self .dialogType == DIALOG_BATCH :
545
585
return BatchInputSelectionPanel (self .param , self .row , self .col , self .dialog )
546
586
else :
@@ -553,14 +593,14 @@ def createWidget(self):
553
593
widget .setEditText ("" )
554
594
return widget
555
595
556
- def refresh (self ):
557
- items = []
558
- layers = dataobjects . getRasterLayers ()
559
- if self .param . optional :
560
- items . append (( self .NOT_SELECTED , None ) )
561
- for layer in layers :
562
- items . append (( getExtendedLayerName ( layer ), layer ) )
563
- self .widget . update ( items )
596
+ def selectFile (self ):
597
+ filename , selected_filter = self . getFileName ( self . combo . currentText ())
598
+ if filename :
599
+ filename = dataobjects . getRasterSublayer ( filename , self .param )
600
+ items = self .combo . additionalItems ( )
601
+ items . append ( filename )
602
+ self . combo . setAdditionalItems ( items )
603
+ self .combo . setCurrentIndex ( self . combo . findText ( filename ) )
564
604
565
605
def setValue (self , value ):
566
606
if self .dialogType == DIALOG_STANDARD :
@@ -572,7 +612,14 @@ def setValue(self, value):
572
612
573
613
def value (self ):
574
614
if self .dialogType == DIALOG_STANDARD :
575
- return self .widget .getValue ()
615
+ try :
616
+ layer = self .combo .currentLayer ()
617
+ if layer :
618
+ return layer
619
+ else :
620
+ return self .combo .currentText ()
621
+ except :
622
+ return self .combo .currentText ()
576
623
elif self .dialogType == DIALOG_BATCH :
577
624
return self .widget .getText ()
578
625
else :
@@ -615,16 +662,43 @@ class VectorWidgetWrapper(WidgetWrapper):
615
662
616
663
def createWidget (self ):
617
664
if self .dialogType == DIALOG_STANDARD :
618
- layers = dataobjects .getVectorLayers (self .param .datatype )
619
- items = []
665
+ widget = QWidget ()
666
+ layout = QHBoxLayout ()
667
+ layout .setMargin (0 )
668
+ layout .setContentsMargins (0 , 0 , 0 , 0 )
669
+ layout .setSpacing (2 )
670
+ self .combo = QgsMapLayerComboBox ()
671
+ layout .addWidget (self .combo )
672
+ btn = QToolButton ()
673
+ btn .setText ('...' )
674
+ btn .setToolTip (self .tr ("Select file" ))
675
+ btn .clicked .connect (self .selectFile )
676
+ layout .addWidget (btn )
677
+
678
+ widget .setLayout (layout )
679
+
680
+ filters = QgsMapLayerProxyModel .Filters ()
681
+ if self .param .datatype == [- 1 ] or - 1 in self .param .datatype :
682
+ filters = QgsMapLayerProxyModel .HasGeometry
683
+ if QgsWkbTypes .PointGeometry in self .param .datatype :
684
+ filters |= QgsMapLayerProxyModel .PointLayer
685
+ if QgsWkbTypes .LineGeometry in self .param .datatype :
686
+ filters |= QgsMapLayerProxyModel .LineLayer
687
+ if QgsWkbTypes .PolygonGeometry in self .param .datatype :
688
+ filters |= QgsMapLayerProxyModel .PolygonLayer
689
+
620
690
if self .param .optional :
621
- items .append ((self .NOT_SELECTED , None ))
622
- for layer in layers :
623
- items .append ((getExtendedLayerName (layer ), layer ))
624
- widget = InputLayerSelectorPanel (items , self .param )
625
- widget .name = self .param .name
626
- widget .valueChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
691
+ self .combo .setAllowEmptyLayer (True )
692
+ if ProcessingConfig .getSetting (ProcessingConfig .SHOW_CRS_DEF ):
693
+ self .combo .setShowCrs (True )
694
+
695
+ self .combo .setFilters (filters )
696
+ self .combo .setExcludedProviders (['grass' ])
697
+
698
+ self .combo .currentIndexChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
699
+ self .combo .currentTextChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
627
700
return widget
701
+
628
702
elif self .dialogType == DIALOG_BATCH :
629
703
widget = BatchInputSelectionPanel (self .param , self .row , self .col , self .dialog )
630
704
widget .valueChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
@@ -639,18 +713,14 @@ def createWidget(self):
639
713
widget .setEditText ("" )
640
714
return widget
641
715
642
- def _populate (self , widget ):
643
- items = []
644
- layers = dataobjects .getVectorLayers (self .param .datatype )
645
- layers .sort (key = lambda lay : lay .name ())
646
- if self .param .optional :
647
- items .append ((self .NOT_SELECTED , None ))
648
- for layer in layers :
649
- items .append ((getExtendedLayerName (layer ), layer ))
650
- self .widget .update (items )
651
-
652
- def refresh (self ):
653
- self ._populate (self .widget )
716
+ def selectFile (self ):
717
+ filename , selected_filter = self .getFileName (self .combo .currentText ())
718
+ if filename :
719
+ filename = dataobjects .getRasterSublayer (filename , self .param )
720
+ items = self .combo .additionalItems ()
721
+ items .append (filename )
722
+ self .combo .setAdditionalItems (items )
723
+ self .combo .setCurrentIndex (self .combo .findText (filename ))
654
724
655
725
def setValue (self , value ):
656
726
if self .dialogType == DIALOG_STANDARD :
@@ -663,9 +733,13 @@ def setValue(self, value):
663
733
def value (self ):
664
734
if self .dialogType == DIALOG_STANDARD :
665
735
try :
666
- return self .widget .itemData (self .widget .currentIndex ())
736
+ layer = self .combo .currentLayer ()
737
+ if layer :
738
+ return layer
739
+ else :
740
+ return self .combo .currentText ()
667
741
except :
668
- return self .widget . getValue ()
742
+ return self .combo . currentText ()
669
743
elif self .dialogType == DIALOG_BATCH :
670
744
return self .widget .value ()
671
745
else :
@@ -809,16 +883,31 @@ class TableWidgetWrapper(WidgetWrapper):
809
883
810
884
def createWidget (self ):
811
885
if self .dialogType == DIALOG_STANDARD :
812
- widget = QComboBox ()
813
- layers = dataobjects .getTables ()
814
- layers .sort (key = lambda lay : lay .name ())
886
+ widget = QWidget ()
887
+ layout = QHBoxLayout ()
888
+ layout .setMargin (0 )
889
+ layout .setContentsMargins (0 , 0 , 0 , 0 )
890
+ layout .setSpacing (2 )
891
+ self .combo = QgsMapLayerComboBox ()
892
+ layout .addWidget (self .combo )
893
+ btn = QToolButton ()
894
+ btn .setText ('...' )
895
+ btn .setToolTip (self .tr ("Select file" ))
896
+ btn .clicked .connect (self .selectFile )
897
+ layout .addWidget (btn )
898
+
899
+ widget .setLayout (layout )
900
+
815
901
if self .param .optional :
816
- widget .addItem (self .NOT_SELECTED , None )
817
- for layer in layers :
818
- widget .addItem (layer .name (), layer )
819
- widget .currentIndexChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
820
- widget .name = self .param .name
902
+ self .combo .setAllowEmptyLayer (True )
903
+
904
+ self .combo .setFilters (QgsMapLayerProxyModel .VectorLayer )
905
+ self .combo .setExcludedProviders (['grass' ])
906
+
907
+ self .combo .currentIndexChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
908
+ self .combo .currentTextChanged .connect (lambda : self .widgetValueHasChanged .emit (self ))
821
909
return widget
910
+
822
911
elif self .dialogType == DIALOG_BATCH :
823
912
return BatchInputSelectionPanel (self .param , self .row , self .col , self .dialog )
824
913
else :
@@ -833,6 +922,15 @@ def createWidget(self):
833
922
widget .addItem (self .dialog .resolveValueDescription (layer ), layer )
834
923
return widget
835
924
925
+ def selectFile (self ):
926
+ filename , selected_filter = self .getFileName (self .combo .currentText ())
927
+ if filename :
928
+ filename = dataobjects .getRasterSublayer (filename , self .param )
929
+ items = self .combo .additionalItems ()
930
+ items .append (filename )
931
+ self .combo .setAdditionalItems (items )
932
+ self .combo .setCurrentIndex (self .combo .findText (filename ))
933
+
836
934
def setValue (self , value ):
837
935
if self .dialogType == DIALOG_STANDARD :
838
936
pass # TODO
@@ -844,9 +942,13 @@ def setValue(self, value):
844
942
def value (self ):
845
943
if self .dialogType == DIALOG_STANDARD :
846
944
try :
847
- return self .widget .itemData (self .widget .currentIndex ())
945
+ layer = self .combo .currentLayer ()
946
+ if layer :
947
+ return layer
948
+ else :
949
+ return self .combo .currentText ()
848
950
except :
849
- return self .widget . getValue ()
951
+ return self .combo . currentText ()
850
952
elif self .dialogType == DIALOG_BATCH :
851
953
return self .widget .value ()
852
954
else :
0 commit comments