コード例 #1
0
    def progress_bar(self):
        try:
            return self._progress_bar
        except AttributeError:
            message_bar_item = QgsMessageBarItem("")

            label = QLabel(self.tr("Computing cartogram"))
            label.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            message_bar_item.layout().addWidget(label)

            progress_bar = QProgressBar()
            progress_bar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            progress_bar.setMaximum(100)
            message_bar_item.layout().addWidget(progress_bar)

            cancel_button = QPushButton(self.tr("Cancel"))
            cancel_button.clicked.connect(self.cancel_task)
            message_bar_item.layout().addWidget(cancel_button)

            self.iface.messageBar().pushWidget(message_bar_item)
            self._progress_bar_message_bar_item = message_bar_item
            self._progress_bar = progress_bar
            self._cancel_button = cancel_button

            return self._progress_bar
コード例 #2
0
class MessageBarProgress(QgsProcessingFeedback):
    def __init__(self, algname=None):
        QgsProcessingFeedback.__init__(self)

        self.msg = []
        self.progressMessageBar = \
            iface.messageBar().createMessage(self.tr('Executing algorithm <i>{0}</i>'.format(algname if algname else '')))
        self.progress = QProgressBar()
        self.progressChanged.connect(self.progress.setValue)
        self.progress.setMaximum(100)
        self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.progressMessageBar.layout().addWidget(self.progress)
        iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)

    def reportError(self, msg, fatalError=False):
        self.msg.append(msg)

    def close(self):
        if self.msg:
            dlg = MessageDialog()
            dlg.setTitle(
                QCoreApplication.translate('MessageBarProgress',
                                           'Problem executing algorithm'))
            dlg.setMessage("<br>".join(self.msg))
            dlg.exec_()
        iface.messageBar().clearWidgets()

    def tr(self, string, context=''):
        if context == '':
            context = 'MessageBarProgress'
        return QCoreApplication.translate(context, string)
コード例 #3
0
    def process_meta_file(self):
        meta_file = self.select_meta_file()
        if meta_file:
            # process peaks
            processed_peaks = get_peaks(meta_file)
            self.peaks.append(processed_peaks)
            self.populate_lists()

            self.iface.messageBar().pushSuccess(
                "Success", "Meta file processed successfully!")

            # process hydrographs
            progressMessageBar = self.iface.messageBar().createMessage(
                "Processing hydrographs...")
            progress = QProgressBar()
            progress.setMaximum(
                len(self.peaks[0]["storm"].sort_values().unique()))
            progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            progressMessageBar.layout().addWidget(progress)
            self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

            processed_hydrographs = get_hydrographs(meta_file,
                                                    progress=progress)
            self.hydrographs.append(processed_hydrographs)

            self.iface.messageBar().clearWidgets()
            self.iface.messageBar().pushSuccess(
                "Success", "Hydrographs processed successfully!")

            model = DataFrameModel(self.peaks[0])
            self.dockwidget.dataTableView.setModel(model)
コード例 #4
0
ファイル: MessageBarProgress.py プロジェクト: pblottiere/QGIS
class MessageBarProgress(QgsProcessingFeedback):

    def __init__(self, algname=None):
        QgsProcessingFeedback.__init__(self)

        self.msg = []
        self.progressMessageBar = \
            iface.messageBar().createMessage(self.tr('Executing algorithm <i>{0}</i>'.format(algname if algname else '')))
        self.progress = QProgressBar()
        self.progressChanged.connect(self.progress.setValue)
        self.progress.setMaximum(100)
        self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.progressMessageBar.layout().addWidget(self.progress)
        self.message_bar_item = iface.messageBar().pushWidget(self.progressMessageBar,
                                                              Qgis.Info)

    def reportError(self, msg, fatalError=False):
        self.msg.append(msg)

    def close(self):
        if self.msg:
            dlg = MessageDialog()
            dlg.setTitle(QCoreApplication.translate('MessageBarProgress', 'Problem executing algorithm'))
            dlg.setMessage("<br>".join(self.msg))
            dlg.exec_()
        iface.messageBar().popWidget(self.message_bar_item)

    def tr(self, string, context=''):
        if context == '':
            context = 'MessageBarProgress'
        return QCoreApplication.translate(context, string)
コード例 #5
0
 def publish(self):
     progressMessageBar = self.bar.createMessage(
         self.tr("Publishing layers"))
     progress = QProgressBar()
     progress.setMaximum(100)
     progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
     progressMessageBar.layout().addWidget(progress)
     self.bar.pushWidget(progressMessageBar, Qgis.Info)
     QCoreApplication.processEvents()
     task = self.getPublishTask(self.parent)
     task.progressChanged.connect(progress.setValue)
     ret = execute(task.run)
     self.bar.clearWidgets()
     task.finished(ret)
     if task.exception is not None:
         self.bar.clearWidgets()
         self.bar.pushMessage(self.tr("Error while publishing"),
                              self.tr("See QGIS log for details"),
                              level=Qgis.Warning,
                              duration=5)
         QgsMessageLog.logMessage(task.exception,
                                  'GeoCat Bridge',
                                  level=Qgis.Critical)
     self.updateLayersPublicationStatus(task.geodataServer is not None,
                                        task.metadataServer is not None)
コード例 #6
0
 def create_progress_bar(self, message, size):
     progress_message_bar = self.iface.messageBar().createMessage(message)
     progress_b = QProgressBar()
     progress_b.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
     progress_message_bar.layout().addWidget(progress_b)
     self.iface.messageBar().pushWidget(progress_message_bar)
     progress_b.setMaximum(size)
     return progress_b
コード例 #7
0
ファイル: utils.py プロジェクト: spch-GL/OpenComptage
def create_progress_bar(message):

    progress_widget = QProgressBar()
    progress_widget.setMaximum(100)
    progress_widget.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
    message_bar = iface.messageBar().createMessage(message)
    message_bar.setWidget(progress_widget)
    iface.messageBar().pushMessage('')
    iface.messageBar().pushWidget(message_bar)

    return progress_widget
コード例 #8
0
 def startProgressBar(self, iniMsg):
     #iniMsg ="Disabling Snapping to Layer: "
     #iface=self.iface
     progressMessageBar = iface.messageBar().createMessage(
         self.SETTINGS, iniMsg)
     progress = QProgressBar()
     progress.setMaximum(100)
     progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
     #pass the progress bar to the message Bar
     progressMessageBar.layout().addWidget(progress)
     iface.messageBar().pushWidget(progressMessageBar)
     return progress, progressMessageBar
コード例 #9
0
    def OnGenerate(self):
        """Reads the directory and other input values. Loops the TIF files and runs the conversion."""

        input_dir = self.textInput.toPlainText()
        output_dir = self.textOutput.toPlainText()
        if input_dir == output_dir:
            iface.messageBar().pushMessage(
                self.tr("Error"),
                self.tr("The input and output directories must differ"),
                level=Qgis.Critical)
            return

        directory = os.fsencode(input_dir)

        # Sets the color values
        r_color = self.mColorButton.color().red()
        g_color = self.mColorButton.color().green()
        b_color = self.mColorButton.color().blue()

        # Sets the progress bar item to show progress in the loop
        progressMessageBar = iface.messageBar().createMessage("Converting...")
        progress = QProgressBar()
        progress.setMaximum(len(os.listdir(directory)))
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        i = 0
        # Loop the directory
        for file in os.listdir(directory):
            progress.setValue(i + 1)
            filename = os.fsdecode(file)
            if filename.endswith(".tif"):
                src_filename = os.path.join(input_dir, filename)
                dst_filename = os.path.join(output_dir, filename)
                try:
                    self.addAlpha(src_filename, dst_filename, r_color, g_color,
                                  b_color)
                except:
                    iface.messageBar().pushMessage(
                        self.tr("Error"),
                        self.
                        tr("The conversion did not work. Please check input and out directories."
                           ),
                        level=Qgis.Critical)
                    return

        # If succeeded the message appears
        iface.messageBar().clearWidgets()
        iface.messageBar().pushMessage(
            self.tr("Success"),
            self.tr("Output layers saved to {}").format(output_dir),
            level=Qgis.Success)
コード例 #10
0
    def createProgressbar(self, loopnumber):
        """
        Create a progress bar when iterating over features
        """
        progressMessageBar = self.messageBar.createMessage(
            str(u"Chargement des données..."))
        progress = QProgressBar()
        progress.setMinimum(0)
        progress.setMaximum(loopnumber)
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.messageBar.pushWidget(progressMessageBar)

        return progress
コード例 #11
0
    def initField(self):
        # get current layer
        layer = self.iface.mapCanvas().currentLayer(
        )  # nF = layer.selectedFeatureCount() #print nF #self.ui.txX.setText("Yes, you can!")
        layer.setLabelsEnabled(True)
        vpr = layer.dataProvider()
        # Get the field of current comobox
        cbField_origin = str(
            self.ui.cbField.currentText())  #print cbField_origin
        print(cbField_origin)

        # start to edit attributes of fields
        layer.startEditing()
        allFeatures = layer.getFeatures()

        count = layer.featureCount()

        infoString = str(
            "<font color='red'> Creating and initializing the label fields......Wait this completed please......</font>"
        )
        progressMessageBar = self.iface.messageBar().createMessage(infoString)
        progress = QProgressBar()
        progress.setMaximum(count)
        progress.setAlignment(QtCore.Qt.AlignLeft | QtCore.Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        # loop for initialization
        n = -1
        for feature in allFeatures:
            feature[share.field_list[0][0]] = feature[cbField_origin]
            feature[share.field_list[1][0]] = 999999999999999999.0
            feature[share.field_list[2][0]] = 999999999999999999.0
            feature[share.field_list[3][0]] = 0.0
            feature[share.field_list[4][0]] = 1
            feature[share.field_list[5][0]] = "Center"
            feature[share.field_list[6][0]] = "Half"

            n = n + 1
            layer.updateFeature(feature)

            progress.setValue(n + 1)
        self.iface.messageBar().clearWidgets()

        # updateExtents and refresh mapCanvas
        #layer.updateExtents()
        layer.commitChanges()  # make sure that fields are initialize correctly
        self.iface.mapCanvas().refresh()
コード例 #12
0
 def __init__(self, parent, msg = ''):
     '''
     progressBar class instatiation method. It creates a QgsMessageBar with provided msg and a working QProgressBar
     :param parent:
     :param msg: string
     '''
     self.iface = parent.iface
     widget = self.iface.messageBar().createMessage("GooGIS plugin:",msg)
     progressBar = QProgressBar()
     progressBar.setRange(0,0) #(1,steps)
     progressBar.setValue(0)
     progressBar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
     widget.layout().addWidget(progressBar)
     QApplication.processEvents()
     self.iface.messageBar().pushWidget(widget, Qgis.Info, 50)
     QApplication.processEvents()
コード例 #13
0
class MessageBarProgress(object):
    def __init__(self, algname=None):
        self.msg = []
        self.progressMessageBar = \
            iface.messageBar().createMessage(self.tr('Executing algorithm <i>{0}</i>'.format(algname if algname else '')))
        self.progress = QProgressBar()
        self.progress.setMaximum(100)
        self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.progressMessageBar.layout().addWidget(self.progress)
        iface.messageBar().pushWidget(self.progressMessageBar,
                                      iface.messageBar().INFO)

    def error(self, msg):
        self.msg.append(msg)

    def setText(self, text):
        pass

    def setPercentage(self, i):
        self.progress.setValue(i)

    def setInfo(self, _):
        pass

    def setCommand(self, _):
        pass

    def setDebugInfo(self, _):
        pass

    def setConsoleInfo(self, _):
        pass

    def close(self):
        if self.msg:
            dlg = MessageDialog()
            dlg.setTitle(
                QCoreApplication.translate('MessageBarProgress',
                                           'Problem executing algorithm'))
            dlg.setMessage("<br>".join(self.msg))
            dlg.exec_()
        iface.messageBar().clearWidgets()

    def tr(self, string, context=''):
        if context == '':
            context = 'MessageBarProgress'
        return QCoreApplication.translate(context, string)
コード例 #14
0
class MessageBarProgress(object):

    def __init__(self, algname=None):
        self.msg = []
        self.progressMessageBar = \
            iface.messageBar().createMessage(self.tr('Executing algorithm <i>{0}</i>'.format(algname if algname else '')))
        self.progress = QProgressBar()
        self.progress.setMaximum(100)
        self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.progressMessageBar.layout().addWidget(self.progress)
        iface.messageBar().pushWidget(self.progressMessageBar,
                                      iface.messageBar().INFO)

    def error(self, msg):
        self.msg.append(msg)

    def setText(self, text):
        pass

    def setPercentage(self, i):
        self.progress.setValue(i)

    def setInfo(self, _):
        pass

    def setCommand(self, _):
        pass

    def setDebugInfo(self, _):
        pass

    def setConsoleInfo(self, _):
        pass

    def close(self):
        if self.msg:
            dlg = MessageDialog()
            dlg.setTitle(QCoreApplication.translate('MessageBarProgress', 'Problem executing algorithm'))
            dlg.setMessage("<br>".join(self.msg))
            dlg.exec_()
        iface.messageBar().clearWidgets()

    def tr(self, string, context=''):
        if context == '':
            context = 'MessageBarProgress'
        return QCoreApplication.translate(context, string)
コード例 #15
0
class ProgessBarDialog(QDialog):
    def __init__(self, GTFS_folder, parent=None):
        QDialog.__init__(self, parent)
        self.resize(310, 140)
        self.setWindowTitle("Info")

        self.process_info = QLineEdit(self)
        self.process_info.resize(230, 20)
        self.process_info.move(40, 35)
        self.process_info.setAlignment(Qt.AlignVCenter)

        self.progBar = QProgressBar(self)
        self.progBar.resize(230,20)
        self.progBar.move(40, 70)
        self.progBar.setAlignment(Qt.AlignVCenter)

        self.newTask(GTFS_folder)

    def newTask(self,GTFS_folder):
        self.task = HeavyTask(GTFS_folder)
        self.task.progressChanged.connect(lambda: self.progBar.setValue(self.task.progress()))
        self.task.progressChanged.connect(lambda: self.info(self.task.progress()))
        QgsApplication.taskManager().addTask(self.task)

    def info(self,value):
        if value == 10:
            self.process_info.setText("Unzipping file")
           
        elif value == 60:
            self.process_info.setText("Saving layers into GeoPackage")
          
        elif value == 70:
            self.process_info.setText("Loading layers from GeoPackage")

        elif value == 80:
            self.process_info.setText("Deleting unzipped folder")
          
        elif value == 85:
            self.process_info.setText("Connecting shapes")

        elif value == 95:
            self.process_info.setText("Coloring of line layers")
        
        elif value == 100:
            time.sleep(2)
            self.close()
    def progressBar(self):
        progressMessageBar = self.iface.messageBar().createMessage(
            "Project setup...")
        progress = QProgressBar()
        progress.setMaximum(5)
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        for i in range(5):
            time.sleep(1)
            progress.setValue(i + 1)

        self.iface.messageBar().clearWidgets()
        energy_plant_radiation_class.popupMessage(self, "Project setup:",
                                                  "Completed with success",
                                                  "success")
        print("Project Loaded")
コード例 #17
0
class MessageBarProgressItem(QObject):
    """
    Message bar item which shows a progress report bar
    """

    def __init__(self, text, iface: QgisInterface, parent: QObject = None):
        """
        Constructor for MessageBarProgressItem
        :param text: text to show
        :param parent: parent object
        """
        super().__init__(parent)
        self.iface = iface
        self.progressMessageBar = \
            self.iface.messageBar().createMessage(text)
        self.progress = QProgressBar()
        self.progress.setMaximum(100)
        self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.progressMessageBar.destroyed.connect(self.clear_progress)
        self.progressMessageBar.layout().addWidget(self.progress)
        self.iface.messageBar().pushWidget(self.progressMessageBar,
                                           Qgis.Info)

    def close(self):  # pylint disable=may-be-static
        """
        Closes the message bar item
        """
        if self.progressMessageBar is not None:
            self.iface.messageBar().popWidget(self.progressMessageBar)

    def clear_progress(self):
        """
        Called on deletion of the progress bar, e.g. by user closing the bar
        """
        self.progress = None
        self.progressMessageBar = None

    def set_progress(self, progress: int):
        """
        Sets the progress to show in the item
        :param progress: integer for percent progress, 0 - 100
        """
        if self.progress is not None:
            self.progress.setValue(progress)
コード例 #18
0
class Source:
    def __init__(self):
        placeholder = 100

    def set_iface(self, iface):
        self.iface = iface

    def has_options_dialog(self):
        return False

    def download_data(self, url, path, msg):
        if not os.path.exists(path):
            try:
                progressMessageBar = self.iface.messageBar().createMessage(
                    "Downloading " + msg)
                self.progress = QProgressBar()
                self.progress.setMaximum(100)
                self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
                progressMessageBar.layout().addWidget(self.progress)
                self.iface.messageBar().pushWidget(progressMessageBar,
                                                   Qgis.Info)
                http = urllib3.PoolManager()
                response = http.request('GET', url, preload_content=False)
                content_length = response.headers['Content-Length']
                total_size = int(content_length)
                downloaded = 0
                CHUNK = 256 * 10240
                self.progress.setMinimum(0)
                self.progress.setMaximum(total_size)
                with open(path, 'wb') as fp:
                    while True:
                        time.sleep(1)
                        chunk = response.read(CHUNK)
                        downloaded += len(chunk)
                        self.progress.setValue(downloaded)
                        if not chunk:
                            break
                        fp.write(chunk)
                response.release_conn()
                self.iface.messageBar().clearWidgets()

            except urllib3.exceptions.MaxRetryError:
                QMessageBox.information(self.iface.mainWindow(), "HTTP Error",
                                        "Unable to download file")
コード例 #19
0
def start_worker(worker, message_bar, message):
    """
    Configure the QgsMessageBar with a :guilabel:`Cancel` button and start
    the worker in a new thread

    :param worker: the worker to be started
    :param message_bar: the message bar to be used to display progress
    :param message: a message describing the task to be performed
    """
    # configure the QgsMessageBar
    message_bar_item = message_bar.createMessage(message)
    progress_bar = QProgressBar()
    progress_bar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
    cancel_button = QPushButton()
    cancel_button.setText('Cancel')
    cancel_button.clicked.connect(worker.kill)
    message_bar_item.layout().addWidget(progress_bar)
    message_bar_item.layout().addWidget(cancel_button)
    message_bar.pushWidget(message_bar_item, Qgis.Info)

    # start the worker in a new thread
    thread = QThread(message_bar.parent())
    worker.moveToThread(thread)

    worker.set_message.connect(
        lambda message: set_worker_message(message, message_bar_item))

    worker.toggle_show_progress.connect(
        lambda show: toggle_worker_progress(show, progress_bar))

    worker.toggle_show_cancel.connect(
        lambda show: toggle_worker_cancel(show, cancel_button))

    worker.finished.connect(lambda result: worker_finished(
        result, thread, worker, message_bar, message_bar_item))

    worker.error.connect(
        lambda e, exception_str: worker_error(e, exception_str, message_bar))

    worker.progress.connect(progress_bar.setValue)
    thread.started.connect(worker.run)
    thread.start()
    return thread, message_bar_item
コード例 #20
0
    def __import_data(self):
        assert(self.project)
        dir_ = QFileDialog.getExistingDirectory(
            None,
            u"Data directory",
            QgsProject.instance().readEntry("albion", "last_dir", "")[0],
            QFileDialog.ShowDirsOnly | QFileDialog.DontUseNativeDialog
        )
        if not dir_:
            return
        QgsProject.instance().writeEntry("albion", "last_dir", dir_),

        progressMessageBar = self.__iface.messageBar().createMessage(
            "Loading {}...".format(dir_)
        )
        progress = QProgressBar()
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.__iface.messageBar().pushWidget(progressMessageBar)

        self.project.import_data(dir_, ProgressBar(progress))
        #self.project.triangulate()
        self.project.create_section_view_0_90(4)

        self.__iface.messageBar().clearWidgets()

        collar = QgsProject.instance().mapLayersByName("collar")
        if len(collar):
            collar[0].reload()
            collar[0].updateExtents()
            self.__iface.setActiveLayer(collar[0])
            QApplication.instance().processEvents()
            while self.__iface.mapCanvas().isDrawing():
                QApplication.instance().processEvents()
            self.__iface.zoomToActiveLayer()

        self.__iface.actionSaveProject().trigger()

        self.__viewer3d.widget().resetScene(self.project)
        self.__current_section.clear()
        self.__current_section.addItems(self.project.sections())
コード例 #21
0
class progressBar:
    def __init__(self, parent, title=''):
        '''
        progressBar class instatiation method. It creates a QgsMessageBar with provided msg and a working QProgressBar
        :param parent:
        :param msg: string
        '''
        self.iface = parent.iface
        self.title = title

    def start(self, max=0, msg=''):
        self.widget = self.iface.messageBar().createMessage(self.title, msg)
        self.progressBar = QProgressBar()
        self.progressBar.setRange(0, max)
        self.progressBar.setValue(0)
        self.progressBar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.widget.layout().addWidget(self.progressBar)
        QApplication.processEvents()
        self.iface.messageBar().pushWidget(self.widget, Qgis.Info, 50)
        QApplication.processEvents()

    def setProgress(self, value):
        try:
            self.progressBar.setValue(value)
            QApplication.processEvents()
        except:
            pass

    def setMsg(self, msg):
        self.widget.setText(msg)
        QApplication.processEvents()

    def stop(self, msg=''):
        '''
        the progressbar is stopped with a succes message
        :param msg: string
        :return:
        '''
        self.iface.messageBar().clearWidgets()
        message = self.iface.messageBar().createMessage(self.title, msg)
        self.iface.messageBar().pushWidget(message, Qgis.Info, 2)
コード例 #22
0
ファイル: GTFS.py プロジェクト: Kozzba/dp-test-repositary
    def onSubmit(self):
        self.choosing.close()

        progressMessageBar = iface.messageBar().createMessage("")

        self.process_info = QLabel()
        progressMessageBar.layout().addWidget(self.process_info)

        progress = QProgressBar()
        progress.setMaximum(100)
        progress.setAlignment(Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)

        iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        task = LoadTask(self.dockwidget.input_dir.filePath(), self.do_zones)
        task.progressChanged.connect(
            lambda: progress.setValue(task.progress()))
        task.progressChanged.connect(lambda: self.info(task.progress()))

        QgsApplication.taskManager().addTask(task)
コード例 #23
0
    def import_mesh(self):
        qfd = QFileDialog()
        path = ""

        import_function = load_IO()
        fil = ''
        for model in import_function:
            fil += import_function[model]['extension']() + ';'

        fname = QFileDialog.getOpenFileName(qfd, 'Import Mesh file', path, fil)
        fname = fname[0]
        if fname == '':
            return

        filename, file_extension = os.path.splitext(fname)
        if file_extension == '':
            return

        progressMessageBar = self.iface.messageBar().createMessage("Load Mesh")
        progress = QProgressBar()
        progress.setMaximum(10)
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        self.mesh = Mesh([], [], [], [])
        for model in import_function:
            ext = import_function[model]['extension']()
            if file_extension in ext:
                progress.setValue(0)
                self.mesh = import_function[model]['import'](self.mesh, fname)
                progress.setValue(3)
                self.mesh._calculate_face_nodes()
                progress.setValue(6)
                #                self.mesh._remove_hanging_nodes()
                self.mesh.calc_parameters()
                progress.setValue(9)
                Mesh2Shapefile(self.mesh)

        self.iface.messageBar().clearWidgets()
コード例 #24
0
    def prepareProcess(self, process, message):
        """
        Prepares the process to be executed.
        Creates a message bar.
        Connects the destroyed progress bar signal to the process cancel method
        """
        # Setting the progress bar
        progressMessageBar = self.iface.messageBar().createMessage(message)
        progressBar = QProgressBar()
        progressBar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progressBar)
        self.iface.messageBar().pushWidget(progressMessageBar,
                                           self.iface.messageBar().INFO)

        #connecting the destroyed signal
        progressMessageBar.destroyed.connect(
            process.messenger.progressCanceled)

        #storing the process and its related progressBar
        self.processDict[process] = progressBar

        #initiating processing
        QThreadPool.globalInstance().start(process)
