def add_central_toolbar_button(self): widget = QWidget() widget.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Preferred) layout = QHBoxLayout() layout.addStretch() self.btnLogin = QPushButton() palette = self.btnLogin.palette() palette.setColor(QPalette.Button, PLANET_COLOR) self.btnLogin.setPalette(palette) self.btnLogin.setText("Log in") #self.btnLogin.setAutoRaise(True) self.btnLogin.setAttribute(Qt.WA_TranslucentBackground) self.btnLogin.clicked.connect(self.btn_login_clicked) icon = QIcon( os.path.join(plugin_path, "resources", "planet-logo-p.svg")) labelIcon = QLabel() labelIcon.setPixmap(icon.pixmap(QSize(16, 16))) layout.addWidget(labelIcon) self.labelLoggedIn = QLabel() self.labelLoggedIn.setText("") layout.addWidget(self.labelLoggedIn) layout.addWidget(self.btnLogin) layout.addStretch() widget.setLayout(layout) self.toolbar.addWidget(widget)
class LayerItemWidget(QWidget): def __init__(self, layer, parent=None): super(LayerItemWidget, self).__init__(parent) self.layer = layer self.layout = QHBoxLayout() self.check = QCheckBox() self.check.setText(layer.name()) self.labelMetadata = QLabel() self.labelMetadata.setFixedWidth(50) self.labelData = QLabel() self.labelData.setFixedWidth(50) self.layout.addWidget(self.check) self.layout.addWidget(self.labelData) self.layout.addWidget(self.labelMetadata) self.setLayout(self.layout) def name(self): return self.layer.name() def iconPath(self, server): return os.path.join(os.path.dirname(os.path.dirname(__file__)), "icons", "%s.png" % server.__class__.__name__.lower()[:-6]) def setMetadataPublished(self, server): self.labelMetadata.setPixmap(QPixmap(self.iconPath(server))) def setDataPublished(self, server): self.labelData.setPixmap(QPixmap(self.iconPath(server))) def checked(self): return self.check.isChecked() def setCheckState(self, state): self.check.setCheckState(state)
class ImageItemWidget(QFrame): checked_state_changed = pyqtSignal() def __init__(self, image, sort_criteria): QFrame.__init__(self) self.image = image self.properties = image['properties'] datetime = iso8601.parse_date(self.properties[sort_criteria]) self.time = datetime.strftime('%H:%M:%S') self.date = datetime.strftime('%b %d, %Y') text = f"""{self.date}<span style="color: rgb(100,100,100);"> {self.time} UTC</span><br> <b>{DAILY_ITEM_TYPES_DICT[self.properties['item_type']]}</b><br> """ url = f"{image['_links']['thumbnail']}?api_key={PlanetClient.getInstance().api_key()}" self.checkBox = QCheckBox("") self.checkBox.setChecked(True) self.checkBox.stateChanged.connect(self.checked_state_changed.emit) self.nameLabel = QLabel(text) self.iconLabel = QLabel() layout = QHBoxLayout() layout.setMargin(0) layout.addWidget(self.checkBox) pixmap = QPixmap(PLACEHOLDER_THUMB, 'SVG') thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) self.iconLabel.setFixedSize(48, 48) self.nam = QNetworkAccessManager() self.nam.finished.connect(self.iconDownloaded) self.nam.get(QNetworkRequest(QUrl(url))) layout.addWidget(self.iconLabel) layout.addWidget(self.nameLabel) layout.addStretch() self.setLayout(layout) def iconDownloaded(self, reply): img = QImage() img.loadFromData(reply.readAll()) pixmap = QPixmap(img) thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) def set_selected(self, checked): self.checkBox.setChecked(checked) def is_selected(self): return self.checkBox.isChecked()
def _add_results(self, preselect: int = -1, row_number: int = 0): ''' adds results to the map canvas and to the result list of the dialog ''' provider = self.preview_layer.layer.dataProvider() for i, result in enumerate(self.results): feature = QgsFeature() coords = result['geometry']['coordinates'] geom = QgsGeometry.fromPointXY(QgsPointXY(coords[0], coords[1])) feature.setGeometry(geom) feature.setAttributes([ i + 1, result['properties']['text'], ]) provider.addFeature(feature) properties = result['properties'] radio = QRadioButton(properties['text']) preview = QLabel() preview.setMaximumWidth(20) preview.setMinimumWidth(20) self.results_contents.addWidget(preview, i + row_number, 0) self.results_contents.addWidget(radio, i + row_number, 1) if self.show_score: score = QLabel(f'Score {properties["score"]}') self.results_contents.addWidget(score, i + row_number, 2) img_path = os.path.join(ICON_PATH, f'marker_{i+1}.png') if os.path.exists(img_path): pixmap = QPixmap(img_path) preview.setPixmap( pixmap.scaled(preview.size(), Qt.KeepAspectRatio, Qt.SmoothTransformation)) # results clicked in the dialog are highlighted on the map radio.toggled.connect( lambda c, i=i, f=feature: self._toggle_result(i, f)) if i == preselect: radio.setChecked(True) self.preview_layer.layer.commitChanges() extent = self.preview_layer.layer.extent() if not extent.isEmpty(): transform = QgsCoordinateTransform( self.preview_layer.layer.crs(), self.canvas.mapSettings().destinationCrs(), QgsProject.instance()) self.canvas.setExtent(transform.transform(extent)) self.canvas.zoomByFactor(1.5) self.canvas.refresh()
def _add_thumbnails_to_tree_view(self, tree_view): """ Gets a list of model indexes corresponding to extFiles objects to show a preview """ model = tree_view.model() for idx in model.getPixmapIndexList(): url = model.data(idx, Qt.UserRole)['url'] res, image = self._controller.download_image("{}{}".format( url, SUFFIX_GET_THUMBNAIL)) if res: pixmap = QPixmap() pixmap.loadFromData(image) label = QLabel() label.setPixmap(pixmap) tree_view.setIndexWidget(idx, label)
def __init__(self, text, icon): super().__init__() layout = QHBoxLayout() layout.setMargin(0) iconlabel = QLabel() iconlabel.setPixmap(icon.pixmap(QSize(24, 24))) layout.addWidget(iconlabel) label = QLabel(text) layout.addWidget(label) layout.addStretch() self.setLayout(layout)
def setup_default_preset(self): """Setup the display of presets""" preset_folder = resources_path('map_preset') folders = os.listdir(preset_folder) for folder_name in folders: file_path = join(preset_folder, folder_name, folder_name + '.json') with open(file_path, encoding='utf8') as json_file: data = json.load(json_file, object_hook=as_enum) item = QListWidgetItem(self.dialog.list_default_mp) item.setFlags(Qt.ItemIsSelectable | Qt.ItemIsUserCheckable | Qt.ItemIsEnabled) self.dialog.list_default_mp.addItem(item) widget = QFrame() widget.setFrameStyle(QFrame.StyledPanel) widget.setStyleSheet('QFrame { margin: 3px; };') widget.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) hbox = QHBoxLayout() vbox = QVBoxLayout() picture = QLabel() icon_path = resources_path('map_preset', folder_name, folder_name + '_icon.png') if not os.path.isfile(icon_path): icon_path = resources_path('icons', 'QuickOSM.svg') icon = QPixmap(icon_path) icon.scaled(QSize(150, 250), Qt.KeepAspectRatio) picture.setPixmap(icon) picture.setStyleSheet( 'max-height: 150px; max-width: 250px; margin-right: 50px;') hbox.addWidget(picture) title = QLabel(data['file_name']) title.setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Fixed) title.setStyleSheet('font: bold 20px; margin-bottom: 25px;') vbox.addWidget(title) for label in data['description']: if not label: label = tr('No description') real_label = QLabel(label) real_label.setWordWrap(True) vbox.addWidget(real_label) hbox.addItem(vbox) widget.setLayout(hbox) item.setSizeHint(widget.minimumSizeHint()) self.dialog.list_default_mp.setItemWidget(item, widget)
def mk_prj_storage_icon(self, qgs_type_storage: str) -> QLabel: """Returns a QLabel with the matching icon for the storage type. :param qgs_type_storage: storage type :type qgs_type_storage: str :return: QLabel to be set in a cellWidget :rtype: QLabel """ lbl_location_type = QLabel(self.tableWidget) lbl_location_type.setPixmap( QPixmap(icon_per_storage_type(qgs_type_storage))) lbl_location_type.setScaledContents(True) lbl_location_type.setMaximumSize(20, 20) lbl_location_type.setAlignment(Qt.AlignCenter) lbl_location_type.setTextInteractionFlags(Qt.NoTextInteraction) lbl_location_type.setToolTip(qgs_type_storage) return lbl_location_type
class ImageReviewWidget(QFrame): selectedChanged = pyqtSignal() def __init__(self, image): super().__init__() self.image = image self.checkBox = QCheckBox() self.checkBox.setChecked(True) self.checkBox.stateChanged.connect(self.checkStateChanged) hlayout = QHBoxLayout() hlayout.setMargin(0) hlayout.addStretch() hlayout.addWidget(self.checkBox) vlayout = QVBoxLayout() vlayout.setMargin(0) vlayout.addLayout(hlayout) self.label = QLabel() pixmap = QPixmap(PLACEHOLDER_THUMB, "SVG") thumb = pixmap.scaled(96, 96, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.label.setPixmap(thumb) self.label.setFixedSize(96, 96) url = f"{image['_links']['thumbnail']}?api_key={PlanetClient.getInstance().api_key()}" download_thumbnail(url, self) vlayout.addWidget(self.label) self.setLayout(vlayout) self.setFrameStyle(QFrame.Panel | QFrame.Raised) def checkStateChanged(self): self.selectedChanged.emit() self.label.setEnabled(self.checkBox.isChecked()) def selected(self): return self.checkBox.isChecked() def set_thumbnail(self, img): self.thumbnail = QPixmap(img) thumb = self.thumbnail.scaled(96, 96, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.label.setPixmap(thumb)
class DistanceInputPanel(NumberInputPanel): """ Distance input panel for use outside the modeler - this input panel contains a label showing the distance unit. """ def __init__(self, param): super().__init__(param) self.label = QLabel('') label_margin = self.fontMetrics().width('X') self.layout().insertSpacing(1, label_margin / 2) self.layout().insertWidget(2, self.label) self.layout().insertSpacing(3, label_margin / 2) self.warning_label = QLabel() icon = QgsApplication.getThemeIcon('mIconWarning.svg') size = max(24, self.spnValue.height() * 0.5) self.warning_label.setPixmap( icon.pixmap(icon.actualSize(QSize(size, size)))) self.warning_label.setToolTip( self. tr('Distance is in geographic degrees. Consider reprojecting to a projected local coordinate system for accurate results.' )) self.layout().insertWidget(4, self.warning_label) self.layout().insertSpacing(5, label_margin) self.setUnits(QgsUnitTypes.DistanceUnknownUnit) def setUnits(self, units): self.label.setText(QgsUnitTypes.toString(units)) self.warning_label.setVisible(units == QgsUnitTypes.DistanceDegrees) def setUnitParameterValue(self, value): units = QgsUnitTypes.DistanceUnknownUnit layer = self.getLayerFromValue(value) if isinstance(layer, QgsMapLayer): units = layer.crs().mapUnits() elif isinstance(value, QgsCoordinateReferenceSystem): units = value.mapUnits() elif isinstance(value, str): crs = QgsCoordinateReferenceSystem(value) if crs.isValid(): units = crs.mapUnits() self.setUnits(units)
class DistanceInputPanel(NumberInputPanel): """ Distance input panel for use outside the modeler - this input panel contains a label showing the distance unit. """ def __init__(self, param): super().__init__(param) self.label = QLabel('') label_margin = self.fontMetrics().width('X') self.layout().insertSpacing(1, label_margin / 2) self.layout().insertWidget(2, self.label) self.layout().insertSpacing(3, label_margin / 2) self.warning_label = QLabel() icon = QgsApplication.getThemeIcon('mIconWarning.svg') size = max(24, self.spnValue.height() * 0.5) self.warning_label.setPixmap(icon.pixmap(icon.actualSize(QSize(size, size)))) self.warning_label.setToolTip(self.tr('Distance is in geographic degrees. Consider reprojecting to a projected local coordinate system for accurate results.')) self.layout().insertWidget(4, self.warning_label) self.layout().insertSpacing(5, label_margin) self.setUnits(QgsUnitTypes.DistanceUnknownUnit) def setUnits(self, units): self.label.setText(QgsUnitTypes.toString(units)) self.warning_label.setVisible(units == QgsUnitTypes.DistanceDegrees) def setUnitParameterValue(self, value): units = QgsUnitTypes.DistanceUnknownUnit layer = self.getLayerFromValue(value) if isinstance(layer, QgsMapLayer): units = layer.crs().mapUnits() elif isinstance(value, QgsCoordinateReferenceSystem): units = value.mapUnits() elif isinstance(value, str): crs = QgsCoordinateReferenceSystem(value) if crs.isValid(): units = crs.mapUnits() self.setUnits(units)
class ServerItemWidget(QWidget): def __init__(self, server_class, server_name, parent=None): """ Widget used by the list widget control to show all available server instances. """ super(ServerItemWidget, self).__init__(parent) icon = server_class.getWidgetClass().getPngIcon() self.layout = QHBoxLayout() self.label = QLabel() self.serverName = server_name self.iconLabel = QLabel() self.iconLabel.setPixmap(icon) self.iconLabel.setFixedWidth(50) self.layout.addWidget(self.iconLabel) self.layout.addWidget(self.label) self.setLayout(self.layout) @property def serverName(self): return self.label.text() @serverName.setter def serverName(self, name): self.label.setText(name)
def __get_custom_widget_item_for_result(self, qr_result): label = QLabel() if not qr_result: style = WIDGET_STYLE_QUALITY_RULE_INITIAL_STATE label.setText("0%") elif qr_result.level == EnumQualityRuleResult.SUCCESS: style = WIDGET_STYLE_QUALITY_RULE_SUCCESS icon = QIcon( ":/Asistente-LADM-COL/resources/images/qr_validation.svg") label.setPixmap(icon.pixmap(QSize(16, 16))) elif qr_result.level == EnumQualityRuleResult.ERRORS: style = WIDGET_STYLE_QUALITY_RULE_ERRORS label.setText(str(qr_result.record_count)) elif qr_result.level == EnumQualityRuleResult.UNDEFINED: style = WIDGET_STYLE_QUALITY_RULE_UNDEFINED else: # EnumQualityRuleResult.CRITICAL style = WIDGET_STYLE_QUALITY_RULE_CRITICAL label.setAlignment(Qt.AlignHCenter | Qt.AlignVCenter) label.setStyleSheet("QLabel{}".format(style)) return label
class ServerItemWidget(QWidget): def __init__ (self, server, parent = None): super(ServerItemWidget, self).__init__(parent) self.server = server self.layout = QHBoxLayout() self.label = QLabel() self.label.setText(server.name) self.iconLabel = QLabel() self.iconLabel.setPixmap(QPixmap(self.iconPath(server))) self.iconLabel.setFixedWidth(50) self.layout.addWidget(self.iconLabel) self.layout.addWidget(self.label) self.setLayout(self.layout) def iconPath(self, server): return os.path.join(os.path.dirname(os.path.dirname(__file__)), "icons", "%s_black.png" % self.server.__class__.__name__.lower()[:-6]) def setServerName(self, name): self.label.setText(name) def serverName(self): return self.label.text()
class AboutBox(QDialog): """ About box of the plugin """ def __init__(self, parent=None): QWidget.__init__(self, parent) mainLayout = QVBoxLayout() logo_file_path = PluginGlobals.instance().logo_file_path self.logo = QLabel() self.logo.setPixmap(QPixmap(logo_file_path)) mainLayout.addWidget(self.logo) title = u"À propos de l'extension GéoGrandEst…" description = u"""Extension pour QGIS donnant un accès simplifié aux ressources géographiques utiles aux partenaires de GéoGrandEst Version {0} Plus d'informations à l'adresse suivante : {1} """.format(PluginGlobals.instance().PLUGIN_VERSION, PluginGlobals.instance().PLUGIN_SOURCE_REPOSITORY) self.textArea = QTextEdit() self.textArea.setReadOnly(True) self.textArea.setText(description) self.textArea.setFrameShape(QFrame.NoFrame) mainLayout.addWidget(self.textArea) self.setModal(True) self.setSizeGripEnabled(False) self.setLayout(mainLayout) self.setFixedSize(400, 250) self.setWindowTitle(title)
class PlanetOrderItemTypeWidget(QWidget): selectionChanged = pyqtSignal() def __init__(self, item_type, images): super().__init__() self.thumbnails = [] self.item_type = item_type self.images = images layout = QGridLayout() layout.setMargin(0) self.labelThumbnail = QLabel() pixmap = QPixmap(PLACEHOLDER_THUMB, "SVG") thumb = pixmap.scaled(96, 96, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.labelThumbnail.setPixmap(thumb) self.labelThumbnail.setFixedSize(96, 96) layout.addWidget(self.labelThumbnail, 0, 0, 3, 1) for image in images: url = f"{image['_links']['thumbnail']}?api_key={PlanetClient.getInstance().api_key()}" download_thumbnail(url, self) labelName = IconLabel( f"<b>{PlanetClient.getInstance().item_types_names()[self.item_type]}</b>", SATELLITE_ICON, ) labelNumItems = IconLabel(f"{len(images)} items", NITEMS_ICON) layout.addWidget(labelNumItems, 0, 1) layout.addWidget(labelName, 1, 1) self.btnDetails = QPushButton() self.btnDetails.setFlat(True) self.btnDetails.setIcon(EXPAND_MORE_ICON) self.btnDetails.clicked.connect(self._btnDetailsClicked) layout.addWidget(self.btnDetails, 0, 2) self.widgetDetails = QWidget() layout.addWidget(self.widgetDetails, 3, 0, 1, 3) line = QFrame() line.setFrameShape(QFrame.HLine) line.setFrameShadow(QFrame.Sunken) layout.addWidget(line, 4, 0, 1, 3) self.setLayout(layout) self.widgetDetails.hide() self.updateGeometry() self.populate_details() def populate_details(self): self.bundleWidgets = [] client = PlanetClient.getInstance() permissions = [img[PERMISSIONS] for img in self.images] item_bundles = client.bundles_for_item_type(self.item_type, permissions=permissions) default = default_bundles.get(self.item_type, "") def _center(obj): hlayout = QHBoxLayout() hlayout.addStretch() hlayout.addWidget(obj) hlayout.addStretch() return hlayout layout = QVBoxLayout() layout.setMargin(0) layout.setSpacing(20) layout.addLayout(_center(QLabel("<b>RECTIFIED ASSETS</b>"))) gridlayout = QGridLayout() gridlayout.setMargin(0) widgets = {} i = 0 for bundleid, bundle in item_bundles.items(): if bundle["rectification"] == "orthorectified": name = bundle["name"] description = bundle["description"] udm = bundle.get("auxiliaryFiles", "").lower().startswith("udm2") assets = bundle["assets"][self.item_type] can_harmonize = ("ortho_analytic_4b_sr" in assets or "ortho_analytic_8b_sr" in assets) w = PlanetOrderBundleWidget(bundleid, name, description, udm, can_harmonize, True) gridlayout.addWidget(w, i // 2, i % 2) w.setSelected(False) widgets[bundleid] = w w.selectionChanged.connect( partial(self._bundle_selection_changed, w)) self.bundleWidgets.append(w) i += 1 selected = False for defaultid in default: for bundleid, w in widgets.items(): if defaultid == bundleid: w.setSelected(True) selected = True break if selected: break layout.addLayout(gridlayout) self.labelUnrectified = QLabel("<b>UNRECTIFIED ASSETS</b>") layout.addLayout(_center(self.labelUnrectified)) self.widgetUnrectified = QWidget() gridlayoutUnrect = QGridLayout() gridlayoutUnrect.setMargin(0) i = 0 for bundleid, bundle in item_bundles.items(): if bundle["rectification"] != "orthorectified": name = bundle["name"] description = bundle["description"] udm = bundle.get("auxiliaryFiles", "").lower().startswith("udm2") assets = bundle["assets"][self.item_type] can_harmonize = ("ortho_analytic_4b_sr" in assets or "ortho_analytic_8b_sr" in assets) w = PlanetOrderBundleWidget(bundleid, name, description, udm, can_harmonize, False) gridlayoutUnrect.addWidget(w, i // 2, i % 2) w.selectionChanged.connect( partial(self._bundle_selection_changed, w)) self.bundleWidgets.append(w) i += 1 self.widgetUnrectified.setLayout(gridlayoutUnrect) layout.addWidget(self.widgetUnrectified) self.labelMore = QLabel('<a href="#">+ Show More</a>') self.labelMore.setOpenExternalLinks(False) self.labelMore.setTextInteractionFlags(Qt.LinksAccessibleByMouse) self.labelMore.linkActivated.connect(self._showMoreClicked) layout.addLayout(_center(self.labelMore)) self.widgetUnrectified.hide() self.labelUnrectified.hide() self.widgetDetails.setLayout(layout) def _bundle_selection_changed(self, widget): for w in self.bundleWidgets: if widget != w: w.setSelected(False, False) self.selectionChanged.emit() def _showMoreClicked(self): visible = self.widgetUnrectified.isVisible() self.widgetUnrectified.setVisible(not visible) self.labelUnrectified.setVisible(not visible) if visible: self.labelMore.setText('<a href="#">+ Show More</a>') else: self.labelMore.setText('<a href="#">- Show Less</a>') def expand(self): self.widgetDetails.show() self.btnDetails.setIcon(EXPAND_LESS_ICON) self.updateGeometry() def _btnDetailsClicked(self): if self.widgetDetails.isVisible(): self.widgetDetails.hide() self.btnDetails.setIcon(EXPAND_MORE_ICON) else: self.widgetDetails.show() self.btnDetails.setIcon(EXPAND_LESS_ICON) self.updateGeometry() def bundles(self): bundles = [] for w in self.bundleWidgets: if w.selected(): bundle = {} bundle["id"] = w.bundleid bundle["name"] = w.name bundle["filetype"] = w.filetype() bundle["udm"] = w.udm bundle["rectified"] = w.rectified bundle["canharmonize"] = w.can_harmonize bundles.append(bundle) return bundles def set_thumbnail(self, img): thumbnail = QPixmap(img) self.thumbnails.append( thumbnail.scaled(96, 96, Qt.KeepAspectRatio, Qt.SmoothTransformation)) if len(self.images) == len(self.thumbnails): bboxes = [img[GEOMETRY] for img in self.images] pixmap = createCompoundThumbnail(bboxes, self.thumbnails) thumb = pixmap.scaled(128, 128, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.labelThumbnail.setPixmap(thumb)
from qgis.PyQt.QtCore import Qt from qgis.PyQt.QtWidgets import QLabel from qgis.PyQt.QtGui import QImage, QPixmap from qgis.utils import iface import sqlite3 UNIQUE_FIELD = "unique_field_name" BLOB_FIELD = "picture_field_name" FIELD_VALUE = '[%unique_field_name%]' vl = iface.activeLayer() pr = vl.dataProvider() db = pr.dataSourceUri().split(' ')[0].replace('dbname=', '').replace("'", "") conn = sqlite3.connect(db) sql = "SELECT {0} FROM {1} WHERE {2}={3}".format(BLOB_FIELD, vl.name(), UNIQUE_FIELD, FIELD_VALUE) c = conn.cursor() c.execute(sql) rows = c.fetchone() c.close() conn.close() qimg = QImage.fromData(rows[0]) pixmap = QPixmap.fromImage(qimg) label = QLabel() h = label.height() w = label.width() label.setPixmap(pixmap.scaled(w, h, Qt.KeepAspectRatio)) label.show()
class PhotoViewer(QScrollArea): """ Widget for viewing images by incorporating basic navigation options. """ def __init__(self, parent=None, photo_path=""): QScrollArea.__init__(self, parent) self.setBackgroundRole(QPalette.Dark) self._printer = QPrinter() self._lbl_photo = QLabel() self._lbl_photo.setBackgroundRole(QPalette.Base) self._lbl_photo.setSizePolicy(QSizePolicy.Ignored, QSizePolicy.Ignored) self._lbl_photo.setScaledContents(True) self.setWidget(self._lbl_photo) self._photo_path = photo_path self._ph_image = None self._scale_factor = 1.0 self._aspect_ratio = -1 self._create_actions() if self._photo_path: self.load_document(self._photo_path) def _create_actions(self): """ Create actions for basic image navigation. """ self._zoom_in_act = QAction( QApplication.translate("PhotoViewer", "Zoom &In (25%)"), self) self._zoom_in_act.setShortcut( QApplication.translate("PhotoViewer", "Ctrl++")) self._zoom_in_act.setEnabled(False) self._zoom_in_act.triggered.connect(self.zoom_in) self._zoom_out_act = QAction( QApplication.translate("PhotoViewer", "Zoom &Out (25%)"), self) self._zoom_out_act.setShortcut( QApplication.translate("PhotoViewer", "Ctrl+-")) self._zoom_out_act.setEnabled(False) self._zoom_out_act.triggered.connect(self.zoom_out) self._normal_size_act = QAction( QApplication.translate("PhotoViewer", "&Normal Size"), self) self._normal_size_act.setShortcut( QApplication.translate("PhotoViewer", "Ctrl+S")) self._normal_size_act.setEnabled(False) self._normal_size_act.triggered.connect(self.normal_size) self._fit_to_window_act = QAction( QApplication.translate("PhotoViewer", "&Fit to Window"), self) self._fit_to_window_act.setShortcut( QApplication.translate("PhotoViewer", "Ctrl+F")) self._fit_to_window_act.setEnabled(False) self._fit_to_window_act.setCheckable(True) self._fit_to_window_act.triggered.connect(self.fit_to_window) self._print_act = QAction( QApplication.translate("PhotoViewer", "&Print"), self) self._print_act.setShortcut( QApplication.translate("PhotoViewer", "Ctrl+P")) self._print_act.setEnabled(False) self._print_act.triggered.connect(self.print_photo) def zoom_in(self): self.scale_photo(1.25) def zoom_out(self): self.scale_photo(0.8) def normal_size(self): self._lbl_photo.adjustSize() self._scale_factor = 1.0 def fit_to_window(self): fit_to_win = self._fit_to_window_act.isChecked() self.setWidgetResizable(fit_to_win) if not fit_to_win: self.normal_size() self.update_actions() def print_photo(self): print_dialog = QPrintDialog(self._printer, self) if print_dialog.exec_() == QDialog.Accepted: painter = QPainter(self._printer) rect = painter.viewport() size = self._lbl_photo.pixmap().size() size.scale(rect.size(), Qt.KeepAspectRatio) painter.setViewport(rect.x(), rect.y(), size.width(), size.height()) painter.setWindow(self._lbl_photo.pixmap().rect()) painter.drawPixmap(0, 0, self._lbl_photo.pixmap()) def wheelEvent(self, event): """ Zoom the image based on the mouse wheel rotation action. :param event: Event containing the wheel rotation info. :type event: QWheelEvent """ degrees = event.delta() / 8 num_steps = degrees / 15 if num_steps < 0: abs_num_steps = abs(num_steps) zoom_factor = 1 + (abs_num_steps * 0.25) else: zoom_factor = 1 - (num_steps * 0.2) self.scale_photo(zoom_factor) def heightForWidth(self, width): if self._aspect_ratio != -1: return width / self._aspect_ratio else: return -1 def resizeEvent(self, event): """ Event for resizing the widget based on the pixmap's aspect ratio. :param event: Contains event parameters for the resize event. :type event: QResizeEvent """ super(PhotoViewer, self).resizeEvent(event) def update_actions(self): self._zoom_out_act.setEnabled(not self._fit_to_window_act.isChecked()) self._zoom_in_act.setEnabled(not self._fit_to_window_act.isChecked()) self._normal_size_act.setEnabled( not self._fit_to_window_act.isChecked()) def scale_photo(self, factor): """ :param factor: Value by which the image will be increased/decreased in the view. :type factor: float """ if not self._lbl_photo.pixmap().isNull(): self._scale_factor *= factor self._lbl_photo.resize(self._scale_factor * self._lbl_photo.pixmap().size()) self._adjust_scroll_bar(self.horizontalScrollBar(), factor) self._adjust_scroll_bar(self.verticalScrollBar(), factor) self._zoom_in_act.setEnabled(self._scale_factor < 3.0) self._zoom_out_act.setEnabled(self._scale_factor > 0.333) def _adjust_scroll_bar(self, scroll_bar, factor): scroll_bar.setValue( int(factor * scroll_bar.value() + ((factor - 1) * scroll_bar.pageStep() / 2))) def load_document(self, photo_path): if photo_path: self._ph_image = QImage(photo_path) if self._ph_image.isNull(): return False self._photo_path = photo_path ph_pixmap = QPixmap.fromImage(self._ph_image) self._lbl_photo.setPixmap(ph_pixmap) self._scale_factor = 1.0 self._aspect_ratio = ph_pixmap.width() / ph_pixmap.height() self._fit_to_window_act.setEnabled(True) self._print_act.setEnabled(True) self._fit_to_window_act.trigger() self.update_actions() return ph_pixmap return True def photo_location(self): """ :returns: Absolute path of the photo in the central document repository. """ return self._photo_path def set_actions(self, menu): """ Add custom actions to the sub-window menu """ menu.addSeparator() menu.addAction(self._zoom_in_act) menu.addAction(self._zoom_out_act) menu.addAction(self._normal_size_act) menu.addAction(self._fit_to_window_act) menu.addSeparator() menu.addAction(self._print_act)
def onAbout(self): self.about_dlg = QWidget() vlayout = QVBoxLayout() l = QLabel(""" <h1>QGIS GML Application Schema Toolbox</h1> <h3>Version: {}</h3> <p>This plugin is a prototype aiming at experimenting with the manipulation of <b>Complex Features</b> streams.</p> <p>Two modes are available: <ul><li>A mode where the <b>initial XML hierarchical view</b> is preserved. In this mode, an XML instance is represented by a unique QGIS vector layer with a column that stores the XML subtree for each feature. Augmented tools are available to identify a feature or display the attribute table of the layer.</li> <li>A mode where the XML hierarchical data is first <b>converted to a relational database</b>. In this mode, the data is spread accross different QGIS layers. Links between tables are declared as QGIS relations and "relation reference" widgets. It then allows to use the standard QGIS attribute table (in "forms" mode) to navigate the relationel model.</li> </ul> <p>Custom Qt-based viewers can be run on XML elements of given types.</p> <p>Teams involved in the development of the current plugin: <ul> <li><a href="http://www.oslandia.com">Oslandia</a> (current version of the QGIS plugin, and first proof of concept)</li> <li><a href="http://www.spatialys.com">Spatialys</a> (GMLAS driver in OGR)</li> <li><a href="http://www.camptocamp.com">camptocamp</a> (former version of the plugin)</li> </ul> </p> <p>Funders involved: <ul> <li><a href="http://www.brgm.fr">BRGM</a></li> <li><a href="https://www.eea.europa.eu/">European Environment Agency</a> (Copernicus funding)</li> <li><b>The Association of Finnish Local and Regional Authorities</b> (through <a href="http://www.gispo.fi">Gispo.fi</a>)</li> </ul> </p> """.format(plugin_version())) l.setWordWrap(True) vlayout.addWidget(l) hlayout = QHBoxLayout() hlayout2 = QHBoxLayout() l2 = QLabel() l2.setPixmap( QPixmap(os.path.join(os.path.dirname(__file__), "logo_brgm.svg")).scaledToWidth( 200, Qt.SmoothTransformation)) l3 = QLabel() l3.setPixmap( QPixmap(os.path.join(os.path.dirname(__file__), "logo_eea.png")).scaledToWidth( 200, Qt.SmoothTransformation)) l4 = QLabel() l4.setPixmap( QPixmap( os.path.join(os.path.dirname(__file__), "logo_oslandia.png")).scaledToWidth( 150, Qt.SmoothTransformation)) l5 = QLabel() l5.setPixmap( QPixmap( os.path.join(os.path.dirname(__file__), "logo_spatialys.png")).scaledToWidth( 100, Qt.SmoothTransformation)) l6 = QLabel() l6.setPixmap( QPixmap(os.path.join(os.path.dirname(__file__), "logo_c2c.svg")).scaledToWidth( 100, Qt.SmoothTransformation)) hlayout.addWidget(l2) hlayout.addWidget(l3) vlayout.addLayout(hlayout) hlayout2.addWidget(l4) hlayout2.addWidget(l5) hlayout2.addWidget(l6) vlayout.addLayout(hlayout2) self.about_dlg.setLayout(vlayout) self.about_dlg.setWindowTitle(plugin_name()) self.about_dlg.setWindowModality(Qt.WindowModal) self.about_dlg.show() self.about_dlg.resize(600, 800)
def show_results(self, api_results, pg_connections=dict()): """Display the results in a table.""" logger.info("Results manager called. Displaying the results") tbl_result = self.tbl_result # Get the name (and other informations) of all databases whose # connection is set up in QGIS if pg_connections == {}: pg_connections = self.pg_connections else: pass # Set table rows if api_results.get("total") >= 10: tbl_result.setRowCount(10) else: tbl_result.setRowCount(api_results.get("total")) # dimensions (see https://github.com/isogeo/isogeo-plugin-qgis/issues/276) hheader = tbl_result.horizontalHeader() # make the entire width of the table is occupied hheader.setSectionResizeMode(1) # make date and icone columns width adapted to their content # so title and adding columns occupy the rest of the available width hheader.setSectionResizeMode(1, 3) hheader.setSectionResizeMode(2, 3) vheader = tbl_result.verticalHeader() # Looping inside the table lines. For each of them, showing the title, # abstract, geometry type, and a button that allow to add the data # to the canvas. count = 0 for i in api_results.get("results"): md = Metadata.clean_attributes(i) # get metadata's keywords from tags, they will be displayed in QGIS # 'layer properties' if the layer is added to the canvas md.keywords = [ md.tags.get(kw) for kw in md.tags if kw.startswith("keyword:isogeo") ] # COLUMN 1 - Title and abstract # Displaying the metadata title inside a button title = md.title_or_name() if title: btn_md_title = QPushButton( plg_tools.format_button_title(title)) else: btn_md_title = QPushButton( self.tr("Undefined", context=__class__.__name__)) btn_md_title.setStyleSheet("font: italic") # Connecting the button to the full metadata popup btn_md_title.pressed.connect(partial(self.md_asked.emit, md._id)) # Putting the abstract as a tooltip on this button if md.abstract: btn_md_title.setToolTip(md.abstract[:300]) else: pass # Insert it in column 1 tbl_result.setCellWidget(count, 0, btn_md_title) # COLUMN 2 - Data last update lbl_date = QLabel(tbl_result) lbl_date.setText(plg_tools.handle_date(md._modified)) lbl_date.setMargin(5) lbl_date.setAlignment(Qt.AlignCenter) tbl_result.setCellWidget(count, 1, lbl_date) # COLUMN 3 - Geometry type lbl_geom = QLabel(tbl_result) if md.geometry: if md.geometry == "TIN": tbl_result.setItem(count, 2, QTableWidgetItem("TIN")) elif md.geometry in known_geom_list: for geom_type in self.pix_geom_dict: if md.geometry in geom_type: geom_item = self.pix_geom_dict.get(geom_type) lbl_geom.setPixmap(geom_item.get("pix")) lbl_geom.setToolTip( self.tr(geom_item.get("tooltip"), context=__class__.__name__)) else: continue else: tbl_result.setItem( count, 2, QTableWidgetItem( self.tr("Unknown geometry", context=__class__.__name__)), ) else: if "rasterDataset" in md.type: lbl_geom.setPixmap(pix_rastr) lbl_geom.setToolTip( self.tr("Raster", context=__class__.__name__)) elif "service" in md.type: lbl_geom.setPixmap(pix_serv) lbl_geom.setToolTip( self.tr("Service", context=__class__.__name__)) else: lbl_geom.setPixmap(pix_nogeo) lbl_geom.setToolTip( self.tr("Unknown geometry", context=__class__.__name__)) lbl_geom.setAlignment(Qt.AlignCenter) tbl_result.setCellWidget(count, 2, lbl_geom) # COLUMN 4 - Add options add_options_dict = {} # Build metadata portal URL if the setting is checked in "Settings" tab add_portal_md_url = int( qsettings.value("isogeo/settings/add_metadata_url_portal", 0)) portal_base_url = self.form_mng.input_portal_url.text() portal_md_url = "" if add_portal_md_url and portal_base_url != "": portal_md_url = portal_base_url + md._id else: pass # Files and PostGIS direct access if md.format: # If the data is a vector and the path is available, store # useful information in the dict if md.format in li_formats_vect and md.path: add_path = self._filepath_builder(md.path) if add_path: params = [ "vector", add_path, md.title, md.abstract, md.keywords, portal_md_url, ] add_options_dict[self.tr( "Data file", context=__class__.__name__)] = params else: pass # Same if the data is a raster elif md.format in li_formats_rastr and md.path: add_path = self._filepath_builder(md.path) if add_path: params = [ "raster", add_path, md.title, md.abstract, md.keywords, portal_md_url, ] add_options_dict[self.tr( "Data file", context=__class__.__name__)] = params else: pass # If the data is a postGIS table and the connexion has # been saved in QGIS. elif md.format == "postgis": if md.path: base_name = md.path else: base_name = "No path" if base_name in pg_connections.keys(): params = {} params["base_name"] = base_name schema_table = md.name if schema_table is not None and "." in schema_table: params["schema"] = schema_table.split(".")[0] params["table"] = schema_table.split(".")[1] params["abstract"] = md.abstract params["title"] = md.title params["keywords"] = md.keywords params["md_portal_url"] = portal_md_url add_options_dict[self.tr( "PostGIS table", context=__class__.__name__)] = params else: pass else: pass else: logger.debug( "Metadata {} has a format ({}) but it's not handled hear or path is" "missing".format(md._id, md.format)) pass # Associated service layers if md.type == "vectorDataset" or md.type == "rasterDataset": for layer in md.serviceLayers: service = layer.get("service") if service is not None: srv_details = { "path": service.get("path", "NR"), "formatVersion": service.get("formatVersion"), } # WMTS if service.get("format") == "wmts": params = self.layer_adder.build_wmts_url( layer, srv_details, rsc_type="ds_dyn_lyr_srv") # EFS, EMS, WMS or WFS elif service.get("format") in list( self.service_dict.keys()): url_builder = self.service_dict.get( service.get("format")).get("url_builder") params = url_builder( layer, srv_details, rsc_type="ds_dyn_lyr_srv", mode="quicky", ) else: params = [0] logger.debug( "Service with no format detected for '{}' metadata : {}" .format(md._id, service)) pass if params[0] != 0: basic_md = [ md.title, md.abstract, md.keywords, portal_md_url, ] params.append(basic_md) add_options_dict["{} : {}".format( params[0], params[1])] = params else: pass # New association mode. For services metadata sheet, the layers # are stored in the purposely named include: "layers". elif md.type == "service": if md.layers is not None: srv_details = { "path": md.path, "formatVersion": md.formatVersion, } # WMTS if md.format == "wmts": for layer in md.layers: name_url = self.layer_adder.build_wmts_url( layer, srv_details, rsc_type="service") if name_url[0] != 0: btn_label = "WMTS : {}".format(name_url[1]) add_options_dict[btn_label] = name_url else: continue # EFS, EMS, WMS or WFS elif md.format in list(self.service_dict.keys()): url_builder = self.service_dict.get( md.format).get("url_builder") for layer in md.layers: name_url = url_builder(layer, srv_details, rsc_type="service", mode="quicky") if name_url[0] != 0: add_options_dict[name_url[5]] = name_url else: continue else: pass else: pass # Now the plugin has tested every possibility for the layer to be # added. The "Add" column has to be filled accordingly. # If the data can't be added, just insert "can't" text. if add_options_dict == {}: text = self.tr("Can't be added", context=__class__.__name__) fake_button = QPushButton(text) fake_button.setStyleSheet("text-align: left") fake_button.setEnabled(False) tbl_result.setCellWidget(count, 3, fake_button) # If the data can be added else: data_info = {"limitations": None, "layer": None} # retrieves data limitations data_info["limitations"] = md.limitations # If there is only one way for the data to be added, insert a button. if len(add_options_dict) == 1: text = list(add_options_dict.keys())[0] params = add_options_dict.get(text) option_type = text.split(" : ")[0] # services if option_type.lower() in list(self.service_dict.keys()): icon = self.service_dict.get( option_type.lower()).get("ico") # PostGIS table elif option_type.startswith( self.tr("PostGIS table", context=__class__.__name__)): icon = ico_pgis # Data file elif option_type.startswith( self.tr("Data file", context=__class__.__name__)): icon = ico_file # Unkown option else: logger.debug( "Undefined add option type : {}/{} --> {}".format( option_type, text, params)) # create the add button with the icon corresponding to the add option add_button = QPushButton(icon, option_type) add_button.setStyleSheet("text-align: left") # connect the widget to the adding method from LayerAdder class data_info["layer"] = ("info", params, count) add_button.pressed.connect( partial(self.lim_checker.check, data_info)) tbl_result.setCellWidget(count, 3, add_button) # Else, add a combobox, storing all possibilities. else: combo = QComboBox() for option in add_options_dict: option_type = option.split(" : ")[0] # services if option_type.lower() in list( self.service_dict.keys()): icon = self.service_dict.get( option_type.lower()).get("ico") # PostGIS table elif option.startswith( self.tr("PostGIS table", context=__class__.__name__)): icon = ico_pgis # Data file elif option.startswith( self.tr("Data file", context=__class__.__name__)): icon = ico_file # Unkown option else: logger.debug( "Undefined add option type : {}/{} --> {}". format(option_type, text, params)) # add a combobox item with the icon corresponding to the add option combo.addItem(icon, option, add_options_dict.get(option)) # connect the widget to the adding method from LayerAdder class data_info["layer"] = ("index", count) combo.activated.connect( partial(self.lim_checker.check, data_info)) combo.model().sort( 0) # sort alphabetically on option prefix. see: #113 tbl_result.setCellWidget(count, 3, combo) # make the widget (button or combobox) width the same as the column width tbl_result.cellWidget(count, 3).setFixedWidth(hheader.sectionSize(3)) count += 1 # dimensions bis (see https://github.com/isogeo/isogeo-plugin-qgis/issues/276) # last column take the width of his content hheader.setSectionResizeMode(3, 3) # the height of the row adapts to the content without falling below 30px vheader.setMinimumSectionSize(30) vheader.setSectionResizeMode(3) # method ending return None
class QmsSearchResultItemWidget(QWidget): def __init__(self, geoservice, image_ba, parent=None, extent_renderer=None): QWidget.__init__(self, parent) self.extent_renderer = extent_renderer self.layout = QHBoxLayout(self) self.layout.setContentsMargins(5, 10, 5, 10) self.setLayout(self.layout) self.service_icon = QLabel(self) self.service_icon.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) self.service_icon.resize(24, 24) qimg = QImage.fromData(image_ba) pixmap = QPixmap.fromImage(qimg) self.service_icon.setPixmap(pixmap) self.layout.addWidget(self.service_icon) self.service_desc_layout = QGridLayout(self) self.service_desc_layout.setSpacing(0) self.layout.addLayout(self.service_desc_layout) self.service_name = QLabel(self) self.service_name.setTextFormat(Qt.RichText) self.service_name.setWordWrap(True) self.service_name.setText(u" <strong> {} </strong>".format( geoservice.get('name', u""))) self.service_desc_layout.addWidget(self.service_name, 0, 0, 1, 3) self.service_type = QLabel(self) self.service_type.setTextFormat(Qt.RichText) self.service_type.setWordWrap(True) self.service_type.setText(geoservice.get('type', u"").upper() + " ") self.service_desc_layout.addWidget(self.service_type, 1, 0) self.service_deteils = QLabel(self) self.service_deteils.setTextFormat(Qt.RichText) self.service_deteils.setWordWrap(True) self.service_deteils.setOpenExternalLinks(True) self.service_deteils.setText(u"<a href=\"{0}\">{1}</a>, ".format( Client().geoservice_info_url(geoservice.get('id', u"")), self.tr('details'))) self.service_desc_layout.addWidget(self.service_deteils, 1, 1) self.service_report = QLabel(self) self.service_report.setTextFormat(Qt.RichText) self.service_report.setWordWrap(True) self.service_report.setOpenExternalLinks(True) self.service_report.setText(u"<a href=\"{0}\">{1}</a><div/>".format( Client().geoservice_report_url(geoservice.get('id', u"")), self.tr('report a problem'))) self.service_desc_layout.addWidget(self.service_report, 1, 2) self.service_desc_layout.setColumnStretch(2, 1) self.status_label = QLabel(self) self.status_label.setTextFormat(Qt.RichText) self.status_label.setText(u'\u2022') status = geoservice.get('cumulative_status', u'') if status == 'works': self.status_label.setStyleSheet("color: green; font-size: 30px") if status == 'failed': self.status_label.setStyleSheet("color: red; font-size: 30px") if status == 'problematic': self.status_label.setStyleSheet("color: yellow; font-size: 30px") self.layout.addWidget(self.status_label) self.addButton = QToolButton() self.addButton.setText(self.tr("Add")) self.addButton.clicked.connect(self.addToMap) self.layout.addWidget(self.addButton) self.setSizePolicy(QSizePolicy.Preferred, QSizePolicy.Minimum) self.geoservice = geoservice self.image_ba = image_ba def addToMap(self): try: QApplication.setOverrideCursor(QCursor(Qt.WaitCursor)) client = Client() client.set_proxy(*QGISSettings.get_qgis_proxy()) geoservice_info = client.get_geoservice_info(self.geoservice) ds = DataSourceSerializer.read_from_json(geoservice_info) add_layer_to_map(ds) CachedServices().add_service(self.geoservice, self.image_ba) except Exception as ex: plPrint(unicode(ex)) pass finally: QApplication.restoreOverrideCursor() def mouseDoubleClickEvent(self, event): self.addToMap() def enterEvent(self, event): extent = self.geoservice.get('extent', None) if self.extent_renderer and extent: if ';' in extent: extent = extent.split(';')[1] geom = QgsGeometry.fromWkt(extent) self.extent_renderer.show_feature(geom) def leaveEvent(self, event): if self.extent_renderer: self.extent_renderer.clear_feature()
class DistanceInputPanel(NumberInputPanel): """ Distance input panel for use outside the modeler - this input panel contains a label showing the distance unit. """ def __init__(self, param): super().__init__(param) self.label = QLabel('') self.units_combo = QComboBox() self.base_units = QgsUnitTypes.DistanceUnknownUnit for u in (QgsUnitTypes.DistanceMeters, QgsUnitTypes.DistanceKilometers, QgsUnitTypes.DistanceFeet, QgsUnitTypes.DistanceMiles, QgsUnitTypes.DistanceYards): self.units_combo.addItem(QgsUnitTypes.toString(u), u) label_margin = self.fontMetrics().width('X') self.layout().insertSpacing(1, label_margin / 2) self.layout().insertWidget(2, self.label) self.layout().insertWidget(3, self.units_combo) self.layout().insertSpacing(4, label_margin / 2) self.warning_label = QLabel() icon = QgsApplication.getThemeIcon('mIconWarning.svg') size = max(24, self.spnValue.height() * 0.5) self.warning_label.setPixmap(icon.pixmap(icon.actualSize(QSize(size, size)))) self.warning_label.setToolTip(self.tr('Distance is in geographic degrees. Consider reprojecting to a projected local coordinate system for accurate results.')) self.layout().insertWidget(4, self.warning_label) self.layout().insertSpacing(5, label_margin) self.setUnits(QgsUnitTypes.DistanceUnknownUnit) def setUnits(self, units): self.label.setText(QgsUnitTypes.toString(units)) if QgsUnitTypes.unitType(units) != QgsUnitTypes.Standard: self.units_combo.hide() self.label.show() else: self.units_combo.setCurrentIndex(self.units_combo.findData(units)) self.units_combo.show() self.label.hide() self.warning_label.setVisible(units == QgsUnitTypes.DistanceDegrees) self.base_units = units def setUnitParameterValue(self, value): units = QgsUnitTypes.DistanceUnknownUnit layer = self.getLayerFromValue(value) if isinstance(layer, QgsMapLayer): units = layer.crs().mapUnits() elif isinstance(value, QgsCoordinateReferenceSystem): units = value.mapUnits() elif isinstance(value, str): crs = QgsCoordinateReferenceSystem(value) if crs.isValid(): units = crs.mapUnits() self.setUnits(units) def getValue(self): val = super().getValue() if isinstance(val, float) and self.units_combo.isVisible(): display_unit = self.units_combo.currentData() return val * QgsUnitTypes.fromUnitToUnitFactor(display_unit, self.base_units) return val def setValue(self, value): try: self.spnValue.setValue(float(value)) except: return
class CoordinateCaptureDockWidget(QDockWidget): closingPlugin = pyqtSignal() def __init__(self, parent=None): """Constructor.""" super(CoordinateCaptureDockWidget, self).__init__(parent) self.setWindowTitle(self.tr("Coordinate Capture")) self.setGeometry(0, 0, 300, 228) self.dockWidgetContents = QWidget(self) self.setWidget(self.dockWidgetContents) self.gridLayout = QGridLayout() self.dockWidgetContents.setLayout(self.gridLayout) self.dockWidgetContents.layout().setColumnMinimumWidth(0, 36) self.userCrsToolButton = QToolButton(self.dockWidgetContents) self.userCrsToolButton.setIcon( QIcon(":/plugins/coordinate_capture/mIconProjectionEnabled.svg")) self.userCrsToolButton.setToolTip( self.tr("Click to select the CRS to use for coordinate display")) self.userCrsLabel = QLabel(self.dockWidgetContents) self.userCrsLabel.setPixmap( QPixmap(":/plugins/coordinate_capture/transformed.svg")) self.userCrsLabel.setGeometry(self.userCrsToolButton.geometry()) self.userCrsEdit = QLineEdit(self.dockWidgetContents) self.userCrsEdit.setReadOnly(True) self.userCrsEdit.setToolTip( self.tr("Coordinate in your selected CRS (lat,lon or east,north)")) self.copyUserCrsCoordinatesAction = self.userCrsEdit.addAction( QIcon(":/plugins/coordinate_capture/mActionEditCopy.svg"), QLineEdit.TrailingPosition) self.copyUserCrsCoordinatesAction.triggered.connect( self.copyUserCrsCoordinates) self.canvasCrsEdit = QLineEdit(self.dockWidgetContents) self.canvasCrsEdit.setReadOnly(True) self.canvasCrsEdit.setToolTip( self. tr("Coordinate in map canvas coordinate reference system (lat,lon or east,north)" )) self.copyCanvasCrsCoordinatesAction = self.canvasCrsEdit.addAction( QIcon(":/plugins/coordinate_capture/mActionEditCopy.svg"), QLineEdit.TrailingPosition) self.copyCanvasCrsCoordinatesAction.triggered.connect( self.copyCanvasCrsCoordinates) self.trackMouseButton = QToolButton(self.dockWidgetContents) self.trackMouseButton.setIcon( QIcon(":/plugins/coordinate_capture/tracking.svg")) self.trackMouseButton.setCheckable(True) self.trackMouseButton.setToolTip( self.tr( "Click to enable mouse tracking. Click the canvas to stop")) self.trackMouseButton.setChecked(False) # Create the action for tool self.captureButton = QPushButton(self.dockWidgetContents) self.captureButton.setText(self.tr("Start Capture")) self.captureButton.setToolTip( self.tr("Click to enable coordinate capture")) self.captureButton.setIcon( QIcon(":/plugins/coordinate_capture/coordinate_capture.png")) self.captureButton.setWhatsThis( self. tr("Click on the map to view coordinates and capture to clipboard." )) # // Set the icons # setCurrentTheme(QString()); self.dockWidgetContents.layout().addWidget(self.userCrsToolButton, 0, 0) self.dockWidgetContents.layout().addWidget(self.userCrsEdit, 0, 1) self.dockWidgetContents.layout().addWidget(self.userCrsLabel, 1, 0) self.dockWidgetContents.layout().addWidget(self.canvasCrsEdit, 1, 1) self.dockWidgetContents.layout().addWidget(self.trackMouseButton, 2, 0) self.dockWidgetContents.layout().addWidget(self.captureButton, 2, 1) def copyUserCrsCoordinates(self): self.userCrsEdit.selectAll() self.userCrsEdit.copy() def copyCanvasCrsCoordinates(self): self.canvasCrsEdit.selectAll() self.canvasCrsEdit.copy() def closeEvent(self, event): self.closingPlugin.emit() event.accept()
# print(qgs.libraryPaths()) # print(QgsProviderRegistry.instance().pluginList()) # wrap in dialog dlg = QDialog() layout = QVBoxLayout(dlg) image_lbl = QLabel(dlg) layout.addWidget(image_lbl) # layout.setMargin(0) # First WMS, with tileset image = render_wms_to_image(xyz=False) if image.isNull(): qgs.exitQgis() sys.exit(1) image_lbl.setPixmap(QPixmap.fromImage(image)) dlg.setWindowTitle('WMS Scene Render Test') dlg.exec_() # Then XYZ image = render_wms_to_image(xyz=True) # image = thumbnail_image(item_type="PSScene4Band", item_id="20160831_143848_0c79") if image.isNull(): qgs.exitQgis() sys.exit(1) image_lbl.setPixmap(QPixmap.fromImage(image)) # b1 = QPushButton("ok", dlg)
class SceneItemWidget(QFrame): def __init__(self, scene): QWidget.__init__(self) self.scene = scene self.properties = scene[PROPERTIES] self.setMouseTracking(True) datetime = iso8601.parse_date(self.properties["acquired"]) time = datetime.strftime("%H:%M:%S") date = datetime.strftime("%b %d, %Y") text = f"""{date}<span style="color: rgb(100,100,100);"> {time} UTC</span><br> <b>{PlanetClient.getInstance().item_types_names()[self.properties['item_type']]}</b> """ self.nameLabel = QLabel(text) self.iconLabel = QLabel() self.toolsButton = QLabel() self.toolsButton.setPixmap(COG_ICON.pixmap(QSize(18, 18))) self.toolsButton.mousePressEvent = self.showContextMenu pixmap = QPixmap(PLACEHOLDER_THUMB, "SVG") thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) layout = QHBoxLayout() layout.setMargin(2) vlayout = QVBoxLayout() vlayout.setMargin(0) vlayout.addWidget(self.iconLabel) self.iconWidget = QWidget() self.iconWidget.setFixedSize(48, 48) self.iconWidget.setLayout(vlayout) layout.addWidget(self.iconWidget) layout.addWidget(self.nameLabel) layout.addStretch() layout.addWidget(self.toolsButton) layout.addSpacing(10) self.setLayout(layout) self.nam = QNetworkAccessManager() self.nam.finished.connect(self.iconDownloaded) url = f"{scene['_links']['thumbnail']}?api_key={PlanetClient.getInstance().api_key()}" self.nam.get(QNetworkRequest(QUrl(url))) self.footprint = QgsRubberBand(iface.mapCanvas(), QgsWkbTypes.PolygonGeometry) self.footprint.setStrokeColor(PLANET_COLOR) self.footprint.setWidth(2) self.geom = qgsgeometry_from_geojson(scene[GEOMETRY]) self.setStyleSheet("SceneItemWidget{border: 2px solid transparent;}") def showContextMenu(self, evt): menu = QMenu() add_menu_section_action("Current item", menu) zoom_act = QAction("Zoom to extent", menu) zoom_act.triggered.connect(self.zoom_to_extent) menu.addAction(zoom_act) open_act = QAction("Open in Search Panel", menu) open_act.triggered.connect(self.open_in_explorer) menu.addAction(open_act) menu.exec_(self.toolsButton.mapToGlobal(evt.pos())) def open_in_explorer(self): from .pe_explorer_dockwidget import show_explorer_and_search_daily_images request = build_search_request(string_filter("id", self.scene[ID]), [self.properties[ITEM_TYPE]]) show_explorer_and_search_daily_images(request) def zoom_to_extent(self): rect = QgsRectangle(self.geom.boundingBox()) canvasCrs = iface.mapCanvas().mapSettings().destinationCrs() transform = QgsCoordinateTransform(QgsCoordinateReferenceSystem(4326), canvasCrs, QgsProject.instance()) newrect = transform.transform(rect) newrect.scale(1.05) iface.mapCanvas().setExtent(newrect) iface.mapCanvas().refresh() def iconDownloaded(self, reply): img = QImage() img.loadFromData(reply.readAll()) pixmap = QPixmap(img) thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) def show_footprint(self): rect = QgsRectangle(self.geom.boundingBox()) canvasCrs = iface.mapCanvas().mapSettings().destinationCrs() transform = QgsCoordinateTransform(QgsCoordinateReferenceSystem(4326), canvasCrs, QgsProject.instance()) newrect = transform.transform(rect) self.footprint.setToGeometry(QgsGeometry.fromRect(newrect)) def hide_footprint(self): self.footprint.reset(QgsWkbTypes.PolygonGeometry) def enterEvent(self, event): self.setStyleSheet( "SceneItemWidget{border: 2px solid rgb(0, 157, 165);}") self.show_footprint() def leaveEvent(self, event): self.setStyleSheet("SceneItemWidget{border: 2px solid transparent;}") self.hide_footprint()
class QmsSearchResultItemWidget(QWidget): def __init__(self, geoservice, image_ba, parent=None, extent_renderer=None): QWidget.__init__(self, parent) self.extent_renderer = extent_renderer self.layout = QHBoxLayout(self) self.layout.setContentsMargins(5, 10, 5, 10) self.setLayout(self.layout) self.service_icon = QLabel(self) self.service_icon.setSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) self.service_icon.resize(24, 24) qimg = QImage.fromData(image_ba) pixmap = QPixmap.fromImage(qimg) self.service_icon.setPixmap(pixmap) self.layout.addWidget(self.service_icon) self.service_desc_layout = QGridLayout(self) self.service_desc_layout.setSpacing(0) self.layout.addLayout(self.service_desc_layout) self.service_name = QLabel(self) self.service_name.setTextFormat(Qt.RichText) self.service_name.setWordWrap(True) self.service_name.setText(u" <strong> {} </strong>".format(geoservice.get('name', u""))) self.service_desc_layout.addWidget(self.service_name, 0, 0, 1, 3) self.service_type = QLabel(self) self.service_type.setTextFormat(Qt.RichText) self.service_type.setWordWrap(True) self.service_type.setText(geoservice.get('type', u"").upper() + " ") self.service_desc_layout.addWidget(self.service_type, 1, 0) self.service_deteils = QLabel(self) self.service_deteils.setTextFormat(Qt.RichText) self.service_deteils.setWordWrap(True) self.service_deteils.setOpenExternalLinks(True) self.service_deteils.setText(u"<a href=\"{0}\">{1}</a>, ".format( Client().geoservice_info_url(geoservice.get('id', u"")), self.tr('details') )) self.service_desc_layout.addWidget(self.service_deteils, 1, 1) self.service_report = QLabel(self) self.service_report.setTextFormat(Qt.RichText) self.service_report.setWordWrap(True) self.service_report.setOpenExternalLinks(True) self.service_report.setText(u"<a href=\"{0}\">{1}</a><div/>".format( Client().geoservice_report_url(geoservice.get('id', u"")), self.tr('report a problem') )) self.service_desc_layout.addWidget(self.service_report, 1, 2) self.service_desc_layout.setColumnStretch(2, 1) self.status_label = QLabel(self) self.status_label.setTextFormat(Qt.RichText) self.status_label.setText(u'\u2022') status = geoservice.get('cumulative_status', u'') if status == 'works': self.status_label.setStyleSheet("color: green; font-size: 30px") if status == 'failed': self.status_label.setStyleSheet("color: red; font-size: 30px") if status == 'problematic': self.status_label.setStyleSheet("color: yellow; font-size: 30px") self.layout.addWidget(self.status_label) self.addButton = QToolButton() self.addButton.setText(self.tr("Add")) self.addButton.clicked.connect(self.addToMap) self.layout.addWidget(self.addButton) self.setSizePolicy(QSizePolicy.Preferred, QSizePolicy.Minimum) self.geoservice = geoservice self.image_ba = image_ba def addToMap(self): try: QApplication.setOverrideCursor(QCursor(Qt.WaitCursor)) client = Client() client.set_proxy(*QGISSettings.get_qgis_proxy()) geoservice_info = client.get_geoservice_info(self.geoservice) ds = DataSourceSerializer.read_from_json(geoservice_info) add_layer_to_map(ds) CachedServices().add_service(self.geoservice, self.image_ba) except Exception as ex: plPrint(unicode(ex)) pass finally: QApplication.restoreOverrideCursor() def mouseDoubleClickEvent(self, event): self.addToMap() def enterEvent(self, event): extent = self.geoservice.get('extent', None) if self.extent_renderer and extent: if ';' in extent: extent = extent.split(';')[1] geom = QgsGeometry.fromWkt(extent) self.extent_renderer.show_feature(geom) def leaveEvent(self, event): if self.extent_renderer: self.extent_renderer.clear_feature()
class ItemWidgetBase(QFrame): checkedStateChanged = pyqtSignal() thumbnailChanged = pyqtSignal() def __init__(self, item): QFrame.__init__(self) self.item = item self.is_updating_checkbox = False self.setMouseTracking(True) self.setStyleSheet("ItemWidgetBase{border: 2px solid transparent;}") def _setup_ui(self, text, thumbnailurl): self.lockLabel = QLabel() iconSize = QSize(16, 16) self.lockLabel.setPixmap(LOCK_ICON.pixmap(iconSize)) self.checkBox = QCheckBox("") self.checkBox.clicked.connect(self.check_box_state_changed) self.nameLabel = QLabel(text) self.iconLabel = QLabel() self.labelZoomTo = QLabel() self.labelZoomTo.setPixmap(ZOOMTO_ICON.pixmap(QSize(18, 18))) self.labelZoomTo.setToolTip("Zoom to extent") self.labelZoomTo.mousePressEvent = self.zoom_to_extent self.labelAddPreview = QLabel() self.labelAddPreview.setPixmap(ADD_PREVIEW_ICON.pixmap(QSize(18, 18))) self.labelAddPreview.setToolTip("Add preview layer to map") self.labelAddPreview.mousePressEvent = self._add_preview_clicked layout = QHBoxLayout() layout.setMargin(0) layout.addWidget(self.checkBox) layout.addWidget(self.lockLabel) pixmap = QPixmap(PLACEHOLDER_THUMB, "SVG") self.thumbnail = None thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) self.iconLabel.setFixedSize(48, 48) layout.addWidget(self.iconLabel) if thumbnailurl is not None: download_thumbnail(thumbnailurl, self) layout.addWidget(self.nameLabel) layout.addStretch() layout.addWidget(self.labelZoomTo) layout.addWidget(self.labelAddPreview) layout.addSpacing(10) self.setLayout(layout) self.footprint = QgsRubberBand(iface.mapCanvas(), QgsWkbTypes.PolygonGeometry) self.footprint.setStrokeColor(PLANET_COLOR) self.footprint.setWidth(2) def set_thumbnail(self, img): self.thumbnail = QPixmap(img) thumb = self.thumbnail.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) self.thumbnailChanged.emit() def is_selected(self): return self.checkBox.checkState() == Qt.Checked def _geom_bbox_in_project_crs(self): transform = QgsCoordinateTransform( QgsCoordinateReferenceSystem("EPSG:4326"), QgsProject.instance().crs(), QgsProject.instance(), ) return transform.transformBoundingBox(self.geom.boundingBox()) def _geom_in_project_crs(self): transform = QgsCoordinateTransform( QgsCoordinateReferenceSystem("EPSG:4326"), QgsProject.instance().crs(), QgsProject.instance(), ) geom = QgsGeometry(self.geom) geom.transform(transform) return geom def show_footprint(self): self.footprint.setToGeometry(self._geom_in_project_crs()) def hide_footprint(self): self.footprint.reset(QgsWkbTypes.PolygonGeometry) def enterEvent(self, event): self.setStyleSheet( "ItemWidgetBase{border: 2px solid rgb(0, 157, 165);}") self.show_footprint() def leaveEvent(self, event): self.setStyleSheet("ItemWidgetBase{border: 2px solid transparent;}") self.hide_footprint() def zoom_to_extent(self, evt): rect = QgsRectangle(self._geom_bbox_in_project_crs()) rect.scale(1.05) iface.mapCanvas().setExtent(rect) iface.mapCanvas().refresh() def _add_preview_clicked(self, evt): self.add_preview() @waitcursor def add_preview(self): send_analytics_for_preview(self.item.images()) create_preview_group(self.name(), self.item.images()) def check_box_state_changed(self): self.update_children_items() self.update_parent_item() self.checkedStateChanged.emit() def update_parent_item(self): parent = self.item.parent() if parent is not None: w = parent.treeWidget().itemWidget(parent, 0) w.update_checkbox() def update_children_items(self): total = self.item.childCount() if self.checkBox.isTristate(): self.checkBox.setTristate(False) self.checkBox.setChecked(False) for i in range(total): w = self.item.treeWidget().itemWidget(self.item.child(i), 0) w.set_checked(self.checkBox.isChecked()) def update_checkbox(self): selected = 0 total = self.item.childCount() for i in range(total): w = self.item.treeWidget().itemWidget(self.item.child(i), 0) if w.is_selected(): selected += 1 if selected == total: self.checkBox.setTristate(False) self.checkBox.setCheckState(Qt.Checked) elif selected == 0: self.checkBox.setTristate(False) self.checkBox.setCheckState(Qt.Unchecked) else: self.checkBox.setTristate(True) self.checkBox.setCheckState(Qt.PartiallyChecked) def set_checked(self, checked): self.checkBox.setChecked(checked) self.update_children_items() def update_thumbnail(self): thumbnails = self.scene_thumbnails() if thumbnails and None not in thumbnails: bboxes = [img[GEOMETRY] for img in self.item.images()] pixmap = createCompoundThumbnail(bboxes, thumbnails) thumb = pixmap.scaled(48, 48, Qt.KeepAspectRatio, Qt.SmoothTransformation) self.iconLabel.setPixmap(thumb) self.thumbnailChanged.emit() def scene_thumbnails(self): thumbnails = [] try: for i in range(self.item.childCount()): w = self.item.treeWidget().itemWidget(self.item.child(i), 0) thumbnails.extend(w.scene_thumbnails()) except RuntimeError: # item might not exist anymore. In this case, we just return # an empty list pass return thumbnails
def initGui(self): _ = self.add_action( 'serval_icon.svg', text=u'Show Serval Toolbars', add_to_menu=True, callback=self.show_toolbar, always_on=True, ) _ = self.add_action( 'serval_icon.svg', text=u'Hide Serval Toolbars', add_to_menu=True, callback=self.hide_toolbar, always_on=True, ) self.probe_btn = self.add_action( 'probe.svg', text="Probe raster", callback=self.activate_probing, add_to_toolbar=self.toolbar, checkable=True, ) self.map_tool_btn[self.probe_tool] = self.probe_btn self.color_btn = QgsColorButton() self.color_btn.setColor(Qt.gray) self.color_btn.setMinimumSize(QSize(40, 24)) self.color_btn.setMaximumSize(QSize(40, 24)) self.toolbar.addWidget(self.color_btn) self.color_picker_connection(connect=True) self.color_btn.setDisabled(True) self.toolbar.addWidget(QLabel("Band:")) self.bands_cbo = QComboBox() self.bands_cbo.addItem("1", 1) self.toolbar.addWidget(self.bands_cbo) self.bands_cbo.currentIndexChanged.connect(self.update_active_bands) self.bands_cbo.setDisabled(True) self.spin_boxes = BandBoxes() self.toolbar.addWidget(self.spin_boxes) self.spin_boxes.enter_hit.connect(self.apply_spin_box_values) self.draw_btn = self.add_action( 'draw.svg', text="Apply Value(s) To Single Cell", callback=self.activate_drawing, add_to_toolbar=self.toolbar, checkable=True, ) self.map_tool_btn[self.draw_tool] = self.draw_btn self.apply_spin_box_values_btn = self.add_action( 'apply_const_value.svg', text="Apply Value(s) to Selection", callback=self.apply_spin_box_values, add_to_toolbar=self.toolbar, ) self.gom_btn = self.add_action( 'apply_nodata_value.svg', text="Apply NoData to Selection", callback=self.apply_nodata_value, add_to_toolbar=self.toolbar, ) self.exp_dlg_btn = self.add_action( 'apply_expression_value.svg', text="Apply Expression Value To Selection", callback=self.define_expression, add_to_toolbar=self.toolbar, checkable=False, ) self.low_pass_filter_btn = self.add_action( 'apply_low_pass_filter.svg', text="Apply Low-Pass 3x3 Filter To Selection", callback=self.apply_low_pass_filter, add_to_toolbar=self.toolbar, checkable=False, ) self.undo_btn = self.add_action( 'undo.svg', text="Undo", callback=self.undo, add_to_toolbar=self.toolbar, ) self.redo_btn = self.add_action( 'redo.svg', text="Redo", callback=self.redo, add_to_toolbar=self.toolbar, ) self.set_nodata_btn = self.add_action( 'set_nodata.svg', text="Edit Raster NoData Values", callback=self.set_nodata, add_to_toolbar=self.toolbar, ) self.settings_btn = self.add_action( 'edit_settings.svg', text="Serval Settings", callback=self.edit_settings, add_to_toolbar=self.toolbar, always_on=True, ) self.show_help = self.add_action( 'help.svg', text="Help", add_to_menu=True, callback=self.show_website, add_to_toolbar=self.toolbar, always_on=True, ) # Selection Toolbar line_width_icon = QIcon(icon_path("line_width.svg")) line_width_lab = QLabel() line_width_lab.setPixmap(line_width_icon.pixmap(22, 12)) self.sel_toolbar.addWidget(line_width_lab) self.line_width_sbox = QgsDoubleSpinBox() self.line_width_sbox.setMinimumSize(QSize(50, 24)) self.line_width_sbox.setMaximumSize(QSize(50, 24)) # self.line_width_sbox.setButtonSymbols(QAbstractSpinBox.NoButtons) self.line_width_sbox.setValue(1) self.line_width_sbox.setMinimum(0.01) self.line_width_sbox.setShowClearButton(False) self.line_width_sbox.setToolTip("Selection Line Width") self.line_width_sbox.valueChanged.connect(self.update_selection_tool) self.width_unit_cbo = QComboBox() self.width_units = ("map units", "pixel width", "pixel height", "hairline",) for u in self.width_units: self.width_unit_cbo.addItem(u) self.width_unit_cbo.setToolTip("Selection Line Width Unit") self.sel_toolbar.addWidget(self.line_width_sbox) self.sel_toolbar.addWidget(self.width_unit_cbo) self.width_unit_cbo.currentIndexChanged.connect(self.update_selection_tool) self.line_select_btn = self.add_action( 'select_line.svg', text="Select Raster Cells by Line", callback=self.activate_line_selection, add_to_toolbar=self.sel_toolbar, checkable=True, ) self.polygon_select_btn = self.add_action( 'select_polygon.svg', text="Select Raster Cells by Polygon", callback=self.activate_polygon_selection, add_to_toolbar=self.sel_toolbar, checkable=True, ) self.selection_from_layer_btn = self.add_action( 'select_from_layer.svg', text="Create Selection From Layer", callback=self.selection_from_layer, add_to_toolbar=self.sel_toolbar, ) self.selection_to_layer_btn = self.add_action( 'selection_to_layer.svg', text="Create Memory Layer From Selection", callback=self.selection_to_layer, add_to_toolbar=self.sel_toolbar, ) self.clear_selection_btn = self.add_action( 'clear_selection.svg', text="Clear selection", callback=self.clear_selection, add_to_toolbar=self.sel_toolbar, ) self.toggle_all_touched_btn = self.add_action( 'all_touched.svg', text="Toggle All Touched Get Selected", callback=self.toggle_all_touched, checkable=True, checked=True, add_to_toolbar=self.sel_toolbar, ) self.all_touched = True self.enable_toolbar_actions(enable=False) self.check_undo_redo_btns()