[qgis] 01/06: Imported Upstream version 2.14.3+dfsg
Sebastiaan Couwenberg
sebastic at moszumanska.debian.org
Fri May 20 15:40:07 UTC 2016
This is an automated email from the git hooks/post-receive script.
sebastic pushed a commit to branch master
in repository qgis.
commit bf5cbed3365f03250d0c8f4f8b8416d4071eded7
Author: Bas Couwenberg <sebastic at xs4all.nl>
Date: Fri May 20 14:59:53 2016 +0200
Imported Upstream version 2.14.3+dfsg
---
CMakeLists.txt | 2 +-
ChangeLog | 179 +++++++++++++++++++++
debian/changelog | 10 +-
debian/python-qgis.install.in | 3 +-
ms-windows/osgeo4w/browser-grass.bat.tmpl | 1 +
python/PyQt/CMakeLists.txt | 22 ++-
python/PyQt/PyQt4/QtCore.py | 40 +++++
python/PyQt/PyQt4/{QtCore.py => QtNetwork.py} | 16 +-
python/PyQt/PyQt4/{QtCore.py => QtSql.py} | 16 +-
python/PyQt/PyQt4/{QtCore.py => QtSvg.py} | 16 +-
python/PyQt/PyQt4/{QtCore.py => QtTest.py} | 16 +-
python/PyQt/PyQt4/{QtCore.py => QtXml.py} | 16 +-
python/PyQt/PyQt4/{QtCore.py => uic/__init__.py} | 19 ++-
python/PyQt/PyQt4/uic/properties.py | 1 +
python/PyQt/PyQt4/{QtCore.py => uic/pyuic.py} | 21 ++-
python/PyQt/PyQt5/QtCore.py | 2 +
python/PyQt/PyQt5/QtNetwork.py | 1 +
python/PyQt/PyQt5/QtSql.py | 1 +
python/PyQt/PyQt5/QtSvg.py | 1 +
python/PyQt/PyQt5/QtTest.py | 1 +
python/PyQt/PyQt5/QtWidgets.py | 2 +
python/PyQt/PyQt5/QtXml.py | 1 +
.../{PyQt4/QtCore.py => PyQt5/uic/__init__.py} | 19 ++-
python/PyQt/PyQt5/uic/properties.py | 1 +
python/PyQt/PyQt5/uic/pyuic.py | 1 +
python/core/__init__.py | 2 +-
python/core/symbology-ng/qgsfillsymbollayerv2.sip | 4 +
python/core/symbology-ng/qgslinesymbollayerv2.sip | 1 +
python/plugins/processing/gui/ParametersPanel.py | 4 +-
.../plugins/processing/gui/ScriptEditorDialog.py | 3 +
resources/function_help/json/$scale | 2 +-
scripts/qgis_fixes/fix_pyqt.py | 18 +--
scripts/release.pl | 6 +-
src/app/qgisapp.cpp | 13 +-
src/app/qgsfieldsproperties.cpp | 2 +-
src/core/geometry/qgsgeometry.cpp | 2 +-
src/core/qgsapplication.cpp | 4 +-
src/core/qgsexpression.cpp | 16 +-
src/core/qgsvectorlayerfeatureiterator.cpp | 15 +-
src/core/symbology-ng/qgsfillsymbollayerv2.cpp | 22 +++
src/core/symbology-ng/qgsfillsymbollayerv2.h | 5 +-
src/core/symbology-ng/qgslinesymbollayerv2.cpp | 5 +
src/core/symbology-ng/qgslinesymbollayerv2.h | 1 +
src/gui/qgsadvanceddigitizingdockwidget.cpp | 4 +-
src/gui/qgsfieldproxymodel.cpp | 4 +-
src/gui/symbology-ng/qgssymbollayerv2widget.cpp | 1 +
.../qgsdelimitedtextfeatureiterator.cpp | 1 +
src/providers/mssql/qgsmssqlfeatureiterator.cpp | 5 +-
src/providers/ogr/qgsogrconnpool.h | 3 +-
src/providers/ogr/qgsogrfeatureiterator.cpp | 15 +-
src/providers/ogr/qgsogrfeatureiterator.h | 2 +-
src/providers/ogr/qgsogrprovider.cpp | 16 +-
src/providers/oracle/qgsoraclefeatureiterator.cpp | 4 +
.../postgres/qgspostgresfeatureiterator.cpp | 4 +-
.../postgres/qgspostgresfeatureiterator.h | 1 +
.../spatialite/qgsspatialitefeatureiterator.cpp | 4 +
.../virtual/qgsvirtuallayerfeatureiterator.cpp | 4 +-
src/python/qgspythonutilsimpl.cpp | 6 +-
src/server/qgswfsserver.cpp | 33 ++--
tests/src/core/CMakeLists.txt | 1 +
tests/src/core/testqgsconnectionpool.cpp | 141 ++++++++++++++++
tests/src/core/testqgsexpression.cpp | 41 +++++
tests/src/core/testqgsgeometry.cpp | 6 +
tests/src/gui/testqgsfieldexpressionwidget.cpp | 50 ++++++
tests/src/python/providertestbase.py | 5 +-
tests/src/python/qgis_interface.py | 2 +-
tests/src/python/test_qgsblendmodes.py | 1 +
tests/src/python/test_qgscomposition.py | 1 +
.../test_qgsgeometrygeneratorsymbollayerv2.py | 2 +-
tests/src/python/test_qgsrelationeditwidget.py | 6 +-
tests/src/python/test_qgssymbollayerv2.py | 41 ++++-
tests/src/python/test_qgsvectorlayer.py | 11 +-
tests/src/python/utilities.py | 4 +-
73 files changed, 792 insertions(+), 160 deletions(-)
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 21fdbc4..6e16eac 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -1,6 +1,6 @@
SET(CPACK_PACKAGE_VERSION_MAJOR "2")
SET(CPACK_PACKAGE_VERSION_MINOR "14")
-SET(CPACK_PACKAGE_VERSION_PATCH "2")
+SET(CPACK_PACKAGE_VERSION_PATCH "3")
SET(COMPLETE_VERSION ${CPACK_PACKAGE_VERSION_MAJOR}.${CPACK_PACKAGE_VERSION_MINOR}.${CPACK_PACKAGE_VERSION_PATCH})
SET(RELEASE_NAME "Essen")
IF (POLICY CMP0048) # in CMake 3.0.0+
diff --git a/ChangeLog b/ChangeLog
index 73312a3..9760ef2 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,182 @@
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-20
+
+ Precise that scale function returns the denominator and not the scale itself
+
+ (cherry-picked from 69a8c381abeb810625bf972354e3492827b28915)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-20
+
+ Save annotations to project.qgs in creation order (fix #14812)
+
+ Save annotations to project file in the order they were loaded or
+ created, so that annotations have the same display order each
+ time the project is opened.
+
+ (cherry-picked from 82d465cd9434d4445fe4fa44af8a5fd085cbc566)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-20
+
+ Ensure that providers fetch geometry for a QgsFeatureRequest
+ with an expression filter which requires geometry
+
+ (cherry-picked from 858914eef589b2426209d500c162c4773c41fbd5)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-20
+
+ Set expression context for geometry generator builder (fix #14833)
+
+ (cherry-picked from 7187148afb9d7c2d6670ef82b361f7d3b116fdc7)
+
+Juergen E. Fischer <jef at norbit.de> 2016-05-17
+
+ osgeo4w: add qt plugin directories to browser with grass (followup b758a8c)
+
+ (cherry picked from commit 6663a4cc821a9cf3ddc7ced1e65ba42f8fa945da)
+
+Matthias Kuhn <matthias at opengis.ch> 2016-05-16
+
+ Fix bug in edit virtual field
+
+ The index was transformed twice from field index to field origin index,
+ resulting in a corrupted index (most often being 0 in the end).
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ [expressions] Fix fetching joined column refs when expression is
+ not prepared (fix #14746)
+
+ (cherry-picked from febe30d991111712f95a476e97862ca5a890b9aa)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ [cad] Fix invalid coordinates when x/y snapping is enabled and
+ subsequent segments are parallel
+
+ (cherry-picked from 90d116c6f509098f001bf1b10e8a58d081e46a14)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Ensure that @symbol_color is always correct for symbol layer types
+ with subsymbols
+
+ (cherry-picked from cda387cb6f96e01d0c677c974f1a18e5d0bcbce9)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Fix memory leak in OGR provider when feature has no geometry
+ and FilterRect is used
+
+ (cherry-picked from 6b80518a5b55ab30fb19493266d5626d0f89d26b)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Fix major(?) memory leak with python code execution
+
+ (cherry-picked from 73733a65edd2bbc8156bf36484995457c35f6b68)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Avoid refreshing canvas for every joined feature
+
+ Instead of setting the provider's subsetString to fetch joined
+ features, use a feature request with FilterExpression instead.
+ (Setting the subsetString results in a canvas refresh.)
+
+ Performance should be similar (if expression compilation is
+ enabled) and this also has the advantage of avoiding provider-
+ specific behaviour (eg case insensitive matching).
+
+ (fix #14800)
+
+ (cherry-picked from 22acf3b1a3e7a6afe094ec6dec83776256d2655a)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Fix QgsFieldComboWidget not updating fields when calling setFilter()
+
+ (cherry-picked from a389d237fcff1f61941cdba5237079e80abe6717)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-16
+
+ Fix datetime fields not shown in QgsFieldComboWidget when set to date filter
+
+ (cherry-picked from b4029dc7f0169b60117c4ece7c15a31a8766cb4f)
+
+Alexander Bruy <alexander.bruy at gmail.com> 2016-05-09
+
+ [processing] don't crash if user canceled script loading
+
+ (cherry picked from commit 583eaeff7f1994290b1a9428d8b1a7c42848a5c9)
+
+Alexander Bruy <alexander.bruy at gmail.com> 2016-05-09
+
+ [processing] add support for int64 fields (fix #14777)
+
+ (cherry picked from commit f1e6d8731b67b47ce44dc03c5e4d9b7dfe676a0f)
+
+Nyall Dawson <nyall.dawson at gmail.com> 2016-05-10
+
+ Fix feature fields does not include virtual or joined fields when
+ feature is requested using a QgsFeatureRequest with FilterFid
+
+Alessandro Pasotti <apasotti at boundlessgeo.com> 2016-05-05
+
+ [server] Fixes segfault on wrong TypeName
+
+ Unreported - WFS-T
+
+ (cherry-picked from 8e781b4ec01b276e0c2be76db5742cf5227d6bd7)
+
+ Funded by Boundless
+
+Sandro Mani <manisandro at gmail.com> 2016-05-04
+
+ Also use datasource instead of filepath when ref/unref-ing and invalidating.
+
+Juergen E. Fischer <jef at norbit.de> 2016-05-04
+
+ release.pl: don't created branches from tag names
+
+ (cherry picked from commit 919c54ef5fabe7b7c2eef9c91094642c47b2eb7c)
+
+Matthias Kuhn <matthias at opengis.ch> 2016-05-02
+
+ Fixup for AppStartup test which requires SIP API V1
+
+Matthias Kuhn <matthias at opengis.ch> 2016-05-02
+
+ Early import qgis in tests to set SIP API
+
+Matthias Kuhn <matthias at opengis.ch> 2016-05-02
+
+ Improve qgis.PyQt compatibility layer
+
+Sandro Mani <manisandro at gmail.com> 2016-04-20
+
+ Add connection pool test
+
+Sandro Mani <manisandro at gmail.com> 2016-04-11
+
+ Move QgsProviderRegistry::instance delete call after deferred delete call
+
+Sandro Mani <manisandro at gmail.com> 2016-04-10
+
+ Pass the full ogr data source URI as connInfo in qgsConnectionPool_ConnectionCreate.
+
+ This fixes corrupt rendering when loading the same dataset twice with different options (i.e. layers), see issue #14560.
+
+rldhont <rldhont at gmail.com> 2016-04-29
+
+ [BUGFIX][QGIS Server] WFS GetFeature with propertyname retrieves requested fields
+
+rldhont <rldhont at gmail.com> 2016-04-29
+
+ [BUGFIX] QgsGeometry exportToGeoJSON return 'null' for null Geometry
+
+Juergen E. Fischer <jef at norbit.de> 2016-04-29
+
+ Release of 2.14.2
+
Nyall Dawson <nyall.dawson at gmail.com> 2016-04-29
Fix calculation of point symbol bounds using data defined rotation or offset
diff --git a/debian/changelog b/debian/changelog
index 2c0290e..8d1b55c 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -1,8 +1,14 @@
-qgis (2.14.2) UNRELEASED; urgency=medium
+qgis (2.14.3) UNRELEASED; urgency=medium
+
+ * Release of 2.14.3
+
+ -- Jürgen E. Fischer <jef at norbit.de> Fri, 20 May 2016 14:05:10 +0200
+
+qgis (2.14.2) unstable; urgency=medium
* Release of 2.14.2
- -- Jürgen E. Fischer <jef at norbit.de> Fri, 29 Apr 2016 14:00:28 +0200
+ -- Jürgen E. Fischer <jef at norbit.de> Fri, 20 May 2016 14:05:09 +0200
qgis (2.14.1) unstable; urgency=medium
diff --git a/debian/python-qgis.install.in b/debian/python-qgis.install.in
index 34a677a..87920d8 100644
--- a/debian/python-qgis.install.in
+++ b/debian/python-qgis.install.in
@@ -1,8 +1,9 @@
usr/lib/python*/*-packages/qgis/*.py
usr/lib/python*/*-packages/qgis/*.so
+usr/lib/python*/*-packages/qgis/PyQt/*
+usr/lib/python*/*-packages/qgis/analysis/*
usr/lib/python*/*-packages/qgis/core/*
usr/lib/python*/*-packages/qgis/gui/*
-usr/lib/python*/*-packages/qgis/analysis/*
usr/lib/python*/*-packages/qgis/networkanalysis/*
usr/lib/python*/*-packages/qgis/server/*
usr/lib/python*/*-packages/qgis/testing/*
diff --git a/ms-windows/osgeo4w/browser-grass.bat.tmpl b/ms-windows/osgeo4w/browser-grass.bat.tmpl
index ef05a8c..72f77e9 100644
--- a/ms-windows/osgeo4w/browser-grass.bat.tmpl
+++ b/ms-windows/osgeo4w/browser-grass.bat.tmpl
@@ -4,4 +4,5 @@ call "%OSGEO4W_ROOT%"\apps\grass\grass- at grassversion@\etc\env.bat
@echo off
path %OSGEO4W_ROOT%\apps\@package@\bin;%OSGEO4W_ROOT%\apps\grass\grass- at grassversion@\lib;%OSGEO4W_ROOT%\apps\grass\grass- at grassversion@\bin;%PATH%
set QGIS_PREFIX_PATH=%OSGEO4W_ROOT:\=/%/apps/@package@
+set QT_PLUGIN_PATH=%OSGEO4W_ROOT%\apps\@package@\qtplugins;%OSGEO4W_ROOT%\apps\qt4\plugins
start "QGIS Browser" /B "%OSGEO4W_ROOT%"\bin\@package at -browser-bin.exe %*
diff --git a/python/PyQt/CMakeLists.txt b/python/PyQt/CMakeLists.txt
index e005a81..80fe79c 100644
--- a/python/PyQt/CMakeLists.txt
+++ b/python/PyQt/CMakeLists.txt
@@ -1,5 +1,5 @@
-SET (QGIS_PYQT_DIR ${QGIS_DATA_DIR}/python/PyQt)
-SET (PYTHON_OUTPUT_DIRECTORY ${QGIS_OUTPUT_DIRECTORY}/python)
+SET (QGIS_PYQT_DIR ${PYTHON_SITE_PACKAGES_DIR}/qgis/PyQt)
+SET (PYTHON_OUTPUT_DIRECTORY ${QGIS_OUTPUT_DIRECTORY}/python/qgis/PyQt)
SET(PYQT_COMPAT_FILES
__init__.py
@@ -9,7 +9,15 @@ SET(PYQT_COMPAT_FILES
QtPrintSupport.py
QtWebKit.py
QtWebKitWidgets.py
+ QtNetwork.py
+ QtXml.py
+ QtSql.py
+ QtTest.py
+ QtSvg.py
Qsci.py
+ uic/__init__.py
+ uic/pyuic.py
+ uic/properties.py
)
ADD_CUSTOM_TARGET(pyqtcompat ALL)
@@ -21,16 +29,16 @@ ELSE(ENABLE_QT5)
ENDIF(ENABLE_QT5)
FOREACH(pyfile ${PYQT_COMPAT_FILES})
+ GET_FILENAME_COMPONENT(_dir ${pyfile} PATH)
SET(pyfile ${PYQT_PREFIX}/${pyfile})
- LIST(APPEND PYQT_COMPAT_FILES_PREFIXED ${pyfile})
ADD_CUSTOM_COMMAND(TARGET pyqtcompat
POST_BUILD
- COMMAND ${CMAKE_COMMAND} -E make_directory ${PYTHON_OUTPUT_DIRECTORY}/PyQt
- COMMAND ${CMAKE_COMMAND} -E copy ${pyfile} ${PYTHON_OUTPUT_DIRECTORY}/PyQt
+ COMMAND ${CMAKE_COMMAND} -E make_directory ${PYTHON_OUTPUT_DIRECTORY}/${_dir}
+ COMMAND ${CMAKE_COMMAND} -E copy ${pyfile} ${PYTHON_OUTPUT_DIRECTORY}/${_dir}
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
DEPENDS ${pyfile}
)
+ INSTALL(FILES ${pyfile} DESTINATION "${QGIS_PYQT_DIR}/${_dir}")
ENDFOREACH(pyfile)
-PY_COMPILE(pyqtcompat "${PYTHON_OUTPUT_DIRECTORY}/PyQt")
-INSTALL(FILES ${PYQT_COMPAT_FILES_PREFIXED} DESTINATION "${QGIS_PYQT_DIR}")
+PY_COMPILE(pyqtcompat "${PYTHON_OUTPUT_DIRECTORY}")
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtCore.py
index cca3d6b..b4cdbf9 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtCore.py
@@ -23,4 +23,44 @@ __copyright__ = '(C) 2015, Matthias Kuhn'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
+import sip
+for api in ["QDate", "QDateTime", "QString", "QTextStream", "QTime", "QUrl", "QVariant"]:
+ sip.setapi(api, 2)
+
from PyQt4.QtCore import *
+from PyQt4.QtGui import QItemSelectionModel, QSortFilterProxyModel
+
+# Add a __nonzero__ method onto QPyNullVariant so we can check for null values easier.
+# >>> value = QPyNullVariant("int")
+# >>> if value:
+# >>> print "Not a null value"
+from types import MethodType
+from PyQt4.QtCore import QPyNullVariant
+
+
+def __nonzero__(self):
+ return False
+
+
+def __repr__(self):
+ return 'NULL'
+
+
+def __eq__(self, other):
+ return isinstance(other, QPyNullVariant) or other is None
+
+
+def __ne__(self, other):
+ return not isinstance(other, QPyNullVariant) and other is not None
+
+
+def __hash__(self):
+ return 2178309
+
+QPyNullVariant.__nonzero__ = MethodType(__nonzero__, None, QPyNullVariant)
+QPyNullVariant.__repr__ = MethodType(__repr__, None, QPyNullVariant)
+QPyNullVariant.__eq__ = MethodType(__eq__, None, QPyNullVariant)
+QPyNullVariant.__ne__ = MethodType(__ne__, None, QPyNullVariant)
+QPyNullVariant.__hash__ = MethodType(__hash__, None, QPyNullVariant)
+
+NULL = QPyNullVariant(int)
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtNetwork.py
similarity index 73%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/QtNetwork.py
index cca3d6b..98192db 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtNetwork.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ QtNetwork.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,10 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.QtNetwork import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtSql.py
similarity index 74%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/QtSql.py
index cca3d6b..a5a0638 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtSql.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ QtSql.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,10 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.QtSql import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtSvg.py
similarity index 74%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/QtSvg.py
index cca3d6b..9b14b4b 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtSvg.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ QtSvg.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : March 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,10 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'March 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.QtSvg import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtTest.py
similarity index 73%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/QtTest.py
index cca3d6b..19ebec2 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtTest.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ QtTest.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,10 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.QtTest import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/QtXml.py
similarity index 74%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/QtXml.py
index cca3d6b..e73e911 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/QtXml.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ QtXml.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,10 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.QtXml import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/uic/__init__.py
similarity index 65%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/uic/__init__.py
index cca3d6b..99123d9 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/uic/__init__.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ __init__.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,13 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt4.uic.Compiler import indenter, compiler
+from PyQt4.uic.objcreator import widgetPluginPath
+from PyQt4.uic import properties, uiparser, Compiler
+from PyQt4.uic import *
diff --git a/python/PyQt/PyQt4/uic/properties.py b/python/PyQt/PyQt4/uic/properties.py
new file mode 100644
index 0000000..4601fce
--- /dev/null
+++ b/python/PyQt/PyQt4/uic/properties.py
@@ -0,0 +1 @@
+from PyQt4.uic import properties
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt4/uic/pyuic.py
similarity index 66%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt4/uic/pyuic.py
index cca3d6b..68a0cb8 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt4/uic/pyuic.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ pyuic.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,15 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+
+import sip
+for api in ["QDate", "QDateTime", "QString", "QTextStream", "QTime", "QUrl", "QVariant"]:
+ sip.setapi(api, 2)
+
+from PyQt4.uic import pyuic
diff --git a/python/PyQt/PyQt5/QtCore.py b/python/PyQt/PyQt5/QtCore.py
index 3518202..b024ae8 100644
--- a/python/PyQt/PyQt5/QtCore.py
+++ b/python/PyQt/PyQt5/QtCore.py
@@ -1 +1,3 @@
from PyQt5.QtCore import *
+NULL = QVariant()
+QPyNullVariant = QVariant()
diff --git a/python/PyQt/PyQt5/QtNetwork.py b/python/PyQt/PyQt5/QtNetwork.py
new file mode 100644
index 0000000..aff365e
--- /dev/null
+++ b/python/PyQt/PyQt5/QtNetwork.py
@@ -0,0 +1 @@
+from PyQt5.QtNetwork import *
diff --git a/python/PyQt/PyQt5/QtSql.py b/python/PyQt/PyQt5/QtSql.py
new file mode 100644
index 0000000..736745e
--- /dev/null
+++ b/python/PyQt/PyQt5/QtSql.py
@@ -0,0 +1 @@
+from PyQt5.QtSql import *
diff --git a/python/PyQt/PyQt5/QtSvg.py b/python/PyQt/PyQt5/QtSvg.py
new file mode 100644
index 0000000..7f76c2b
--- /dev/null
+++ b/python/PyQt/PyQt5/QtSvg.py
@@ -0,0 +1 @@
+from PyQt5.QtSvg import *
diff --git a/python/PyQt/PyQt5/QtTest.py b/python/PyQt/PyQt5/QtTest.py
new file mode 100644
index 0000000..7230171
--- /dev/null
+++ b/python/PyQt/PyQt5/QtTest.py
@@ -0,0 +1 @@
+from PyQt5.QtTest import *
diff --git a/python/PyQt/PyQt5/QtWidgets.py b/python/PyQt/PyQt5/QtWidgets.py
index c82e3d4..738ebfb 100644
--- a/python/PyQt/PyQt5/QtWidgets.py
+++ b/python/PyQt/PyQt5/QtWidgets.py
@@ -1 +1,3 @@
from PyQt5.QtWidgets import *
+
+QLayout.setMargin = lambda self, m: self.setContentsMargins(m, m, m, m)
diff --git a/python/PyQt/PyQt5/QtXml.py b/python/PyQt/PyQt5/QtXml.py
new file mode 100644
index 0000000..b556556
--- /dev/null
+++ b/python/PyQt/PyQt5/QtXml.py
@@ -0,0 +1 @@
+from PyQt5.QtXml import *
diff --git a/python/PyQt/PyQt4/QtCore.py b/python/PyQt/PyQt5/uic/__init__.py
similarity index 65%
copy from python/PyQt/PyQt4/QtCore.py
copy to python/PyQt/PyQt5/uic/__init__.py
index cca3d6b..fe97eb1 100644
--- a/python/PyQt/PyQt4/QtCore.py
+++ b/python/PyQt/PyQt5/uic/__init__.py
@@ -2,11 +2,11 @@
"""
***************************************************************************
- QtCore.py
+ __init__.py
---------------------
- Date : November 2015
- Copyright : (C) 2015 by Matthias Kuhn
- Email : matthias at opengis dot ch
+ Date : February 2016
+ Copyright : (C) 2016 by Jürgen E. Fischer
+ Email : jef at norbit dot de
***************************************************************************
* *
* This program is free software; you can redistribute it and/or modify *
@@ -17,10 +17,13 @@
***************************************************************************
"""
-__author__ = 'Matthias Kuhn'
-__date__ = 'November 2015'
-__copyright__ = '(C) 2015, Matthias Kuhn'
+__author__ = 'Jürgen E. Fischer'
+__date__ = 'February 2016'
+__copyright__ = '(C) 2016, Jürgen E. Fischer'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
-from PyQt4.QtCore import *
+from PyQt5.uic.Compiler import indenter, compiler
+from PyQt5.uic.objcreator import widgetPluginPath
+from PyQt5.uic import properties, uiparser, Compiler
+from PyQt5.uic import *
diff --git a/python/PyQt/PyQt5/uic/properties.py b/python/PyQt/PyQt5/uic/properties.py
new file mode 100644
index 0000000..95c9981
--- /dev/null
+++ b/python/PyQt/PyQt5/uic/properties.py
@@ -0,0 +1 @@
+from PyQt5.uic import properties
diff --git a/python/PyQt/PyQt5/uic/pyuic.py b/python/PyQt/PyQt5/uic/pyuic.py
new file mode 100644
index 0000000..98e5be2
--- /dev/null
+++ b/python/PyQt/PyQt5/uic/pyuic.py
@@ -0,0 +1 @@
+from PyQt5.uic import pyuic
diff --git a/python/core/__init__.py b/python/core/__init__.py
index 647de19..e8fe1b7 100644
--- a/python/core/__init__.py
+++ b/python/core/__init__.py
@@ -174,7 +174,7 @@ except ImportError:
# TODO: Fixme, this creates an invalid variant, not a NULL one
from PyQt5.QtCore import QVariant
NULL = QVariant()
- except ImportError:
+ except (ImportError, RuntimeError):
pass
diff --git a/python/core/symbology-ng/qgsfillsymbollayerv2.sip b/python/core/symbology-ng/qgsfillsymbollayerv2.sip
index 353f10c..0f4fbaf 100644
--- a/python/core/symbology-ng/qgsfillsymbollayerv2.sip
+++ b/python/core/symbology-ng/qgsfillsymbollayerv2.sip
@@ -843,6 +843,9 @@ class QgsPointPatternFillSymbolLayer : QgsImageFillSymbolLayer
virtual QSet<QString> usedAttributes() const;
+ void setColor( const QColor& c );
+ virtual QColor color() const;
+
protected:
void applyDataDefinedSettings( QgsSymbolV2RenderContext& context );
};
@@ -879,6 +882,7 @@ class QgsCentroidFillSymbolLayerV2 : QgsFillSymbolLayerV2
void toSld( QDomDocument &doc, QDomElement &element, const QgsStringMap& props ) const;
void setColor( const QColor& color );
+ QColor color() const;
QgsSymbolV2* subSymbol();
bool setSubSymbol( QgsSymbolV2* symbol /Transfer/ );
diff --git a/python/core/symbology-ng/qgslinesymbollayerv2.sip b/python/core/symbology-ng/qgslinesymbollayerv2.sip
index e7ba989..d376e9c 100644
--- a/python/core/symbology-ng/qgslinesymbollayerv2.sip
+++ b/python/core/symbology-ng/qgslinesymbollayerv2.sip
@@ -145,6 +145,7 @@ class QgsMarkerLineSymbolLayerV2 : QgsLineSymbolLayerV2
void toSld( QDomDocument &doc, QDomElement &element, const QgsStringMap& props ) const;
void setColor( const QColor& color );
+ virtual QColor color() const;
QgsSymbolV2* subSymbol();
bool setSubSymbol( QgsSymbolV2* symbol /Transfer/);
diff --git a/python/plugins/processing/gui/ParametersPanel.py b/python/plugins/processing/gui/ParametersPanel.py
index 27dc9d8..bf3dcf7 100644
--- a/python/plugins/processing/gui/ParametersPanel.py
+++ b/python/plugins/processing/gui/ParametersPanel.py
@@ -437,8 +437,8 @@ class ParametersPanel(BASE, WIDGET):
if datatype == ParameterTableField.DATA_TYPE_STRING:
fieldTypes = [QVariant.String]
elif datatype == ParameterTableField.DATA_TYPE_NUMBER:
- fieldTypes = [QVariant.Int, QVariant.Double, QVariant.ULongLong,
- QVariant.UInt]
+ fieldTypes = [QVariant.Int, QVariant.Double, QVariant.LongLong,
+ QVariant.UInt, QVariant.ULongLong]
fieldNames = set()
for field in layer.pendingFields():
diff --git a/python/plugins/processing/gui/ScriptEditorDialog.py b/python/plugins/processing/gui/ScriptEditorDialog.py
index 1870be0..db7e6bf 100644
--- a/python/plugins/processing/gui/ScriptEditorDialog.py
+++ b/python/plugins/processing/gui/ScriptEditorDialog.py
@@ -202,6 +202,9 @@ class ScriptEditorDialog(BASE, WIDGET):
self.filename = QFileDialog.getOpenFileName(
self, self.tr('Save script'), scriptDir, filterName)
+ if self.filename == '':
+ return
+
QApplication.setOverrideCursor(QCursor(Qt.WaitCursor))
with codecs.open(self.filename, 'r', encoding='utf-8') as f:
txt = f.read()
diff --git a/resources/function_help/json/$scale b/resources/function_help/json/$scale
index 35c171c..34d1734 100644
--- a/resources/function_help/json/$scale
+++ b/resources/function_help/json/$scale
@@ -1,7 +1,7 @@
{
"name": "$scale",
"type": "function",
- "description": "Returns the current scale of the map canvas.<br><br>Note: This function is only available in some contexts and will be 0 otherwise.",
+ "description": "Returns the current scale denominator of the map canvas.<br><br>Note: This function is only available in some contexts and will be 0 otherwise.",
"examples": [
{ "expression":"$scale", "returns":"10000"}
]
diff --git a/scripts/qgis_fixes/fix_pyqt.py b/scripts/qgis_fixes/fix_pyqt.py
index c464ad0..2717d10 100644
--- a/scripts/qgis_fixes/fix_pyqt.py
+++ b/scripts/qgis_fixes/fix_pyqt.py
@@ -11,7 +11,7 @@ from lib2to3.fixer_util import (Name, Comma, FromImport, Newline,
MAPPING = {
"PyQt4.QtGui": [
- ("PyQt.QtGui", [
+ ("qgis.PyQt.QtGui", [
"QIcon",
"QCursor",
"QColor",
@@ -34,7 +34,7 @@ MAPPING = {
"QFontMetricsF",
"QGradient",
]),
- ("PyQt.QtWidgets", [
+ ("qgis.PyQt.QtWidgets", [
"QAbstractButton",
"QAbstractGraphicsShapeItem",
"QAbstractItemDelegate",
@@ -235,7 +235,7 @@ MAPPING = {
"qDrawWinButton",
"qDrawWinPanel",
]),
- ("PyQt.QtPrintSupport", [
+ ("qgis.PyQt.QtPrintSupport", [
"QPrinter",
"QAbstractPrintDialog",
"QPageSetupDialog",
@@ -245,13 +245,13 @@ MAPPING = {
"QPrintPreviewWidget",
"QPrinterInfo",
]),
- ("PyQt.QtCore", [
+ ("qgis.PyQt.QtCore", [
"QItemSelectionModel",
"QSortFilterProxyModel",
]),
],
"PyQt4.QtCore": [
- ("PyQt.QtCore", [
+ ("qgis.PyQt.QtCore", [
"QAbstractItemModel",
"QAbstractTableModel",
"QByteArray",
@@ -304,15 +304,15 @@ MAPPING = {
]),
],
"PyQt4.QtNetwork": [
- ("PyQt.QtNetwork", ["QNetworkReply", "QNetworkRequest"])
+ ("qgis.PyQt.QtNetwork", ["QNetworkReply", "QNetworkRequest"])
],
"PyQt4.QtXml": [
- ("PyQt.QtXml", [
+ ("qgis.PyQt.QtXml", [
"QDomDocument"
]),
],
"PyQt4.QtSci": [
- ("PyQt.QtSci", [
+ ("qgis.PyQt.QtSci", [
"QsciAPIs",
"QsciLexerCustom",
"QsciLexerPython",
@@ -321,7 +321,7 @@ MAPPING = {
]),
],
"PyQt4.QtWebkit": [
- ("PyQt.QtWebkitWidgets", [
+ ("qgis.PyQt.QtWebkitWidgets", [
"QGraphicsWebView",
"QWebFrame",
"QWebHitTestResult",
diff --git a/scripts/release.pl b/scripts/release.pl
index 1032af2..4fdd30c 100755
--- a/scripts/release.pl
+++ b/scripts/release.pl
@@ -202,11 +202,11 @@ unless( $dopoint ) {
run( "git commit -a -m 'Bump version to $newmajor.$newminor'", "bump version failed" );
}
-my $topush = ($dopoint ? "" : "master ") . "$relbranch $reltag $ltrtag";
+my $topush = ($dopoint ? "" : "master ") . "$relbranch";
print "Push dry-run...\n";
-run( "git push -n origin $topush", "push dry run failed" );
-print "Now manually push and upload the tarballs :\n\tgit push origin $topush\n\trsync qgis-$version.tar.bz2* qgis.org:/var/www/downloads/\n\n";
+run( "git push -n --follow-tags origin $topush", "push dry run failed" );
+print "Now manually push and upload the tarballs :\n\tgit push --follow-tags origin $topush\n\trsync qgis-$version.tar.bz2* qgis.org:/var/www/downloads/\n\n";
=head1 NAME
diff --git a/src/app/qgisapp.cpp b/src/app/qgisapp.cpp
index 928d3cb..cb05993 100644
--- a/src/app/qgisapp.cpp
+++ b/src/app/qgisapp.cpp
@@ -1574,14 +1574,19 @@ void QgisApp::showStyleManagerV2()
void QgisApp::writeAnnotationItemsToProject( QDomDocument& doc )
{
QList<QgsAnnotationItem*> items = annotationItems();
- QList<QgsAnnotationItem*>::const_iterator itemIt = items.constBegin();
- for ( ; itemIt != items.constEnd(); ++itemIt )
+ QgsAnnotationItem* item;
+ QListIterator<QgsAnnotationItem*> i( items );
+ // save lowermost annotation (at end of list) first
+ i.toBack();
+ while ( i.hasPrevious() )
{
- if ( ! *itemIt )
+ item = i.previous();
+
+ if ( ! item )
{
continue;
}
- ( *itemIt )->writeXML( doc );
+ item->writeXML( doc );
}
}
diff --git a/src/app/qgsfieldsproperties.cpp b/src/app/qgsfieldsproperties.cpp
index 6b43ab4..c47ef2e 100644
--- a/src/app/qgsfieldsproperties.cpp
+++ b/src/app/qgsfieldsproperties.cpp
@@ -289,7 +289,7 @@ void QgsFieldsProperties::setRow( int row, int idx, const QgsField& field )
QWidget* expressionWidget = new QWidget;
expressionWidget->setLayout( new QHBoxLayout );
QToolButton* editExpressionButton = new QToolButton;
- editExpressionButton->setProperty( "Index", mLayer->fields().fieldOriginIndex( idx ) );
+ editExpressionButton->setProperty( "Index", idx );
editExpressionButton->setIcon( QgsApplication::getThemeIcon( "/mIconExpression.svg" ) );
connect( editExpressionButton, SIGNAL( clicked() ), this, SLOT( updateExpression() ) );
expressionWidget->layout()->setContentsMargins( 0, 0, 0, 0 );
diff --git a/src/core/geometry/qgsgeometry.cpp b/src/core/geometry/qgsgeometry.cpp
index 1395d0b..ae3a176 100644
--- a/src/core/geometry/qgsgeometry.cpp
+++ b/src/core/geometry/qgsgeometry.cpp
@@ -912,7 +912,7 @@ QString QgsGeometry::exportToGeoJSON( int precision ) const
{
if ( !d->geometry )
{
- return QString();
+ return QString( "null" );
}
return d->geometry->asJSON( precision );
}
diff --git a/src/core/qgsapplication.cpp b/src/core/qgsapplication.cpp
index 986a797..dc6f26b 100644
--- a/src/core/qgsapplication.cpp
+++ b/src/core/qgsapplication.cpp
@@ -867,8 +867,6 @@ void QgsApplication::initQgis()
void QgsApplication::exitQgis()
{
- delete QgsProviderRegistry::instance();
-
delete QgsAuthManager::instance();
//Ensure that all remaining deleteLater QObjects are actually deleted before we exit.
@@ -876,6 +874,8 @@ void QgsApplication::exitQgis()
//LeakSanitiser noise which hides real issues
QgsApplication::sendPostedEvents( nullptr, QEvent::DeferredDelete );
+ delete QgsProviderRegistry::instance();
+
//delete all registered functions from expression engine (see above comment)
QgsExpression::cleanRegisteredFunctions();
diff --git a/src/core/qgsexpression.cpp b/src/core/qgsexpression.cpp
index 737f6ce..a478da7 100644
--- a/src/core/qgsexpression.cpp
+++ b/src/core/qgsexpression.cpp
@@ -4262,11 +4262,23 @@ QgsExpression::Node*QgsExpression::NodeLiteral::clone() const
QVariant QgsExpression::NodeColumnRef::eval( QgsExpression *parent, const QgsExpressionContext *context )
{
Q_UNUSED( parent );
+ int index = mIndex;
+
+ if ( index < 0 )
+ {
+ // have not yet found field index - first check explicitly set fields collection
+ if ( context && context->hasVariable( QgsExpressionContext::EXPR_FIELDS ) )
+ {
+ QgsFields fields = qvariant_cast<QgsFields>( context->variable( QgsExpressionContext::EXPR_FIELDS ) );
+ index = fields.fieldNameIndex( mName );
+ }
+ }
+
if ( context && context->hasVariable( QgsExpressionContext::EXPR_FEATURE ) )
{
QgsFeature feature = qvariant_cast<QgsFeature>( context->variable( QgsExpressionContext::EXPR_FEATURE ) );
- if ( mIndex >= 0 )
- return feature.attribute( mIndex );
+ if ( index >= 0 )
+ return feature.attribute( index );
else
return feature.attribute( mName );
}
diff --git a/src/core/qgsvectorlayerfeatureiterator.cpp b/src/core/qgsvectorlayerfeatureiterator.cpp
index 0694001..184e5ca 100644
--- a/src/core/qgsvectorlayerfeatureiterator.cpp
+++ b/src/core/qgsvectorlayerfeatureiterator.cpp
@@ -685,12 +685,7 @@ void QgsVectorLayerFeatureIterator::FetchJoinInfo::addJoinedAttributesCached( Qg
void QgsVectorLayerFeatureIterator::FetchJoinInfo::addJoinedAttributesDirect( QgsFeature& f, const QVariant& joinValue ) const
{
// no memory cache, query the joined values by setting substring
- QString subsetString = joinLayer->dataProvider()->subsetString(); // provider might already have a subset string
- QString bkSubsetString = subsetString;
- if ( !subsetString.isEmpty() )
- {
- subsetString.prepend( '(' ).append( ") AND " );
- }
+ QString subsetString;
QString joinFieldName;
if ( joinInfo->joinFieldName.isEmpty() && joinInfo->joinFieldIndex >= 0 && joinInfo->joinFieldIndex < joinLayer->fields().count() )
@@ -723,8 +718,6 @@ void QgsVectorLayerFeatureIterator::FetchJoinInfo::addJoinedAttributesDirect( Qg
subsetString += '=' + v;
}
- joinLayer->dataProvider()->setSubsetString( subsetString, false );
-
// maybe user requested just a subset of layer's attributes
// so we do not have to cache everything
bool hasSubset = joinInfo->joinFieldNamesSubset();
@@ -736,6 +729,8 @@ void QgsVectorLayerFeatureIterator::FetchJoinInfo::addJoinedAttributesDirect( Qg
QgsFeatureRequest request;
request.setFlags( QgsFeatureRequest::NoGeometry );
request.setSubsetOfAttributes( attributes );
+ request.setFilterExpression( subsetString );
+ request.setLimit( 1 );
QgsFeatureIterator fi = joinLayer->getFeatures( request );
// get first feature
@@ -765,8 +760,6 @@ void QgsVectorLayerFeatureIterator::FetchJoinInfo::addJoinedAttributesDirect( Qg
{
// no suitable join feature found, keeping empty (null) attributes
}
-
- joinLayer->dataProvider()->setSubsetString( bkSubsetString, false );
}
@@ -801,6 +794,8 @@ bool QgsVectorLayerFeatureIterator::nextFeatureFid( QgsFeature& f )
QgsFeatureIterator fi = mSource->mProviderFeatureSource->getFeatures( mProviderRequest );
if ( fi.nextFeature( f ) )
{
+ f.setFields( mSource->mFields );
+
if ( mSource->mHasEditBuffer )
updateChangedAttributes( f );
diff --git a/src/core/symbology-ng/qgsfillsymbollayerv2.cpp b/src/core/symbology-ng/qgsfillsymbollayerv2.cpp
index ec27bd5..ba5229e 100644
--- a/src/core/symbology-ng/qgsfillsymbollayerv2.cpp
+++ b/src/core/symbology-ng/qgsfillsymbollayerv2.cpp
@@ -2317,6 +2317,11 @@ void QgsLinePatternFillSymbolLayer::setColor( const QColor& c )
mColor = c;
}
+QColor QgsLinePatternFillSymbolLayer::color() const
+{
+ return mFillLineSymbol ? mFillLineSymbol->color() : mColor;
+}
+
QgsLinePatternFillSymbolLayer::~QgsLinePatternFillSymbolLayer()
{
delete mFillLineSymbol;
@@ -3370,6 +3375,18 @@ QSet<QString> QgsPointPatternFillSymbolLayer::usedAttributes() const
return attributes;
}
+void QgsPointPatternFillSymbolLayer::setColor( const QColor& c )
+{
+ mColor = c;
+ if ( mMarkerSymbol )
+ mMarkerSymbol->setColor( c );
+}
+
+QColor QgsPointPatternFillSymbolLayer::color() const
+{
+ return mMarkerSymbol ? mMarkerSymbol->color() : mColor;
+}
+
//////////////
@@ -3404,6 +3421,11 @@ void QgsCentroidFillSymbolLayerV2::setColor( const QColor& color )
mColor = color;
}
+QColor QgsCentroidFillSymbolLayerV2::color() const
+{
+ return mMarker ? mMarker->color() : mColor;
+}
+
void QgsCentroidFillSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context )
{
mMarker->setAlpha( context.alpha() );
diff --git a/src/core/symbology-ng/qgsfillsymbollayerv2.h b/src/core/symbology-ng/qgsfillsymbollayerv2.h
index 48bca51..d14dd30 100644
--- a/src/core/symbology-ng/qgsfillsymbollayerv2.h
+++ b/src/core/symbology-ng/qgsfillsymbollayerv2.h
@@ -896,7 +896,7 @@ class CORE_EXPORT QgsLinePatternFillSymbolLayer: public QgsImageFillSymbolLayer
void setLineWidth( double w );
double lineWidth() const { return mLineWidth; }
void setColor( const QColor& c ) override;
- QColor color() const override { return mColor; }
+ QColor color() const override;
void setOffset( double offset ) { mOffset = offset; }
double offset() const { return mOffset; }
@@ -1026,6 +1026,8 @@ class CORE_EXPORT QgsPointPatternFillSymbolLayer: public QgsImageFillSymbolLayer
QgsMapUnitScale mapUnitScale() const override;
virtual QSet<QString> usedAttributes() const override;
+ void setColor( const QColor& c ) override;
+ virtual QColor color() const override;
protected:
QgsMarkerSymbolV2* mMarkerSymbol;
@@ -1077,6 +1079,7 @@ class CORE_EXPORT QgsCentroidFillSymbolLayerV2 : public QgsFillSymbolLayerV2
void toSld( QDomDocument &doc, QDomElement &element, const QgsStringMap& props ) const override;
void setColor( const QColor& color ) override;
+ QColor color() const override;
QgsSymbolV2* subSymbol() override;
bool setSubSymbol( QgsSymbolV2* symbol ) override;
diff --git a/src/core/symbology-ng/qgslinesymbollayerv2.cpp b/src/core/symbology-ng/qgslinesymbollayerv2.cpp
index 26b6843..cfd9d48 100644
--- a/src/core/symbology-ng/qgslinesymbollayerv2.cpp
+++ b/src/core/symbology-ng/qgslinesymbollayerv2.cpp
@@ -809,6 +809,11 @@ void QgsMarkerLineSymbolLayerV2::setColor( const QColor& color )
mColor = color;
}
+QColor QgsMarkerLineSymbolLayerV2::color() const
+{
+ return mMarker ? mMarker->color() : mColor;
+}
+
void QgsMarkerLineSymbolLayerV2::startRender( QgsSymbolV2RenderContext& context )
{
mMarker->setAlpha( context.alpha() );
diff --git a/src/core/symbology-ng/qgslinesymbollayerv2.h b/src/core/symbology-ng/qgslinesymbollayerv2.h
index 83a118f..0b0cbda 100644
--- a/src/core/symbology-ng/qgslinesymbollayerv2.h
+++ b/src/core/symbology-ng/qgslinesymbollayerv2.h
@@ -194,6 +194,7 @@ class CORE_EXPORT QgsMarkerLineSymbolLayerV2 : public QgsLineSymbolLayerV2
void toSld( QDomDocument &doc, QDomElement &element, const QgsStringMap& props ) const override;
void setColor( const QColor& color ) override;
+ virtual QColor color() const override;
QgsSymbolV2* subSymbol() override;
bool setSubSymbol( QgsSymbolV2* symbol ) override;
diff --git a/src/gui/qgsadvanceddigitizingdockwidget.cpp b/src/gui/qgsadvanceddigitizingdockwidget.cpp
index 87dec83..03d1c3c 100644
--- a/src/gui/qgsadvanceddigitizingdockwidget.cpp
+++ b/src/gui/qgsadvanceddigitizingdockwidget.cpp
@@ -574,7 +574,7 @@ bool QgsAdvancedDigitizingDockWidget::applyConstraints( QgsMapMouseEvent* e )
}
else if ( mXConstraint->isLocked() )
{
- if ( cosa == 0 )
+ if ( qgsDoubleNear( cosa, 0.0 ) )
{
res = false;
}
@@ -590,7 +590,7 @@ bool QgsAdvancedDigitizingDockWidget::applyConstraints( QgsMapMouseEvent* e )
}
else if ( mYConstraint->isLocked() )
{
- if ( sina == 0 )
+ if ( qgsDoubleNear( sina, 0.0 ) )
{
res = false;
}
diff --git a/src/gui/qgsfieldproxymodel.cpp b/src/gui/qgsfieldproxymodel.cpp
index f0a14aa..d65c693 100644
--- a/src/gui/qgsfieldproxymodel.cpp
+++ b/src/gui/qgsfieldproxymodel.cpp
@@ -28,6 +28,7 @@ QgsFieldProxyModel::QgsFieldProxyModel( QObject *parent )
QgsFieldProxyModel *QgsFieldProxyModel::setFilters( const Filters& filters )
{
mFilters = filters;
+ invalidateFilter();
return this;
}
@@ -52,7 +53,8 @@ bool QgsFieldProxyModel::filterAcceptsRow( int source_row, const QModelIndex &so
( mFilters.testFlag( LongLong ) && type == QVariant::LongLong ) ||
( mFilters.testFlag( Int ) && type == QVariant::Int ) ||
( mFilters.testFlag( Double ) && type == QVariant::Double ) ||
- ( mFilters.testFlag( Date ) && type == QVariant::Date ) )
+ ( mFilters.testFlag( Date ) && type == QVariant::Date ) ||
+ ( mFilters.testFlag( Date ) && type == QVariant::DateTime ) )
return true;
return false;
diff --git a/src/gui/symbology-ng/qgssymbollayerv2widget.cpp b/src/gui/symbology-ng/qgssymbollayerv2widget.cpp
index a840de9..ed76136 100644
--- a/src/gui/symbology-ng/qgssymbollayerv2widget.cpp
+++ b/src/gui/symbology-ng/qgssymbollayerv2widget.cpp
@@ -3109,6 +3109,7 @@ QgsGeometryGeneratorSymbolLayerWidget::QgsGeometryGeneratorSymbolLayerWidget( co
setupUi( this );
modificationExpressionSelector->setLayer( const_cast<QgsVectorLayer*>( vl ) );
modificationExpressionSelector->loadFieldNames();
+ modificationExpressionSelector->setExpressionContext( _getExpressionContext( this ) );
cbxGeometryType->addItem( QgsApplication::getThemeIcon( "/mIconPolygonLayer.svg" ), tr( "Polygon / MultiPolygon" ), QgsSymbolV2::Fill );
cbxGeometryType->addItem( QgsApplication::getThemeIcon( "/mIconLineLayer.svg" ), tr( "LineString / MultiLineString" ), QgsSymbolV2::Line );
cbxGeometryType->addItem( QgsApplication::getThemeIcon( "/mIconPointLayer.svg" ), tr( "Point / MultiPoint" ), QgsSymbolV2::Marker );
diff --git a/src/providers/delimitedtext/qgsdelimitedtextfeatureiterator.cpp b/src/providers/delimitedtext/qgsdelimitedtextfeatureiterator.cpp
index 6af54bf..43eacf8 100644
--- a/src/providers/delimitedtext/qgsdelimitedtextfeatureiterator.cpp
+++ b/src/providers/delimitedtext/qgsdelimitedtextfeatureiterator.cpp
@@ -128,6 +128,7 @@ QgsDelimitedTextFeatureIterator::QgsDelimitedTextFeatureIterator( QgsDelimitedTe
!( mRequest.flags() & QgsFeatureRequest::NoGeometry )
|| mTestGeometry
|| ( mTestSubset && mSource->mSubsetExpression->needsGeometry() )
+ || ( request.filterType() == QgsFeatureRequest::FilterExpression && request.filterExpression()->needsGeometry() )
)
)
{
diff --git a/src/providers/mssql/qgsmssqlfeatureiterator.cpp b/src/providers/mssql/qgsmssqlfeatureiterator.cpp
index 5cff00a..d315b52 100644
--- a/src/providers/mssql/qgsmssqlfeatureiterator.cpp
+++ b/src/providers/mssql/qgsmssqlfeatureiterator.cpp
@@ -102,7 +102,10 @@ void QgsMssqlFeatureIterator::BuildStatement( const QgsFeatureRequest& request )
}
// get geometry col
- if ( !( request.flags() & QgsFeatureRequest::NoGeometry ) && mSource->isSpatial() )
+ if (( !( request.flags() & QgsFeatureRequest::NoGeometry )
+ || ( request.filterType() == QgsFeatureRequest::FilterExpression && request.filterExpression()->needsGeometry() )
+ )
+ && mSource->isSpatial() )
{
mStatement += QString( ",[%1]" ).arg( mSource->mGeometryColName );
}
diff --git a/src/providers/ogr/qgsogrconnpool.h b/src/providers/ogr/qgsogrconnpool.h
index 6f5e059..5d28f78 100644
--- a/src/providers/ogr/qgsogrconnpool.h
+++ b/src/providers/ogr/qgsogrconnpool.h
@@ -35,7 +35,8 @@ inline QString qgsConnectionPool_ConnectionToName( QgsOgrConn* c )
inline void qgsConnectionPool_ConnectionCreate( QString connInfo, QgsOgrConn*& c )
{
c = new QgsOgrConn;
- c->ds = OGROpen( connInfo.toUtf8().constData(), false, nullptr );
+ QString filePath = connInfo.left( connInfo.indexOf( "|" ) );
+ c->ds = OGROpen( filePath.toUtf8().constData(), false, nullptr );
c->path = connInfo;
c->valid = true;
}
diff --git a/src/providers/ogr/qgsogrfeatureiterator.cpp b/src/providers/ogr/qgsogrfeatureiterator.cpp
index 9bb8294..8850109 100644
--- a/src/providers/ogr/qgsogrfeatureiterator.cpp
+++ b/src/providers/ogr/qgsogrfeatureiterator.cpp
@@ -43,7 +43,7 @@ QgsOgrFeatureIterator::QgsOgrFeatureIterator( QgsOgrFeatureSource* source, bool
{
mFeatureFetched = false;
- mConn = QgsOgrConnPool::instance()->acquireConnection( mSource->mFilePath );
+ mConn = QgsOgrConnPool::instance()->acquireConnection( mSource->mProvider->dataSourceUri() );
if ( mSource->mLayerName.isNull() )
{
@@ -74,6 +74,10 @@ QgsOgrFeatureIterator::QgsOgrFeatureIterator( QgsOgrFeatureSource* source, bool
}
mRequest.setSubsetOfAttributes( attrs );
}
+ if ( request.filterType() == QgsFeatureRequest::FilterExpression && request.filterExpression()->needsGeometry() )
+ {
+ mFetchGeometry = true;
+ }
// make sure we fetch just relevant fields
// unless it's a VRT data source filtered by geometry as we don't know which
@@ -226,13 +230,14 @@ bool QgsOgrFeatureIterator::fetchFeature( QgsFeature& feature )
{
if ( !readFeature( fet, feature ) )
continue;
+ else
+ OGR_F_Destroy( fet );
if ( !mRequest.filterRect().isNull() && !feature.constGeometry() )
continue;
// we have a feature, end this cycle
feature.setValid( true );
- OGR_F_Destroy( fet );
return true;
} // while
@@ -408,7 +413,7 @@ bool QgsOgrFeatureIterator::readFeature( OGRFeatureH fet, QgsFeature& feature )
QgsOgrFeatureSource::QgsOgrFeatureSource( const QgsOgrProvider* p )
: mProvider( p )
{
- mFilePath = p->filePath();
+ mDataSource = p->dataSourceUri();
mLayerName = p->layerName();
mLayerIndex = p->layerIndex();
mSubsetString = p->mSubsetString;
@@ -416,12 +421,12 @@ QgsOgrFeatureSource::QgsOgrFeatureSource( const QgsOgrProvider* p )
mFields = p->mAttributeFields;
mDriverName = p->ogrDriverName;
mOgrGeometryTypeFilter = wkbFlatten( p->mOgrGeometryTypeFilter );
- QgsOgrConnPool::instance()->ref( mFilePath );
+ QgsOgrConnPool::instance()->ref( mDataSource );
}
QgsOgrFeatureSource::~QgsOgrFeatureSource()
{
- QgsOgrConnPool::instance()->unref( mFilePath );
+ QgsOgrConnPool::instance()->unref( mDataSource );
}
QgsFeatureIterator QgsOgrFeatureSource::getFeatures( const QgsFeatureRequest& request )
diff --git a/src/providers/ogr/qgsogrfeatureiterator.h b/src/providers/ogr/qgsogrfeatureiterator.h
index f9732b7..57b2a82 100644
--- a/src/providers/ogr/qgsogrfeatureiterator.h
+++ b/src/providers/ogr/qgsogrfeatureiterator.h
@@ -34,7 +34,7 @@ class QgsOgrFeatureSource : public QgsAbstractFeatureSource
protected:
const QgsOgrProvider* mProvider;
- QString mFilePath;
+ QString mDataSource;
QString mLayerName;
int mLayerIndex;
QString mSubsetString;
diff --git a/src/providers/ogr/qgsogrprovider.cpp b/src/providers/ogr/qgsogrprovider.cpp
index 7e6df60..a170890 100644
--- a/src/providers/ogr/qgsogrprovider.cpp
+++ b/src/providers/ogr/qgsogrprovider.cpp
@@ -374,7 +374,7 @@ QgsOgrProvider::QgsOgrProvider( QString const & uri )
<< QgsVectorDataProvider::NativeType( tr( "Date & Time" ), "datetime", QVariant::DateTime );
}
- QgsOgrConnPool::instance()->ref( mFilePath );
+ QgsOgrConnPool::instance()->ref( dataSourceUri() );
}
QgsOgrProvider::~QgsOgrProvider()
@@ -685,7 +685,7 @@ OGRwkbGeometryType QgsOgrProvider::getOgrGeomType( OGRLayerH ogrLayer )
void QgsOgrProvider::loadFields()
{
- QgsOgrConnPool::instance()->invalidateConnections( filePath() );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
//the attribute fields need to be read again when the encoding changes
mAttributeFields.clear();
@@ -1276,7 +1276,7 @@ bool QgsOgrProvider::changeAttributeValues( const QgsChangedAttributesMap &attr_
{
pushError( tr( "OGR error syncing to disk: %1" ).arg( CPLGetLastErrorMsg() ) );
}
- QgsOgrConnPool::instance()->invalidateConnections( filePath() );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
return true;
}
@@ -1341,7 +1341,7 @@ bool QgsOgrProvider::changeGeometryValues( const QgsGeometryMap &geometry_map )
OGR_F_Destroy( theOGRFeature );
}
- QgsOgrConnPool::instance()->invalidateConnections( filePath() );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
return syncToDisc();
}
@@ -2540,7 +2540,7 @@ QByteArray QgsOgrProvider::quotedIdentifier( QByteArray field ) const
void QgsOgrProvider::forceReload()
{
- QgsOgrConnPool::instance()->invalidateConnections( filePath() );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
}
QByteArray QgsOgrUtils::quotedIdentifier( QByteArray field, const QString& ogrDriverName )
@@ -2605,7 +2605,7 @@ bool QgsOgrProvider::syncToDisc()
{
shapeIndex = true;
close();
- QgsOgrConnPool::instance()->invalidateConnections( mFilePath );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
QFile::remove( sbnIndexFile );
open();
}
@@ -2621,7 +2621,7 @@ bool QgsOgrProvider::syncToDisc()
mShapefileMayBeCorrupted = false;
- QgsOgrConnPool::instance()->ref( mFilePath );
+ QgsOgrConnPool::instance()->ref( dataSourceUri() );
if ( shapeIndex )
{
return createSpatialIndex();
@@ -2671,7 +2671,7 @@ void QgsOgrProvider::recalculateFeatureCount()
OGR_L_SetSpatialFilter( ogrLayer, filter );
}
- QgsOgrConnPool::instance()->invalidateConnections( filePath() );
+ QgsOgrConnPool::instance()->invalidateConnections( dataSourceUri() );
}
bool QgsOgrProvider::doesStrictFeatureTypeCheck() const
diff --git a/src/providers/oracle/qgsoraclefeatureiterator.cpp b/src/providers/oracle/qgsoraclefeatureiterator.cpp
index e73fe33..f3ae92e 100644
--- a/src/providers/oracle/qgsoraclefeatureiterator.cpp
+++ b/src/providers/oracle/qgsoraclefeatureiterator.cpp
@@ -68,6 +68,10 @@ QgsOracleFeatureIterator::QgsOracleFeatureIterator( QgsOracleFeatureSource* sour
{
// fetch geometry if requested
mFetchGeometry = ( mRequest.flags() & QgsFeatureRequest::NoGeometry ) == 0;
+ if ( mRequest.filterType() == QgsFeatureRequest::FilterExpression && mRequest.filterExpression()->needsGeometry() )
+ {
+ mFetchGeometry = true;
+ }
if ( !mRequest.filterRect().isNull() )
{
diff --git a/src/providers/postgres/qgspostgresfeatureiterator.cpp b/src/providers/postgres/qgspostgresfeatureiterator.cpp
index 8cbc710..c66eaf3 100644
--- a/src/providers/postgres/qgspostgresfeatureiterator.cpp
+++ b/src/providers/postgres/qgspostgresfeatureiterator.cpp
@@ -37,6 +37,7 @@ QgsPostgresFeatureIterator::QgsPostgresFeatureIterator( QgsPostgresFeatureSource
, mExpressionCompiled( false )
, mOrderByCompiled( false )
, mLastFetch( false )
+ , mFilterRequiresGeometry( false )
{
if ( !source->mTransactionConnection )
{
@@ -101,6 +102,7 @@ QgsPostgresFeatureIterator::QgsPostgresFeatureIterator( QgsPostgresFeatureSource
}
mRequest.setSubsetOfAttributes( attrs );
}
+ mFilterRequiresGeometry = request.filterExpression()->needsGeometry();
if ( QSettings().value( "/qgis/compileExpressions", true ).toBool() )
{
@@ -436,7 +438,7 @@ QString QgsPostgresFeatureIterator::whereClauseRect()
bool QgsPostgresFeatureIterator::declareCursor( const QString& whereClause, long limit, bool closeOnFail, const QString& orderBy )
{
- mFetchGeometry = !( mRequest.flags() & QgsFeatureRequest::NoGeometry ) && !mSource->mGeometryColumn.isNull();
+ mFetchGeometry = ( !( mRequest.flags() & QgsFeatureRequest::NoGeometry ) || mFilterRequiresGeometry ) && !mSource->mGeometryColumn.isNull();
#if 0
// TODO: check that all field indexes exist
if ( !hasAllFields )
diff --git a/src/providers/postgres/qgspostgresfeatureiterator.h b/src/providers/postgres/qgspostgresfeatureiterator.h
index aad3a1b..c61deda 100644
--- a/src/providers/postgres/qgspostgresfeatureiterator.h
+++ b/src/providers/postgres/qgspostgresfeatureiterator.h
@@ -129,6 +129,7 @@ class QgsPostgresFeatureIterator : public QgsAbstractFeatureIteratorFromSource<Q
bool mExpressionCompiled;
bool mOrderByCompiled;
bool mLastFetch;
+ bool mFilterRequiresGeometry;
};
#endif // QGSPOSTGRESFEATUREITERATOR_H
diff --git a/src/providers/spatialite/qgsspatialitefeatureiterator.cpp b/src/providers/spatialite/qgsspatialitefeatureiterator.cpp
index 72dbd5b..d2b5b79 100644
--- a/src/providers/spatialite/qgsspatialitefeatureiterator.cpp
+++ b/src/providers/spatialite/qgsspatialitefeatureiterator.cpp
@@ -95,6 +95,10 @@ QgsSpatiaLiteFeatureIterator::QgsSpatiaLiteFeatureIterator( QgsSpatiaLiteFeature
}
mRequest.setSubsetOfAttributes( attrs );
}
+ if ( request.filterExpression()->needsGeometry() )
+ {
+ mFetchGeometry = true;
+ }
if ( QSettings().value( "/qgis/compileExpressions", true ).toBool() )
{
diff --git a/src/providers/virtual/qgsvirtuallayerfeatureiterator.cpp b/src/providers/virtual/qgsvirtuallayerfeatureiterator.cpp
index 3c70825..21c06e2 100644
--- a/src/providers/virtual/qgsvirtuallayerfeatureiterator.cpp
+++ b/src/providers/virtual/qgsvirtuallayerfeatureiterator.cpp
@@ -121,7 +121,9 @@ QgsVirtualLayerFeatureIterator::QgsVirtualLayerFeatureIterator( QgsVirtualLayerF
}
}
// the last column is the geometry, if any
- if ( !( request.flags() & QgsFeatureRequest::NoGeometry ) && !mDefinition.geometryField().isNull() && mDefinition.geometryField() != "*no*" )
+ if (( !( request.flags() & QgsFeatureRequest::NoGeometry )
+ || ( request.filterType() == QgsFeatureRequest::FilterExpression && request.filterExpression()->needsGeometry() ) )
+ && !mDefinition.geometryField().isNull() && mDefinition.geometryField() != "*no*" )
{
columns += "," + quotedColumn( mDefinition.geometryField() );
}
diff --git a/src/python/qgspythonutilsimpl.cpp b/src/python/qgspythonutilsimpl.cpp
index 3607f74..1c8f5ad 100644
--- a/src/python/qgspythonutilsimpl.cpp
+++ b/src/python/qgspythonutilsimpl.cpp
@@ -298,9 +298,9 @@ bool QgsPythonUtilsImpl::runStringUnsafe( const QString& command, bool single )
// TODO: convert special characters from unicode strings u"..." to \uXXXX
// so that they're not mangled to utf-8
// (non-unicode strings can be mangled)
- PyRun_String( command.toUtf8().data(), single ? Py_single_input : Py_file_input, mMainDict, mMainDict );
-
+ PyObject* obj = PyRun_String( command.toUtf8().data(), single ? Py_single_input : Py_file_input, mMainDict, mMainDict );
bool res = nullptr == PyErr_Occurred();
+ Py_DECREF( obj );
// we are done calling python API, release global interpreter lock
PyGILState_Release( gstate );
@@ -581,6 +581,8 @@ bool QgsPythonUtilsImpl::evalString( const QString& command, QString& result )
if ( success )
result = PyObjectToQString( res );
+ Py_XDECREF( res );
+
// we are done calling python API, release global interpreter lock
PyGILState_Release( gstate );
diff --git a/src/server/qgswfsserver.cpp b/src/server/qgswfsserver.cpp
index 4e4fbcb..51115ba 100644
--- a/src/server/qgswfsserver.cpp
+++ b/src/server/qgswfsserver.cpp
@@ -507,7 +507,8 @@ int QgsWFSServer::getFeature( QgsRequestHandler& request, const QString& format
QgsFeature feature;
mWithGeom = true;
- //QgsAttributeList attrIndexes = provider->attributeIndexes();
+
+ //Using pending attributes and pending fields
QgsAttributeList attrIndexes = layer->pendingAllAttributesList();
QDomNodeList queryChildNodes = queryElem.childNodes();
@@ -515,8 +516,7 @@ int QgsWFSServer::getFeature( QgsRequestHandler& request, const QString& format
{
QStringList::const_iterator alstIt;
QList<int> idxList;
- QMap<QString, int> fieldMap = provider->fieldNameMap();
- QMap<QString, int>::const_iterator fieldIt;
+ QgsFields fields = layer->pendingFields();
QString fieldName;
QDomElement propertyElem;
for ( int q = 0; q < queryChildNodes.size(); q++ )
@@ -529,10 +529,10 @@ int QgsWFSServer::getFeature( QgsRequestHandler& request, const QString& format
{
fieldName = fieldName.section( ":", 1, 1 );
}
- fieldIt = fieldMap.find( fieldName );
- if ( fieldIt != fieldMap.end() )
+ int fieldNameIdx = fields.fieldNameIndex( fieldName );
+ if ( fieldNameIdx > -1 )
{
- idxList.append( fieldIt.value() );
+ idxList.append( fieldNameIdx );
}
}
}
@@ -896,7 +896,7 @@ int QgsWFSServer::getFeature( QgsRequestHandler& request, const QString& format
//map extent
searchRect = layer->extent();
- //QgsAttributeList attrIndexes = provider->attributeIndexes();
+ //Using pending attributes and pending fields
QgsAttributeList attrIndexes = layer->pendingAllAttributesList();
if ( mPropertyName != "*" )
{
@@ -905,16 +905,15 @@ int QgsWFSServer::getFeature( QgsRequestHandler& request, const QString& format
{
QStringList::const_iterator alstIt;
QList<int> idxList;
- QMap<QString, int> fieldMap = provider->fieldNameMap();
- QMap<QString, int>::const_iterator fieldIt;
+ QgsFields fields = layer->pendingFields();
QString fieldName;
for ( alstIt = attrList.begin(); alstIt != attrList.end(); ++alstIt )
{
fieldName = *alstIt;
- fieldIt = fieldMap.find( fieldName );
- if ( fieldIt != fieldMap.end() )
+ int fieldNameIdx = fields.fieldNameIndex( fieldName );
+ if ( fieldNameIdx > -1 )
{
- idxList.append( fieldIt.value() );
+ idxList.append( fieldNameIdx );
}
}
if ( !idxList.isEmpty() )
@@ -1475,7 +1474,15 @@ QDomDocument QgsWFSServer::transaction( const QString& requestBody )
mTypeName = typeNameElem.tagName();
layerList = mConfigParser->mapLayerFromTypeName( mTypeName );
- currentLayer = layerList.at( 0 );
+ // Could be empty!
+ if ( layerList.count() > 0 )
+ {
+ currentLayer = layerList.at( 0 );
+ }
+ else
+ {
+ throw QgsMapServiceException( "RequestNotWellFormed", QString( "Wrong TypeName: %1" ).arg( mTypeName ) );
+ }
QgsVectorLayer* layer = qobject_cast<QgsVectorLayer*>( currentLayer );
// it's a vectorlayer and defined by the administrator as a WFS layer
diff --git a/tests/src/core/CMakeLists.txt b/tests/src/core/CMakeLists.txt
index 9c69357..2e19743 100644
--- a/tests/src/core/CMakeLists.txt
+++ b/tests/src/core/CMakeLists.txt
@@ -112,6 +112,7 @@ ADD_QGIS_TEST(composertabletest testqgscomposertable.cpp)
ADD_QGIS_TEST(composertablev2test testqgscomposertablev2.cpp)
ADD_QGIS_TEST(composerutils testqgscomposerutils.cpp)
ADD_QGIS_TEST(compositiontest testqgscomposition.cpp)
+ADD_QGIS_TEST(connectionpooltest testqgsconnectionpool.cpp)
ADD_QGIS_TEST(contrastenhancementtest testcontrastenhancements.cpp)
ADD_QGIS_TEST(coordinatereferencesystemtest testqgscoordinatereferencesystem.cpp)
ADD_QGIS_TEST(coordinatetransformtest testqgscoordinatetransform.cpp)
diff --git a/tests/src/core/testqgsconnectionpool.cpp b/tests/src/core/testqgsconnectionpool.cpp
new file mode 100644
index 0000000..a350997
--- /dev/null
+++ b/tests/src/core/testqgsconnectionpool.cpp
@@ -0,0 +1,141 @@
+/***************************************************************************
+ testqgsconnectionpool.cpp
+ -----------------------
+ begin : April 2016
+ copyright : (C) 2016 by Sandro Mani
+ email : manisandro at gmail.com
+ ***************************************************************************/
+
+/***************************************************************************
+ * *
+ * This program is free software; you can redistribute it and/or modify *
+ * it under the terms of the GNU General Public License as published by *
+ * the Free Software Foundation; either version 2 of the License, or *
+ * (at your option) any later version. *
+ * *
+ ***************************************************************************/
+#include "qgsapplication.h"
+#include "qgsgeometry.h"
+#include "qgspointv2.h"
+#include "qgslinestringv2.h"
+#include "qgsvectorlayer.h"
+#include <QEventLoop>
+#include <QObject>
+#include <QTemporaryFile>
+#include <QtConcurrentMap>
+#include <QtTest/QtTest>
+
+class TestQgsConnectionPool: public QObject
+{
+ Q_OBJECT
+
+ private slots:
+ void initTestCase();
+ void cleanupTestCase();
+ void layersFromSameDatasetGPX();
+
+ private:
+ struct ReadJob
+ {
+ ReadJob( QgsVectorLayer* _layer ) : layer( _layer ) {}
+ QgsVectorLayer* layer;
+ QList<QgsFeature> features;
+ };
+
+ static void processJob( ReadJob& job )
+ {
+ QgsFeatureIterator it = job.layer->getFeatures();
+ QgsFeature f;
+ while ( it.nextFeature( f ) )
+ {
+ job.features.append( f );
+ }
+ }
+
+};
+
+void TestQgsConnectionPool::initTestCase()
+{
+ QgsApplication::init();
+ QgsApplication::initQgis();
+
+}
+
+void TestQgsConnectionPool::cleanupTestCase()
+{
+ QgsApplication::exitQgis();
+}
+
+void TestQgsConnectionPool::layersFromSameDatasetGPX()
+{
+ // Tests whether features are correctly retrevied from different layers which are
+ // loaded from the same dataset. See issue #14560
+ int nWaypoints = 100000;
+ int nRoutes = 100000;
+ int nRoutePts = 10;
+ QTemporaryFile testFile( "testXXXXXX.gpx" );
+ testFile.setAutoRemove( false );
+ testFile.open();
+ testFile.write( "<gpx version=\"1.1\" creator=\"qgis\">\n" );
+ for ( int i = 0; i < nWaypoints; ++i )
+ {
+ testFile.write( QString( "<wpt lon=\"%1\" lat=\"%1\"><name></name></wpt>\n" ).arg( i ).toLocal8Bit() );
+ }
+ for ( int i = 0; i < nRoutes; ++i )
+ {
+ testFile.write( "<rte><name></name><number></number>\n" );
+ for ( int j = 0; j < nRoutePts; ++j )
+ {
+ testFile.write( QString( "<rtept lon=\"%1\" lat=\"%2\"/>\n" ).arg( j ).arg( i ).toLocal8Bit() );
+ }
+ testFile.write( "</rte>\n" );
+ }
+ testFile.write( "</gpx>\n" );
+ testFile.close();
+
+ QgsVectorLayer* layer1 = new QgsVectorLayer( testFile.fileName() + "|layername=waypoints", "Waypoints", "ogr" );
+ QVERIFY( layer1->isValid() );
+ QgsVectorLayer* layer2 = new QgsVectorLayer( testFile.fileName() + "|layername=routes", "Routes", "ogr" );
+ QVERIFY( layer2->isValid() );
+
+ QList<ReadJob> jobs = QList<ReadJob>() << ReadJob( layer1 ) << ReadJob( layer2 );
+
+ QEventLoop evLoop;
+ QFutureWatcher<void> futureWatcher;
+ connect( &futureWatcher, SIGNAL( finished() ), &evLoop, SLOT( quit() ) );
+ futureWatcher.setFuture( QtConcurrent::map( jobs, processJob ) );
+ evLoop.exec();
+
+ QList<QgsFeature>& layer1Features = jobs[0].features;
+ QList<QgsFeature>& layer2Features = jobs[1].features;
+
+ QVERIFY( layer1Features.count() == nWaypoints );
+ QVERIFY( layer2Features.count() == nRoutes );
+
+ for ( int i = 0, n = layer1Features.count(); i < n; ++i )
+ {
+ const QgsPointV2* geom = dynamic_cast<const QgsPointV2*>( layer1Features[i].geometry()->geometry() );
+ QVERIFY( geom != nullptr );
+ QVERIFY( qFuzzyCompare( geom->x(), i ) );
+ QVERIFY( qFuzzyCompare( geom->y(), i ) );
+ }
+ for ( int i = 0, n = layer2Features.count(); i < n; ++i )
+ {
+ const QgsLineStringV2* geom = dynamic_cast<const QgsLineStringV2*>( layer2Features[i].geometry()->geometry() );
+ QVERIFY( geom != nullptr );
+ int nVtx = geom->vertexCount();
+ QVERIFY( nVtx == nRoutePts );
+ for ( int j = 0; j < nVtx; ++j )
+ {
+ QgsPointV2 p = geom->vertexAt( QgsVertexId( 0, 0, j ) );
+ QVERIFY( qFuzzyCompare( p.x(), j ) );
+ QVERIFY( qFuzzyCompare( p.y(), i ) );
+ }
+ }
+ delete layer1;
+ delete layer2;
+ QFile( testFile.fileName() ).remove();
+}
+
+QTEST_MAIN( TestQgsConnectionPool )
+#include "testqgsconnectionpool.moc"
diff --git a/tests/src/core/testqgsexpression.cpp b/tests/src/core/testqgsexpression.cpp
index ad81e47..4edfe0b 100644
--- a/tests/src/core/testqgsexpression.cpp
+++ b/tests/src/core/testqgsexpression.cpp
@@ -2036,6 +2036,47 @@ class TestQgsExpression: public QObject
QgsExpression nodeExpression( "1 IN (1, 2, 3, 4)" );
QgsExpression nodeExpression2( nodeExpression );
}
+
+ void test_columnRefUnprepared()
+ {
+ //test retrieving fields from feature when expression is unprepared - explicitly specified fields collection
+ //should take precedence over feature's field collection
+
+ QgsFields fields;
+ fields.append( QgsField( "f1", QVariant::String ) );
+
+ QgsFeature f( 1 );
+ f.setFields( fields );
+
+ //also add a joined field - this will not be available in feature's field collection
+ fields.append( QgsField( "j1", QVariant::String ), QgsFields::OriginJoin, 1 );
+
+ f.setAttributes( QgsAttributes() << QVariant( "f1" ) << QVariant( "j1" ) );
+ f.setValid( true );
+
+ QgsExpression e( "\"f1\"" );
+ QgsExpressionContext context;
+ context.setFeature( f );
+ context.setFields( fields );
+ QVariant result = e.evaluate( &context );
+ QCOMPARE( result.toString(), QString( "f1" ) );
+
+ //test joined field
+ QgsExpression e2( "\"j1\"" );
+ result = e2.evaluate( &context );
+ QCOMPARE( result.toString(), QString( "j1" ) );
+
+ // final test - check that feature's field collection is also used when corresponding field NOT found
+ // in explicitly passed field collection
+ fields.append( QgsField( "f2", QVariant::String ) );
+ f.setFields( fields );
+ f.setAttributes( QgsAttributes() << QVariant( "f1" ) << QVariant( "j1" ) << QVariant( "f2" ) );
+ context.setFeature( f );
+ QgsExpression e3( "\"f2\"" );
+ result = e3.evaluate( &context );
+ QCOMPARE( result.toString(), QString( "f2" ) );
+ }
+
};
QTEST_MAIN( TestQgsExpression )
diff --git a/tests/src/core/testqgsgeometry.cpp b/tests/src/core/testqgsgeometry.cpp
index f0e9663..9a05468 100644
--- a/tests/src/core/testqgsgeometry.cpp
+++ b/tests/src/core/testqgsgeometry.cpp
@@ -3311,6 +3311,12 @@ void TestQgsGeometry::exportToGeoJSON()
obtained = geom->exportToGeoJSON();
geojson = "{\"type\": \"MultiPolygon\", \"coordinates\": [[[ [0, 0], [10, 0], [10, 10], [0, 10], [0, 0]]], [[ [2, 2], [4, 2], [4, 4], [2, 4], [2, 2]]]] }";
QCOMPARE( obtained, geojson );
+
+ // no geometry
+ QgsGeometry nullGeom( nullptr );
+ obtained = nullGeom.exportToGeoJSON();
+ geojson = "null";
+ QCOMPARE( obtained, geojson );
}
bool TestQgsGeometry::renderCheck( const QString& theTestName, const QString& theComment, int mismatchCount )
diff --git a/tests/src/gui/testqgsfieldexpressionwidget.cpp b/tests/src/gui/testqgsfieldexpressionwidget.cpp
index ff8d5f0..9700f38 100644
--- a/tests/src/gui/testqgsfieldexpressionwidget.cpp
+++ b/tests/src/gui/testqgsfieldexpressionwidget.cpp
@@ -50,6 +50,7 @@ class TestQgsFieldExpressionWidget : public QObject
void testRemoveJoin();
void asExpression();
void testIsValid();
+ void testFilters();
private:
QgsFieldExpressionWidget* mWidget;
@@ -219,6 +220,55 @@ void TestQgsFieldExpressionWidget::testIsValid()
QgsMapLayerRegistry::instance()->removeMapLayer( layer );
}
+void TestQgsFieldExpressionWidget::testFilters()
+{
+ QgsVectorLayer* layer = new QgsVectorLayer( "point?field=intfld:int&field=stringfld:string&field=string2fld:string&field=longfld:long&field=doublefld:double&field=datefld:date&field=timefld:time&field=datetimefld:datetime", "x", "memory" );
+ QgsMapLayerRegistry::instance()->addMapLayer( layer );
+
+ QScopedPointer< QgsFieldExpressionWidget > widget( new QgsFieldExpressionWidget() );
+ widget->setLayer( layer );
+
+ QCOMPARE( widget->mCombo->count(), 8 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "intfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 1 ), QString( "stringfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 2 ), QString( "string2fld" ) );
+ QCOMPARE( widget->mCombo->itemText( 3 ), QString( "longfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 4 ), QString( "doublefld" ) );
+ QCOMPARE( widget->mCombo->itemText( 5 ), QString( "datefld" ) );
+ QCOMPARE( widget->mCombo->itemText( 6 ), QString( "timefld" ) );
+ QCOMPARE( widget->mCombo->itemText( 7 ), QString( "datetimefld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::String );
+ QCOMPARE( widget->mCombo->count(), 2 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "stringfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 1 ), QString( "string2fld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::Int );
+ QCOMPARE( widget->mCombo->count(), 1 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "intfld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::LongLong );
+ QCOMPARE( widget->mCombo->count(), 1 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "longfld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::Double );
+ QCOMPARE( widget->mCombo->count(), 1 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "doublefld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::Numeric );
+ QCOMPARE( widget->mCombo->count(), 3 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "intfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 1 ), QString( "longfld" ) );
+ QCOMPARE( widget->mCombo->itemText( 2 ), QString( "doublefld" ) );
+
+ widget->setFilters( QgsFieldProxyModel::Date );
+ QCOMPARE( widget->mCombo->count(), 2 );
+ QCOMPARE( widget->mCombo->itemText( 0 ), QString( "datefld" ) );
+ QCOMPARE( widget->mCombo->itemText( 1 ), QString( "datetimefld" ) );
+
+ QgsMapLayerRegistry::instance()->removeMapLayer( layer );
+}
+
QTEST_MAIN( TestQgsFieldExpressionWidget )
#include "testqgsfieldexpressionwidget.moc"
diff --git a/tests/src/python/providertestbase.py b/tests/src/python/providertestbase.py
index be585b2..c2ff215 100644
--- a/tests/src/python/providertestbase.py
+++ b/tests/src/python/providertestbase.py
@@ -62,7 +62,7 @@ class ProviderTestCase(object):
self.assertFalse(geometries[pk], 'Expected null geometry for {}'.format(pk))
def assert_query(self, provider, expression, expected):
- result = set([f['pk'] for f in provider.getFeatures(QgsFeatureRequest().setFilterExpression(expression))])
+ result = set([f['pk'] for f in provider.getFeatures(QgsFeatureRequest().setFilterExpression(expression).setFlags(QgsFeatureRequest.NoGeometry))])
assert set(expected) == result, 'Expected {} and got {} when testing expression "{}"'.format(set(expected), result, expression)
# Also check that filter works when referenced fields are not being retrieved by request
@@ -154,6 +154,9 @@ class ProviderTestCase(object):
# against numeric literals
self.assert_query(provider, 'num_char IN (2, 4, 5)', [2, 4, 5])
+ # geometry
+ self.assert_query(provider, 'intersects($geometry,geom_from_wkt( \'Polygon ((-72.2 66.1, -65.2 66.1, -65.2 72.0, -72.2 72.0, -72.2 66.1))\'))', [1, 2])
+
def testGetFeaturesUncompiled(self):
try:
self.disableCompiler()
diff --git a/tests/src/python/qgis_interface.py b/tests/src/python/qgis_interface.py
index 6c73118..3732205 100644
--- a/tests/src/python/qgis_interface.py
+++ b/tests/src/python/qgis_interface.py
@@ -26,7 +26,7 @@ __copyright__ = ('Copyright (c) 2010 by Ivan Mincik, ivan.mincik at gista.sk and '
import qgis
-from PyQt.QtCore import QObject
+from qgis.PyQt.QtCore import QObject
from qgis.core import QgsMapLayerRegistry
diff --git a/tests/src/python/test_qgsblendmodes.py b/tests/src/python/test_qgsblendmodes.py
index 76aa6b6..2878eea 100644
--- a/tests/src/python/test_qgsblendmodes.py
+++ b/tests/src/python/test_qgsblendmodes.py
@@ -23,6 +23,7 @@ __copyright__ = '(C) 2013, Nyall Dawson, Massimo Endrighi'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
+import qgis
import os
from PyQt4.QtCore import QSize
diff --git a/tests/src/python/test_qgscomposition.py b/tests/src/python/test_qgscomposition.py
index 518a6ce..f758c5b 100644
--- a/tests/src/python/test_qgscomposition.py
+++ b/tests/src/python/test_qgscomposition.py
@@ -12,6 +12,7 @@ __copyright__ = 'Copyright 2012, The QGIS Project'
# This will get replaced with a git SHA1 when you do a git archive
__revision__ = '$Format:%H$'
+import qgis
import os
from PyQt4.QtCore import QFileInfo, QDir
diff --git a/tests/src/python/test_qgsgeometrygeneratorsymbollayerv2.py b/tests/src/python/test_qgsgeometrygeneratorsymbollayerv2.py
index 0ef8302..f9e145b 100644
--- a/tests/src/python/test_qgsgeometrygeneratorsymbollayerv2.py
+++ b/tests/src/python/test_qgsgeometrygeneratorsymbollayerv2.py
@@ -25,7 +25,7 @@ __revision__ = '$Format:%H$'
import os
-from PyQt.QtCore import QSize
+from qgis.PyQt.QtCore import QSize
from qgis.core import (
QgsVectorLayer,
diff --git a/tests/src/python/test_qgsrelationeditwidget.py b/tests/src/python/test_qgsrelationeditwidget.py
index 0097d36..5ca8350 100644
--- a/tests/src/python/test_qgsrelationeditwidget.py
+++ b/tests/src/python/test_qgsrelationeditwidget.py
@@ -36,18 +36,18 @@ from qgis.gui import (
QgsFeatureListView
)
-from PyQt.QtCore import (
+from qgis.PyQt.QtCore import (
QTimer
)
-from PyQt.QtWidgets import (
+from qgis.PyQt.QtWidgets import (
QWidget,
QToolButton,
QTableView,
QListView
)
-from PyQt.QtGui import (
+from qgis.PyQt.QtGui import (
QApplication
)
diff --git a/tests/src/python/test_qgssymbollayerv2.py b/tests/src/python/test_qgssymbollayerv2.py
index 9a673d4..bc96748 100644
--- a/tests/src/python/test_qgssymbollayerv2.py
+++ b/tests/src/python/test_qgssymbollayerv2.py
@@ -364,6 +364,14 @@ class TestQgsSymbolLayerV2(unittest.TestCase):
mMessage = 'Expected "%s" got "%s"' % (mExpectedValue, mValue)
assert mExpectedValue == mValue, mMessage
+ # test colors, need to make sure colors are passed/retrieved from subsymbol
+ mSymbolLayer.setColor(QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.color(), QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(150, 50, 100))
+ mSymbolLayer.subSymbol().setColor(QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.color(), QColor(250, 150, 200))
+
def testQgsLinePatternFillSymbolLayer(self):
"""
Create a new style from a .sld file and match test
@@ -404,8 +412,16 @@ class TestQgsSymbolLayerV2(unittest.TestCase):
mMessage = 'Expected "%s" got "%s"' % (mExpectedValue, mValue)
assert mExpectedValue == mValue, mMessage
+ # test colors, need to make sure colors are passed/retrieved from subsymbol
+ mSymbolLayer.setColor(QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.color(), QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(150, 50, 100))
+ mSymbolLayer.subSymbol().setColor(QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.color(), QColor(250, 150, 200))
+
@unittest.expectedFailure
- def testQgsPointPatternFillSymbolLayer(self):
+ def testQgsPointPatternFillSymbolLayerSld(self):
"""
Create a new style from a .sld file and match test
"""
@@ -452,6 +468,20 @@ class TestQgsSymbolLayerV2(unittest.TestCase):
mMessage = 'Expected "%s" got "%s"' % (mExpectedValue, mValue)
assert mExpectedValue == mValue, mMessage
+ def testQgsPointPatternFillSymbolLayer(self):
+ """
+ Test point pattern fill
+ """
+ # test colors, need to make sure colors are passed/retrieved from subsymbol
+ mSymbolLayer = QgsPointPatternFillSymbolLayer.create()
+
+ mSymbolLayer.setColor(QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.color(), QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(150, 50, 100))
+ mSymbolLayer.subSymbol().setColor(QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.color(), QColor(250, 150, 200))
+
def testQgsSVGFillSymbolLayer(self):
"""
Create a new style from a .sld file and match test
@@ -522,6 +552,14 @@ class TestQgsSymbolLayerV2(unittest.TestCase):
mMessage = 'Expected "%s" got "%s"' % (mExpectedValue, mValue)
assert mExpectedValue == mValue, mMessage
+ # test colors, need to make sure colors are passed/retrieved from subsymbol
+ mSymbolLayer.setColor(QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.color(), QColor(150, 50, 100))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(150, 50, 100))
+ mSymbolLayer.subSymbol().setColor(QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.subSymbol().color(), QColor(250, 150, 200))
+ self.assertEqual(mSymbolLayer.color(), QColor(250, 150, 200))
+
def testQgsSimpleLineSymbolLayerV2(self):
"""
Create a new style from a .sld file and match test
@@ -692,6 +730,5 @@ class TestQgsSymbolLayerV2(unittest.TestCase):
mMessage = 'Expected "%s" got "%s"' % (mExpectedValue, mValue)
assert mExpectedValue == mValue, mMessage
-
if __name__ == '__main__':
unittest.main()
diff --git a/tests/src/python/test_qgsvectorlayer.py b/tests/src/python/test_qgsvectorlayer.py
index ce3a835..6849901 100644
--- a/tests/src/python/test_qgsvectorlayer.py
+++ b/tests/src/python/test_qgsvectorlayer.py
@@ -967,8 +967,15 @@ class TestQgsVectorLayer(unittest.TestCase):
idx = layer.addExpressionField('5', QgsField('test', QVariant.LongLong))
- self.assertEquals(layer.getFeatures().next()[idx], 5)
- self.assertEquals(layer.pendingFields().count(), cnt + 1)
+ fet = next(layer.getFeatures())
+ self.assertEqual(fet[idx], 5)
+ # check fields
+ self.assertEqual(layer.fields().count(), cnt + 1)
+ self.assertEqual(fet.fields(), layer.fields())
+
+ # retrieve single feature and check fields
+ fet = next(layer.getFeatures(QgsFeatureRequest().setFilterFid(1)))
+ self.assertEqual(fet.fields(), layer.fields())
layer.updateExpressionField(idx, '9')
diff --git a/tests/src/python/utilities.py b/tests/src/python/utilities.py
index 1f5f6fa..14930a7 100644
--- a/tests/src/python/utilities.py
+++ b/tests/src/python/utilities.py
@@ -18,8 +18,8 @@ import glob
import platform
import tempfile
-from PyQt.QtCore import QSize, QDir
-from PyQt.QtWidgets import QWidget
+from PyQt4.QtCore import QSize, QDir
+from PyQt4.QtGui import QWidget
from qgis.core import (
QgsApplication,
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-grass/qgis.git
More information about the Pkg-grass-devel
mailing list