コード例 #25
0
ファイル: worker.py プロジェクト: LocateIT/trends.earth
def start_worker(worker, iface, message, with_progress=True):
    # configure the QgsMessageBar
    message_bar_item = iface.messageBar().createMessage(message)
    progress_bar = QProgressBar()
    progress_bar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
    if not with_progress:
        progress_bar.setMinimum(0)
        progress_bar.setMaximum(0)
    cancel_button = QPushButton()
    cancel_button.setText('Cancel')
    cancel_button.clicked.connect(worker.kill)
    message_bar_item.layout().addWidget(progress_bar)
    message_bar_item.layout().addWidget(cancel_button)
    iface.messageBar().pushWidget(message_bar_item, Qgis.Info)

    # start the worker in a new thread
    # let Qt take ownership of the QThread
    thread = QThread(iface.mainWindow())
    worker.moveToThread(thread)

    worker.set_message.connect(lambda message: set_worker_message(
        message, message_bar_item))
    worker.toggle_show_progress.connect(lambda show: toggle_worker_progress(
        show, progress_bar))
    worker.toggle_show_cancel.connect(lambda show: toggle_worker_cancel(
        show, cancel_button))
    worker.finished.connect(lambda result: worker_finished(
        result, thread, worker, iface, message_bar_item))
    worker.error.connect(lambda e: worker_error(e))
    worker.was_killed.connect(lambda result: worker_killed(
        result, thread, worker, iface, message_bar_item))

    worker.progress.connect(progress_bar.setValue)
    thread.started.connect(worker.run)
    thread.start()

    return thread, message_bar_item
コード例 #26
0
    def run_custom_evalscript(self):
        """
        Run operations given user inputted custom evalscript code and return a raster layer based on specifications
        """

        progressMessageBar = self.iface.messageBar().createMessage(
            'Getting mosaic preview')
        progress = QProgressBar()
        progress.setMaximum(3)
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        # get bounding box
        bbox = self.get_bounding_box(default=False)

        # validate and set time interval
        start_date, end_date = self.dockwidget.start_date.text(
        ), self.dockwidget.end_date.text()
        accepted_date_format = "%Y-%m-%d"
        try:
            dt.datetime.strptime(start_date, accepted_date_format)
            dt.datetime.strptime(end_date, accepted_date_format)
        except ValueError:
            raise ValueError(
                "Please enter start and end dates with the format of YYYY-MM-DD (ex. 2000-01-01)."
            )

        time_interval = [start_date, end_date]

        # set and validate max_cc
        max_cc = float(self.dockwidget.custom_max_cc.text())

        assert max_cc >= 0 and max_cc <= 1, 'Please enter a max cloud cover proportion between 0 and 1.'

        # grab user inputted custom evalscript and substitute generic
        custom_evalscript_code = self.dockwidget.custom_evalscript_code.toPlainText(
        )
        preview_eval = custom_evalscript_code

        QgsMessageLog.logMessage('requesting preview image', level=Qgis.Info)

        preview_request = SentinelHubRequest(
            evalscript=preview_eval,
            data_folder='/tmp/mosaic_tests',
            input_data=[
                SentinelHubRequest.input_data(
                    data_collection=DataCollection.SENTINEL2_L2A,
                    time_interval=time_interval,
                    maxcc=max_cc)
            ],
            responses=[
                SentinelHubRequest.output_response('default', MimeType.TIFF)
            ],
            bbox=bbox,
            size=(512, get_image_dimension(bbox=bbox, width=512)),
            config=config)

        preview_request.get_data(save_data=True)
        progress.setValue(3)
        output_file = '/tmp/mosaic_tests' + '/' + preview_request.get_filename_list(
        )[0]

        # add file to QGIS
        custom_layer_name_input = self.dockwidget.custom_layer_name_input.text(
        )
        if len(custom_layer_name_input) != 0:
            layer_name = custom_layer_name_input
        else:
            layer_name = 'custom_evalscript_layer'
        self.iface.addRasterLayer(output_file, layer_name)
        self.iface.messageBar().clearWidgets()

        return None
コード例 #27
0
windows = platform.system() == 'Windows'

LavFilters = "https://github.com/Nevcairiel/LAVFilters/releases/download/0.73.1/LAVFilters-0.73.1-Installer.exe"

# 64 Bits
if platform.machine().endswith('64'):
    FFMPEG = "https://ffmpeg.zeranoe.com/builds/win64/static/ffmpeg-20190225-2e67f75-win64-static.zip"
# 32 Bits
else:
    FFMPEG = "https://ffmpeg.zeranoe.com/builds/win32/static/ffmpeg-20190225-2e67f75-win32-static.zip"

DemGlobal = "http://www.gisandbeers.com/RRSS/Cartografia/DEM-Mundial.rar"

progress = QProgressBar()
progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)

opener = build_opener()
opener.addheaders = [(
    'User-Agent',
    'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/36.0.1941.0 Safari/537.36'
)]
install_opener(opener)


def reporthook(blocknum, blocksize, totalsize):
    readsofar = blocknum * blocksize
    if totalsize > 0:
        percent = readsofar * 1e2 / totalsize
        progress.setValue(int(percent))
コード例 #28
0
    def generate_report(self, db, report_type):
        # Check if mapfish and Jasper are installed, otherwise show where to
        # download them from and return
        if not self.report_dependency.check_if_dependency_is_valid():
            self.report_dependency.download_dependency(URL_REPORTS_LIBRARIES)
            return

        java_home_set = self.java_dependency.set_java_home()
        if not java_home_set:
            self.java_dependency.get_java_on_demand()
            self.logger.info_msg(
                __name__,
                QCoreApplication.translate(
                    "ReportGenerator",
                    "Java is a prerequisite. Since it was not found, it is being configured..."
                ))
            return

        plot_layer = self.app.core.get_layer(db, db.names.LC_PLOT_T, load=True)
        if not plot_layer:
            return

        selected_plots = plot_layer.selectedFeatures()
        if not selected_plots:
            self.logger.warning_msg(
                __name__,
                QCoreApplication.translate(
                    "ReportGenerator",
                    "To generate reports, first select at least a plot!"))
            return

        # Where to store the reports?
        previous_folder = QSettings().value(
            "Asistente-LADM-COL/reports/save_into_dir", ".")
        save_into_folder = QFileDialog.getExistingDirectory(
            None,
            QCoreApplication.translate(
                "ReportGenerator",
                "Select a folder to save the reports to be generated"),
            previous_folder)
        if not save_into_folder:
            self.logger.warning_msg(
                __name__,
                QCoreApplication.translate(
                    "ReportGenerator",
                    "You need to select a folder where to save the reports before continuing."
                ))
            return
        QSettings().setValue("Asistente-LADM-COL/reports/save_into_dir",
                             save_into_folder)

        config_path = os.path.join(DEPENDENCY_REPORTS_DIR_NAME, report_type)
        json_spec_file = os.path.join(config_path, 'spec_json_file.json')

        script_name = ''
        if os.name == 'posix':
            script_name = 'print'
        elif os.name == 'nt':
            script_name = 'print.bat'

        script_path = os.path.join(DEPENDENCY_REPORTS_DIR_NAME, 'bin',
                                   script_name)
        if not os.path.isfile(script_path):
            self.logger.warning(
                __name__,
                "Script file for reports wasn't found! {}".format(script_path))
            return

        self.enable_action_requested.emit(report_type, False)

        # Update config file
        yaml_config_path = self.update_yaml_config(db, config_path)
        self.logger.debug(
            __name__, "Config file for reports: {}".format(yaml_config_path))

        total = len(selected_plots)
        step = 0
        count = 0
        tmp_dir = self.get_tmp_dir()

        # Progress bar setup
        progress = QProgressBar()
        if total == 1:
            progress.setRange(0, 0)
        else:
            progress.setRange(0, 100)
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        self.app.gui.create_progress_message_bar(
            QCoreApplication.translate("ReportGenerator",
                                       "Generating {} report{}...").format(
                                           total, '' if total == 1 else 's'),
            progress)

        polygons_with_holes = []
        multi_polygons = []

        for selected_plot in selected_plots:
            plot_id = selected_plot[db.names.T_ID_F]

            geometry = selected_plot.geometry()
            abstract_geometry = geometry.get()
            if abstract_geometry.ringCount() > 1:
                polygons_with_holes.append(str(plot_id))
                self.logger.warning(
                    __name__,
                    QCoreApplication.translate(
                        "ReportGenerator",
                        "Skipping Annex 17 for plot with {}={} because it has holes. The reporter module does not support such polygons."
                    ).format(db.names.T_ID_F, plot_id))
                continue
            if abstract_geometry.numGeometries() > 1:
                multi_polygons.append(str(plot_id))
                self.logger.warning(
                    __name__,
                    QCoreApplication.translate(
                        "ReportGenerator",
                        "Skipping Annex 17 for plot with {}={} because it is a multi-polygon. The reporter module does not support such polygons."
                    ).format(db.names.T_ID_F, plot_id))
                continue

            # Generate data file
            json_file = self.update_json_data(db, json_spec_file, plot_id,
                                              tmp_dir, report_type)
            self.logger.debug(__name__,
                              "JSON file for reports: {}".format(json_file))

            # Run sh/bat passing config and data files
            proc = QProcess()
            proc.readyReadStandardError.connect(
                functools.partial(self.stderr_ready, proc=proc))
            proc.readyReadStandardOutput.connect(
                functools.partial(self.stdout_ready, proc=proc))

            parcel_number = self.ladm_data.get_parcels_related_to_plots(
                db, [plot_id], db.names.LC_PARCEL_T_PARCEL_NUMBER_F) or ['']
            file_name = '{}_{}_{}.pdf'.format(report_type, plot_id,
                                              parcel_number[0])

            current_report_path = os.path.join(save_into_folder, file_name)
            proc.start(script_path, [
                '-config', yaml_config_path, '-spec', json_file, '-output',
                current_report_path
            ])

            if not proc.waitForStarted():
                # Grant execution permissions
                os.chmod(
                    script_path, stat.S_IXOTH | stat.S_IXGRP | stat.S_IXUSR
                    | stat.S_IRUSR | stat.S_IRGRP)
                proc.start(script_path, [
                    '-config', yaml_config_path, '-spec', json_file, '-output',
                    current_report_path
                ])

            if not proc.waitForStarted():
                proc = None
                self.logger.warning(
                    __name__, "Couldn't execute script to generate report...")
            else:
                loop = QEventLoop()
                proc.finished.connect(loop.exit)
                loop.exec()

                self.logger.debug(__name__,
                                  "{}:{}".format(plot_id, proc.exitCode()))
                if proc.exitCode() == 0:
                    count += 1

                step += 1
                progress.setValue(step * 100 / total)

        os.remove(yaml_config_path)

        self.enable_action_requested.emit(report_type, True)
        self.logger.clear_message_bar()

        if total == count:
            if total == 1:
                msg = QCoreApplication.translate(
                    "ReportGenerator",
                    "The report <a href='file:///{}'>{}</a> was successfully generated!"
                ).format(normalize_local_url(save_into_folder), file_name)
            else:
                msg = QCoreApplication.translate(
                    "ReportGenerator",
                    "All reports were successfully generated in folder <a href='file:///{path}'>{path}</a>!"
                ).format(path=normalize_local_url(save_into_folder))

            self.logger.success_msg(__name__, msg)
        else:
            details_msg = ''
            if polygons_with_holes:
                details_msg += QCoreApplication.translate(
                    "ReportGenerator",
                    " The following polygons were skipped because they have holes and are not supported: {}."
                ).format(", ".join(polygons_with_holes))
            if multi_polygons:
                details_msg += QCoreApplication.translate(
                    "ReportGenerator",
                    " The following polygons were skipped because they are multi-polygons and are not supported: {}."
                ).format(", ".join(multi_polygons))

            if total == 1:
                msg = QCoreApplication.translate(
                    "ReportGenerator",
                    "The report for plot {} couldn't be generated!{} See QGIS log (tab '{}') for details."
                ).format(plot_id, details_msg, self.LOG_TAB)
            else:
                if count == 0:
                    msg = QCoreApplication.translate(
                        "ReportGenerator",
                        "No report could be generated!{} See QGIS log (tab '{}') for details."
                    ).format(details_msg, self.LOG_TAB)
                else:
                    msg = QCoreApplication.translate(
                        "ReportGenerator",
                        "At least one report couldn't be generated!{details_msg} See QGIS log (tab '{log_tab}') for details. Go to <a href='file:///{path}'>{path}</a> to see the reports that were generated."
                    ).format(details_msg=details_msg,
                             path=normalize_local_url(save_into_folder),
                             log_tab=self.LOG_TAB)

            self.logger.warning_msg(__name__, msg)
