18 #include <QPushButton>
20 #include <QHBoxLayout>
40 switch ( p1.first.type() )
42 case QVariant::String:
43 return p1.first.toString() < p2.first.toString();
46 case QVariant::Double:
47 return p1.first.toDouble() < p2.first.toDouble();
51 return p1.first.toInt() < p2.first.toInt();
66 , mMessageBarItem( NULL )
68 , mReferencedAttributeForm( NULL )
69 , mReferencedLayer( NULL )
70 , mReferencingLayer( NULL )
73 , mFeatureListModel( 0 )
74 , mWindowWidget( NULL )
78 , mReadOnlySelector( false )
79 , mAllowMapIdentification( false )
80 , mOrderByValue( false )
81 , mOpenFormButtonVisible( true )
82 , mChainFilters( false )
95 editLayout->
addWidget( mChooserGroupBox );
100 mFilterContainer =
new QWidget;
101 mFilterContainer->
setLayout( mFilterLayout );
102 mChooserGroupBox->
setLayout( chooserLayout );
103 chooserLayout->
addWidget( mFilterContainer );
117 mOpenFormButton->
setText(
tr(
"Open related feature form" ) );
118 editLayout->
addWidget( mOpenFormButton );
122 mHighlightFeatureButton->
setPopupMode( QToolButton::MenuButtonPopup );
126 mHighlightFeatureButton->
addAction( mHighlightFeatureAction );
127 mHighlightFeatureButton->
addAction( mScaleHighlightFeatureAction );
128 mHighlightFeatureButton->
addAction( mPanHighlightFeatureAction );
130 editLayout->
addWidget( mHighlightFeatureButton );
133 mMapIdentificationButton =
new QToolButton(
this );
135 mMapIdentificationButton->
setText(
tr(
"Select on map" ) );
137 editLayout->
addWidget( mMapIdentificationButton );
142 mRemoveFKButton->
setText(
tr(
"No selection" ) );
143 editLayout->
addWidget( mRemoveFKButton );
153 mAttributeEditorLayout =
new QVBoxLayout( mAttributeEditorFrame );
154 mAttributeEditorFrame->
setLayout( mAttributeEditorLayout );
155 mAttributeEditorFrame->
setSizePolicy( mAttributeEditorFrame->
sizePolicy().horizontalPolicy(), QSizePolicy::Expanding );
156 mTopLayout->
addWidget( mAttributeEditorFrame );
159 mInvalidLabel =
new QLabel(
tr(
"The relation is not valid. Please make sure your relation definitions are ok." ) );
164 mInvalidLabel->
setFont( font );
169 mMapIdentificationButton->
hide();
170 mHighlightFeatureButton->
hide();
171 mAttributeEditorFrame->
hide();
172 mInvalidLabel->
hide();
175 connect( mOpenFormButton, SIGNAL( clicked() ),
this, SLOT(
openForm() ) );
176 connect( mHighlightFeatureButton, SIGNAL( triggered(
QAction* ) ),
this, SLOT( highlightActionTriggered(
QAction* ) ) );
191 mAllowNull = allowNullValue;
192 mRemoveFKButton->
setVisible( allowNullValue && mReadOnlySelector );
196 mInvalidLabel->
hide();
198 mRelation = relation;
200 mRelationName = relation.
name();
208 mAttributeEditorFrame->
setTitle( mReferencedLayer->
name() );
211 mAttributeEditorLayout->
addWidget( mReferencedAttributeForm );
216 mInvalidLabel->
show();
232 mMapIdentificationButton->
setEnabled( editable );
234 mIsEditable = editable;
245 if ( !mReferencedLayer )
261 if ( mFeature.
attribute( mFkeyFieldIdx ) == value )
273 mForeignKey = mFeature.
attribute( mFkeyFieldIdx );
275 if ( mReadOnlySelector )
278 QString title = expr.evaluate( &mFeature ).toString();
279 if ( expr.hasEvalError() )
288 if ( i == -1 && mAllowNull )
299 highlightFeature( mFeature );
300 updateAttributeEditorFrame( mFeature );
307 if ( mReadOnlySelector )
312 nullText =
tr(
"%1 (no selection)" ).
arg( nullValue.
toString() );
314 mLineEdit->
setText( nullText );
337 if ( mReferencedLayer )
340 if ( mReadOnlySelector )
355 if ( mReadOnlySelector )
368 return mFeature.
attribute( mFkeyFieldIdx );
375 mEditorContext = context;
377 mMessageBar = messageBar;
388 mEmbedForm = display;
395 mRemoveFKButton->
setVisible( mAllowNull && readOnly );
396 mReadOnlySelector = readOnly;
401 mHighlightFeatureButton->
setVisible( allowMapIdentification );
402 mMapIdentificationButton->
setVisible( allowMapIdentification );
413 mFilterFields = filterFields;
418 mOpenFormButton->
setVisible( openFormButtonVisible );
438 if ( !mReadOnlySelector && mComboBox->
count() == 0 && mReferencedLayer )
446 if ( mFilterFields.
size() )
448 Q_FOREACH (
const QString& fieldName, mFilterFields )
450 QVariantList uniqueValues;
454 mFilterComboBoxes << cb;
460 Q_FOREACH (
QVariant v, uniqueValues )
465 connect( cb, SIGNAL( currentIndexChanged(
int ) ),
this, SLOT( filterChanged() ) );
468 requestedAttrs << fieldName;
481 for (
int i = 0; i < mFilterComboBoxes.
count() - 1; ++i )
487 mFilterCache[mFilterFields[i]][cf] << nf;
495 requestedAttrs += exp.referencedColumns().toSet();
496 requestedAttrs << mRelation.
fieldPairs().first().second;
499 Q_FOREACH (
const QString& attr, requestedAttrs )
515 if ( referencedColumns.
size() > 0 )
518 mFilterModel->
sort( sortIdx );
522 mComboBox->
setModel( mFeatureListModel );
526 if ( mChainFilters && mFeature.
isValid() )
528 for (
int i = 0; i < mFilterFields.
size(); i++ )
532 mFilterComboBoxes[i]->setCurrentIndex( mFilterComboBoxes[i]->findText( f ) );
539 connect( mComboBox, SIGNAL( currentIndexChanged(
int ) ),
this, SLOT( comboReferenceChanged(
int ) ) );
544 void QgsRelationReferenceWidget::highlightActionTriggered(
QAction* action )
546 if ( action == mHighlightFeatureAction )
550 else if ( action == mScaleHighlightFeatureAction )
554 else if ( action == mPanHighlightFeatureAction )
569 attributeDialog.
exec();
572 void QgsRelationReferenceWidget::highlightFeature(
QgsFeature f, CanvasExtent canvasExtent )
592 if ( canvasExtent ==
Scale )
605 else if ( canvasExtent ==
Pan )
616 mHighlight =
new QgsHighlight( mCanvas, f, mReferencedLayer );
632 connect( timer, SIGNAL( timeout() ),
this, SLOT( deleteHighlight() ) );
633 timer->
start( 3000 );
636 void QgsRelationReferenceWidget::deleteHighlight()
648 if ( !mAllowMapIdentification || !mReferencedLayer )
657 mMapTool->
setLayer( mReferencedLayer );
667 connect( mMapTool, SIGNAL( deactivated() ),
this, SLOT( mapToolDeactivated() ) );
672 QString msg =
tr(
"Identify a feature of %1 to be associated. Press <ESC> to cancel." ).
arg( mReferencedLayer->
name() );
674 mMessageBar->
pushItem( mMessageBarItem );
678 void QgsRelationReferenceWidget::comboReferenceChanged(
int index )
682 highlightFeature( mFeature );
683 updateAttributeEditorFrame( mFeature );
687 void QgsRelationReferenceWidget::updateAttributeEditorFrame(
const QgsFeature feature )
690 if ( mAttributeEditorFrame )
692 if ( mReferencedAttributeForm )
694 mReferencedAttributeForm->
setFeature( feature );
699 void QgsRelationReferenceWidget::featureIdentified(
const QgsFeature& feature )
701 if ( mReadOnlySelector )
704 QString title = expr.evaluate( &feature ).toString();
705 if ( expr.hasEvalError() )
710 mForeignKey = feature.
attribute( mFkeyFieldIdx );
720 highlightFeature( feature );
721 updateAttributeEditorFrame( feature );
727 void QgsRelationReferenceWidget::unsetMapTool()
730 if ( mCanvas && mMapTool )
737 void QgsRelationReferenceWidget::mapToolDeactivated()
741 mWindowWidget->
raise();
745 if ( mMessageBar && mMessageBarItem )
747 mMessageBar->
popWidget( mMessageBarItem );
749 mMessageBarItem = NULL;
752 void QgsRelationReferenceWidget::filterChanged()
766 Q_FOREACH (
QComboBox* cb, mFilterComboBoxes )
805 Q_FOREACH (
QComboBox* cb, mFilterComboBoxes )
813 filters <<
QString(
"\"%1\" IS NULL" ).
arg( fieldName );
830 QString filterExpression = filters.
join(
" AND " );
837 while ( it.nextFeature( f ) )
839 featureIds << f.id();
void unsetMapTool(QgsMapTool *mapTool)
Unset the current map tool or last non zoom tool.
QgsFeatureId id() const
Get the feature ID for this feature.
When showing a single feature (e.g. district information when looking at the form of a house) ...
void setRequest(const QgsFeatureRequest &request)
Set a request that will be used to fill this attribute table model.
Class for parsing and evaluation of expressions (formerly called "search strings").
Wrapper for iterator of features from vector data provider or vector layer.
bool isValid() const
Returns the validity of this relation.
static double DEFAULT_HIGHLIGHT_BUFFER_MM
Default highlight buffer in mm.
const QString name() const
A rectangle specified with double values.
static const QColor DEFAULT_HIGHLIGHT_COLOR
Default highlight color.
QgsPoint layerToMapCoordinates(QgsMapLayer *theLayer, QgsPoint point) const
transform point coordinates from layer's CRS to output CRS
const QgsField & field(int fieldIdx) const
Get field at particular index (must be in range 0..N-1)
void setContentsMargins(int left, int top, int right, int bottom)
virtual void loadLayer()
Loads the layer into the model Preferably to be called, before using this model as source for any oth...
void zoomByFactor(double scaleFactor, const QgsPoint *center=0)
Zoom with the factor supplied.
bool isValid() const
Returns the validity of this feature.
A form was opened as a new dialog.
void setText(const QString &)
A groupbox that collapses/expands when toggled and can save its collapsed and checked states...
This class contains context information for attribute editor widgets.
void uniqueValues(int index, QList< QVariant > &uniqueValues, int limit=-1)
Returns unique values for column.
QgsFeatureIterator getFeatures(const QgsFeatureRequest &request=QgsFeatureRequest())
Query the provider for features specified in request.
static QIcon getThemeIcon(const QString &theName)
Helper to get a theme icon.
void setExtent(const QgsRectangle &r)
Set the extent of the map canvas.
bool contains(const QgsRectangle &rect) const
return true when rectangle contains other rectangle
void setFillColor(const QColor &fillColor)
Set polygons fill color.
QgsRectangle boundingBox() const
Returns the bounding box of this feature.
A bar for displaying non-blocking messages to the user.
const QgsMapSettings & mapSettings() const
Get access to properties used for map rendering.
QgsVectorLayer * referencedLayer() const
Access the referenced (parent) layer.
void refresh()
Repaints the canvas map.
A geometry is the spatial representation of a feature.
QString join(const QString &separator) const
The feature class encapsulates a single feature including its id, geometry and a list of field/values...
A model backed by a QgsVectorLayerCache which is able to provide feature/attribute information to a Q...
const QString displayExpression()
Get the preview expression, used to create a human readable preview string.
QString tr(const char *sourceText, const char *disambiguation, int n)
Map canvas is a class for displaying all GIS data types on a canvas.
void setCacheSubsetOfAttributes(const QgsAttributeList &attributes)
Set the subset of attributes to be cached.
void addItem(const QString &text, const QVariant &userData)
void setMapTool(QgsMapTool *mapTool)
Sets the map tool currently being used on the canvas.
void setBuffer(double buffer)
Set line / outline buffer in millimeters.
const QString & name() const
Get the display name of the layer.
int count(const T &value) const
void combineExtentWith(QgsRectangle *rect)
expand the rectangle so that covers both the original rectangle and the given rectangle ...
QVariant property(const char *name) const
static QgsMessageBarItem * createMessage(const QString &text, QWidget *parent=0)
make out a widget containing a message to be displayed on the bar
int toInt(bool *ok) const
bool setDisplayExpression(const QString expression)
bool popWidget(QgsMessageBarItem *item)
QgsVectorLayer * referencingLayer() const
Access the referencing (child) layer This is the layer which has the field(s) which point to another ...
virtual void addItem(QLayoutItem *item)
A class for highlight features on the map.
This class wraps a request for features to a vector layer (or directly its vector data provider)...
void setOverrideCursor(const QCursor &cursor)
void restoreOverrideCursor()
QgsGeometry * centroid() const
Returns the center of mass of a geometry.
QString attributeAlias(int attributeIndex) const
Returns the alias of an attribute name or an empty string if there is no alias.
QgsVectorLayerCache * layerCache() const
Returns the layer cache this model uses as backend.
A class to represent a point.
QVariant itemData(int index, int role) const
bool blockSignals(bool block)
This class caches features of a given QgsVectorLayer.
void setItalic(bool enable)
void setValid(bool validity)
Sets the validity of the feature.
bool setAlignment(QWidget *w, QFlags< Qt::AlignmentFlag > alignment)
QVariant value(const QString &key, const QVariant &defaultValue) const
void pushItem(QgsMessageBarItem *item)
Display a message item on the bar after hiding the currently visible one and putting it in a stack...
QVariant attribute(const QString &name) const
Lookup attribute value from attribute name.
int findData(const QVariant &data, int role, QFlags< Qt::MatchFlag > flags) const
char * toString(const T &value)
void setColor(const QColor &color)
Set line/outline to color, polygon fill to color with alpha = 63.
void setModel(QAbstractItemModel *model)
virtual void sort(int column, Qt::SortOrder order=Qt::AscendingOrder) override
Sort by the given column using the given order.
void setTitle(const QString &title)
const QgsVectorLayerTools * vectorLayerTools() const
void setCurrentIndex(int index)
const QgsGeometry * constGeometry() const
Gets a const pointer to the geometry object associated with this feature.
QList< FieldPair > fieldPairs() const
Returns the field pairs which form this relation The first element of each pair are the field names f...
void setText(const QString &text)
double toDouble(bool *ok) const
bool setProperty(const char *name, const QVariant &value)
QgsRectangle extent() const
Returns the current zoom exent of the map canvas.
void setInjectNull(bool injectNull)
If true is specified, a NULL value will be injected.
const QgsFields & pendingFields() const
returns field list in the to-be-committed state
bool nextFeature(QgsFeature &f)
Geometry is not required. It may still be returned if e.g. required for a filter condition.
QgsPoint asPoint() const
Return contents of the geometry as a point if wkbType is WKBPoint, otherwise returns [0...
bool connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
int fieldNameIndex(const QString &fieldName) const
Returns the index of a field name or -1 if the field does not exist.
QgsFeatureIterator getFeatures(const QgsFeatureRequest &featureRequest=QgsFeatureRequest())
Query this VectorLayerCache for features.
QString arg(qlonglong a, int fieldWidth, int base, const QChar &fillChar) const
virtual void setFilteredFeatures(QgsFeatureIds ids)
Specify a list of features, which the filter will accept.
static double DEFAULT_HIGHLIGHT_MIN_WIDTH_MM
Default highlight line/outline minimum width in mm.
void setWordWrap(bool on)
void setSpacing(int spacing)
A form was embedded as a widget on another form.
void addLayout(QLayout *layout, int stretch)
void setMinWidth(double width)
Set minimum line / outline width in millimeters.
QVariant::Type type() const
Gets variant type of the field as it will be retrieved from data source.
void setSingleShot(bool singleShot)
void scale(double scaleFactor, const QgsPoint *c=0)
Scale the rectangle around its center point.