コード例 #29
0
class OSMDownloaderDialog(QDialog, FORM_CLASS):
    def __init__(self, iface, startX, startY, endX, endY, parent=None):
        """Constructor."""
        super(OSMDownloaderDialog, self).__init__(parent)
        # Set up the user interface from Designer.
        # After setupUI you can access any designer object by doing
        # self.<objectname>, and you can use autoconnect slots - see
        # http://qt-project.org/doc/qt-4.8/designer-using-a-ui-file.html
        # #widgets-and-dialogs-with-auto-connect
        self.setupUi(self)

        self.iface = iface

        self.setCoordinates(startX, startY, endX, endY)

        self.threadpool = QThreadPool()

        self.size = 0

    def setCoordinates(self, startX, startY, endX, endY):
        if startX < endX:
            minLong = startX
            maxLong = endX
        else:
            minLong = endX
            maxLong = startX

        if startY < endY:
            minLat = startY
            maxLat = endY
        else:
            minLat = endY
            maxLat = startY

        self.wEdit.setText(str(minLong))
        self.sEdit.setText(str(minLat))
        self.eEdit.setText(str(maxLong))
        self.nEdit.setText(str(maxLat))

    @pyqtSlot()
    def on_saveButton_clicked(self):
        ret = QFileDialog.getSaveFileName(parent=None, caption='Define file name and location', filter='OSM Files(*.osm)')
        fileName = ret[0]

        split = fileName.split('.')
        if len(split)>0 and split[-1] == 'osm':
            pass
        else:
            fileName += '.osm'

        self.filenameEdit.setText(fileName)

    @pyqtSlot()
    def on_button_box_accepted(self):
        if self.filenameEdit.text() == '':
            QMessageBox.warning(self, self.tr("Warning!"), self.tr("Please, select a location to save the file."))
            return

        # Initiating processing
        osmRequest = OSMRequest(self.filenameEdit.text())
        osmRequest.setParameters(self.wEdit.text(), self.sEdit.text(), self.eEdit.text(), self.nEdit.text())
        # Connecting end signal
        osmRequest.signals.processFinished.connect(self.processFinished)
        osmRequest.signals.sizeReported.connect(self.reportSize)
        osmRequest.signals.proxyOpened.connect(self.proxy)
        osmRequest.signals.errorOccurred.connect(self.errorOccurred)
        osmRequest.signals.userCanceled.connect(self.userCanceled)
        # Setting the progress bar
        self.progressMessageBar = self.iface.messageBar().createMessage('Downloading data...')
        self.progressBar = QProgressBar()
        self.progressBar.setAlignment(Qt.AlignLeft|Qt.AlignVCenter)
        self.progressMessageBar.layout().addWidget(self.progressBar)
        self.iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)
        self.progressBar.setRange(0, 0)
        self.progressMessageBar.destroyed.connect(osmRequest.signals.cancel)
        # Starting process
        self.threadpool.start(osmRequest)

    @pyqtSlot(str)
    def proxy(self, proxy):
        self.progressMessageBar.setText('Proxy set to: '+proxy)

    @pyqtSlot(str)
    def errorOccurred(self, message):
        QMessageBox.warning(self, 'Fatal!', message)
        self.close()

    @pyqtSlot()
    def userCanceled(self):
        QMessageBox.warning(self, 'Info!', 'Process canceled by user!')
        self.close()

    @pyqtSlot(float)
    def reportSize(self, size):
        self.size = size
        self.progressMessageBar.setText('Downloading: '+"{0:.2f}".format(size)+' megabytes from OSM servers...')

    @pyqtSlot(str)
    def processFinished(self, message):
        self.progressBar.setRange(0, 100)
        self.progressBar.setValue(100)
        self.progressMessageBar.setText('Downloaded '+"{0:.2f}".format(self.size)+' megabytes in total from OSM servers')
        QMessageBox.warning(self, 'Info!', message)

        if self.checkBox.isChecked():
            self.iface.addVectorLayer(self.filenameEdit.text(), 'osm_data', 'ogr')

        self.close()
コード例 #30
0
class Window(QDialog):
    def __init__(self):
        super().__init__()
        self.title = "PyQt5 ProgressBar"
        self.top = 200
        self.left = 500
        self.width = 300
        self.height = 100
        self.setWindowIcon(QtGui.QIcon("icon.png"))
        self.setWindowTitle(self.title)
        self.setGeometry(self.left, self.top, self.width, self.height)
        vbox = QVBoxLayout()
        self.progressbar = QProgressBar()
        #self.progressbar.setOrientation(Qt.Vertical)
        self.progressbar.setMaximum(100)
        vbox.addWidget(self.progressbar)
        self.startProgressBar()
        self.setLayout(vbox)
        #self.show()

    def startProgressBar(self):
        self.thread = MyThread()
        self.thread.change_value.connect(self.setProgressBarAndMessages)
        self.thread.start()

    def setProgressBarAndMessages(self, val):
        self.progressbar.setValue(val)
        # --- Progress bar in the QGIS user messages (top)
        if val <= 10:
            message = "Starting..."
            self.progressMessageBar = iface.messageBar().createMessage(message)
            self.progress = QProgressBar()
            self.progress.setMaximum(100)
            self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            self.progressMessageBar.layout().addWidget(self.progress)
            iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)
            self.progress.setValue(val)
        elif val < 50:
            message = "First half"
            self.progressMessageBar = iface.messageBar().createMessage(message)
            self.progress = QProgressBar()
            self.progress.setMaximum(100)
            self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            self.progressMessageBar.layout().addWidget(self.progress)
            iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)
            self.progress.setValue(val)
        elif val < 100:
            message = "Second Half"
            self.progressMessageBar = iface.messageBar().createMessage(message)
            self.progress = QProgressBar()
            self.progress.setMaximum(100)
            self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            self.progressMessageBar.layout().addWidget(self.progress)
            iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)
            self.progress.setValue(val)
        elif val == 100:
            message = "Complete"
            self.progressMessageBar = iface.messageBar().createMessage(message)
            self.progress = QProgressBar()
            self.progress.setMaximum(100)
            self.progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            self.progressMessageBar.layout().addWidget(self.progress)
            iface.messageBar().pushWidget(self.progressMessageBar, Qgis.Info)
            self.progress.setValue(val)
            iface.messageBar().clearWidgets()
コード例 #31
0
ファイル: simex_plugin.py プロジェクト: diisilva/simex_plugin
    def run(self):
        """Run method that performs all the real work"""
        
        def blankPaint(geometry):
            
            blank = ee.Image(0).mask(0)
            geometryDraw = blank.paint(geometry, '0000AA', 1)
            
            return geometryDraw
        # Create the dialog with elements (after translation) and keep reference
        # Only create GUI ONCE in callback, so that it will only load when the plugin is started
        if self.first_start == True:
            self.first_start = False
            self.dlg = simex_pluginDialog()

        # show the dialog
        self.dlg.show()
        # Run the dialog event loop
        result = self.dlg.exec_()
        # See if OK was pressed
        if result:
      
            uf = self.dlg.selectUF.currentText()
            path = self.dlg.path.toPlainText()
            row = self.dlg.row.toPlainText()
            cloud_cover = int(self.dlg.cloudcover.cleanText())
            startdate = self.dlg.startdate.date().toString('yyyy-MM-dd') 
            enddate = self.dlg.enddate.date().toString('yyyy-MM-dd') 
            self.iface.messageBar().pushMessage('loading ...')
            geometry = path_row_am.filterMetadata('PATH', 'equals', int(path)).filterMetadata('ROW', 'equals', int(row)).geometry()
            countourGeometry = blankPaint(geometry)
            Map.centerObject(geometry, 100)
            progressMessageBar = iface.messageBar().createMessage("loading...")
            progress = QProgressBar()
            progress.setMaximum(10)
            progress.setAlignment(Qt.AlignLeft|Qt.AlignVCenter)
            progressMessageBar.layout().addWidget(progress)
            iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

            for i in range(10):
                time.sleep(1)
                progress.setValue(i + 1)
            
            parametrosColecaoL8 = { 'collectionid': 'LANDSAT/LC08/C01/T1_SR',
                    'geometry': geometry.centroid(),
                    'dateStart': ee.Date(startdate),
                    'dateEnd': ee.Date(enddate),
                    'cloud_cover': cloud_cover,
                }
            colecaoL8 = getCollection(parametrosColecaoL8).select(bandNames("l8")['bandNames'],bandNames("l8")['newNames'])\
                                        .map(getSMA).map(getNDFI)
            #nImages = colecaoL8.size().getInfo()
            #colList = colecaoL8.toList(nImages)
            #idG = 1

            listYears = list(range(int(startdate[:4]),int(enddate[:4])+1))
          
            for item in listYears:
                
                #imgYear = ee.Image(colecaoL8.filterDate(str(item) + '-01-01',str(item+1) + '-01-01').sort('cloud_cover').first())

                colYear = colecaoL8.filterDate(str(item) + '-01-01',str(item+1) + '-01-01').sort('cloud_cover').limit(3)                
                colList = colYear.toList(5)
                idG = 1

                while idG < 3:
                    
                    img = ee.Image(colList.get(idG))

                    try:
                        dictionaryInfos = ee.Dictionary({'satellite_name':img.get('satellite_name'),
                                            'date':img.get('date'),
                                            'cloud_cover':img.get('cloud_cover')}).getInfo()
                        if listYears.index(item) == len(listYears)-2:
                            status = True
                        else:
                            status = False  

                        Map.addLayer(img, {'bands': ['swir2'],'gain' : [0.2],'gamma':0.6},\
                                            'B7_' + str(dictionaryInfos['date']).replace('-','_')+'_'+dictionaryInfos['satellite_name'],status)
                    
                        Map.addLayer(img,{"bands": ['ndfi'],
                                                    "palette": ['ffffff', 'fffcff', 'fff9ff', 'fff7ff', 'fff4ff', 'fff2ff', 'ffefff', 'ffecff', 'ffeaff', 'ffe7ff',
                                                                'ffe5ff', 'ffe2ff', 'ffe0ff', 'ffddff', 'ffdaff', 'ffd8ff', 'ffd5ff', 'ffd3ff', 'ffd0ff', 'ffceff',
                                                                'ffcbff', 'ffc8ff', 'ffc6ff', 'ffc3ff', 'ffc1ff', 'ffbeff', 'ffbcff', 'ffb9ff', 'ffb6ff', 'ffb4ff',
                                                                'ffb1ff', 'ffafff', 'ffacff', 'ffaaff', 'ffa7ff', 'ffa4ff', 'ffa2ff', 'ff9fff', 'ff9dff', 'ff9aff',
                                                                'ff97ff', 'ff95ff', 'ff92ff', 'ff90ff', 'ff8dff', 'ff8bff', 'ff88ff', 'ff85ff', 'ff83ff', 'ff80ff',
                                                                'ff7eff', 'ff7bff', 'ff79ff', 'ff76ff', 'ff73ff', 'ff71ff', 'ff6eff', 'ff6cff', 'ff69ff', 'ff67ff',
                                                                'ff64ff', 'ff61ff', 'ff5fff', 'ff5cff', 'ff5aff', 'ff57ff', 'ff55ff', 'ff52ff', 'ff4fff', 'ff4dff',
                                                                'ff4aff', 'ff48ff', 'ff45ff', 'ff42ff', 'ff40ff', 'ff3dff', 'ff3bff', 'ff38ff', 'ff36ff', 'ff33ff',
                                                                'ff30ff', 'ff2eff', 'ff2bff', 'ff29ff', 'ff26ff', 'ff24ff', 'ff21ff', 'ff1eff', 'ff1cff', 'ff19ff',
                                                                'ff17ff', 'ff14ff', 'ff12ff', 'ff0fff', 'ff0cff', 'ff0aff', 'ff07ff', 'ff05ff', 'ff02ff', 'ff00ff',
                                                                'ff00ff', 'ff0af4', 'ff15e9', 'ff1fdf', 'ff2ad4', 'ff35c9', 'ff3fbf', 'ff4ab4', 'ff55aa', 'ff5f9f',
                                                                'ff6a94', 'ff748a', 'ff7f7f', 'ff8a74', 'ff946a', 'ff9f5f', 'ffaa55', 'ffb44a', 'ffbf3f', 'ffc935',
                                                                'ffd42a', 'ffdf1f', 'ffe915', 'fff40a', 'ffff00', 'ffff00', 'fffb00', 'fff700', 'fff300', 'fff000',
                                                                'ffec00', 'ffe800', 'ffe400', 'ffe100', 'ffdd00', 'ffd900', 'ffd500', 'ffd200', 'ffce00', 'ffca00',
                                                                'ffc600', 'ffc300', 'ffbf00', 'ffbb00', 'ffb700', 'ffb400', 'ffb000', 'ffac00', 'ffa800', 'ffa500',
                                                                'ffa500', 'f7a400', 'f0a300', 'e8a200', 'e1a200', 'd9a100', 'd2a000', 'ca9f00', 'c39f00', 'bb9e00',
                                                                'b49d00', 'ac9c00', 'a59c00', '9d9b00', '969a00', '8e9900', '879900', '7f9800', '789700', '709700',
                                                                '699600', '619500', '5a9400', '529400', '4b9300', '439200', '349100', '2d9000', '258f00', '1e8e00',
                                                                '168e00', '0f8d00', '078c00', '008c00', '008c00', '008700', '008300', '007f00', '007a00', '007600',
                                                                '007200', '006e00', '006900', '006500', '006100', '005c00', '005800', '005400', '005000', '004c00'],\
                                                                "min":0,"max":200},'NDFI_' + str(dictionaryInfos['date']).replace('-','_')+'_'+dictionaryInfos['satellite_name'],status)
                    
                    except Exception as e:
                    # print('Exception\n',str(e))
                        pass

                    idG = idG + 1 

            for i in range(10):
                
                time.sleep(1)
                progress.setValue(i + 1)
            
            iface.messageBar().clearWidgets()
            Map.addLayer(countourGeometry,{ 'palette': '#000000', 'opacity': 0.8 },str(path) + '_' + str(row))
            
            for item in auxLayers[dicAuxState[uf]][0]:
               
                outline = blankPaint(auxLayers[dicAuxState[uf]][item][1][1])
                Map.addLayer(outline,auxLayers[dicAuxState[uf]][item][1][3],\
                                auxLayers[dicAuxState[uf]][item][1][2], False)
コード例 #32
0
    def CreateMISB(self):
        ''' Create MISB Video '''
        ''' Only tested using DJI Data '''
        # Create ProgressBar
        self.iface.messageBar().clearWidgets()
        progressMessageBar = self.iface.messageBar().createMessage("Creating video packets...")
        progress = QProgressBar()
        progress.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        self.iface.messageBar().pushWidget(progressMessageBar, QGis.Info)
        
        QApplication.setOverrideCursor(Qt.WaitCursor)
        QApplication.processEvents()
                
        HFOV = self.sp_hfov.value()
        #VFOV = self.sp_vfov.value()
        
        index = self.cmb_telemetry.currentIndex()
        out_record = self.cmb_telemetry.itemData(index)
        rowCount = self.GetRows(out_record)
        progress.setMaximum(rowCount)
        
        d = {}
        with open(out_record) as csvfile:
            reader = csv.DictReader(csvfile)
            for row in reader:
                date_start = datetime.strptime(row["CUSTOM.updateTime"], '%Y/%m/%d %H:%M:%S.%f')
                break
        
        with open(out_record) as csvfile:
            reader = csv.DictReader(csvfile)
            for row in reader:
                for k in row:
                    stripK = k.strip()
                    stripV = row[k].strip()
                    d[stripK] = stripV    
            
                # We create the klv file for every moment
                sizeTotal = 0
                bufferData = b''
                cnt = 0

                for k, v in d.items():
                    try:
                        if k == "CUSTOM.updateTime":
                            # We prevent it from failing in the exact times that don't have milliseconds
                            try:
                                date_end = datetime.strptime(v, '%Y/%m/%d %H:%M:%S.%f')
                            except:
                                date_end = datetime.strptime(v, '%Y/%m/%d %H:%M:%S')
    
                            _bytes = datetime_to_bytes(date_end)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key2 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Platform Heading Angle
                        if k == "OSD.yaw":
                            OSD_yaw = float(v)
                            _bytes = float_to_bytes(round(OSD_yaw, 4), _domain5, _range5)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key5 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes   
                        
                        # Platform Pitch Angle
                        if k == "OSD.pitch":
                            OSD_pitch = 0.0
                            _bytes = float_to_bytes(round(OSD_pitch, 4), _domain6, _range6)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key6 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Platform Roll Angle
                        if k == "OSD.roll":
                            OSD_roll = 0.0
                            _bytes = float_to_bytes(round(OSD_roll, 4), _domain7, _range7)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key7 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Sensor Latitude
                        if k == "OSD.latitude":
                            OSD_latitude = float(v)
                            _bytes = float_to_bytes(round(OSD_latitude, 4), _domain13, _range13)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key13 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Sensor Longitude
                        if k == "OSD.longitude":
                            OSD_longitude = float(v)
                            _bytes = float_to_bytes(OSD_longitude, _domain14, _range14)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key14 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes

                        # Sensor True Altitude
                        if k == "OSD.altitude [m]":
                            OSD_altitude = float(v)
                            _bytes = float_to_bytes(round(OSD_altitude, 4), _domain15, _range15)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key15 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Sensor Ellipsoid Height
                        if k == "OSD.height [m]":
                            OSD_height = float(v)
                            _bytes = float_to_bytes(round(OSD_height, 4), _domain75, _range75)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key75 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes
                        
                        # Sensor Relative Azimuth Angle
                        if k == "GIMBAL.yaw":
                            #GIMBAL_yaw = float(v)
                            GIMBAL_yaw = 0.0
                            _bytes = float_to_bytes(round(GIMBAL_yaw, 4), _domain18, _range18)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key18 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes   
                        
                        # Sensor Relative Elevation Angle
                        if k == "GIMBAL.pitch":
                            GIMBAL_pitch = float(v)
                            _bytes = float_to_bytes(round(GIMBAL_pitch, 4), _domain19, _range19)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key19 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes   
                        
                        # Sensor Relative Roll Angle
                        if k == "GIMBAL.roll":
                            GIMBAL_roll = 0.0
                            _bytes = float_to_bytes(round(GIMBAL_roll, 4), _domain20, _range20)
                            _len = int_to_bytes(len(_bytes))
                            _bytes = _key20 + _len + _bytes
                            sizeTotal += len(_bytes)
                            bufferData += _bytes   
                            
                    except Exception:
                        print("Multiplexer error")
                        continue    
                
                try:
                    # Diference time
                    td = date_end - date_start
                    end_path = self.klv_folder + "/%.1f.klv" % (round(td.total_seconds(), 1))
                    
                    # CheckSum
                    v = abs(hash(end_path)) % (10 ** 4)
                    _bytes = int_to_bytes(v, 4)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key1 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                    
                    # Sensor Horizontal Field of View
                    v = self.sp_hfov.value()
                    _bytes = float_to_bytes(float(v), _domain16, _range16)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key16 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                    
                    # Sensor Vertical Field of View
                    v = self.sp_vfov.value()
                    _bytes = float_to_bytes(float(v), _domain17, _range17)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key17 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes

                    # TODO : Check these calculations
                    # Slant Range                    
                    anlge = 180 + (OSD_pitch + GIMBAL_pitch)
                    slantRange = abs(OSD_altitude / (cos(radians(anlge))))
                    
                    _bytes = float_to_bytes(round(slantRange, 4), _domain21, _range21)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key21 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                    
                    # Target Width
                    # targetWidth = 0.0
                    targetWidth = 2.0 * slantRange * tan(radians(HFOV / 2.0)) 
                    
                    _bytes = float_to_bytes(round(targetWidth, 4), _domain22, _range22)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key22 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                    
                    # Frame Center Latitude
                    angle = 90 + (OSD_pitch + GIMBAL_pitch)
                    tgHzDist = OSD_altitude * tan(radians(angle))
                    r_earth = 6371008.8
                    
                    dy =  tgHzDist * cos(radians(OSD_yaw))
                    framecenterlatitude = OSD_latitude  + (dy / r_earth) * (180 / pi)
                    
                    _bytes = float_to_bytes(round(framecenterlatitude, 4), _domain23, _range23)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key23 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                       
                    # Frame Center Longitude
                    dx = tgHzDist * sin(radians(OSD_yaw))
                    framecenterlongitude = OSD_longitude + (dx / r_earth) * (180 / pi) / cos(OSD_latitude * pi/180)
                    
                    _bytes = float_to_bytes(round(framecenterlongitude, 4), _domain24, _range24)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key24 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                    
                    # Frame Center Elevation 
                    frameCenterElevation = 0.0
                    
                    _bytes = float_to_bytes(frameCenterElevation, _domain25, _range25)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key25 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes

                    # TODO : If we save the corners in the klv have a overflow
#                     # CALCULATE CORNERS COORDINATES
#                     sensor = (OSD_longitude, OSD_latitude, OSD_altitude)
#                     frameCenter = (destPoint[0], destPoint[1], frameCenterElevation)
#                     FOV = (VFOV, HFOV)
#                     others = (OSD_yaw, GIMBAL_yaw, targetWidth, slantRange)
#                     cornerPointUL, cornerPointUR, cornerPointLR, cornerPointLL = CornerEstimationWithoutOffsets(sensor=sensor, frameCenter=frameCenter, FOV=FOV, others=others)
#                      
#                     # Corner Latitude Point 1 (Full)
#                     _bytes = float_to_bytes(round(cornerPointUL[0],4), _domain82, _range82)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key82 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                       
#                     # Corner Longitude Point 1 (Full)
#                     _bytes = float_to_bytes(round(cornerPointUL[1],4), _domain83, _range83)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key83 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                       
#                     # Corner Latitude Point 2 (Full) 
#                     _bytes = float_to_bytes(round(cornerPointUR[0],4), _domain84, _range84)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key84 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                       
#                     # Corner Longitude Point 2 (Full) 
#                     _bytes = float_to_bytes(round(cornerPointUR[1],4), _domain85, _range85)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key85 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                       
#                     # Corner Latitude Point 3 (Full)
#                     _bytes = float_to_bytes(round(cornerPointLR[0],4), _domain86, _range86)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key86 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                        
#                     # Corner Longitude Point 3 (Full)
#                     _bytes = float_to_bytes(round(cornerPointLR[1],4), _domain87, _range87)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key87 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                       
#                     # Corner Latitude Point 4 (Full)
#                     _bytes = float_to_bytes(round(cornerPointLL[0],4), _domain88, _range88)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key88 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
#                        
#                     # Corner Longitude Point 4 (Full)
#                     _bytes = float_to_bytes(round(cornerPointLL[1],4), _domain89, _range89)
#                     _len = int_to_bytes(len(_bytes))
#                     _bytes = _key89 + _len + _bytes
#                     sizeTotal += len(_bytes)
#                     bufferData += _bytes
                     
                    # Platform Pitch Angle (Full)
                    _bytes = float_to_bytes(round(OSD_pitch, 4), _domain90, _range90)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key90 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                     
                    # Platform Roll Angle (Full)
                    _bytes = float_to_bytes(round(OSD_roll, 4), _domain91, _range91)
                    _len = int_to_bytes(len(_bytes))
                    _bytes = _key91 + _len + _bytes
                    sizeTotal += len(_bytes)
                    bufferData += _bytes
                            
                    # set packet header
                    writeData = cle
                    writeData += int_to_bytes(sizeTotal)
                    writeData += bufferData
                    
                    # Write packet
                    f_write = open(end_path, "wb+")
                    f_write.write(writeData)
                    f_write.close()
                    
                    cnt += 1
                    
                    progress.setValue(cnt)
                    
                except Exception as e:
                    print("Multiplexer error : " + str(e))   
 
        QApplication.restoreOverrideCursor() 
        QApplication.processEvents()    
        progress.setValue(rowCount)
        self.iface.messageBar().clearWidgets()
        # We add it to the manager
        _, name = os.path.split(self.video_file)
        self.parent.AddFileRowToManager(name, self.video_file, islocal=True, klv_folder=self.klv_folder)
        # Close dialog
        self.close()
        return
コード例 #33
0
    def run(self):
        """Run method that performs all the real work"""
        
        layers = self.iface.mapCanvas().layers()
        layer_list = []
        self.dlg.layerComboBox.clear()
        for layer in layers:
            layer_list.append(layer.name())
        self.dlg.layerComboBox.addItems(layer_list)
        # TODO: Make the active layer the selected item in combo box  aLayer = qgis.utils.iface.activeLayer()
        
        # TODO: Add signal to update toleranceSpinBox.suffix (Degrees) from layerComboBox.crs.mapUnits when layer is selected:
        #my_UnitType = { 0: 'Meters', 1: 'Feet', 2: 'Degrees', 7: 'NauticalMiles', 8: 'Kilometers', 9: 'Yards', 10: 'Miles', 3: 'UnknownUnit'}
        #suffix = my_UnitType[aLayer.crs().mapUnits()]
        
        # show the dialog
        self.dlg.show()
        # Run the dialog event loop
        result = self.dlg.exec_()
        # See if OK was pressed
        if result:
            if self.checkNetworkXModule() < 0:
                return -4
            import networkx as nx
            
            layerName = self.dlg.layerComboBox.currentText()
            try:
                aLayer = QgsProject.instance().mapLayersByName(layerName)[0]
            except:
                self.iface.messageBar().pushMessage("Error", "Failed to load layer!", level=Qgis.Critical)
                return -1

            try:

                previousEditingMode = True
                if not aLayer.isEditable():
                    aLayer.startEditing()
                    #self.iface.messageBar().pushMessage("Info", "Layer " + aLayer.name() + " needs to be in edit mode", level=Qgis.Info)
                    #self.iface.messageBar().pushMessage("Error", "Layer " + aLayer.name() + " needs to be in edit mode", level=Qgis.Critical)
                    #return -2
                    previousEditingMode = False
                     
                attrIdx = self.getAttributeIndex(aLayer)
                if attrIdx < 0:
                    return -3  

                progressMessageBar = self.iface.messageBar().createMessage("Creating network graph...")
                progress = QProgressBar()
                progress.setMaximum(aLayer.featureCount())
                progress.setAlignment(Qt.AlignLeft|Qt.AlignVCenter)
                progressMessageBar.layout().addWidget(progress)
                self.iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)          
                
                G = nx.Graph()

                aLayer.beginEditCommand("Clear group attribute, create graph")
                # construct undirected graph
                tolerance = self.dlg.toleranceSpinBox.value()
                if tolerance == 0:
                    tolerance = 0.000001
                count = 0
                for feat in aLayer.getFeatures():
                    count += 1
                    progress.setValue(count)
                    done = aLayer.changeAttributeValue(feat.id(), attrIdx, -1)
                    geom = feat.geometry()
                    QgsGeometry.convertToSingleType(geom)       # QGIS 3.x seems to load single LineString as MultiLineString??
                    line = geom.asPolyline()
                    
                    for i in range(len(line)-1):
                        G.add_edges_from([((int(line[i][0]/tolerance), int(line[i][1]/tolerance)), (int(line[i+1][0]/tolerance), int(line[i+1][1]/tolerance)), 
                                          {'fid': feat.id()})])     # first scale by tolerance, then convert to int.  Before doing this, there were problems (in NetworkX v1) with floats not equating, thus creating disconnects that weren't there.
                    if count % 100 == 0:
                        QApplication.processEvents()      # keep the UI responsive, every 100 features
                        #TODO: check to see if Esc pressed

                aLayer.endEditCommand()
                
                self.iface.messageBar().pushMessage("Finding connected subgraphs, please wait...",  level=Qgis.Warning)     # WARNING - to highlight the next stage, where we cannot show progress
                QApplication.processEvents()
                connected_components = list(nx.connected_component_subgraphs(G))    # this takes a long time.  TODO: how to show progress?
                self.iface.messageBar().pushMessage("Updating group attribute...",  level=Qgis.Info)
                QApplication.processEvents()
                          
                # gather edges and components to which they belong
                fid_comp = {}
                for i, graph in enumerate(connected_components):
                   for edge in graph.edges(data=True):
                       fid_comp[edge[2].get('fid', None)] = i
                
                # write output to csv file
                #with open('C:/Tmp/Components.csv', 'wb') as f:
                #    w = csv.DictWriter(f, fieldnames=['fid', 'group'])
                #    w.writeheader()
                #    for (fid, group) in fid_comp.items():
                #        w.writerow({'fid': fid, 'group': group})
                
                aLayer.beginEditCommand("Update group attribute")
                for (fid, group) in fid_comp.items():
                    done = aLayer.changeAttributeValue(fid, attrIdx, group)
                aLayer.endEditCommand()
                
                groups = list(set(fid_comp.values()))            
                if self.dlg.stylingCheckBox.isChecked():
                    aLayer.beginEditCommand("Update layer styling")
                    categories = []
                    firstCat = True
                    for cat in groups:
                        symbol = QgsSymbol.defaultSymbol(aLayer.geometryType())
                        symbol.setColor(QColor(randint(0,255), randint(0,255), randint(0,255)))
                        if firstCat:
                            firstCat = False
                        else:
                            symbol.setWidth(symbol.width()*5)
                        category = QgsRendererCategory(cat, symbol, "%d" % cat)
                        categories.append(category)

                    field = self.dlg.attributeNameEditBox.text()
                    renderer = QgsCategorizedSymbolRenderer(field, categories)
                    aLayer.setRenderer(renderer)

#                    if self.iface.mapCanvas().isCachingEnabled():
#                        aLayer.setCacheImage(None)
#                    else:
#                        self.iface.mapCanvas().refresh()
                    aLayer.triggerRepaint()
                    aLayer.endEditCommand()            
                   
                self.iface.messageBar().clearWidgets()   
                self.iface.messageBar().pushMessage("Found main network and %d disconnected islands in layer %s" % (len(groups)-1, aLayer.name()),  level=Qgis.Success)

                aLayer.commitChanges()
#                if not previousEditingMode: 
    
            except Exception as e:
                self.iface.messageBar().pushMessage("Error", "Exception caught: %s.  Please report an issue to the author of the plugin." % repr(e), level=Qgis.Critical)
                
コード例 #34
0
class ThinGreyscaleDialog(QDialog, FORM_CLASS):
    def __init__(self, iface, parent=None):
        """Constructor."""
        self.iface = iface
        self.plugin_dir = dirname(__file__)
        self.THINGREYSCALE = self.tr('ThinGreyscale')
        self.BROWSE = self.tr('Browse')
        self.CANCEL = self.tr('Cancel')
        self.CLOSE = self.tr('Close')
        self.HELP = self.tr('Help')
        self.OK = self.tr('OK')
        self.DEFAULTPROVIDER = 'GTiff'
        self.DEFAULTEXTENSION = '.tif'
        self.EXTRAEXTENSION = ' *.tiff'
        super(ThinGreyscaleDialog, self).__init__(parent)
        # Set up the user interface from Designer.
        # After setupUI you can access any designer object by doing
        # self.<objectname>, and you can use autoconnect slots - see
        # http://qt-project.org/doc/qt-4.8/designer-using-a-ui-file.html
        # #widgets-and-dialogs-with-auto-connect
        self.setupUi(self)

        self.showInfo("Connecting UI components")
        okButton = self.button_box.button(QDialogButtonBox.Ok)
        okButton.setText(self.OK)
        cancelButton = self.button_box.button(QDialogButtonBox.Cancel)
        cancelButton.setText(self.CANCEL)
        cancelButton.setEnabled(False)
        closeButton = self.button_box.button(QDialogButtonBox.Close)
        closeButton.setText(self.CLOSE)
        browseButton = self.browseButton
        browseButton.setText(self.BROWSE)
        self.calcHistPushButton.setEnabled(False)
        self.listModel = QStandardItemModel(self.levelsListView)
        self.levelsListView.setModel(self.listModel)
        self.levelsListView.sizeHintForColumn(20)
        #self.levelValuesCheckBox.setEnabled(False)
        # Help button
        helpButton = self.helpButton
        helpButton.setText(self.HELP)

        # Connect signals
        self.showInfo("Connecting signals")
        okButton.clicked.connect(self.startWorker)
        cancelButton.clicked.connect(self.killWorker)
        closeButton.clicked.connect(self.reject)
        helpButton.clicked.connect(self.help)
        browseButton.clicked.connect(self.browse)

        inpIndexCh = self.inputRaster.currentIndexChanged['QString']
        inpIndexCh.connect(self.layerchanged)
        bandCh = self.bandComboBox.currentIndexChanged['QString']
        bandCh.connect(self.bandChanged)
        #self.iface.legendInterface().itemAdded.connect(
        #    self.layerlistchanged)
        #self.iface.legendInterface().itemRemoved.connect(
        #    self.layerlistchanged)
        #QObject.disconnect(self.button_box, SIGNAL("rejected()"), self.reject)
        self.button_box.rejected.disconnect(self.reject)
        calchistPr = self.calcHistPushButton.clicked
        calchistPr.connect(self.calculateHistogram)
        sugglevPr = self.suggestlevelsPushButton.clicked
        sugglevPr.connect(self.suggestLevels)
        addlevPr = self.addlevelPushButton.clicked
        addlevPr.connect(self.addLevel)
        dellevPr = self.deletelevelsPushButton.clicked
        dellevPr.connect(self.removeLevel)

        maxvalCh = self.maxValueSpinBox.valueChanged
        maxvalCh.connect(self.minmaxvalueChanged)
        maxvalFi = self.maxValueSpinBox.editingFinished
        maxvalFi.connect(self.minmaxvalueEdFinished)
        minvalCh = self.minValueSpinBox.valueChanged
        minvalCh.connect(self.minmaxvalueChanged)
        minvalFi = self.minValueSpinBox.editingFinished
        minvalFi.connect(self.minmaxvalueEdFinished)

        # Set instance variables
        #self.mem_layer = None
        self.worker = None
        self.inputlayerid = None
        self.inputlayer = None
        self.layerlistchanging = False
        self.minvalue = 1
        self.inputrasterprovider = None
        self.histobins = 50
        self.setupScene = QGraphicsScene(self)
        self.histoGraphicsView.setScene(self.setupScene)
        # Is the layer band of an integer type
        self.intband = False
        self.histogramAvailable = False
        self.histo = None
        self.histopadding = 1

    def startWorker(self):
        """Initialises and starts the worker thread."""
        try:
            layerindex = self.inputRaster.currentIndex()
            layerId = self.inputRaster.itemData(layerindex)
            inputlayer = QgsProject.instance().mapLayer(layerId)
            #inputlayer = QgsMapLayerRegistry.instance().mapLayer(layerId)
            if inputlayer is None:
                self.showError(self.tr('No input layer defined'))
                return
            # create a reference to the layer that is being processed
            # (for use when creating the resulting raster layer)
            self.thinninglayer = inputlayer
            self.levels = []
            #self.levelsListView.selectAll()
            #selected = self.levelsListView.selectedIndexes()
            if self.levelsListView.model().rowCount() == 0:
                self.showInfo("Levels must be specified!")
                return
            for i in range(self.levelsListView.model().rowCount()):
                levelstring = self.levelsListView.model().item(i).text()
            #for i in selected:
            #    levelstring = self.levelsListView.model().itemData(i)[0]
                if self.intband:
                    self.levels.append(int(levelstring))
                else:
                    self.levels.append(float(levelstring))
            #self.levelsListView.clearSelection()
            # create a new worker instance
            worker = Worker(inputlayer, self.levels, self.intband)
            # configure the QgsMessageBar
            msgBar = self.iface.messageBar().createMessage(
                                        self.tr('Skeletonising'), '')
            self.aprogressBar = QProgressBar()
            self.aprogressBar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            acancelButton = QPushButton()
            acancelButton.setText(self.CANCEL)
            acancelButton.clicked.connect(self.killWorker)
            msgBar.layout().addWidget(self.aprogressBar)
            msgBar.layout().addWidget(acancelButton)
            # Has to be popped after the thread has finished (in
            # workerFinished).
            self.iface.messageBar().pushWidget(msgBar,
                                        Qgis.Info)
            self.messageBar = msgBar
            # start the worker in a new thread
            thread = QThread(self)
            worker.moveToThread(thread)
            worker.finished.connect(self.workerFinished)
            worker.error.connect(self.workerError)
            worker.status.connect(self.workerInfo)
            worker.progress.connect(self.progressBar.setValue)
            worker.progress.connect(self.aprogressBar.setValue)
            worker.iterprogress.connect(self.iterProgressBar.setValue)
            thread.started.connect(worker.run)
            thread.start()
            self.thread = thread
            self.worker = worker
            self.button_box.button(QDialogButtonBox.Ok).setEnabled(False)
            self.button_box.button(QDialogButtonBox.Close).setEnabled(False)
            self.button_box.button(QDialogButtonBox.Cancel).setEnabled(True)
        except:
            import traceback
            self.showError(traceback.format_exc())
        else:
            pass

    def workerFinished(self, ok, ret):
        """Handles the output from the worker and cleans up after the
           worker has finished."""
        # clean up the worker and thread
        self.showInfo("Handling the result")
        self.worker.deleteLater()
        self.thread.quit()
        self.thread.wait()
        self.thread.deleteLater()
        # remove widget from message bar (pop)
        self.iface.messageBar().popWidget(self.messageBar)
        if ok and ret is not None:
            #self.showInfo("Ret: "+str(ret[10,]))
            # Transformation:
            self.minx = self.thinninglayer.extent().xMinimum()
            self.maxx = self.thinninglayer.extent().xMaximum()
            self.miny = self.thinninglayer.extent().yMinimum()
            self.maxy = self.thinninglayer.extent().yMaximum()
            self.rows = self.thinninglayer.height()
            self.cols = self.thinninglayer.width()
            self.xres = (self.maxx - self.minx) / float(self.cols)
            self.yres = (self.maxy - self.miny) / float(self.rows)
            geotransform = (self.minx, self.xres, 0, self.maxy, 0, -self.yres)
            try:
                format = self.DEFAULTPROVIDER
                driver = gdal.GetDriverByName(format)
                NOVALUE = 0
                metadata = driver.GetMetadata()
                fileName = self.outputRaster.text()
                if self.outputRaster.text() == "":
                    self.showInfo("No output file specified, " +
                                         "creating a temporary file")
                    # Get a temporary file
                    fileName = mktemp(prefix='greyskel',
                           suffix=self.DEFAULTEXTENSION)
                fileInfo = QFileInfo(fileName)
                filepath = fileInfo.absolutePath()
                baseName = fileInfo.baseName()
                suffix = fileInfo.suffix()
                thisfilename = filepath + baseName + '.' + suffix
                thisfilename = fileName
                self.showInfo("File name: " + thisfilename)
                gdaldatatype = gdal.GDT_Byte
                skelmatrix = None
                if self.levelValuesCheckBox.isChecked():
                    # Transform the pixel values back to the original
                    # level values
                    my_dict = {}
                    # Add zero to handle the "empty" pixels
                    my_dict[0] = 0
                    for i in range(len(self.levels)):
                        my_dict[i + 1] = self.levels[i]
                    skelmatrix = np.vectorize(my_dict.__getitem__,
                                              otypes=[np.float])(ret)
                    gdaldatatype = gdal.GDT_Int32
                    if not self.intband:
                        gdaldatatype = gdal.GDT_Float32
                else:
                    skelmatrix = ret
                outDataset = driver.Create(thisfilename, self.cols,
                                           self.rows, 1, gdaldatatype)
                if self.thinninglayer.dataProvider().crs() is not None:
                    srs = self.thinninglayer.dataProvider().crs()
                    outDataset.SetProjection(srs.toWkt().encode('ascii',
                                                               'ignore'))
                skeletonband = outDataset.GetRasterBand(1)
                skeletonband.WriteArray(skelmatrix)
                skeletonband.SetNoDataValue(NOVALUE)
                #stats = skeletonband.GetStatistics(False, True)
                #skeletonband.SetStatistics(stats[0], stats[1],
                #                                 stats[2], stats[3])
                outDataset.SetGeoTransform(geotransform)
                outDataset = None  # To close the file
                # report the result
                rlayer = QgsRasterLayer(thisfilename, baseName)
                self.layerlistchanging = True
                #QgsMapLayerRegistry.instance().addMapLayer(rlayer)
                QgsProject.instance().addMapLayer(rlayer)
                self.layerlistchanging = False
            except:
                import traceback
                self.showError("Can't write the skeleton file:  %s" %
                                   self.outputRaster.text() + ' - ' +
                                   traceback.format_exc())
                okb = self.button_box.button(QDialogButtonBox.Ok)
                okb.setEnabled(True)
                closb = self.button_box.button(QDialogButtonBox.Close)
                closb.setEnabled(True)
                cancb = self.button_box.button(QDialogButtonBox.Cancel)
                cancb.setEnabled(False)
                return
            QgsMessageLog.logMessage(self.tr('ThinGreyscale finished'),
                                self.THINGREYSCALE, Qgis.Info)
        else:
            # notify the user that something went wrong
            if not ok:
                self.showError(self.tr('Aborted') + '!')
            else:
                self.showError(self.tr('No skeleton created') + '!')
        self.progressBar.setValue(0.0)
        #self.aprogressBar.setValue(0.0)
        self.iterProgressBar.setValue(0.0)
        self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
        self.button_box.button(QDialogButtonBox.Close).setEnabled(True)
        self.button_box.button(QDialogButtonBox.Cancel).setEnabled(False)

    def workerError(self, exception_string):
        """Report an error from the worker."""
        #QgsMessageLog.logMessage(self.tr('Worker failed - exception') +
        #                         ': ' + str(exception_string),
        #                         self.THINGREYSCALE,
        #                         QgsMessageLog.CRITICAL)
        self.showError(exception_string)

    def workerInfo(self, message_string):
        """Report an info message from the worker."""
        QgsMessageLog.logMessage(self.tr('Worker') + ': ' + message_string,
                                 self.THINGREYSCALE, Qgis.Info)

    def layerchanged(self, number=0):
        """Do the necessary updates after a layer selection has
           been changed."""
        self.showInfo("Layer changed")
        # If the layer list is being updated, don't do anything
        if self.layerlistchanging:
            return
        layerindex = self.inputRaster.currentIndex()
        layerId = self.inputRaster.itemData(layerindex)
        self.inputlayerid = layerId
        #self.inputlayer = QgsMapLayerRegistry.instance().mapLayer(layerId)
        self.inputlayer = QgsProject.instance().mapLayer(layerId)
        if self.inputlayer is not None:
            self.inputrasterprovider = self.inputlayer.dataProvider()
            self.bandComboBox.clear()
            bandcount = self.inputlayer.bandCount()
            #self.showInfo("Layer bandcount: "+str(bandcount))
            for i in range(bandcount):
                self.bandComboBox.addItem(self.inputlayer.bandName(i + 1), i)
                #self.showInfo("Band " + str(i) + ": " +
                #                self.inputlayer.bandName(i+1))
            # Check if the driver supports Create() or CreateCopy()
            #gdalmetadata = self.inputlayer.metadata()
            #self.showInfo("Layer metadata: " +
            #                str(gdalmetadata.encode('utf-8')))
            #provstring = '<p>GDAL provider</p>\n'
            #providerpos = gdalmetadata.find(provstring)
            #brpos = gdalmetadata.find('<br>', providerpos + len(provstring))
            #self.gdalprovider = gdalmetadata[int(providerpos +
            #                             len(provstring)):int(brpos)]
            #self.showInfo('GDAL provider: '+self.gdalprovider)
            #drivername = self.gdalprovider.encode('ascii', 'ignore')
            #theDriver = gdal.GetDriverByName(drivername)
            #if theDriver is None:
            #    self.showInfo("Unable to get the raster driver")
            #else:
            #data    theMetadata = theDriver.GetMetadata()
                #self.showInfo("Driver metadata: "+str(theMetadata))
                #if ((gdal.DCAP_CREATE in theMetadata) and
                #        theMetadata[gdal.DCAP_CREATE] == 'YES'):
                #    self.canCreate = True
                #if (theMetadata.has_key(gdal.DCAP_CREATECOPY) and
                #if ((gdal.DCAP_CREATECOPY in theMetadata) and
                #        theMetadata[gdal.DCAP_CREATECOPY] == 'YES'):
                #    self.canCreateCopy = True
                #self.showInfo('raster provider type: ' +
                #                str(self.inputlayer.providerType()))
                # Determine the file suffix
                #self.gdalext = ""
                #if gdal.DMD_EXTENSION in theMetadata:
                #    self.gdalext = "." + theMetadata[gdal.DMD_EXTENSION]
                #else:
                #    self.showInfo("No extension available in GDAL metadata")
                # by parsing the layer metadata looking for
                #           "Dataset Description"
                #descstring = 'Dataset Description</p>\n<p>'
                #descpos = gdalmetadata.find(descstring)
                #ppos = gdalmetadata.find('</p>',descpos+len(descstring))
                #filename = gdalmetadata[descpos+len(descstring):ppos]
                #self.gdalext = splitext(filename)[1]
                #self.showInfo('GDAL extension: '+self.gdalext)
                # Determine the datatype
                #datatypestring = 'Data Type</p>\n<p>'
                #datatypepos = gdalmetadata.find(datatypestring)
                #ppos = gdalmetadata.find('</p>',
                #                   datatypepos + len(datatypestring))
                #datatypedesc = gdalmetadata[datatypepos +
                #                            len(datatypestring):ppos]
                #shortdesc = datatypedesc.split()[0]
                #self.showInfo('GDAL data type: GDT_'+shortdesc)
                # Call the findGdalDatatype function
                #self.findGdalDatatype(shortdesc)
            #   self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
            self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
            self.calcHistPushButton.setEnabled(True)
            self.suggestlevelsPushButton.setEnabled(True)

    def bandChanged(self):
        band = self.bandComboBox.currentIndex() + 1
        self.showInfo("Band changed: " + str(band))
        statistics = self.inputrasterprovider.bandStatistics(band)
        #self.showInfo("Band statistics: " + str(statistics.minimumValue) +
        #                            " - " + str(statistics.maximumValue) +
        #                            " - " + str(statistics.mean))
        self.bandmin = statistics.minimumValue
        self.bandmax = statistics.maximumValue
        dt = self.inputrasterprovider.dataType(band)
        # Integer data type
        if (dt == Qgis.Byte or dt == Qgis.UInt16 or dt == Qgis.Int16
                            or dt == Qgis.UInt32 or dt == Qgis.Int32):
            self.intband = True
            self.minValueSpinBox.setDecimals(0)
            self.maxValueSpinBox.setDecimals(0)
            self.levelSpinBox.setDecimals(0)
            self.bandMinLabel.setText(str(int(statistics.minimumValue)))
            self.bandMaxLabel.setText(str(int(statistics.maximumValue)))
        else:
            self.intband = False
            self.minValueSpinBox.setDecimals(5)
            self.maxValueSpinBox.setDecimals(5)
            self.levelSpinBox.setDecimals(5)
            minlabtext = "{0:.5f}".format(statistics.minimumValue)
            self.bandMinLabel.setText(minlabtext)
            maxlabtext = "{0:.5f}".format(statistics.maximumValue)
            self.bandMaxLabel.setText(maxlabtext)
        #self.minValueSpinBox.setMinimum(statistics.minimumValue)
        self.maxValueSpinBox.setMinimum(statistics.minimumValue)
        #self.minValueSpinBox.setMaximum(statistics.maximumValue)
        self.maxValueSpinBox.setMaximum(statistics.maximumValue)
        #self.minValueSpinBox.setValue(statistics.minimumValue)
        if not (statistics.statsGathered & statistics.Mean):
            bandmean = (statistics.minimumValue + statistics.maximumValue) / 2
        else:
            #self.showInfo("statsgathered: " + str(statistics.statsGathered))
            bandmean = statistics.mean
        if self.intband:
            self.minValueSpinBox.setValue(int(ceil(bandmean)))
        else:
            self.minValueSpinBox.setValue(bandmean)
        self.maxValueSpinBox.setValue(statistics.maximumValue)
        self.histMinValue.setText(str(statistics.minimumValue))
        self.histMaxValue.setText(str(statistics.maximumValue))
        self.levelSpinBox.setMinimum(statistics.minimumValue)
        self.levelSpinBox.setMaximum(statistics.maximumValue)
        self.histogramAvailable = False
        #if self.inputrasterprovider.hasStatistics(band):
        #if statistics.statsGathered:
            #histogram = statistics.histogramVector
            #self.showInfo("Histogram: " + str(histogram))
            #range = min to max
            #np.histogram(band, 50, range)

    def minmaxvalueChanged(self):
        #if self.minValueSpinBox is None:
        #    return
        minvalue = self.minValueSpinBox.value()
        #if minvalue is None:
        #    return
        #if self.maxValueSpinBox is None:
        #    return
        maxvalue = self.maxValueSpinBox.value()
        #if maxvalue is None:
        #   return
        if isnan(maxvalue) or isnan(minvalue):
            return
        self.showInfo("minvalue: " + str(minvalue) + " Maxvalue: " +
                                                       str(maxvalue))
        #if self.intband:
        #    minvalue = int(minvalue)
        #    maxvalue = int(maxvalue)
        if abs(maxvalue - minvalue) < 0.00001:
        #if maxvalue == maxvalue:
            self.calcHistPushButton.setEnabled(False)
        else:
            self.calcHistPushButton.setEnabled(True)
        # Update the min and max value spinboxes
        self.minValueSpinBox.setMaximum(maxvalue)
        self.maxValueSpinBox.setMinimum(minvalue)
        self.minValueSpinBox.setMinimum(self.bandmin)

    def minmaxvalueEdFinished(self):
        minvalue = self.minValueSpinBox.value()
        maxvalue = self.maxValueSpinBox.value()
        if self.intband:
            minvalue = int(minvalue)
            maxvalue = int(maxvalue)
        self.showInfo("minvalue: " + str(minvalue) + " Maxvalue: " +
                                    str(maxvalue))
        # Update the spin box for adding levels
        self.levelSpinBox.setMinimum(minvalue)
        self.levelSpinBox.setMaximum(maxvalue)
        if self.levelSpinBox.value() < minvalue:
            self.levelSpinBox.setValue(minvalue)
        if self.levelSpinBox.value() > maxvalue:
            self.levelSpinBox.setValue(maxvalue)
        # Update the min and max value spinboxes
        self.minValueSpinBox.setMaximum(maxvalue)
        self.maxValueSpinBox.setMinimum(minvalue)

        # Adjust the levels:
        i = 0
        while self.levelsListView.model().item(i):
        #for i in range(self.levelsListView.model().rowCount()):
            #self.showInfo("Element: " +
            #       str(self.levelsListView.model().item(i).text()))
            #continue
            value = float(self.levelsListView.model().item(i).text())
            if value < minvalue:
                if i == 0:
                    self.levelsListView.model().item(i).setText(str(minvalue))
                    i = i + 1
                else:
                    self.levelsListView.model().removeRow(i)
            elif value > maxvalue:
                if i == self.levelsListView.model().rowCount() - 1:
                    self.levelsListView.model().item(i).setText(str(maxvalue))
                    i = i + 1
                else:
                    self.levelsListView.model().removeRow(i)
            else:
                i = i + 1
        self.drawHistogram()

    def calculateHistogram(self):
        self.showInfo("Calculating histogram...")
        if self.inputlayer is None:
            return
        
        self.showInfo("Calculating histogram...")
        # Check if there is only one value
        myrange = (self.minValueSpinBox.value(),
                   self.maxValueSpinBox.value())
        self.inputextent = self.inputlayer.extent()
        self.inputrdp = self.inputlayer.dataProvider()
        width = self.inputlayer.width()
        height = self.inputlayer.height()
        if width == 0 or height == 0:
            self.showInfo("Image has zero width or height")
            return
        extwidth = self.inputextent.width()
        extheight = self.inputextent.height()
        # Read the raster block and get the maximum value
        rasterblock = self.inputrdp.block(1, self.inputextent,
                                          width, height)
        # Create a numpy array version of the image
        imageMat = np.zeros((height, width), dtype=np.float16)
        # This one takes a lot of time!
        for row in range(height):
            for column in range(width):
                imageMat[row, column] = rasterblock.value(row, column)
                self.showInfo("Image: " + str(height) + ", " + str(width) + " - " + str(imageMat[row, column]))
        self.histo = np.histogram(imageMat, self.histobins, myrange)
        #relevantpixels = imageMat[np.where(imageMat >= bandval)]
        minlevel = float(self.bandMinLabel.text())
        relevantpixels = imageMat[np.where(imageMat >= minlevel)]
        #self.showInfo("Histogram: " + str(self.histo))
        nanpercentage = 100.0 - 100.0 * len(relevantpixels) / (width * height)
        self.bandNANLabel.setText("{0:.1f}".format(nanpercentage))
        #self.showInfo("Percentage NAN: " + str(100.0 - 100.0 *
        #                    len(relevantpixels) / (width * height)))
        #self.showInfo("First element: " + str(self.histo[0]))
        #self.showInfo("First element, first: " + str(self.histo[0][0]))
        #self.showInfo("First element, second: " + str(self.histo[0][1]))
        self.histMinValue.setText(str(self.minValueSpinBox.value()))
        self.histMaxValue.setText(str(self.maxValueSpinBox.value()))
        if self.intband:
            self.histMinValue.setText(str(int(self.minValueSpinBox.value())))
            self.histMaxValue.setText(str(int(self.maxValueSpinBox.value())))
        self.histogramAvailable = True
        self.drawHistogram()

    def drawHistogram(self):
        #if self.inputlayer is None:
        #    return
        self.showInfo("Drawing histogram...")
        viewprect = QRectF(self.histoGraphicsView.viewport().rect())
        self.histoGraphicsView.setSceneRect(viewprect)
        self.setupScene.clear()
        self.setupScene.update()
        histbottom = self.histoGraphicsView.sceneRect().bottom()
        histtop = self.histoGraphicsView.sceneRect().top()
        left = self.histoGraphicsView.sceneRect().left() + self.histopadding
        right = self.histoGraphicsView.sceneRect().right() - self.histopadding
        histheight = histbottom - histtop
        histwidth = right - left
        step = 1.0 * histwidth / self.histobins
        maxlength = histheight
        padding = 1
        ll = QPoint(self.histopadding - 1, histheight - padding)
        start = QPointF(self.histoGraphicsView.mapToScene(ll))

        # Check if there is only one value
        #myrange = (self.minValueSpinBox.value(),self.maxValueSpinBox.value())
        if self.histogramAvailable:
            maxvalue = 0.0
            for i in range(len(self.histo[0])):
                if self.histo[0][i] > maxvalue:
                    maxvalue = self.histo[0][i]
            if maxvalue == 0:
                return
            self.maxBinNumber.setText(str(maxvalue))
            # Create the histogram:
            #self.showInfo("maxvalue: " + str(maxvalue))
            #self.showInfo("maxlength: " + str(maxlength))
            #self.showInfo("step: " + str(step))
            for i in range(self.histobins):
                binnumber = self.histo[0][i]
                if binnumber == 0:
                    continue
                height = (1.0 * self.histo[0][i] / maxvalue *
                                          (maxlength - padding))
                rectangle = QGraphicsRectItem(start.x() + step * i,
                                          start.y(),
                                          step,
                                          -height)
                rectangle.setPen(QPen(QColor(102, 102, 102)))
                rectangle.setBrush(QBrush(QColor(240, 240, 240)))
                self.setupScene.addItem(rectangle)
                #self.showInfo(str(i) + ": " + str(height))
            #if self.levelsListView.model().rowCount() > 0:
        # Add lines for the levels
        minvalue = float(self.histMinValue.text())
        maxvalue = float(self.histMaxValue.text())
        datarange = maxvalue - minvalue
        if datarange == 0:
            return
        i = 0
        while self.levelsListView.model().item(i):
            #self.showInfo("Element: " +
            #       str(self.levelsListView.model().item(i).text()))
            #continue
            value = float(self.levelsListView.model().item(i).text())
            xvalue = start.x() + histwidth * (value - minvalue) / datarange
            line = QGraphicsLineItem(xvalue, 0, xvalue, histheight)
            if i == 0 or i == (self.levelsListView.model().rowCount() - 1):
                line.setPen(QPen(QColor(204, 0, 0)))
            else:
                line.setPen(QPen(QColor(0, 204, 0)))
            self.setupScene.addItem(line)
            i = i + 1

    def suggestLevels(self):
        self.listModel.clear()
        self.showInfo("Suggesting levels")
        levels = self.levelsSpinBox.value()
        startvalue = self.minValueSpinBox.value()
        endvalue = self.maxValueSpinBox.value()
        increment = (endvalue - startvalue) / levels
        for i in range(levels + 1):
            value = startvalue + increment * i
            if self.intband:
                value = int(value)
            item = QStandardItem(str(value))
            self.listModel.appendRow(item)
        self.drawHistogram()

    def addLevel(self):
        newvalue = self.levelSpinBox.value()
        if self.intband:
            newvalue = int(newvalue)
        for i in range(self.listModel.rowCount()):
            # Check if the value is already in the list
            if self.listModel.item(i).text() == str(newvalue):
                return
            else:
                # Maintain a sorted list of distances
                if (float(self.listModel.item(i).text()) >
                                 float(str(newvalue))):
                    item = QStandardItem(str(newvalue))
                    self.listModel.insertRow(i, item)
                    self.drawHistogram()
                    return
        item = QStandardItem(str(newvalue))
        self.listModel.appendRow(item)
        #if self.histogramAvailable:
        #    addLevelsToHistogram()
        self.drawHistogram()

    def removeLevel(self):
        self.levelsListView.setUpdatesEnabled(False)
        indexes = self.levelsListView.selectedIndexes()
        indexes.sort()
        for i in range(len(indexes) - 1, -1, -1):
            self.listModel.removeRow(indexes[i].row())
        self.levelsListView.setUpdatesEnabled(True)
        #if self.histogramAvailable:
        #    removeLevelFromHistogram()
        self.drawHistogram()

    def layerlistchanged(self):
        self.layerlistchanging = True
        self.showInfo("Layer list changed")
        # Repopulate the input layer combo box
        # Save the currently selected input layer
        inputlayerid = self.inputlayerid
        self.inputRaster.clear()
        for alayer in self.iface.legendInterface().layers():
            if alayer.type() == QgsMapLayer.RasterLayer:
                gdalmetadata = alayer.metadata()
                # Skip WMS layers
                WMSstring = 'Web Map Service'
                wmspos = gdalmetadata.find(WMSstring)
                if wmspos != -1:
                    continue
                self.inputRaster.addItem(alayer.name(), alayer.id())
        # Set the previous selection
        for i in range(self.inputRaster.count()):
            if self.inputRaster.itemData(i) == inputlayerid:
                self.inputRaster.setCurrentIndex(i)
        self.layerlistchanging = False
        #self.updateui()

    def updateui(self):
        """Do the necessary updates after a layer selection has
           been changed."""
        #if self.layerlistchanged:
        #    return
        #self.outputRaster.setText(self.inputRaster.currentText() +
        #                           '_' + 'thinned')
        layerindex = self.inputRaster.currentIndex()
        layerId = self.inputRaster.itemData(layerindex)
        #inputlayer = QgsMapLayerRegistry.instance().mapLayer(layerId)
        inputlayer = QgsProject.instance().mapLayer(layerId)
        if inputlayer is not None:
            pass
        else:
            pass

    def findGdalDatatype(self, shortdesc):
            gdaldatatype = None
            # // Unknown or unspecified type
            # GDT_Unknown = GDALDataType(C.GDT_Unknown)
            if shortdesc == 'Unknown':
                gdaldatatype = gdal.GDT_Unknown
            # // Eight bit unsigned integer
            # GDT_Byte = GDALDataType(C.GDT_Byte)
            elif shortdesc == 'Byte':
                gdaldatatype = gdal.GDT_Byte
            # // Sixteen bit unsigned integer
            # GDT_UInt16 = GDALDataType(C.GDT_UInt16)
            elif shortdesc == 'UInt16':
                gdaldatatype = gdal.GDT_UInt16
            # // Sixteen bit signed integer
            # GDT_Int16 = GDALDataType(C.GDT_Int16)
            elif shortdesc == 'Int16':
                gdaldatatype = gdal.GDT_Int16
            # // Thirty two bit unsigned integer
            # GDT_UInt32 = GDALDataType(C.GDT_UInt32)
            elif shortdesc == 'UInt32':
                gdaldatatype = gdal.GDT_UInt32
            # // Thirty two bit signed integer
            # GDT_Int32 = GDALDataType(C.GDT_Int32)
            elif shortdesc == 'Int32':
                gdaldatatype = gdal.GDT_Int32
            # // Thirty two bit floating point
            # GDT_Float32 = GDALDataType(C.GDT_Float32)
            elif shortdesc == 'Float32':
                gdaldatatype = gdal.GDT_Float32
            # // Sixty four bit floating point
            # GDT_Float64 = GDALDataType(C.GDT_Float64)
            elif shortdesc == 'Float64':
                gdaldatatype = gdal.GDT_Float64
            # // Complex Int16
            # GDT_CInt16 = GDALDataType(C.GDT_CInt16)
            elif shortdesc == 'CInt16':
                gdaldatatype = gdal.CInt16
            # // Complex Int32
            # GDT_CInt32 = GDALDataType(C.GDT_CInt32)
            elif shortdesc == 'CInt32':
                gdaldatatype = gdal.CInt32
            # // Complex Float32
            # GDT_CFloat32 = GDALDataType(C.GDT_CFloat32)
            elif shortdesc == 'CFloat32':
                gdaldatatype = gdal.CFloat32
            # // Complex Float64
            # GDT_CFloat64 = GDALDataType(C.GDT_CFloat64)
            elif shortdesc == 'CFloat64':
                gdaldatatype = gdal.CFloat64
            # // maximum type # + 1
            # GDT_TypeCount = GDALDataType(C.GDT_TypeCount)
            elif shortdesc == 'TypeCount':
                gdaldatatype = gdal.TypeCount
            self.gdaldatatype = gdaldatatype

    def killWorker(self):
        """Kill the worker thread."""
        if self.worker is not None:
            QgsMessageLog.logMessage(self.tr('Killing worker'),
                                     self.THINGREYSCALE, Qgis.Info)
            self.worker.kill()

    def showError(self, text):
        """Show an error."""
        self.iface.messageBar().pushMessage(self.tr('Error'), text,
                                            level=QgsMessageBar.CRITICAL,
                                            duration=3)
        QgsMessageLog.logMessage('Error: ' + text, self.THINGREYSCALE,
                                 QgsMessageLog.CRITICAL)

    def showWarning(self, text):
        """Show a warning."""
        self.iface.messageBar().pushMessage(self.tr('Warning'), text,
                                            level=QgsMessageBar.WARNING,
                                            duration=2)
        QgsMessageLog.logMessage('Warning: ' + text, self.THINGREYSCALE,
                                 QgsMessageLog.WARNING)

    def showInfo(self, text):
        """Show info."""
        self.iface.messageBar().pushMessage(self.tr('Info'), text,
                                            level=Qgis.Info,
                                            duration=2)
        QgsMessageLog.logMessage('Info: ' + text, self.THINGREYSCALE,
                                 Qgis.Info)

    # def help(self):
        # #QDesktopServices.openUrl(QUrl.fromLocalFile(self.plugin_dir +
        #                                 "/help/build/html/index.html"))
        # QDesktopServices.openUrl(QUrl.fromLocalFile(self.plugin_dir +
        #                                            "/help/index.html"))
        # #showPluginHelp()

    def tr(self, message):
        """Get the translation for a string using Qt translation API.

        :param message: String for translation.
        :type message: str, QString

        :returns: Translated version of message.
        :rtype: QString
        """
        return QCoreApplication.translate('ThinGreyScaleDialog', message)

    def browse(self):
        settings = QSettings()
        key = '/UI/lastShapefileDir'
        outDir = settings.value(key)
        home = outDir
        #outDir = expanduser("~")
        #filter = (self.DEFAULTPROVIDER + " (*" +
        #             self.DEFAULTEXTENSION + ");;All files (*)")
        filter = (self.DEFAULTPROVIDER + " (*" +
                     self.DEFAULTEXTENSION + self.EXTRAEXTENSION + ")")
        #if (self.gdalprovider != self.DEFAULTPROVIDER and
        #                                     (self.canCreateCopy or
        #                                           self.canCreate)):
        #    filter = (self.gdalprovider + " (*" + self.gdalext +
        #                                          ");;" + filter)
        outFilePath = QFileDialog.getSaveFileName(self,
                                   'Specify file name for skeleton',
                                                     outDir, filter)
        outFilePath = unicode(outFilePath)
        if outFilePath:
            root, ext = splitext(outFilePath)
            if ext.lower() != '.tif' and ext.lower() != '.tiff':
                outFilePath = '%s.tif' % outFilePath
            outDir = dirname(outFilePath)
            settings.setValue(key, outDir)
        #        (self.canCreateCopy or self.canCreate):
        #    fileName = splitext(str(fileName))[0]+self.gdalext
        self.outputRaster.setText(outFilePath)

    # Overriding
    def resizeEvent(self, event):
        #self.showInfo("resizeEvent")
        self.calculateHistogram()

    def help(self):
        #QDesktopServices.openUrl(QUrl.fromLocalFile(
        #                 self.plugin_dir + "/help/html/index.html"))
        showPluginHelp(None, "help/html/index")

    # Implement the accept method to avoid exiting the dialog when
    # starting the work
    def accept(self):
        """Accept override."""
        pass

    # Implement the reject method to have the possibility to avoid
    # exiting the dialog when cancelling
    def reject(self):
        """Reject override."""
        # exit the dialog
        QDialog.reject(self)
コード例 #35
0
    def processRequest(self):
        #iface.messageBar().pushMessage("BC TRO API", "Processing Request", level=0)

        progressMessageBar = iface.messageBar().createMessage("Processing Request...")
        progress = QProgressBar()
        progress.setMaximum(100)
        progress.setAlignment(Qt.AlignLeft|Qt.AlignVCenter)
        progressMessageBar.layout().addWidget(progress)
        iface.messageBar().pushWidget(progressMessageBar, Qgis.Info)

        #API Code here
        apilayer = 'bctroapi'
        maplayerName = "BC TRO"
        layers_names = []
        lopen = False
        for layer in QgsProject.instance().mapLayers().values():
            if layer.name() == maplayerName:
                lopen = True
            layers_names.append(layer.name())
        progress.setValue(10)
        #Params from dialog
        troformat = str(self.dlg.Formatcombobox.currentText())
        area = self.dlg.AreaTextBox.text()
        radius = "{}".format(self.dlg.RadiusSlider.value())
        x = self.dlg.Xtextbox.text()
        y = self.dlg.Ytextbox.text()
        epsg = str(self.dlg.Projectioncombobox.currentText()) #self.iface.mapCanvas().mapSettings().destinationCrs().authid()
        api_token = self.dlg.APIKeyTextBox.text()
        progress.setValue(20)
        time.sleep(0.5)
        #Set EPSG value as expected by TRO API
        if "27700" in epsg:
            epsg = "27700"
        elif "4326" in epsg:
            epsg = "4326"
        elif "3857" in epsg:
            epsg = "3857"
        else:
            return;
        progress.setValue(25)
        #Construct request parameters
        payload = {'api_token':api_token,'epsg': epsg, 'x': x, 'y': y, 'radius': radius}
        print ("API Payload: {}".format(payload))

        #Set Endpoint from troformat
        if troformat == "TRO-D":
            url = 'https://dev.trafficorders.uk/tro/v1/trod'
        else:
            url = 'https://dev.trafficorders.uk/tro/v1/{}'.format(troformat.lower())

        progress.setValue(30)
        # Send Request
        print ("Sending Request...")
        try:
            response = requests.get(url,params=payload)
            print ("Normal Request Success")
        except:
            print ("Normal Request Failed")
            """try:
                response = requests.get(url,params=payload, verify ='IONOS_trafficorders.uk.pem')
                print ("PEM File Request Success")
            except:
                print ("PEM File Request Failed")"""
            try:
                response = requests.get(url,params=payload, verify = False)
                print ("Verify Request Success")
            except:
                print ("Verify Request Failed")
                QMessageBox.critical(self.iface.mainWindow(),
                        "BC TRO API error",
                            "The request processed unsuccesfully!\n\n"
                                "Error Code:\n"
                                "Unable to send GET request")
                iface.messageBar().clearWidgets()
                return

        progress.setValue(50)
        print(response.url)
        print("Status: {}".format(response.status_code))

        #Check request status for error
        if response.status_code != 200:
            QMessageBox.critical(self.iface.mainWindow(),
                "BC TRO API error",
                    "The request processed unsuccesfully!\n\n"
                        "Error Code:\n"
                        "{}".format(response.status_code))
            iface.messageBar().clearWidgets()
            return
        progress.setValue(60)
        #Convert JSON to Geojson
        r_json = self.geojsontojson(response.json(),troformat)
        progress.setValue(70)

        #Save Converted Geojson to file
        path_to_tro_layer = os.path.join(self.temp_dir,"bcnativedata.geojson")

        print ("Write Geojson...")
        with open(path_to_tro_layer, "w") as outfile:
            outfile.write(r_json)
        progress.setValue(80)
        ExitMessage = ''
        #Map geojson file
        #print("{}".format(self.currentformat))
        #print(troformat)
        if not lopen:
            #Open file
            print ("Open Geojson...")
            if not self.addTROlayers(path_to_tro_layer,epsg,maplayerName,troformat):
                ExitMessage = 'Layer Failed'
            else:
                self.currentformat = troformat
                ExitMessage = 'Layer added to map'

        elif self.currentformat != troformat:
            print ("Rebuild table format...")

            #Remove Layer
            vlayers = QgsProject.instance().mapLayersByName(maplayerName)
            for vlayer in vlayers:
                QgsProject.instance().removeMapLayer(vlayer.id())

            #Add - Rebuilding Table structure
            if not self.addTROlayers(path_to_tro_layer,epsg,maplayerName,troformat):
                ExitMessage = 'Layer Failed'
            else:
                self.currentformat = troformat
                ExitMessage = 'Layer added to map - Format change'
        else:
            print ("Reload Geojson...")

            #Refresh Layer
            vlayers = QgsProject.instance().mapLayersByName(maplayerName)
            for vlayer in vlayers:
                vlayer.dataProvider().reloadData()
                vlayer.triggerRepaint()

            ExitMessage = 'Layer refreshed'
        progress.setValue(100)
        #Show Exit message
        iface.messageBar().clearWidgets()
        iface.messageBar().pushMessage("BC TRO API", ExitMessage, level=3)
コード例 #36
0
class NNJoinDialog(QDialog, FORM_CLASS):
    def __init__(self, iface, parent=None):
        """Constructor."""
        self.iface = iface
        self.plugin_dir = dirname(__file__)
        # Some translated text (to enable reuse)
        self.NNJOIN = self.tr('NNJoin')
        self.CANCEL = self.tr('Cancel')
        self.CLOSE = self.tr('Close')
        self.HELP = self.tr('Help')
        self.OK = self.tr('OK')
        super(NNJoinDialog, self).__init__(parent)
        # Set up the user interface from Designer.
        # After setupUI you can access any designer object by doing
        # self.<objectname>, and you can use autoconnect slots - see
        # http://qt-project.org/doc/qt-4.8/designer-using-a-ui-file.html#\
        # widgets-and-dialogs-with-auto-connect
        self.setupUi(self)
        # Modify ui components
        okButton = self.button_box.button(QDialogButtonBox.Ok)
        okButton.setText(self.OK)
        self.cancelButton = self.button_box.button(QDialogButtonBox.Cancel)
        self.cancelButton.setText(self.CANCEL)
        closeButton = self.button_box.button(QDialogButtonBox.Close)
        closeButton.setText(self.CLOSE)
        self.approximate_input_geom_cb.setCheckState(Qt.Unchecked)
        self.approximate_input_geom_cb.setVisible(False)
        stytxt = "QCheckBox:checked {color: red; background-color: white}"
        self.approximate_input_geom_cb.setStyleSheet(stytxt)
        self.use_indexapprox_cb.setCheckState(Qt.Unchecked)
        self.use_indexapprox_cb.setVisible(False)
        self.use_indexapprox_cb.setStyleSheet(stytxt)
        self.use_index_nonpoint_cb.setCheckState(Qt.Unchecked)
        self.use_index_nonpoint_cb.setVisible(False)
        self.button_box.button(QDialogButtonBox.Ok).setEnabled(False)
        self.button_box.button(QDialogButtonBox.Cancel).setEnabled(False)
        # Help button
        helpButton = self.helpButton
        helpButton.setText(self.HELP)

        # Connect signals
        okButton.clicked.connect(self.startWorker)
        # self.cancelButton.clicked.connect(self.killWorker)
        closeButton.clicked.connect(self.reject)
        helpButton.clicked.connect(self.help)
        self.approximate_input_geom_cb.stateChanged['int'].connect(
            self.useindexchanged)
        self.use_indexapprox_cb.stateChanged['int'].connect(
            self.useindexchanged)
        self.use_index_nonpoint_cb.stateChanged['int'].connect(
            self.useindexchanged)
        inpIndexCh = self.inputVectorLayer.currentIndexChanged['QString']
        inpIndexCh.connect(self.layerchanged)
        joinIndexCh = self.joinVectorLayer.currentIndexChanged['QString']
        # joinIndexCh.connect(self.layerchanged)
        joinIndexCh.connect(self.joinlayerchanged)
        # self.distancefieldname.editingFinished.connect(self.fieldchanged)
        self.distancefieldname.textChanged.connect(self.distfieldchanged)
        self.joinPrefix.editingFinished.connect(self.fieldchanged)
        theRegistry = QgsProject.instance()
        theRegistry.layersAdded.connect(self.layerlistchanged)
        theRegistry.layersRemoved.connect(self.layerlistchanged)
        # Disconnect the cancel button to avoid exiting.
        self.button_box.rejected.disconnect(self.reject)

        # Set instance variables
        self.mem_layer = None
        self.worker = None
        self.inputlayerid = None
        self.joinlayerid = None
        self.layerlistchanging = False

    def startWorker(self):
        """Initialises and starts the worker thread."""
        try:
            layerindex = self.inputVectorLayer.currentIndex()
            layerId = self.inputVectorLayer.itemData(layerindex)
            inputlayer = QgsProject.instance().mapLayer(layerId)
            if inputlayer is None:
                self.showError(self.tr('No input layer defined'))
                return
            joinindex = self.joinVectorLayer.currentIndex()
            joinlayerId = self.joinVectorLayer.itemData(joinindex)
            joinlayer = QgsProject.instance().mapLayer(joinlayerId)
            if joinlayer is None:
                self.showError(self.tr('No join layer defined'))
                return
            if joinlayer is not None and joinlayer.crs().isGeographic():
                self.showWarning('Geographic CRS used for the join layer -'
                                 ' distances will be in decimal degrees!')
            outputlayername = self.outputDataset.text()
            approximateinputgeom = self.approximate_input_geom_cb.isChecked()
            joinprefix = self.joinPrefix.text()
            # useindex = True
            useindex = self.use_index_nonpoint_cb.isChecked()
            useindexapproximation = self.use_indexapprox_cb.isChecked()
            distancefieldname = self.distancefieldname.text()
            selectedinputonly = self.inputSelected.isChecked()
            selectedjoinonly = self.joinSelected.isChecked()
            excludecontaining = self.exclude_containing_poly_cb.isChecked()
            # create a new worker instance
            self.worker = Worker(inputlayer, joinlayer, outputlayername,
                            joinprefix, distancefieldname,
                            approximateinputgeom, useindexapproximation,
                            useindex, selectedinputonly, selectedjoinonly,
                            excludecontaining)
            # configure the QgsMessageBar
            msgBar = self.iface.messageBar().createMessage(
                                                self.tr('Joining'), '')
            self.aprogressBar = QProgressBar()
            self.aprogressBar.setAlignment(Qt.AlignLeft | Qt.AlignVCenter)
            acancelButton = QPushButton()
            acancelButton.setText(self.CANCEL)
            # acancelButton.clicked.connect(self.killWorker)
            msgBar.layout().addWidget(self.aprogressBar)
            msgBar.layout().addWidget(acancelButton)
            # Has to be popped after the thread has finished (in
            # workerFinished).
            self.iface.messageBar().pushWidget(msgBar,
                                               Qgis.Info)
            #                      self.iface.messageBar().INFO)
            self.messageBar = msgBar
            # start the worker in a new thread
            self.mythread = QThread(self)  # QT requires the "self"
            self.worker.status.connect(self.workerInfo)
            self.worker.progress.connect(self.progressBar.setValue)
            self.worker.progress.connect(self.aprogressBar.setValue)
            self.worker.finished.connect(self.workerFinished)
            self.worker.error.connect(self.workerError)
            # Must come before movetothread:
            self.cancelButton.clicked.connect(self.worker.kill)
            acancelButton.clicked.connect(self.worker.kill)
            self.worker.finished.connect(self.worker.deleteLater)
            self.worker.finished.connect(self.mythread.quit)
            # self.worker.error.connect(self.worker.deleteLater)
            # self.worker.error.connect(self.mythread.quit)
            # Must come before thread.started.connect!:
            self.worker.moveToThread(self.mythread)
            self.mythread.started.connect(self.worker.run)
            self.mythread.finished.connect(self.mythread.deleteLater)
            self.mythread.start()
            # self.thread = thread
            # self.worker = worker
            self.button_box.button(QDialogButtonBox.Ok).setEnabled(False)
            self.button_box.button(QDialogButtonBox.Close).setEnabled(False)
            self.button_box.button(QDialogButtonBox.Cancel).setEnabled(True)
            if layerId == joinlayerId:
                self.showInfo("The join layer is the same as the"
                              " input layer - doing a self join!")
        except:
            import traceback
            self.showError("Error starting worker: " + traceback.format_exc())
        else:
            pass
        # End of startworker

    def workerFinished(self, ok, ret):
        """Handles the output from the worker and cleans up after the
           worker has finished."""
        # remove widget from message bar (pop)
        self.iface.messageBar().popWidget(self.messageBar)
        if ok and ret is not None:
            # report the result
            mem_layer = ret
            QgsMessageLog.logMessage(self.tr('NNJoin finished'),
                                     self.NNJOIN, Qgis.Info)
            mem_layer.dataProvider().updateExtents()
            mem_layer.commitChanges()
            self.layerlistchanging = True
            QgsProject.instance().addMapLayer(mem_layer)
            self.layerlistchanging = False
        else:
            # notify the user that something went wrong
            if not ok:
                self.showError(self.tr('Aborted') + '!')
            else:
                self.showError(self.tr('No layer created') + '!')
        self.progressBar.setValue(0.0)
        self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
        self.button_box.button(QDialogButtonBox.Close).setEnabled(True)
        self.button_box.button(QDialogButtonBox.Cancel).setEnabled(False)
        # End of workerFinished

    def workerError(self, exception_string):
        """Report an error from the worker."""
        self.showError(exception_string)

    def workerInfo(self, message_string):
        """Report an info message from the worker."""
        QgsMessageLog.logMessage(self.tr('Worker') + ': ' + message_string,
                                 self.NNJOIN, Qgis.Info)

    def fieldchanged(self, number=0):
        # If the layer list is being updated, don't do anything
        if self.layerlistchanging:
            return
        self.updateui()
        # End of fieldchanged

    def distfieldchanged(self, number=0):
        # If the layer list is being updated, don't do anything
        # if self.layerlistchanging:
        #     return

        # Retrieve the input layer
        layerindex = self.inputVectorLayer.currentIndex()
        layerId = self.inputVectorLayer.itemData(layerindex)
        inputlayer = QgsProject.instance().mapLayer(layerId)
        # Retrieve the join layer
        joinindex = self.joinVectorLayer.currentIndex()
        joinlayerId = self.joinVectorLayer.itemData(joinindex)
        joinlayer = QgsProject.instance().mapLayer(joinlayerId)
        # Enable the OK button (if layers are OK)
        if inputlayer is not None and joinlayer is not None:
            self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
        if inputlayer is not None:
            # Set the default background (white) for the distance field name
            self.distancefieldname.setStyleSheet("background:#fff;")
            # Check if the distance field name already is used
            inputfields = inputlayer.fields().toList()
            for infield in inputfields:
                if infield.name() == self.distancefieldname.text():
                    self.distancefieldname.setStyleSheet("background:#f00;")
                    self.showInfo(
                           "Distance field name conflict in input layer")
                    if self.button_box.button(
                                         QDialogButtonBox.Ok).isEnabled():
                        self.button_box.button(
                                   QDialogButtonBox.Ok).setEnabled(False)
            if joinlayer is not None:
                joinfields = joinlayer.fields().toList()
                for joinfield in joinfields:
                    if (self.joinPrefix.text() + joinfield.name() ==
                                           self.distancefieldname.text()):
                        self.distancefieldname.setStyleSheet(
                                                       "background:#f00;")
                        self.showInfo(
                             "Distance field name conflict in join layer")
                        if self.button_box.button(
                                          QDialogButtonBox.Ok).isEnabled():
                            self.button_box.button(
                                    QDialogButtonBox.Ok).setEnabled(False)
        # self.updateui()
        # End of distfieldchanged

    def joinlayerchanged(self, number=0):
        # If the layer list is being updated, don't do anything
        if self.layerlistchanging:
            return
        # Retrieve the join layer
        joinindex = self.joinVectorLayer.currentIndex()
        joinlayerId = self.joinVectorLayer.itemData(joinindex)
        self.joinlayerid = joinlayerId
        joinlayer = QgsProject.instance().mapLayer(joinlayerId)
        # Geographic? - give a warning!
        if joinlayer is not None and joinlayer.crs().isGeographic():
            self.showWarning('Geographic CRS used for the join layer -'
                             ' distances will be in decimal degrees!')
        self.layerchanged()
        # End of joinlayerchanged

    def layerchanged(self, number=0):
        """Do the necessary updates after a layer selection has
           been changed."""
        # If the layer list is being updated, don't do anything
        if self.layerlistchanging:
            return
        # Retrieve the input layer
        layerindex = self.inputVectorLayer.currentIndex()
        layerId = self.inputVectorLayer.itemData(layerindex)
        self.inputlayerid = layerId
        inputlayer = QgsProject.instance().mapLayer(layerId)
        # Retrieve the join layer
        joinindex = self.joinVectorLayer.currentIndex()
        joinlayerId = self.joinVectorLayer.itemData(joinindex)
        self.joinlayerid = joinlayerId
        joinlayer = QgsProject.instance().mapLayer(joinlayerId)
        # Update the input layer UI label with input geometry
        # type information
        if inputlayer is not None:
            inputwkbtype = inputlayer.wkbType()
            inputlayerwkbtext = self.getwkbtext(inputwkbtype)
            self.inputgeometrytypelabel.setText(inputlayerwkbtext)
        # Update the join layer UI label with join geometry type
        # information
        if joinlayer is not None:
            joinwkbtype = joinlayer.wkbType()
            joinlayerwkbtext = self.getwkbtext(joinwkbtype)
            self.joingeometrytypelabel.setText(joinlayerwkbtext)
        # Check the coordinate systems
        # Different CRSs? - give a warning!
        if (inputlayer is not None and joinlayer is not None and
                inputlayer.crs() != joinlayer.crs()):
            self.showWarning(
                  'Layers have different CRS! - Input CRS authid: ' +
                  str(inputlayer.crs().authid()) +
                  ' - Join CRS authid: ' +
                  str(joinlayer.crs().authid()) +
                  ".  The input layer will be transformed.")
        self.updateui()
        # end of layerchanged

    def useindexchanged(self, number=0):
        self.updateui()

    def layerlistchanged(self):
        # When a layer has been added to or removed by the user,
        # the comboboxes should be updated to include the new
        # possibilities.
        self.layerlistchanging = True
        # Repopulate the input and join layer combo boxes
        # Save the currently selected input layer
        inputlayerid = self.inputlayerid
        layers = QgsProject.instance().mapLayers()
        layerslist = []
        for id in layers.keys():
            if layers[id].type() == QgsMapLayer.VectorLayer:
                if not layers[id].isValid():
                    QMessageBox.information(None,
                        self.tr('Information'),
                        'Layer ' + layers[id].name() + ' is not valid')
                if layers[id].wkbType() != QgsWkbTypes.NoGeometry:
                    layerslist.append((layers[id].name(), id))
        # Add the layers to the input layers combobox
        self.inputVectorLayer.clear()
        for layerdescription in layerslist:
            self.inputVectorLayer.addItem(layerdescription[0],
                                        layerdescription[1])
        # Set the previous selection for the input layer
        for i in range(self.inputVectorLayer.count()):
            if self.inputVectorLayer.itemData(i) == inputlayerid:
                self.inputVectorLayer.setCurrentIndex(i)
        # Save the currently selected join layer
        joinlayerid = self.joinlayerid
        # Add the layers to the join layers combobox
        self.joinVectorLayer.clear()
        for layerdescription in layerslist:
            self.joinVectorLayer.addItem(layerdescription[0],
                                        layerdescription[1])
        # Set the previous selection for the join layer
        for i in range(self.joinVectorLayer.count()):
            if self.joinVectorLayer.itemData(i) == joinlayerid:
                self.joinVectorLayer.setCurrentIndex(i)
        self.layerlistchanging = False
        self.updateui()
        # End of layerlistchanged

    def updateui(self):
        """Do the necessary updates after a layer selection has
           been changed."""
        # if self.layerlistchanged:
        #     return
        # Update the output dataset name
        self.outputDataset.setText(self.inputVectorLayer.currentText() +
                                   '_' + self.joinVectorLayer.currentText())
        # Retrieve the input layer
        layerindex = self.inputVectorLayer.currentIndex()
        layerId = self.inputVectorLayer.itemData(layerindex)
        inputlayer = QgsProject.instance().mapLayer(layerId)
        # Retrieve the join layer
        joinindex = self.joinVectorLayer.currentIndex()
        joinlayerId = self.joinVectorLayer.itemData(joinindex)
        joinlayer = QgsProject.instance().mapLayer(joinlayerId)
        # Enable the OK button (if layers are OK)
        if inputlayer is not None and joinlayer is not None:
            self.button_box.button(QDialogButtonBox.Ok).setEnabled(True)
        # Check the geometry type of the input layer and set
        # user interface options accordingly
        if inputlayer is not None:
            wkbType = inputlayer.wkbType()
            geomType = inputlayer.geometryType()  # not used yet
            joinwkbType = QgsWkbTypes.Unknown
            joingeomType = QgsWkbTypes.UnknownGeometry  # not used yet
            if joinlayer is not None:
                joinwkbType = joinlayer.wkbType()
                joingeomType = joinlayer.geometryType()
            # If the input layer is not a point layer, allow choosing
            # approximate geometry (centroid)
            if wkbType == QgsWkbTypes.Point or wkbType == QgsWkbTypes.Point25D:
                # Input layer is a simple point layer and can not
                # be approximated
                self.approximate_input_geom_cb.blockSignals(True)
                self.approximate_input_geom_cb.setCheckState(Qt.Unchecked)
                self.approximate_input_geom_cb.setVisible(False)
                self.approximate_input_geom_cb.blockSignals(False)
            else:
                # Input layer is not a point layer, so approximation
                # is possible
                self.approximate_input_geom_cb.blockSignals(True)
                self.approximate_input_geom_cb.setVisible(True)
                self.approximate_input_geom_cb.blockSignals(False)
            # Update the use index checkbox
            if ((wkbType == QgsWkbTypes.LineString or
                    wkbType == QgsWkbTypes.LineString25D or
                    wkbType == QgsWkbTypes.Polygon or
                    wkbType == QgsWkbTypes.Polygon25D) and
                    not self.approximate_input_geom_cb.isChecked()):
                # The input layer is a line or polygong layer that
                # is not approximated, so the user is allowed to
                # choose not to use the spatial index (not very useful!)
                if not self.use_index_nonpoint_cb.isVisible():
                    self.use_index_nonpoint_cb.blockSignals(True)
                    self.use_index_nonpoint_cb.setCheckState(Qt.Checked)
                    self.use_index_nonpoint_cb.setVisible(True)
                    self.use_index_nonpoint_cb.blockSignals(False)
            else:
                # The input layer is either a point approximation
                # or it is a point layer (or some kind of
                # multigeometry!), anyway we won't allow the user to
                # choose not to use a spatial index
                self.use_index_nonpoint_cb.blockSignals(True)
                self.use_index_nonpoint_cb.setCheckState(Qt.Unchecked)
                self.use_index_nonpoint_cb.setVisible(False)
                self.use_index_nonpoint_cb.blockSignals(False)
            # This does not work!!????
            # Update the use index approximation checkbox:
            if (((wkbType == QgsWkbTypes.Point) or
                 (wkbType == QgsWkbTypes.Point25D) or
                 self.approximate_input_geom_cb.isChecked()) and
                not (joinwkbType == QgsWkbTypes.Point or
                         joinwkbType == QgsWkbTypes.Point25D)):
                # For non-point join layers and point input layers,
                # the user is allowed to choose an approximation (the
                # index geometry) to be used for the join geometry in
                # the join.
                self.use_indexapprox_cb.setVisible(True)
            else:
                # For point join layers, and non-point,
                # non-point-approximated input layers, the user is
                # not allowed to choose an approximation (the index
                # geometry) to be used for the join geometry in the
                # join.
                self.use_indexapprox_cb.blockSignals(True)
                self.use_indexapprox_cb.setCheckState(Qt.Unchecked)
                self.use_indexapprox_cb.setVisible(False)
                self.use_indexapprox_cb.blockSignals(False)

            # Update the exclude containing polygon checkbox:
            if ((wkbType == QgsWkbTypes.Point or
                 wkbType == QgsWkbTypes.Point25D or
                 self.approximate_input_geom_cb.isChecked()) and
                (joinwkbType == QgsWkbTypes.Polygon or
                 joinwkbType == QgsWkbTypes.Polygon25D) and
                (not self.use_indexapprox_cb.isChecked())):
                # For polygon join layers and point input layers,
                # the user is allowed to choose to exclude the
                # containing polygon in the join.
                self.exclude_containing_poly_cb.blockSignals(True)
                self.exclude_containing_poly_cb.setVisible(True)
                self.exclude_containing_poly_cb.blockSignals(False)
            else:
                self.exclude_containing_poly_cb.blockSignals(True)
                self.exclude_containing_poly_cb.setCheckState(Qt.Unchecked)
                self.exclude_containing_poly_cb.setVisible(False)
                self.exclude_containing_poly_cb.blockSignals(False)

            # Set the default background (white) for the distance field name
            self.distancefieldname.setStyleSheet("background:#fff;")
            # Check if the distance field name already is used
            inputfields = inputlayer.fields().toList()
            for infield in inputfields:
                if infield.name() == self.distancefieldname.text():
                    self.distancefieldname.setStyleSheet("background:#f00;")
                    self.showInfo(
                           "Distance field name conflict in input layer")
                    if self.button_box.button(
                                         QDialogButtonBox.Ok).isEnabled():
                        self.button_box.button(
                                   QDialogButtonBox.Ok).setEnabled(False)
                    break
            if joinlayer is not None:
                joinfields = joinlayer.fields().toList()
                for joinfield in joinfields:
                    if (self.joinPrefix.text() + joinfield.name() ==
                                           self.distancefieldname.text()):
                        self.distancefieldname.setStyleSheet(
                                                       "background:#f00;")
                        self.showInfo(
                             "Distance field name conflict in join layer")
                        if self.button_box.button(
                                          QDialogButtonBox.Ok).isEnabled():
                            self.button_box.button(
                                    QDialogButtonBox.Ok).setEnabled(False)
                        break
        else:
            # No input layer defined, so options are disabled
            self.approximate_input_geom_cb.setVisible(False)
            self.use_indexapprox_cb.setVisible(False)
            self.use_index_nonpoint_cb.setVisible(False)
        # End of updateui

    def getwkbtext(self, number):
        if number == QgsWkbTypes.Unknown:
            return "Unknown"
        elif number == QgsWkbTypes.Point:
            return "Point"
        elif number == QgsWkbTypes.LineString:
            return "LineString"
        elif number == QgsWkbTypes.Polygon:
            return "Polygon"
        elif number == QgsWkbTypes.MultiPoint:
            return "MultiPoint"
        elif number == QgsWkbTypes.MultiLineString:
            return "MultiLineString"
        elif number == QgsWkbTypes.MultiPolygon:
            return "MultiPolygon"
        elif number == QgsWkbTypes.NoGeometry:
            return "NoGeometry"
        elif number == QgsWkbTypes.Point25D:
            return "Point25D"
        elif number == QgsWkbTypes.LineString25D:
            return "LineString25D"
        elif number == QgsWkbTypes.Polygon25D:
            return "Polygon25D"
        elif number == QgsWkbTypes.MultiPoint25D:
            return "MultiPoint25D"
        elif number == QgsWkbTypes.MultiLineString25D:
            return "MultiLineString25D"
        elif number == QgsWkbTypes.MultiPolygon25D:
            return "MultiPolygon25D"
        else:
            showError('Unknown or invalid geometry type: ' + str(number))
            return "Don't know"
        # End of getwkbtext

    def killWorker(self):
        """Kill the worker thread."""
        # if self.worker is not None:
        #     self.showInfo(self.tr('Killing worker'))
        #     self.worker.kill()

    def showError(self, text):
        """Show an error."""
        self.iface.messageBar().pushMessage(self.tr('Error'), text,
                                            level=Qgis.Critical,
                                            duration=3)
        QgsMessageLog.logMessage('Error: ' + text, self.NNJOIN,
                                 Qgis.Critical)

    def showWarning(self, text):
        """Show a warning."""
        self.iface.messageBar().pushMessage(self.tr('Warning'), text,
                                            level=Qgis.Warning,
                                            duration=2)
        QgsMessageLog.logMessage('Warning: ' + text, self.NNJOIN,
                                 Qgis.Warning)

    def showInfo(self, text):
        """Show info."""
        self.iface.messageBar().pushMessage(self.tr('Info'), text,
                                            level=Qgis.Info,
                                            duration=2)
        QgsMessageLog.logMessage('Info: ' + text, self.NNJOIN,
                                 Qgis.Info)

    def help(self):
        QDesktopServices.openUrl(QUrl.fromLocalFile(
                         self.plugin_dir + "/help/html/index.html"))
        # showPluginHelp(None, "help/html/index")

    def tr(self, message):
        """Get the translation for a string using Qt translation API.

        :param message: String for translation.
        :type message: str, QString

        :returns: Translated version of message.
        :rtype: QString
        """
        return QCoreApplication.translate('NNJoinDialog', message)

    # Implement the accept method to avoid exiting the dialog when
    # starting the work
    def accept(self):
        """Accept override."""
        pass

    # Implement the reject method to have the possibility to avoid
    # exiting the dialog when cancelling
    def reject(self):
        """Reject override."""
        # exit the dialog
        QDialog.reject(self)