252 changes: 154 additions & 98 deletions NEWS

Large diffs are not rendered by default.

1 change: 1 addition & 0 deletions debian/libqgis-dev.install
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,4 @@ usr/include/qgis/*
usr/lib/libqgis_core.so
usr/lib/libqgis_gui.so
usr/lib/libqgis_analysis.so
usr/lib/libqgis_networkanalysis.so
3 changes: 0 additions & 3 deletions debian/libqgis{QGIS_ABI}-dev.install

This file was deleted.

17 changes: 14 additions & 3 deletions debian/rules
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@ CMAKE_OPTS := \
-D QGIS_CGIBIN_SUBDIR=/usr/lib/cgi-bin \
-D WITH_APIDOC=TRUE

MAKEFLAGS += VERBOSE=YES

ifneq (,$(findstring $(DISTRIBUTION),"squeeze wheezy lucid maverick natty oneiric precise"))
CMAKE_OPTS += -D WITH_PYSPATIALITE=TRUE
endif
Expand All @@ -57,18 +59,27 @@ else
CMAKE_OPTS += -D WITH_GLOBE=TRUE
endif

ifneq (,$(findstring $(DISTRIBUTION),"wheezy sid"))
CPPFLAGS := $(shell dpkg-buildflags --get CPPFLAGS)
CFLAGS := $(shell dpkg-buildflags --get CFLAGS) $(CPPFLAGS)
CXXFLAGS := $(shell dpkg-buildflags --get CXXFLAGS) $(CPPFLAGS)
LDFLAGS := $(shell dpkg-buildflags --get LDFLAGS)
endif

ifneq (,$(findstring noopt,$(DEB_BUILD_OPTIONS)))
CFLAGS += -O0
CXXFLAGS += -O0
else
CFLAGS += -O2
CXXFLAGS += -O2
endif

ifeq (,$(findstring nostrip,$(DEB_BUILD_OPTIONS)))
INSTALL_PROGRAM += -s
endif

ifneq (,$(findstring debug,$(DEB_BUILD_OPTIONS)))
CMAKE_OPTS += -D CMAKE_BUILD_TYPE=Debug -D ENABLE_TESTS=TRUE
MAKEFLAGS += VERBOSE=YES
endif

ifneq (,$(findstring profile,$(DEB_BUILD_OPTIONS)))
Expand Down Expand Up @@ -99,7 +110,7 @@ debian/build/CMakeCache.txt: $(TEMPLATES) CMakeLists.txt
# Add here commands to configure the package.
[ -d debian/build ] || mkdir debian/build
[ ! -e CMakeCache.txt ] || rm CMakeCache.txt
cd debian/build; cmake $(CMAKE_OPTS) ../..
cd debian/build; CFLAGS="$(CFLAGS)" CXXFLAGS="$(CXXFLAGS)" LDFLAGS="$(LDFLAGS)" cmake $(CMAKE_OPTS) ../..

build: build-stamp

Expand Down Expand Up @@ -144,7 +155,7 @@ install: build
$(MAKE) -C debian/build install DESTDIR=$(CURDIR)/debian/tmp

# remove unwanted files
rm debian/tmp/usr/share/qgis/doc/api/installdox
! [ -f debian/tmp/usr/share/qgis/doc/api/installdox ] || rm debian/tmp/usr/share/qgis/doc/api/installdox
! [ -f debian/tmp/usr/share/qgis/doc/api/jquery.js ] || rm debian/tmp/usr/share/qgis/doc/api/jquery.js

# Install menu pixmap
Expand Down
94 changes: 47 additions & 47 deletions doc/TRANSLATORS

Large diffs are not rendered by default.

339 changes: 199 additions & 140 deletions doc/news.html

Large diffs are not rendered by default.

54 changes: 54 additions & 0 deletions doc/news.t2t
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,60 @@ Change history for the QGIS Project
Last Updated: %%date(%A %B %d, %Y)
Last Change : %%mtime(%A %B %d, %Y)

= Whats new in Version 1.8.0 'Lisboa'? =

This is a new feature release. Building on the foundation of
QGIS 1.7.x releases, Lisboa introduces many new features,
improvements and bug fixes. Here is a summary of some of the
key new features.

- QGIS Browser - a stand alone app and a new panel in QGIS. The browser lets you easily navigate your file system and connection based (PostGIS, WFS etc.) datasets, preview them and drag and drop items into the canvas.
- DB Manager - the DB manager is now officially part of QGIS core. You can drag layers from the QGIS Browser into DB Manager and it will import your layer into your spatial database. Drag and drop tables between spatial databases and they will get imported. You can use the DB Manager to execute SQL queries against your spatial database and then view the spatial output for queries by adding the results to QGIS as a query layer.
- Action Tool - now there is a tool on the map tools toolbar that will allow you to click on a vector feature and execute an action.
- MSSQL Spatial Support - you can now connect to your Microsoft SQL Server spatial databases using QGIS.
- Customization - allows setting up simplified QGIS interface by hiding various components of main window and widgets in dialogs.
- New symbol layer types - Line Pattern Fill, Point Pattern fill
- Composers - have multiple lines on legend items using a specified character
- Expression based labelling
- Heatmap tool - a new core plugin has been added for generating raster heatmaps from point data. You may need to activate this plugin using the plugin manager.
- GPS Tracking - The GPS live tracking user interface was overhauled and many fixes and improvements were added to it.
- Menu Re-organisation - The menus were re-organised a little - we now have separate menus for Vector and Raster and many plugins were updated to place their menus in the new Vector and Raster top level menus.
- Offset Curves - a new digitising tool for creating offset curves was added.
- Terrain Analysis Plugin - a new core plugin was added for doing terrain analysis - and it can make really good looking coloured relief maps.
- Ellipse renderer — symbollayer to render ellipse shapes (and also rectangles, triangles, crosses by specifying width and height). Moreover, the symbol layer allows to set all parameters (width, height, colors, rotation, outline with) from data fields, in mm or map units
- New scale selector with predefined scales
- Option to add layers to selected or active group
- Pan To Selected tool
- New tools in Vector menu - densify geoemtries, Build spatial index
- Export/add geometry column tool can export info using layer CRS, project CRS or ellipsoidal measurements
- Model/view based tree for rules in rule-based renderer
- Updated CRS selector dialog
- Improvements in Spatial Bookmarks
- Plugin metadata in metadata.txt
- New plugin repository
- Refactored postgres data provider: support for arbitrary key (including non-numeric and multi column), support for requesting a certain geometry type and/or srid in QgsDataSourceURI
added gdal_fillnodata to GDALTools plugin
- Support for PostGIS TopoGeometry datatype
- Python bindings for vector field symbollayer and general updates to the python bindings.
- New message log window
- Benchmark program
- Row cache for attribute table
- Legend independent drawing order
- UUID generation widget for attribute table
- Added support of editable views in SpatiaLite databases
- Expression based widget in field calculator
- Creation of event layers in analysis lib using linear referencing
- Group selected layers option added to the TOC context menu
- load/save layer style (new symbology) from/to SLD document
- WFS support in QGIS Server
- Option to skip WKT geometry when copying from attribute table
- upport for zipped and gzipped layers
- Test suite now passes all tests on major platforms and nightly tests
- Copy and paste styles between layers
- Set tile size for WMS layers
- Support for nesting projects within other projects
-

= Whats new in Version 1.7.2 'Wroclaw'? =

This is a bugfix release over version 1.7.1. The following changes
Expand Down
3,962 changes: 2,004 additions & 1,958 deletions i18n/qgis_af.ts

Large diffs are not rendered by default.

3,968 changes: 2,005 additions & 1,963 deletions i18n/qgis_ar.ts

Large diffs are not rendered by default.

3,962 changes: 2,006 additions & 1,956 deletions i18n/qgis_bg.ts

Large diffs are not rendered by default.

3,969 changes: 2,002 additions & 1,967 deletions i18n/qgis_ca_ES.ts

Large diffs are not rendered by default.

2,519 changes: 1,303 additions & 1,216 deletions i18n/qgis_cs_CZ.ts

Large diffs are not rendered by default.

3,956 changes: 1,999 additions & 1,957 deletions i18n/qgis_da_DK.ts

Large diffs are not rendered by default.

4,194 changes: 2,025 additions & 2,169 deletions i18n/qgis_de.ts

Large diffs are not rendered by default.

3,965 changes: 2,017 additions & 1,948 deletions i18n/qgis_el_GR.ts

Large diffs are not rendered by default.

652 changes: 415 additions & 237 deletions i18n/qgis_es.ts

Large diffs are not rendered by default.

3,898 changes: 2,045 additions & 1,853 deletions i18n/qgis_et_EE.ts

Large diffs are not rendered by default.

3,961 changes: 2,006 additions & 1,955 deletions i18n/qgis_fa.ts

Large diffs are not rendered by default.

3,934 changes: 2,027 additions & 1,907 deletions i18n/qgis_fi.ts

Large diffs are not rendered by default.

2,277 changes: 1,201 additions & 1,076 deletions i18n/qgis_fr.ts

Large diffs are not rendered by default.

5,418 changes: 2,750 additions & 2,668 deletions i18n/qgis_gl_ES.ts

Large diffs are not rendered by default.

3,953 changes: 2,003 additions & 1,950 deletions i18n/qgis_he.ts

Large diffs are not rendered by default.

3,948 changes: 2,034 additions & 1,914 deletions i18n/qgis_hr_HR.ts

Large diffs are not rendered by default.

4,540 changes: 2,383 additions & 2,157 deletions i18n/qgis_hu.ts

Large diffs are not rendered by default.

3,896 changes: 2,040 additions & 1,856 deletions i18n/qgis_id.ts

Large diffs are not rendered by default.

3,926 changes: 2,023 additions & 1,903 deletions i18n/qgis_is.ts

Large diffs are not rendered by default.

10,172 changes: 2,022 additions & 8,150 deletions i18n/qgis_it.ts

Large diffs are not rendered by default.

7,161 changes: 3,722 additions & 3,439 deletions i18n/qgis_ja.ts

Large diffs are not rendered by default.

3,940 changes: 2,014 additions & 1,926 deletions i18n/qgis_ka_GE.ts

Large diffs are not rendered by default.

3,903 changes: 2,044 additions & 1,859 deletions i18n/qgis_ko_KR.ts

Large diffs are not rendered by default.

3,945 changes: 2,013 additions & 1,932 deletions i18n/qgis_lo.ts

Large diffs are not rendered by default.

3,955 changes: 2,006 additions & 1,949 deletions i18n/qgis_lt.ts

Large diffs are not rendered by default.

1,485 changes: 796 additions & 689 deletions i18n/qgis_lv.ts

Large diffs are not rendered by default.

3,943 changes: 2,024 additions & 1,919 deletions i18n/qgis_mn.ts

Large diffs are not rendered by default.

2,064 changes: 1,129 additions & 935 deletions i18n/qgis_nl.ts

Large diffs are not rendered by default.

3,962 changes: 2,002 additions & 1,960 deletions i18n/qgis_no.ts

Large diffs are not rendered by default.

2,465 changes: 1,276 additions & 1,189 deletions i18n/qgis_pl_PL.ts

Large diffs are not rendered by default.

7,248 changes: 3,779 additions & 3,469 deletions i18n/qgis_pt_BR.ts

Large diffs are not rendered by default.

3,908 changes: 2,036 additions & 1,872 deletions i18n/qgis_pt_PT.ts

Large diffs are not rendered by default.

3,953 changes: 2,007 additions & 1,946 deletions i18n/qgis_ro.ts

Large diffs are not rendered by default.

4,735 changes: 1,091 additions & 3,644 deletions i18n/qgis_ru.ts

Large diffs are not rendered by default.

3,940 changes: 2,014 additions & 1,926 deletions i18n/qgis_sk.ts

Large diffs are not rendered by default.

2,831 changes: 1,495 additions & 1,336 deletions i18n/qgis_sl_SI.ts

Large diffs are not rendered by default.

3,945 changes: 2,013 additions & 1,932 deletions i18n/qgis_sq_AL.ts

Large diffs are not rendered by default.

3,938 changes: 2,038 additions & 1,900 deletions i18n/qgis_sr_CS-Latn.ts

Large diffs are not rendered by default.

3,944 changes: 2,022 additions & 1,922 deletions i18n/qgis_sv.ts

Large diffs are not rendered by default.

3,962 changes: 2,002 additions & 1,960 deletions i18n/qgis_ta.ts

Large diffs are not rendered by default.

3,908 changes: 2,038 additions & 1,870 deletions i18n/qgis_th.ts

Large diffs are not rendered by default.

3,935 changes: 2,021 additions & 1,914 deletions i18n/qgis_tr.ts

Large diffs are not rendered by default.

3,906 changes: 2,033 additions & 1,873 deletions i18n/qgis_uk.ts

Large diffs are not rendered by default.

3,934 changes: 2,021 additions & 1,913 deletions i18n/qgis_vi.ts

Large diffs are not rendered by default.

3,961 changes: 2,002 additions & 1,959 deletions i18n/qgis_xh.ts

Large diffs are not rendered by default.

3,951 changes: 2,010 additions & 1,941 deletions i18n/qgis_zh_CN.ts

Large diffs are not rendered by default.

3,921 changes: 2,025 additions & 1,896 deletions i18n/qgis_zh_TW.ts

Large diffs are not rendered by default.

Binary file modified images/icons/qgis-icon-60x60.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions mac/cmake/1qt.cmake.in
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ ENDFOREACH (QFW)
# Qt plugins

EXECUTE_PROCESS (COMMAND mkdir -p "${QPLUGDIR}/../imageformats")
FOREACH (QI qgif;qjpeg;qsvg;qtiff)
FOREACH (QI qgif;qico;qjpeg;qsvg;qtiff)
IF (NOT EXISTS "${QPLUGDIR}/../imageformats/lib${QI}.dylib")
EXECUTE_PROCESS (COMMAND ditto ${QARCHS} "@QT_PLUGINS_DIR@/imageformats/lib${QI}.dylib" "${QPLUGDIR}/../imageformats/lib${QI}.dylib")
ENDIF ()
Expand Down Expand Up @@ -177,7 +177,7 @@ FOREACH (QFW ${QTLISTQG})
IF (@OSX_HAVE_LOADERPATH@)
SET (QFW_CHG_TO "${ATLOADER}/@QGIS_PLUGIN_SUBDIR_REV@/${QGIS_FW_SUBDIR}/${LIBPOST}")
ENDIF ()
FOREACH (QI qgif;qjpeg;qsvg;qtiff)
FOREACH (QI qgif;qico;qjpeg;qsvg;qtiff)
INSTALLNAMETOOL_CHANGE ("${QFW_CHG}" "${QFW_CHG_TO}" "${QPLUGDIR}/../imageformats/lib${QI}.dylib")
ENDFOREACH (QI)
FOREACH (QC cn;jp;kr;tw)
Expand Down
15 changes: 15 additions & 0 deletions python/core/qgscoordinatereferencesystem.sip
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,21 @@ class QgsCoordinateReferenceSystem
*/
bool createFromString( const QString theDefinition );

/*! Set up this srs from a various text formats.
*
* Valid formats: WKT string, "EPSG:n", "EPSGA:n", "AUTO:proj_id,unit_id,lon0,lat0",
* "urn:ogc:def:crs:EPSG::n", PROJ.4 string, filename (with WKT, XML or PROJ.4 string),
* well known name (such as NAD27, NAD83, WGS84 or WGS72),
* ESRI::[WKT string] (directly or in a file), "IGNF:xxx"
*
* For more details on supported formats see OGRSpatialReference::SetFromUserInput()
* ( http://www.gdal.org/ogr/classOGRSpatialReference.html#aec3c6a49533fe457ddc763d699ff8796 )
* @note this function generates a WKT string using OSRSetFromUserInput() and
* passes it to createFromWkt() function.
* @param theDefinition A String containing a coordinate reference system definition.
*/
bool createFromUserInput( const QString theDefinition );

/*! Set up this srs by fetching the appropriate information from the
* sqlite backend. First the system level read only srs.db will be checked
* and then the users ~/.qgis/qgis.db database will be checked for a match.
Expand Down
2 changes: 2 additions & 0 deletions python/core/qgsexpression.sip
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,8 @@ public:

//! return quoted column reference (in double quotes)
static QString quotedColumnRef( QString name );
//! return quoted string (in single quotes)
static QString quotedString( QString text );

//////

Expand Down
2 changes: 1 addition & 1 deletion python/gui/qgsmapcanvas.sip
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ class QgsMapCanvas : QGraphicsView

QgsMapCanvasMap* map();

QgsMapRenderer* mapRenderer();
QgsMapRenderer* mapRenderer() /Transfer/;

//! Accessor for the canvas pixmap
// @deprecated use canvasPaintDevice()
Expand Down
1 change: 1 addition & 0 deletions python/plugins/fTools/fTools.py
Original file line number Diff line number Diff line change
Expand Up @@ -450,6 +450,7 @@ def dosumLines(self):

def dopointsPoly(self):
d = doPointsInPolygon.Dialog(self.iface)
d.show()
d.exec_()

def dorandSel(self):
Expand Down
163 changes: 115 additions & 48 deletions python/plugins/fTools/tools/doGeometry.py
Original file line number Diff line number Diff line change
Expand Up @@ -552,17 +552,15 @@ def export_geometry_info( self ):
nElement = 0

vprovider = self.vlayer.dataProvider()

allAttrs = vprovider.attributeIndexes()
self.emit( SIGNAL( "runStatus( PyQt_PyObject )" ), 0)
self.emit( SIGNAL( "runRange( PyQt_PyObject )" ), ( 0, vprovider.featureCount() ) )

if self.writeShape:
allAttrs = vprovider.attributeIndexes()
vprovider.select( allAttrs )
( fields, index1, index2 ) = self.checkGeometryFields( self.vlayer )
writer = QgsVectorFileWriter( self.myName, self.myEncoding, fields,
vprovider.geometryType(), vprovider.crs() )

vprovider.select( allAttrs )
while vprovider.nextFeature(inFeat):
self.emit( SIGNAL( "runStatus( PyQt_PyObject )" ), nElement )
nElement += 1
Expand All @@ -582,10 +580,9 @@ def export_geometry_info( self ):
del writer
return True
else: # update existing file
newFields = []
geomType = self.vlayer.geometryType()
( index1, index2 ) = self.findOrCreateFields()
( index1, index2 ) = self.findOrCreateFields( self.vlayer )

vprovider.select( allAttrs )
while vprovider.nextFeature(inFeat):
self.emit( SIGNAL( "runStatus( PyQt_PyObject )" ), nElement )
nElement += 1
Expand Down Expand Up @@ -620,11 +617,11 @@ def polygon_centroids( self ):
self.emit( SIGNAL( "runStatus( PyQt_PyObject )" ), nElement )
inGeom = inFeat.geometry()
atMap = inFeat.attributeMap()
outGeom = QgsGeometry( inGeom.centroid() )
outGeom = inGeom.centroid()
if outGeom is None:
return "math_error"
outFeat.setAttributeMap( atMap )
outFeat.setGeometry( outGeom )
outFeat.setGeometry( QgsGeometry( outGeom ) )
writer.addFeature( outFeat )
del writer
return True
Expand Down Expand Up @@ -1030,85 +1027,155 @@ def checkGeometryFields( self, vlayer ):
nameList = []
fieldList = vprovider.fields()
geomType = vlayer.geometryType()
for i in fieldList.keys():
fieldKeys = fieldList.keys()

for i in fieldKeys:
nameList.append( fieldList[ i ].name().toLower() )
if geomType == QGis.Polygon:
( found, index1 ) = self.checkForField( nameList, "AREA" )
if len( fieldKeys ) == max( fieldKeys ): # if equal, then the field geometry is not at the end of the fields list
( found, index ) = self.checkForField( nameList, "AREA" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "AREA" )
if not found:
field = QgsField( "AREA", QVariant.Double, "double", 21, 6, self.tr( "Polygon area" ) )
index1 = len( fieldList.keys() )
field = QgsField( "AREA", QVariant.Double, "double precision", 21, 6, self.tr( "Polygon area" ) )
if len( fieldKeys ) == max( fieldKeys ):
index1 = len( fieldList ) + 1
else:
index1 = len( fieldList )
fieldList[ index1 ] = field

( found, index2 ) = self.checkForField( nameList, "PERIMETER" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "PERIMETER" )
index2 = index + 1
else:
( found, index2 ) = self.checkForField( nameList, "PERIMETER" )
if not found:
field = QgsField( "PERIMETER", QVariant.Double, "double", 21, 6, self.tr( "Polygon perimeter" ) )
index2 = len( fieldList.keys() )
field = QgsField( "PERIMETER", QVariant.Double, "double precision", 21, 6, self.tr( "Polygon perimeter" ) )
if len( fieldKeys ) == max( fieldKeys ):
index2 = len( fieldList ) + 1
else:
index2 = len( fieldList )
fieldList[ index2 ] = field
elif geomType == QGis.Line:
( found, index1 ) = self.checkForField( nameList, "LENGTH" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "LENGTH" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "LENGTH" )
if not found:
field = QgsField( "LENGTH", QVariant.Double, "double", 21, 6, self.tr( "Line length" ) )
index1 = len( fieldList.keys() )
field = QgsField( "LENGTH", QVariant.Double, "double precision", 21, 6, self.tr( "Line length" ) )
if len( fieldKeys ) == max( fieldKeys ):
index1 = len( fieldList ) + 1
else:
index1 = len( fieldList )
fieldList[ index1 ] = field
index2 = index1
else:
( found, index1 ) = self.checkForField( nameList, "XCOORD" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "XCOORD" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "XCOORD" )
if not found:
field = QgsField( "XCOORD", QVariant.Double, "double", 21, 6, self.tr( "Point x coordinate" ) )
index1 = len( fieldList.keys() )
field = QgsField( "XCOORD", QVariant.Double, "double precision", 21, 6, self.tr( "Point x coordinate" ) )
if len( fieldKeys ) == max( fieldKeys ):
index1 = len( fieldList ) + 1
else:
index1 = len( fieldList )
fieldList[ index1 ] = field

( found, index2 ) = self.checkForField( nameList, "YCOORD" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "YCOORD" )
index2 = index + 1
else:
( found, index2 ) = self.checkForField( nameList, "YCOORD" )
if not found:
field = QgsField( "YCOORD", QVariant.Double, "double", 21, 6, self.tr( "Point y coordinate" ) )
index2 = len( fieldList.keys() )
field = QgsField( "YCOORD", QVariant.Double, "double precision", 21, 6, self.tr( "Point y coordinate" ) )
if len( fieldKeys ) == max( fieldKeys ):
index2 = len( fieldList ) + 2
else:
index2 = len( fieldList )
fieldList[ index2 ] = field
return ( fieldList, index1, index2 )

def findOrCreateFields( self ):
vprovider = self.vlayer.dataProvider()
def findOrCreateFields( self, vlayer ):
vprovider = vlayer.dataProvider()
fieldList = vprovider.fields()
geomType = self.vlayer.geometryType()
geomType = vlayer.geometryType()
newFields = []
nameList = []
fieldKeys = fieldList.keys()

for i in fieldList.keys():
for i in fieldKeys:
nameList.append( fieldList[ i ].name().toLower() )

if geomType == QGis.Polygon:
( found, index1 ) = self.checkForField( nameList, "AREA" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "AREA" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "AREA" )
if not found:
field = QgsField( "AREA", QVariant.Double, "double", 21, 6, self.tr( "Polygon area" ) )
index1 = len( fieldList.keys() )
field = QgsField( "AREA", QVariant.Double, "double precision", 21, 6, self.tr( "Polygon area" ) )
if len( fieldKeys ) == max( fieldKeys ):
index1 = len( fieldKeys ) + 1
else:
index1 = len( fieldKeys )
newFields.append( field )

( found, index2 ) = self.checkForField( nameList, "PERIMETER" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "PERIMETER" )
index1 = index + 1
else:
( found, index2 ) = self.checkForField( nameList, "PERIMETER" )
if not found:
field = QgsField( "PERIMETER", QVariant.Double, "double", 21, 6, self.tr( "Polygon perimeter" ) )
index2 = len( fieldList.keys() ) + 1
field = QgsField( "PERIMETER", QVariant.Double, "double precision", 21, 6, self.tr( "Polygon perimeter" ) )
if len( fieldKeys ) == max( fieldKeys ):
index2 = len( fieldKeys ) + 2
else:
index2 = len( fieldKeys ) + 1
newFields.append( field )
elif geomType == QGis.Line:
( found, index1 ) = self.checkForField( nameList, "LENGTH" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "LENGTH" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "LENGTH" )
if not found:
field = QgsField( "LENGTH", QVariant.Double, "double", 21, 6, self.tr( "Line length" ) )
index1 = len( fieldList.keys() )
field = QgsField( "LENGTH", QVariant.Double, "double precision", 21, 6, self.tr( "Line length" ) )
if len( fieldKeys ) == max( fieldKeys ):
index1 = len( fieldKeys ) + 1
else:
index1 = len( fieldKeys )
newFields.append( field )
index2 = index1
else:
( found, index1 ) = self.checkForField( nameList, "XCOORD" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "XCOORD" )
index1 = index + 1
else:
( found, index1 ) = self.checkForField( nameList, "XCOORD" )
if not found:
field = QgsField( "XCOORD", QVariant.Double, "double", 21, 6, self.tr( "Point x coordinate" ) )
index1 = len( fieldList.keys() )
field = QgsField( "XCOORD", QVariant.Double, "double precision", 21, 6, self.tr( "Point x coordinate" ) )
if len( fieldKeys ) == max( fieldKeys ):
index = len( fieldKeys ) + 1
else:
index1 = len( fieldKeys )
newFields.append( field )

( found, index2 ) = self.checkForField( nameList, "YCOORD" )
if len( fieldKeys ) == max( fieldKeys ):
( found, index ) = self.checkForField( nameList, "YCOORD" )
index2 = index + 1
else:
( found, index2 ) = self.checkForField( nameList, "YCOORD" )
if not found:
field = QgsField( "YCOORD", QVariant.Double, "double", 21, 6, self.tr( "Point y coordinate" ) )
index2 = len( fieldList.keys() ) + 1
field = QgsField( "YCOORD", QVariant.Double, "double precision", 21, 6, self.tr( "Point y coordinate" ) )
if len( fieldKeys ) == max( fieldKeys ):
index2 = len( fieldKeys ) + 2
else:
index2 = len( fieldKeys ) + 1
newFields.append( field )

vprovider.addAttributes( newFields )
self.vlayer.updateFieldMap()
vlayer.updateFieldMap()
return ( index1, index2 )

def extractAsLine( self, geom ):
Expand Down
181 changes: 126 additions & 55 deletions python/plugins/fTools/tools/doGeoprocessing.py

Large diffs are not rendered by default.

4 changes: 2 additions & 2 deletions python/plugins/fTools/tools/doMeanCoords.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,10 +50,10 @@ def __init__(self, iface, function):

def populateLayers( self ):
layers = ftools_utils.getLayerNames([QGis.Point, QGis.Line, QGis.Polygon])
QObject.disconnect(self.inShape, SIGNAL("currentIndexChanged(QString)"), self.update)
self.inShape.blockSignals(True)
self.inShape.clear()
self.inShape.blockSignals(False)
self.inShape.addItems(layers)
QObject.connect(self.inShape, SIGNAL("currentIndexChanged(QString)"), self.update)

def updateUi(self):
if self.function == 1:
Expand Down
240 changes: 171 additions & 69 deletions python/plugins/fTools/tools/doPointsInPolygon.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,11 +39,13 @@ class Dialog(QDialog, Ui_Dialog):
def __init__(self, iface):
QDialog.__init__(self, iface.mainWindow())
self.iface = iface
# Set up the user interface from Designer.
self.setupUi(self)
QObject.connect(self.toolOut, SIGNAL("clicked()"), self.outFile)

self.setWindowTitle(self.tr("Count Points in Polygon"))
self.buttonOk = self.buttonBox_2.button( QDialogButtonBox.Ok )
self.btnOk = self.buttonBox.button( QDialogButtonBox.Ok )
self.btnClose = self.buttonBox.button( QDialogButtonBox.Close )

QObject.connect(self.toolOut, SIGNAL("clicked()"), self.outFile)
self.progressBar.setValue(0)
self.populateLayers()

Expand All @@ -56,93 +58,193 @@ def populateLayers( self ):
layers = ftools_utils.getLayerNames([QGis.Point])
self.inPoint.addItems(layers)

def outFile(self):
self.outShape.clear()
(self.shapefileName, self.encoding) = ftools_utils.saveDialog(self)
if self.shapefileName is None or self.encoding is None:
return
self.outShape.setText(QString(self.shapefileName))

def accept(self):
self.buttonOk.setEnabled( False )
if self.inPolygon.currentText() == "":
QMessageBox.information(self, self.tr("Count Points In Polygon"), self.tr("Please specify input polygon vector layer"))
elif self.outShape.text() == "":
QMessageBox.information(self, self.tr("Count Points In Polygon"), self.tr("Please specify output shapefile"))
QMessageBox.information(self, self.tr("Count Points In Polygon"),
self.tr("Please specify input polygon vector layer"))
elif self.inPoint.currentText() == "":
QMessageBox.information(self, self.tr("Count Points In Polygon"), self.tr("Please specify input point vector layer"))
QMessageBox.information(self, self.tr("Count Points In Polygon"),
self.tr("Please specify input point vector layer"))
elif self.lnField.text() == "":
QMessageBox.information(self, self.tr("Count Points In Polygon"), self.tr("Please specify output count field"))
QMessageBox.information(self, self.tr("Count Points In Polygon"),
self.tr("Please specify output count field"))
elif self.outShape.text() == "":
QMessageBox.information(self, self.tr("Count Points In Polygon"),
self.tr("Please specify output shapefile"))
else:
inPoly = self.inPolygon.currentText()
inPts = self.inPoint.currentText()
inField = self.lnField.text()
outPath = self.outShape.text()
if outPath.contains("\\"):
outName = outPath.right((outPath.length() - outPath.lastIndexOf("\\")) - 1)
else:
outName = outPath.right((outPath.length() - outPath.lastIndexOf("/")) - 1)
if outName.endsWith(".shp"):
outName = outName.left(outName.length() - 4)
self.compute(inPoly, inPts, inField, outPath, self.progressBar)
self.outShape.clear()
addToTOC = QMessageBox.question(self, self.tr("Count Points in Polygon"), self.tr("Created output shapefile:\n%1\n\nWould you like to add the new layer to the TOC?").arg(unicode(outPath)), QMessageBox.Yes, QMessageBox.No, QMessageBox.NoButton)
if addToTOC == QMessageBox.Yes:
self.vlayer = QgsVectorLayer(outPath, unicode(outName), "ogr")
QgsMapLayerRegistry.instance().addMapLayer(self.vlayer)
self.populateLayers()
inPoly = ftools_utils.getVectorLayerByName(self.inPolygon.currentText())
inPnts = ftools_utils.getVectorLayerByName(self.inPoint.currentText())

polyProvider = inPoly.dataProvider()
pointProvider = inPnts.dataProvider()
if polyProvider.crs() <> pointProvider.crs():
QMessageBox.warning(self, self.tr("CRS warning!"),
self.tr("Warning: Input layers have non-matching CRS.\nThis may cause unexpected results."))

self.btnOk.setEnabled(False)

self.workThread = PointsInPolygonThread(inPoly, inPnts, self.lnField.text(), self.outShape.text(), self.encoding)

QObject.connect(self.workThread, SIGNAL("rangeChanged(int)"), self.setProgressRange)
QObject.connect(self.workThread, SIGNAL("updateProgress()"), self.updateProgress)
QObject.connect(self.workThread, SIGNAL("processingFinished()"), self.processFinished)
QObject.connect(self.workThread, SIGNAL("processingInterrupted()"), self.processInterrupted)

self.btnClose.setText(self.tr("Cancel"))
QObject.disconnect(self.buttonBox, SIGNAL("rejected()"), self.reject)
QObject.connect(self.btnClose, SIGNAL("clicked()"), self.stopProcessing)

self.workThread.start()

def setProgressRange(self, maxValue):
self.progressBar.setRange(0, maxValue)
self.progressBar.setValue(0)
self.buttonOk.setEnabled( True )

def outFile(self):
def updateProgress(self):
self.progressBar.setValue(self.progressBar.value() + 1)

def processFinished(self):
self.stopProcessing()

addToTOC = QMessageBox.question(self, self.tr("Count Points in Polygon"),
self.tr("Created output shapefile:\n%1\n\nWould you like to add the new layer to the TOC?").arg(self.outShape.text()),
QMessageBox.Yes, QMessageBox.No, QMessageBox.NoButton)
if addToTOC == QMessageBox.Yes:
fileInfo = QFileInfo( self.outShape.text() )
layerName = fileInfo.completeBaseName()
layer = QgsVectorLayer(self.outShape.text(), layerName, "ogr")
QgsMapLayerRegistry.instance().addMapLayer(layer)
self.populateLayers()

self.restoreGui()

def processInterrupted(self):
self.restoreGui()

def stopProcessing(self):
if self.workThread != None:
self.workThread.stop()
self.workThread = None

def restoreGui(self):
self.progressBar.setRange(0, 1)
self.progressBar.setValue(0)
self.outShape.clear()
( self.shapefileName, self.encoding ) = ftools_utils.saveDialog( self )
if self.shapefileName is None or self.encoding is None:
return
self.outShape.setText( QString( self.shapefileName ) )

def compute(self, inPoly, inPts, inField, outPath, progressBar):
polyLayer = ftools_utils.getVectorLayerByName(inPoly)
pointLayer = ftools_utils.getVectorLayerByName(inPts)
polyProvider = polyLayer.dataProvider()
pointProvider = pointLayer.dataProvider()
if polyProvider.crs() <> pointProvider.crs():
QMessageBox.warning(self, self.tr("CRS warning!"), self.tr("Warning: Input layers have non-matching CRS.\nThis may cause unexpected results."))

QObject.disconnect(self.btnClose, SIGNAL("clicked()"), self.stopProcessing)
QObject.connect(self.buttonBox, SIGNAL("rejected()"), self.reject)
self.btnClose.setText(self.tr("Close"))
self.btnOk.setEnabled(True)

class PointsInPolygonThread(QThread):
def __init__( self, inPoly, inPoints, fieldName, outPath, encoding ):
QThread.__init__( self, QThread.currentThread() )
self.mutex = QMutex()
self.stopMe = 0
self.interrupted = False

self.layerPoly = inPoly
self.layerPoints = inPoints
self.fieldName = fieldName
self.outPath = outPath
self.encoding = encoding

def run(self):
self.mutex.lock()
self.stopMe = 0
self.mutex.unlock()

interrupted = False

polyProvider = self.layerPoly.dataProvider()
pointProvider = self.layerPoints.dataProvider()

allAttrs = polyProvider.attributeIndexes()
polyProvider.select(allAttrs)
allAttrs = pointProvider.attributeIndexes()
pointProvider.select(allAttrs)
fieldList = ftools_utils.getFieldList(polyLayer)
index = polyProvider.fieldNameIndex(unicode(inField))

fieldList = ftools_utils.getFieldList(self.layerPoly)
index = polyProvider.fieldNameIndex(unicode(self.fieldName))
if index == -1:
index = polyProvider.fieldCount()
field = QgsField(unicode(inField), QVariant.Double, "real", 24, 15, self.tr("point count field"))
field = QgsField(unicode(self.fieldName), QVariant.Double, "real", 24, 15, self.tr("point count field"))
fieldList[index] = field

sRs = polyProvider.crs()
check = QFile(self.shapefileName)
if check.exists():
if not QgsVectorFileWriter.deleteShapeFile(self.shapefileName):
if QFile(self.outPath).exists():
if not QgsVectorFileWriter.deleteShapeFile(self.outPath):
return
writer = QgsVectorFileWriter(self.shapefileName, self.encoding, fieldList, polyProvider.geometryType(), sRs)
inFeat = QgsFeature()
inFeatB = QgsFeature()

writer = QgsVectorFileWriter(self.outPath, self.encoding, fieldList,
polyProvider.geometryType(), sRs)

spatialIndex = ftools_utils.createIndex( pointProvider )
pointProvider.rewind()
pointProvider.select()

self.emit(SIGNAL("rangeChanged(int)"), polyProvider.featureCount() )

polyFeat = QgsFeature()
pntFeat = QgsFeature()
outFeat = QgsFeature()
inGeom = QgsGeometry()
start = 15.00
add = 85.00 / polyProvider.featureCount()
spatialIndex = ftools_utils.createIndex( pointProvider )
while polyProvider.nextFeature(inFeat):
inGeom = inFeat.geometry()
atMap = inFeat.attributeMap()
while polyProvider.nextFeature(polyFeat):
inGeom = polyFeat.geometry()
atMap = polyFeat.attributeMap()
outFeat.setAttributeMap(atMap)
outFeat.setGeometry(inGeom)
pointList = []

count = 0
pointList = []
hasIntersection = True
pointList = spatialIndex.intersects(inGeom.boundingBox())
if len(pointList) > 0: check = 0
else: check = 1
if check == 0:
for i in pointList:
pointProvider.featureAtId( int( i ), inFeatB , True, allAttrs )
tmpGeom = QgsGeometry( inFeatB.geometry() )
if inGeom.intersects( tmpGeom ):
count = count + 1
outFeat.setAttributeMap(atMap)
if len(pointList) > 0:
hasIntersection = True
else:
hasIntersection = False

if hasIntersection:
for p in pointList:
pointProvider.featureAtId(p, pntFeat , True)
tmpGeom = QgsGeometry(pntFeat.geometry())
if inGeom.intersects(tmpGeom):
count += 1

self.mutex.lock()
s = self.stopMe
self.mutex.unlock()
if s == 1:
interrupted = True
break

outFeat.addAttribute(index, QVariant(count))
writer.addFeature(outFeat)
start = start + 1
progressBar.setValue(start)

self.emit( SIGNAL( "updateProgress()" ) )

self.mutex.lock()
s = self.stopMe
self.mutex.unlock()
if s == 1:
interrupted = True
break

del writer

if not interrupted:
self.emit( SIGNAL( "processingFinished()" ) )
else:
self.emit( SIGNAL( "processingInterrupted()" ) )

def stop(self):
self.mutex.lock()
self.stopMe = 1
self.mutex.unlock()

QThread.wait( self )
13 changes: 7 additions & 6 deletions python/plugins/fTools/tools/doRandPoints.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,12 +50,12 @@ def __init__(self, iface):

def populateLayers( self ):
layers = ftools_utils.getLayerNames([QGis.Polygon, "Raster"])
QObject.disconnect(self.inShape, SIGNAL("currentIndexChanged(QString)"), self.update)
self.inShape.blockSignals(True)
self.inShape.clear()
self.inShape.blockSignals(False)
self.inShape.addItems(layers)
QObject.connect(self.inShape, SIGNAL("currentIndexChanged(QString)"), self.update)

# If input layer is changed, update field list
# If input layer is changed, update field list
def update(self, inputLayer):
self.cmbField.clear()
changedLayer = ftools_utils.getMapLayerByName(unicode(inputLayer))
Expand All @@ -67,6 +67,7 @@ def update(self, inputLayer):
changedLayer = ftools_utils.getVectorLayerByName(inputLayer)
changedFields = ftools_utils.getFieldList(changedLayer)
for i in changedFields:
if changedFields[i].typeName() == "Integer":
self.cmbField.addItem(unicode(changedFields[i].name()))
else:
self.rdoUnstratified.setChecked(True)
Expand All @@ -78,7 +79,7 @@ def update(self, inputLayer):
self.cmbField.setEnabled(False)
self.label_4.setEnabled(False)

# when 'OK' button is pressed, gather required inputs, and initiate random points generation
# when 'OK' button is pressed, gather required inputs, and initiate random points generation
def accept(self):
self.buttonOk.setEnabled( False )
if self.inShape.currentText() == "":
Expand All @@ -99,7 +100,7 @@ def accept(self):
self.progressBar.setValue(5)
mLayer = ftools_utils.getMapLayerByName(unicode(inName))
if mLayer.type() == mLayer.VectorLayer:
inLayer = QgsVectorLayer(unicode(mLayer.source()), unicode(mLayer.name()), unicode(mLayer.dataProvider().name()))
inLayer = ftools_utils.getVectorLayerByName(unicode(inName))
if self.rdoUnstratified.isChecked():
design = self.tr("unstratified")
value = self.spnUnstratified.value()
Expand All @@ -113,7 +114,7 @@ def accept(self):
design = self.tr("field")
value = unicode(self.cmbField.currentText())
elif mLayer.type() == mLayer.RasterLayer:
inLayer = QgsRasterLayer(unicode(mLayer.source()), unicode(mLayer.name()))
inLayer = ftools_utils.getRasterLayerByName(unicode(inName))
design = self.tr("unstratified")
value = self.spnUnstratified.value()
else:
Expand Down
2 changes: 1 addition & 1 deletion python/plugins/fTools/tools/doSelectByLocation.py
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ def __init__(self, iface):
self.iface = iface
# Set up the user interface from Designer.
self.setupUi(self)
self.buttonOk = self.buttonBox_2.button( QDialogButtonBox.Ok )
self.buttonOk = self.buttonBox.button( QDialogButtonBox.Ok )
# populate layer list
self.progressBar.setValue(0)
mapCanvas = self.iface.mapCanvas()
Expand Down
76 changes: 49 additions & 27 deletions python/plugins/fTools/tools/doValidate.py
Original file line number Diff line number Diff line change
Expand Up @@ -50,14 +50,13 @@ def __createMarker(self, point):
self.__marker.setIconType(gui.QgsVertexMarker.ICON_X)
self.__marker.setPenWidth(3)

def setGeom(self, x, y):
def setGeom(self, p):
if not self.__marker is None:
self.reset()
point = QgsPoint(x, y)
if self.__marker is None:
self.__createMarker(point)
self.__createMarker(p)
else:
self.__marker.setCenter(point)
self.__marker.setCenter(p)

def reset(self):
if not self.__marker is None:
Expand Down Expand Up @@ -93,6 +92,15 @@ def __init__(self, iface):
self.storedScale = self.iface.mapCanvas().scale()
# create marker for error
self.marker = MarkerErrorGeometry(self.iface.mapCanvas())

settings = QSettings()
self.restoreGeometry( settings.value("/fTools/ValidateDialog/geometry").toByteArray() )

def closeEvent(self, e):
settings = QSettings()
settings.setValue( "/fTools/ValidateDialog/geometry", QVariant(self.saveGeometry()) )
QMainWindow.closeEvent(self, e)
del self.marker

def keyPressEvent( self, e ):
if ( e.modifiers() == Qt.ControlModifier or \
Expand All @@ -115,34 +123,50 @@ def accept( self ):
elif self.cmbField.isVisible() and self.cmbField.currentText() == "":
QMessageBox.information( self, self.tr("Error!"), self.tr( "Please specify input field" ) )
else:
self.validate( self.inShape.currentText(), self.useSelected.checkState() )
self.vlayer = ftools_utils.getVectorLayerByName( self.inShape.currentText() )
self.validate( self.useSelected.checkState() )

def zoomToError(self, curr, prev):
if curr is None:
return
row = curr.row() # if we clicked in the first column, we want the second
item = self.tblUnique.item(row, 1)
if not item.data(Qt.UserRole) is None:
mc = self.iface.mapCanvas()
x = item.data(Qt.UserRole).toPyObject().x()
y = item.data(Qt.UserRole).toPyObject().y()
self.marker.setGeom(x, y) # Set Marker
mc.zoomToPreviousExtent()
scale = mc.scale()
rect = QgsRectangle(float(x)-(4.0/scale),float(y)-(4.0/scale),
float(x)+(4.0/scale),float(y)+(4.0/scale))
# Set the extent to our new rectangle
mc.setExtent(rect)
# Refresh the map
mc.refresh()

def validate( self, myLayer, mySelection ):
vlayer = ftools_utils.getVectorLayerByName( myLayer )

mc = self.iface.mapCanvas()
mc.zoomToPreviousExtent()

e = item.data(Qt.UserRole).toPyObject()

if type(e)==QgsPoint:
e = mc.mapRenderer().layerToMapCoordinates( self.vlayer, e )

self.marker.setGeom(e)

rect = mc.extent()
rect.expand( 0.25, e )

else:
self.marker.reset()

ft = QgsFeature()
(fid,ok) = self.tblUnique.item(row, 0).text().toInt()
if not ok or not self.vlayer.featureAtId( fid, ft, True):
return

rect = mc.mapRenderer().layerExtentToOutputExtent( self.vlayer, ft.geometry().boundingBox() )
rect.expand(1.05)

# Set the extent to our new rectangle
mc.setExtent(rect)
# Refresh the map
mc.refresh()

def validate( self, mySelection ):
self.tblUnique.clearContents()
self.tblUnique.setRowCount( 0 )
self.lstCount.clear()
self.buttonOk.setEnabled( False )
self.testThread = validateThread( self.iface.mainWindow(), self, vlayer, mySelection )
self.testThread = validateThread( self.iface.mainWindow(), self, self.vlayer, mySelection )
QObject.connect( self.testThread, SIGNAL( "runFinished(PyQt_PyObject)" ), self.runFinishedFromThread )
QObject.connect( self.testThread, SIGNAL( "runStatus(PyQt_PyObject)" ), self.runStatusFromThread )
QObject.connect( self.testThread, SIGNAL( "runRange(PyQt_PyObject)" ), self.runRangeFromThread )
Expand Down Expand Up @@ -176,11 +200,10 @@ def runFinishedFromThread( self, output ):
self.tblUnique.insertRow(count)
fidItem = QTableWidgetItem( str(rec[0]) )
self.tblUnique.setItem( count, 0, fidItem )
if err.hasWhere(): # if there is a location associated with the error
where = err.where()
message = err.what()
errItem = QTableWidgetItem( message )
errItem.setData(Qt.UserRole, QVariant(where))
if err.hasWhere(): # if there is a location associated with the error
errItem.setData(Qt.UserRole, QVariant(err.where()))
self.tblUnique.setItem( count, 1, errItem )
count += 1
self.tblUnique.setHorizontalHeaderLabels( [ self.tr("Feature"), self.tr("Error(s)") ] )
Expand Down Expand Up @@ -211,7 +234,6 @@ def run( self ):
self.running = True
output = self.check_geometry( self.vlayer )
self.emit( SIGNAL( "runFinished(PyQt_PyObject)" ), output )
self.emit( SIGNAL( "runStatus(PyQt_PyObject)" ), 100 )

def stop(self):
self.running = False
Expand Down Expand Up @@ -240,7 +262,7 @@ def check_geometry( self, vlayer ):
self.emit(SIGNAL("runStatus(PyQt_PyObject)"), nElement)
nElement += 1
# Check Add error
if not (geom.isGeosEmpty() or geom.isGeosValid() ) :
if not geom.isGeosEmpty():
lstErrors.append((feat.id(), list(geom.validateGeometry())))
self.emit( SIGNAL( "runStatus(PyQt_PyObject)" ), nFeat )
return lstErrors
10 changes: 4 additions & 6 deletions python/plugins/fTools/tools/doVectorGrid.py
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,7 @@ def accept(self):
self.buttonOk.setEnabled( True )

def compute( self, bound, xOffset, yOffset, polygon ):
crs = self.iface.mapCanvas().mapRenderer().destinationSrs()
crs = ftools_utils.getMapLayerByName(unicode(self.inShape.currentText())).crs()
if not crs.isValid(): crs = None
if polygon:
fields = {0:QgsField("ID", QVariant.Int), 1:QgsField("XMIN", QVariant.Double), 2:QgsField("XMAX", QVariant.Double),
Expand All @@ -163,15 +163,13 @@ def compute( self, bound, xOffset, yOffset, polygon ):
if not QgsVectorFileWriter.deleteShapeFile(self.shapefileName):
return
writer = QgsVectorFileWriter(self.shapefileName, self.encoding, fields, QGis.WKBPolygon, crs)
#writer = QgsVectorFileWriter(outPath, "CP1250", fields, QGis.WKBPolygon, None)
else:
fields = {0:QgsField("ID", QVariant.Int), 1:QgsField("COORD", QVariant.Double)}
check = QFile(self.shapefileName)
if check.exists():
if not QgsVectorFileWriter.deleteShapeFile(self.shapefileName):
return
writer = QgsVectorFileWriter(self.shapefileName, self.encoding, fields, QGis.WKBLineString, crs)
#writer = QgsVectorFileWriter(unicode(outPath), "CP1250", fields, QGis.WKBLineString, None)
outFeat = QgsFeature()
outGeom = QgsGeometry()
idVar = 0
Expand Down Expand Up @@ -279,16 +277,16 @@ def getClosestPixel(self, startVal, targetVal, step, isMin ):
while foundVal is None:
if tmpVal <= targetVal:
if backOneStep:
tmpVal -= step
tmpVal -= step
foundVal = tmpVal
tmpVal += step
else:
backOneStep = isMin
while foundVal is None:
if tmpVal >= targetVal:
if backOneStep:
tmpVal -= step
tmpVal -= step
foundVal = tmpVal
tmpVal += step
return foundVal
return foundVal

131 changes: 63 additions & 68 deletions python/plugins/fTools/tools/frmPointsInPolygon.ui
Original file line number Diff line number Diff line change
@@ -1,107 +1,102 @@
<ui version="4.0" >
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>Dialog</class>
<widget class="QDialog" name="Dialog" >
<property name="windowModality" >
<enum>Qt::NonModal</enum>
</property>
<property name="geometry" >
<widget class="QDialog" name="Dialog">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>383</width>
<height>291</height>
<width>400</width>
<height>300</height>
</rect>
</property>
<property name="windowTitle" >
<property name="windowTitle">
<string>Count Points In Polygons</string>
</property>
<property name="sizeGripEnabled" >
<bool>true</bool>
</property>
<layout class="QGridLayout" name="gridLayout" >
<item row="0" column="0" colspan="2" >
<layout class="QVBoxLayout" >
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0" colspan="2">
<layout class="QVBoxLayout" name="verticalLayout_2">
<item>
<widget class="QLabel" name="label_3" >
<property name="text" >
<widget class="QLabel" name="label_3">
<property name="text">
<string>Input polygon vector layer</string>
</property>
</widget>
</item>
<item>
<widget class="QComboBox" name="inPolygon" />
<widget class="QComboBox" name="inPolygon"/>
</item>
</layout>
</item>
<item row="1" column="0" colspan="2" >
<layout class="QVBoxLayout" >
<item row="1" column="0" colspan="2">
<layout class="QVBoxLayout" name="verticalLayout_3">
<item>
<widget class="QLabel" name="label_4" >
<property name="text" >
<widget class="QLabel" name="label_4">
<property name="text">
<string>Input point vector layer</string>
</property>
</widget>
</item>
<item>
<widget class="QComboBox" name="inPoint" />
<widget class="QComboBox" name="inPoint"/>
</item>
</layout>
</item>
<item row="2" column="0" colspan="2" >
<layout class="QHBoxLayout" >
<item row="2" column="0" colspan="2">
<layout class="QHBoxLayout">
<item>
<widget class="QLabel" name="label_5" >
<property name="text" >
<widget class="QLabel" name="label_5">
<property name="text">
<string>Output count field name</string>
</property>
</widget>
</item>
<item>
<widget class="QLineEdit" name="lnField" >
<property name="text" >
<widget class="QLineEdit" name="lnField">
<property name="text">
<string>PNTCNT</string>
</property>
<property name="maxLength" >
<property name="maxLength">
<number>10</number>
</property>
</widget>
</item>
</layout>
</item>
<item row="3" column="0" colspan="2" >
<spacer name="verticalSpacer" >
<property name="orientation" >
<item row="3" column="0">
<spacer name="verticalSpacer">
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0" >
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>16</height>
<height>40</height>
</size>
</property>
</spacer>
</item>
<item row="4" column="0" colspan="2" >
<layout class="QVBoxLayout" name="verticalLayout" >
<item row="4" column="0" colspan="2">
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<widget class="QLabel" name="label_2" >
<property name="text" >
<widget class="QLabel" name="label_2">
<property name="text">
<string>Output Shapefile</string>
</property>
</widget>
</item>
<item>
<layout class="QHBoxLayout" name="horizontalLayout" >
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<widget class="QLineEdit" name="outShape" >
<property name="readOnly" >
<widget class="QLineEdit" name="outShape">
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<widget class="QToolButton" name="toolOut" >
<property name="text" >
<widget class="QToolButton" name="toolOut">
<property name="text">
<string>Browse</string>
</property>
</widget>
Expand All @@ -110,25 +105,25 @@
</item>
</layout>
</item>
<item row="5" column="0" >
<widget class="QProgressBar" name="progressBar" >
<property name="value" >
<item row="5" column="0">
<widget class="QProgressBar" name="progressBar">
<property name="value">
<number>0</number>
</property>
<property name="alignment" >
<property name="alignment">
<set>Qt::AlignCenter</set>
</property>
<property name="textVisible" >
<property name="textVisible">
<bool>true</bool>
</property>
</widget>
</item>
<item row="5" column="1" >
<widget class="QDialogButtonBox" name="buttonBox_2" >
<property name="orientation" >
<item row="5" column="1">
<widget class="QDialogButtonBox" name="buttonBox">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="standardButtons" >
<property name="standardButtons">
<set>QDialogButtonBox::Close|QDialogButtonBox::Ok</set>
</property>
</widget>
Expand All @@ -138,34 +133,34 @@
<resources/>
<connections>
<connection>
<sender>buttonBox_2</sender>
<sender>buttonBox</sender>
<signal>accepted()</signal>
<receiver>Dialog</receiver>
<slot>accept()</slot>
<hints>
<hint type="sourcelabel" >
<x>133</x>
<y>512</y>
<hint type="sourcelabel">
<x>248</x>
<y>254</y>
</hint>
<hint type="destinationlabel" >
<x>215</x>
<y>290</y>
<hint type="destinationlabel">
<x>157</x>
<y>274</y>
</hint>
</hints>
</connection>
<connection>
<sender>buttonBox_2</sender>
<sender>buttonBox</sender>
<signal>rejected()</signal>
<receiver>Dialog</receiver>
<slot>close()</slot>
<slot>reject()</slot>
<hints>
<hint type="sourcelabel" >
<x>59</x>
<y>512</y>
<hint type="sourcelabel">
<x>316</x>
<y>260</y>
</hint>
<hint type="destinationlabel" >
<x>132</x>
<y>239</y>
<hint type="destinationlabel">
<x>286</x>
<y>274</y>
</hint>
</hints>
</connection>
Expand Down
145 changes: 68 additions & 77 deletions python/plugins/fTools/tools/frmSpatialJoin.ui
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@
<property name="sizeGripEnabled">
<bool>true</bool>
</property>
<layout class="QGridLayout" name="gridLayout">
<item row="0" column="0" colspan="3">
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<layout class="QVBoxLayout">
<item>
<widget class="QLabel" name="label_3">
Expand All @@ -34,7 +34,7 @@
</item>
</layout>
</item>
<item row="1" column="0" colspan="3">
<item>
<layout class="QVBoxLayout">
<item>
<widget class="QLabel" name="label">
Expand All @@ -48,28 +48,24 @@
</item>
</layout>
</item>
<item row="2" column="0" colspan="3">
<item>
<widget class="QGroupBox" name="groupBox_2">
<property name="title">
<string>Attribute Summary</string>
</property>
<layout class="QGridLayout">
<item row="0" column="0" colspan="7">
<widget class="QRadioButton" name="rdoFirst">
<property name="text">
<string>Take attributes of first located feature</string>
</property>
<property name="checked">
<bool>true</bool>
<item row="2" column="6">
<spacer>
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
</widget>
</item>
<item row="1" column="0" colspan="7">
<widget class="QRadioButton" name="rdoSummary">
<property name="text">
<string>Take summary of intersecting features</string>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</widget>
</spacer>
</item>
<item row="2" column="0">
<spacer>
Expand Down Expand Up @@ -97,23 +93,20 @@
</property>
</widget>
</item>
<item row="2" column="2">
<widget class="QCheckBox" name="chkMin">
<property name="enabled">
<bool>false</bool>
</property>
<item row="1" column="0" colspan="7">
<widget class="QRadioButton" name="rdoSummary">
<property name="text">
<string>Min</string>
<string>Take summary of intersecting features</string>
</property>
</widget>
</item>
<item row="2" column="3">
<widget class="QCheckBox" name="chkMax">
<item row="2" column="2">
<widget class="QCheckBox" name="chkMin">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Max</string>
<string>Min</string>
</property>
</widget>
</item>
Expand All @@ -127,19 +120,6 @@
</property>
</widget>
</item>
<item row="2" column="6">
<spacer>
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>40</width>
<height>20</height>
</size>
</property>
</spacer>
</item>
<item row="2" column="5">
<widget class="QCheckBox" name="chkMedian">
<property name="enabled">
Expand All @@ -150,10 +130,30 @@
</property>
</widget>
</item>
<item row="2" column="3">
<widget class="QCheckBox" name="chkMax">
<property name="enabled">
<bool>false</bool>
</property>
<property name="text">
<string>Max</string>
</property>
</widget>
</item>
<item row="0" column="0" colspan="7">
<widget class="QRadioButton" name="rdoFirst">
<property name="text">
<string>Take attributes of first located feature</string>
</property>
<property name="checked">
<bool>true</bool>
</property>
</widget>
</item>
</layout>
</widget>
</item>
<item row="3" column="0" colspan="3">
<item>
<layout class="QVBoxLayout">
<item>
<widget class="QLabel" name="label_2">
Expand Down Expand Up @@ -182,7 +182,7 @@
</item>
</layout>
</item>
<item row="4" column="0" colspan="3">
<item>
<widget class="QGroupBox" name="groupBox_3">
<property name="title">
<string>Output table</string>
Expand All @@ -208,41 +208,32 @@
</layout>
</widget>
</item>
<item row="5" column="0" rowspan="3" colspan="3">
<spacer>
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>359</width>
<height>16</height>
</size>
</property>
</spacer>
</item>
<item row="7" column="1">
<widget class="QProgressBar" name="progressBar">
<property name="value">
<number>24</number>
</property>
<property name="alignment">
<set>Qt::AlignCenter</set>
</property>
<property name="textVisible">
<bool>true</bool>
</property>
</widget>
</item>
<item row="6" column="2" rowspan="2">
<widget class="QDialogButtonBox" name="buttonBox_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="standardButtons">
<set>QDialogButtonBox::Close|QDialogButtonBox::Ok</set>
</property>
</widget>
<item>
<layout class="QHBoxLayout" name="horizontalLayout">
<item>
<widget class="QProgressBar" name="progressBar">
<property name="value">
<number>24</number>
</property>
<property name="alignment">
<set>Qt::AlignCenter</set>
</property>
<property name="textVisible">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<widget class="QDialogButtonBox" name="buttonBox_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="standardButtons">
<set>QDialogButtonBox::Close|QDialogButtonBox::Ok</set>
</property>
</widget>
</item>
</layout>
</item>
</layout>
</widget>
Expand Down
131 changes: 66 additions & 65 deletions python/plugins/fTools/tools/frmVectorSplit.ui
Original file line number Diff line number Diff line change
@@ -1,105 +1,106 @@
<ui version="4.0" >
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>Dialog</class>
<widget class="QDialog" name="Dialog" >
<property name="windowModality" >
<widget class="QDialog" name="Dialog">
<property name="windowModality">
<enum>Qt::NonModal</enum>
</property>
<property name="geometry" >
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>374</width>
<height>306</height>
<width>378</width>
<height>239</height>
</rect>
</property>
<property name="windowTitle" >
<property name="windowTitle">
<string>Vector Split</string>
</property>
<property name="sizeGripEnabled" >
<property name="sizeGripEnabled">
<bool>true</bool>
</property>
<layout class="QGridLayout" name="gridLayout" >
<item row="0" column="0" colspan="2" >
<widget class="QLabel" name="label_3" >
<property name="text" >
<string>Input vector layer</string>
</property>
</widget>
</item>
<item row="1" column="0" colspan="2" >
<widget class="QComboBox" name="inShape" />
</item>
<item row="2" column="0" colspan="2" >
<widget class="QLabel" name="label_4" >
<property name="text" >
<string>Unique ID field</string>
</property>
</widget>
</item>
<item row="3" column="0" colspan="2" >
<widget class="QComboBox" name="inField" />
</item>
<item row="4" column="0" colspan="2" >
<widget class="QLabel" name="label_2" >
<property name="text" >
<string>Output folder</string>
</property>
</widget>
</item>
<item row="5" column="0" colspan="2" >
<layout class="QHBoxLayout" >
<layout class="QGridLayout" name="gridLayout">
<item row="5" column="0" colspan="2">
<layout class="QHBoxLayout">
<item>
<widget class="QLineEdit" name="outShape" >
<property name="readOnly" >
<widget class="QLineEdit" name="outShape">
<property name="readOnly">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<widget class="QToolButton" name="toolOut" >
<property name="text" >
<widget class="QToolButton" name="toolOut">
<property name="text">
<string>Browse</string>
</property>
</widget>
</item>
</layout>
</item>
<item row="6" column="0" >
<spacer>
<property name="orientation" >
<enum>Qt::Vertical</enum>
<item row="2" column="0" colspan="2">
<widget class="QLabel" name="label_4">
<property name="text">
<string>Unique ID field</string>
</property>
<property name="sizeHint" stdset="0" >
<size>
<width>20</width>
<height>40</height>
</size>
</widget>
</item>
<item row="3" column="0" colspan="2">
<widget class="QComboBox" name="inField"/>
</item>
<item row="1" column="0" colspan="2">
<widget class="QComboBox" name="inShape"/>
</item>
<item row="4" column="0" colspan="2">
<widget class="QLabel" name="label_2">
<property name="text">
<string>Output folder</string>
</property>
</spacer>
</widget>
</item>
<item row="0" column="0" colspan="2">
<widget class="QLabel" name="label_3">
<property name="text">
<string>Input vector layer</string>
</property>
</widget>
</item>
<item row="7" column="0" >
<widget class="QProgressBar" name="progressBar" >
<property name="value" >
<item row="7" column="0">
<widget class="QProgressBar" name="progressBar">
<property name="value">
<number>0</number>
</property>
<property name="alignment" >
<property name="alignment">
<set>Qt::AlignHCenter</set>
</property>
<property name="textVisible" >
<property name="textVisible">
<bool>true</bool>
</property>
</widget>
</item>
<item row="7" column="1" >
<widget class="QDialogButtonBox" name="buttonBox_2" >
<property name="orientation" >
<item row="7" column="1">
<widget class="QDialogButtonBox" name="buttonBox_2">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="standardButtons" >
<property name="standardButtons">
<set>QDialogButtonBox::Close|QDialogButtonBox::Ok</set>
</property>
</widget>
</item>
<item row="6" column="0">
<spacer>
<property name="orientation">
<enum>Qt::Vertical</enum>
</property>
<property name="sizeHint" stdset="0">
<size>
<width>20</width>
<height>40</height>
</size>
</property>
</spacer>
</item>
</layout>
</widget>
<resources/>
Expand All @@ -110,11 +111,11 @@
<receiver>Dialog</receiver>
<slot>accept()</slot>
<hints>
<hint type="sourcelabel" >
<hint type="sourcelabel">
<x>124</x>
<y>355</y>
</hint>
<hint type="destinationlabel" >
<hint type="destinationlabel">
<x>215</x>
<y>290</y>
</hint>
Expand All @@ -126,11 +127,11 @@
<receiver>Dialog</receiver>
<slot>close()</slot>
<hints>
<hint type="sourcelabel" >
<hint type="sourcelabel">
<x>50</x>
<y>350</y>
</hint>
<hint type="destinationlabel" >
<hint type="destinationlabel">
<x>132</x>
<y>239</y>
</hint>
Expand Down
18 changes: 18 additions & 0 deletions python/plugins/fTools/tools/ftools_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,16 @@ def getVectorLayerByName( myName ):
else:
return None

# Return QgsRasterLayer from a layer name ( as string )
def getRasterLayerByName( myName ):
layermap = QgsMapLayerRegistry.instance().mapLayers()
for name, layer in layermap.iteritems():
if layer.type() == QgsMapLayer.RasterLayer and layer.name() == myName:
if layer.isValid():
return layer
else:
return None

# Return QgsMapLayer from a layer name ( as string )
def getMapLayerByName( myName ):
layermap = QgsMapLayerRegistry.instance().mapLayers()
Expand Down Expand Up @@ -334,6 +344,14 @@ def getUniqueValuesCount( vlayer, fieldIndex, useSelection ):
count += 1
return count

def getGeomType(gT):
if gT == 3 or gT == 6:
gTypeListPoly = [ QGis.WKBPolygon, QGis.WKBMultiPolygon ]
return gTypeListPoly
elif gT == 2 or gT == 5:
gTypeListLine = [ QGis.WKBLineString, QGis.WKBMultiLineString ]
return gTypeListLine

def getShapesByGeometryType( baseDir, inShapes, geomType ):
outShapes = QStringList()
for fileName in inShapes:
Expand Down
961 changes: 634 additions & 327 deletions resources/customization.xml

Large diffs are not rendered by default.

220 changes: 125 additions & 95 deletions scripts/tsstat.pl
Original file line number Diff line number Diff line change
Expand Up @@ -20,113 +20,143 @@

# translator names here as a hash where the key is the lang_country code used for the ts file name
my $translators= {
af => 'Hendrik Bosman',
ar => 'Assem Kamal, Latif Jalil',
bg => 'Захари Савов, Jordan Tzvetkov',
ca_ES => 'Xavi',
cs_CZ => 'Martin Landa, Peter Antolik, Martin Dzurov, Jan Helebrant',
da_DK => 'Henriette Roued',
de => 'Jürgen E. Fischer, Stephan Holl, Otto Dassau, Werner Macho',
es => 'Carlos Dávila, Javier César Aldariz, Gabriela Awad, Edwin Amado, Mayeul Kauffmann',
el_GR => 'Evripidis Argyropoulos, Mike Pegnigiannis, Nikos Ves',
et_EE => 'Veiko Viil',
fa => 'Mola Pahnadayan',
fi => 'Marko Jarvenpaa',
fr => 'Eve Rousseau, Marc Monnerat, Lionel Roubeyrie, Jean Roc Morreale, Benjamin Bohard, Jeremy Garniaux, Yves Jacolin, Benjamin Lerre, Stéphane Morel, Marie Silvestre, Tahir Tamba, Xavier M, Mayeul Kauffmann, Mehdi Semchaoui',
gl_ES => 'Xan Vieiro',
hu => 'Zoltan Siki',
hr_HR => 'Zoran Jankovic',
is => 'Thordur Ivarsson',
id => 'Januar V. Simarmata, I Made Anombawa',
it => 'Paolo Cavallini, Flavio Rigolon, Maurizio Napolitano, Roberto Angeletti, Alessandro Fanna, Michele Beneventi, Marco Braida, Luca Casagrande, Luca Delucchi, Anne Gishla',
ja => 'BABA Yoshihiko, Yoichi Kayama',
ka_GE => 'Shota Murtskhvaladze, George Machitidze',
ko_KR => 'BJ Jang',
lo => 'Anousak Souphavanh',
lv => 'Maris Nartiss, Pēteris Brūns',
lt => 'Kestas M',
nl => 'Richard Duivenvoorde, Raymond Nijssen, Carlo van Rijswijk',
mn => 'Bayarmaa Enkhtur',
pl_PL => 'Robert Szczepanek, Milena Nowotarska, Borys Jurgiel, Mateusz Loskot, Tomasz Paul, Andrzej Swiader ',
pt_BR => 'Arthur Nanni, Christian Ferreira, Leandro Kaut',
pt_PT => 'Giovanni Manghi, Joana Simoes, Duarte Carreira, Alexandre Neto, Pedro Pereira',
ro => 'Lonut Losifescu-Enescu',
ru => 'Artem Popov',
sk => 'Lubos Balazovic',
sl_SI => 'Jože Detečnik, Dejan Gregor',
sv => 'Lars Luthman, Magnus Homann',
sq_AL => '',
th => 'Man Chao',
tr => 'Osman Yilmaz',
uk => 'Сергей Якунин',
vi => 'Bùi Hữu Mạnh',
zh_CN => 'Zhang Jun',
zh_TW => 'Nungyao Lin',
af => 'Hendrik Bosman',
ar => 'Assem Kamal, Latif Jalil',
bg => 'Захари Савов, Jordan Tzvetkov',
ca_ES => 'Xavi',
cs_CZ => 'Martin Landa, Peter Antolik, Martin Dzurov, Jan Helebrant',
da_DK => 'Henriette Roued',
de => 'Jürgen E. Fischer, Stephan Holl, Otto Dassau, Werner Macho',
es => 'Carlos Dávila, Javier César Aldariz, Gabriela Awad, Edwin Amado, Mayeul Kauffmann',
el_GR => 'Evripidis Argyropoulos, Mike Pegnigiannis, Nikos Ves',
et_EE => 'Veiko Viil',
fa => 'Mola Pahnadayan',
fi => 'Marko Jarvenpaa',
fr => 'Eve Rousseau, Marc Monnerat, Lionel Roubeyrie, Jean Roc Morreale, Benjamin Bohard, Jeremy Garniaux, Yves Jacolin, Benjamin Lerre, Stéphane Morel, Marie Silvestre, Tahir Tamba, Xavier M, Mayeul Kauffmann, Mehdi Semchaoui',
gl_ES => 'Xan Vieiro',
hu => 'Zoltan Siki',
hr_HR => 'Zoran Jankovic',
is => 'Thordur Ivarsson',
id => 'Januar V. Simarmata, I Made Anombawa',
it => 'Paolo Cavallini, Flavio Rigolon, Maurizio Napolitano, Roberto Angeletti, Alessandro Fanna, Michele Beneventi, Marco Braida, Luca Casagrande, Luca Delucchi, Anne Gishla',
ja => 'BABA Yoshihiko, Yoichi Kayama',
ka_GE => 'Shota Murtskhvaladze, George Machitidze',
ko_KR => 'BJ Jang',
lo => 'Anousak Souphavanh',
lv => 'Maris Nartiss, Pēteris Brūns',
lt => 'Kestas M',
nl => 'Richard Duivenvoorde, Raymond Nijssen, Carlo van Rijswijk',
mn => 'Bayarmaa Enkhtur',
pl_PL => 'Robert Szczepanek, Milena Nowotarska, Borys Jurgiel, Mateusz Loskot, Tomasz Paul, Andrzej Swiader ',
pt_BR => 'Arthur Nanni, Christian Ferreira, Leandro Kaut',
pt_PT => 'Giovanni Manghi, Joana Simoes, Duarte Carreira, Alexandre Neto, Pedro Pereira',
ro => 'Lonut Losifescu-Enescu',
ru => 'Artem Popov',
sk => 'Lubos Balazovic',
sl_SI => 'Jože Detečnik, Dejan Gregor',
sv => 'Lars Luthman, Magnus Homann',
sq_AL => '',
th => 'Man Chao',
tr => 'Osman Yilmaz',
uk => 'Сергей Якунин',
vi => 'Bùi Hữu Mạnh',
zh_CN => 'Zhang Jun',
zh_TW => 'Nungyao Lin',
};

my $maxn;

for my $i (<i18n/qgis_*.ts>) {
my ($langcode) = $i =~ /i18n\/qgis_(.*).ts/;
my ($langcode) = $i =~ /i18n\/qgis_(.*).ts/;

my $name;
if($langcode =~ /(.*)_(.*)/) {
my $lang = code2language(lc $1);
my $country = code2country(lc $2);
$name = "$lang ($country)";
} else {
$name = code2language(lc $langcode);
}

my $name;
if($langcode =~ /(.*)_(.*)/) {
my $lang = code2language(lc $1);
my $country = code2country(lc $2);
$name = "$lang ($country)";
} else {
$name = code2language(lc $langcode);
}

open F, "lrelease $i|";

open F, "lrelease $i|";
my($translations,$finished,$unfinished,$untranslated);

my($translations,$finished,$unfinished,$untranslated);
while(<F>) {
if(/Generated (\d+) translation\(s\) \((\d+) finished and (\d+) unfinished\)/) {
$translations=$1;
$finished=$2;
$unfinished=$3;
} elsif(/Ignored (\d+) untranslated source text\(s\)/) {
$untranslated=$1;
}
}

while(<F>) {
if(/Generated (\d+) translation\(s\) \((\d+) finished and (\d+) unfinished\)/) {
$translations=$1;
$finished=$2;
$unfinished=$3;
} elsif(/Ignored (\d+) untranslated source text\(s\)/) {
$untranslated=$1;
}
}
close F;

close F;
my $n = $translations+$untranslated;
$maxn = $n unless defined $maxn;

my $n = $translations+$untranslated;
if( $n>$maxn ) {
print STDERR "$i: more translation than others. ($n>$maxn)\n";
$maxn = $n;
}

push @lang, { code=>$langcode, name=>$name, n=>$n, translations=>$translations, finished=>$finished, unfinished=>$unfinished, untranslated=>$untranslated, percentage=>($n-$untranslated)/$n*100 };
push @lang, { code=>$langcode, name=>$name, n=>$n, translations=>$translations, finished=>$finished, unfinished=>$unfinished, untranslated=>$untranslated, };
}

if ($ARGV[0] eq "site"){
print "<html><body>";
print "<head>";
print "<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\"/>";
print "<style>";
print "body{font-family:sans-serif;}";
print "table {font-size:80%;border-collapse: collapse;}";
print "td {border-left:solid 1px #aaaaaa;border-right:solid 1px #aaaaaa;padding:1px 10px;}";
print ".bartodo{ background-color:red;width:100px;height:20px;}";
print ".bardone{ background-color:green;width:80px;height:20px;font-size:80%;text-align:center;padding-top:4px;height:16px;color:white;}";
print "</style></head>";
print "<table>";
print "<tr><td colspan=\"2\" style=\"width:250px;\">Language</td><td>Count</td><td>Finished</td><td>Unfinished</td><td>Untranslated</td><td>Percentage</td><td>Translators</td></tr>\n";
for my $l (sort { $b->{percentage} <=> $a->{percentage} } @lang) {
print "\n<tr><td><img src=\"flags/", $l->{code}, ".png\">", "</td><td>", $l->{name}, "</td><td>", join("</td><td>", $l->{n}, $l->{finished}, $l->{unfinished}, $l->{untranslated}, sprintf("<div class=\"bartodo\"><div class=\"bardone\" style=\"width:%.1fpx\">%.1f</div></div>", ($l->{percentage}, $l->{percentage})) ), "</td><td>", $translators->{$l->{code}} ,"</tr></tr>";
}
print "</table></body></html>";
foreach my $l (@lang) {
$l->{diff} = $l->{n}-$maxn;
$l->{percentage} = ($l->{finished}+$l->{unfinished}/2)/$maxn*100;
}
else {
print "<style>";
print "table {font-size:80%;}";
print "th {text-align:left; }";
print ".bartodo{ background-color:red;width:100px;height:20px;}";
print ".bardone{ background-color:green;width:80px;height:20px;font-size:80%;text-align:center;padding-top:4px;height:16px;color:white;}";
print "</style>";
print "<table>";
print "<tr><th colspan=\"2\" style=\"width:250px;\">Language</th><th>Finished %</th><th>Translators</th></tr>\n";
for my $l (sort { $b->{percentage} <=> $a->{percentage} } @lang) {
print "\n<tr><td><img src=\"qrc:/images/flags/", $l->{code}, ".png\">", "</td><td>", $l->{name}, "</td><td>", join("</td><td>", sprintf("<div class=\"bartodo\"><div class=\"bardone\" style=\"width:%.1fpx\">%.1f</div></div>", ($l->{percentage}, $l->{percentage})) ), "</td><td>", $translators->{$l->{code}} ,"</tr></tr>";
}
print "</table>";

if ($ARGV[0] eq "site") {
print "<html><body>";
print "<head>";
print "<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\"/>";
print "<style>";
print "body{font-family:sans-serif;}";
print "table {font-size:80%;border-collapse: collapse;}";
print "td {border-left:solid 1px #aaaaaa;border-right:solid 1px #aaaaaa;padding:1px 10px;}";
print ".bartodo{ background-color:red;width:100px;height:20px;}";
print ".bardone{ background-color:green;width:80px;height:20px;font-size:80%;text-align:center;padding-top:4px;height:16px;color:white;}";
print "</style></head>";
print "<table>";
print "<tr><td colspan=\"2\" style=\"width:250px;\">Language</td><td>Count</td><td>Finished</td><td>Unfinished</td><td>Untranslated</td><td>Percentage</td><td>Translators</td></tr>\n";
for my $l (sort { $b->{percentage} <=> $a->{percentage} } @lang) {
printf "\n<tr>"
. '<td><img src="flags/%s.png"></td><td nowrap>%s</td>'
. '<td nowrap>%s</td><td>%d</td><td>%d</td><td>%d</td>'
. '<td><div class="bartodo"><div class="bardone" style="width:%dpx">%.1f</div></div></td>'
. '<td>%s</td>'
. '</tr>',
$l->{code}, $l->{name},
$l->{diff}==0 ? $l->{n} : "$l->{n} ($l->{diff})",
$l->{finished}, $l->{unfinished}, $l->{untranslated},
$l->{percentage}, $l->{percentage},
$translators->{$l->{code}};
}
print "</table></body></html>\n";
} else {
print "<style>";
print "table {font-size:80%;}";
print "th {text-align:left; }";
print ".bartodo{ background-color:red;width:100px;height:20px;}";
print ".bardone{ background-color:green;width:80px;height:20px;font-size:80%;text-align:center;padding-top:4px;height:16px;color:white;}";
print "</style>";
print "<table>";
print "<tr><th colspan=\"2\" style=\"width:250px;\">Language</th><th>Finished %</th><th>Translators</th></tr>\n";
for my $l (sort { $b->{percentage} <=> $a->{percentage} } @lang) {
printf "\n<tr>"
. '<td><img src="qrc:/images/flags/%s.png"></td><td>%s</td>'
. '<td><div title="finished:%d unfinished:%d untranslated:%d" class="bartodo"><div class="bardone" style="width:%dpx">%.1f</div></div></td>'
. '<td>%s</td>'
. '</tr>',
$l->{code}, $l->{name},
$l->{finished}, $l->{unfinished}, $l->{untranslated},
$l->{percentage}, $l->{percentage},
$translators->{$l->{code}};
}
print "</table>\n";
}
5 changes: 5 additions & 0 deletions scripts/update_ts_files.sh
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ cleanup() {
do
[ -f "$i.save" ] && mv "$i.save" "$i"
done

trap "" EXIT
}

trap cleanup EXIT
Expand Down Expand Up @@ -110,6 +112,9 @@ if [ -n "$add" ]; then
fi
echo Updating translations
$LUPDATE$opts -verbose qgis_ts.pro

cleanup

echo Updating TRANSLATORS File
./scripts/tsstat.pl > doc/TRANSLATORS

Expand Down
2 changes: 2 additions & 0 deletions src/app/composer/qgscomposer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,9 @@ QgsComposer::QgsComposer( QgisApp *qgis, const QString& title )
int size = settings.value( "/IconSize", QGIS_ICON_SIZE ).toInt();
setIconSize( QSize( size, size ) );

#ifndef Q_WS_MAC
setFontSize( settings.value( "/fontPointSize", QGIS_DEFAULT_FONTSIZE ).toInt() );
#endif

QToolButton* orderingToolButton = new QToolButton( this );
orderingToolButton->setPopupMode( QToolButton::InstantPopup );
Expand Down
264 changes: 122 additions & 142 deletions src/app/nodetool/qgsmaptoolnodetool.cpp

Large diffs are not rendered by default.

16 changes: 7 additions & 9 deletions src/app/nodetool/qgsmaptoolnodetool.h
Original file line number Diff line number Diff line change
Expand Up @@ -52,11 +52,6 @@ class QgsMapToolNodeTool: public QgsMapToolVertexEdit
//! called when map tool is being deactivated
void deactivate();

/**
* Returns closest vertex to given point from selected feature
*/
QgsPoint closestVertex( QgsPoint point );

public slots:
void selectedFeatureDestroyed();

Expand Down Expand Up @@ -132,22 +127,25 @@ class QgsMapToolNodeTool: public QgsMapToolVertexEdit
QgsFeatureId mAnother;

/** stored position of last press down action to count how much vertexes should be moved */
QgsPoint* mLastCoordinates;
QPoint mPressCoordinates;

/** closest vertex to click */
QgsPoint mClosestVertex;
/** closest vertex to click in map coordinates */
QgsPoint mClosestMapVertex;

/** backup of map coordinates to be able to count change between moves */
QgsPoint mPosMapCoordBackup;

/** active rubberband for selecting vertexes */
QRubberBand *mRubberBand;
QRubberBand *mSelectionRubberBand;

/** rectangle defining area for selecting vertexes */
QRect* mRect;

/** flag to tell if edition points */
bool mIsPoint;

/** vertex to deselect on release */
int mDeselectOnRelease;
};

#endif
86 changes: 55 additions & 31 deletions src/app/nodetool/qgsselectedfeature.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -227,11 +227,23 @@ void QgsSelectedFeature::validationFinished()

void QgsSelectedFeature::deleteSelectedVertexes()
{
int nSelected = 0;
foreach( QgsVertexEntry *entry, mVertexMap )
{
if ( entry->isSelected() )
nSelected++;
}

if ( nSelected == 0 )
return;

int topologicalEditing = QgsProject::instance()->readNumEntry( "Digitizing", "/TopologicalEditing", 0 );
QMultiMap<double, QgsSnappingResult> currentResultList;

mVlayer->beginEditCommand( QObject::tr( "Deleted vertices" ) );

beginGeometryChange();

int count = 0;
for ( int i = mVertexMap.size() - 1; i > -1; i-- )
{
Expand All @@ -250,6 +262,11 @@ void QgsSelectedFeature::deleteSelectedVertexes()
mVlayer->snapWithContext( mVertexMap[i]->point(), ZERO_TOLERANCE, currentResultList, QgsSnapper::SnapToVertex );
}

// only last update should trigger the geometry update
// as vertex selection gets lost on the update
if ( --nSelected == 0 )
endGeometryChange();

if ( !mVlayer->deleteVertex( mFeatureId, i ) )
{
count = 0;
Expand Down Expand Up @@ -283,48 +300,55 @@ void QgsSelectedFeature::deleteSelectedVertexes()
}
}

void QgsSelectedFeature::moveSelectedVertexes( double changeX, double changeY )
void QgsSelectedFeature::moveSelectedVertexes( const QgsVector &v )
{
int nUpdates = 0;
foreach( QgsVertexEntry *entry, mVertexMap )
{
if ( entry->isSelected() )
nUpdates++;
}

if ( nUpdates == 0 )
return;

mVlayer->beginEditCommand( QObject::tr( "Moved vertices" ) );
int topologicalEditing = QgsProject::instance()->readNumEntry( "Digitizing", "/TopologicalEditing", 0 );

beginGeometryChange();

QMultiMap<double, QgsSnappingResult> currentResultList;
for ( int i = mVertexMap.size() - 1; i > -1; i-- )
for ( int i = mVertexMap.size() - 1; i > -1 && nUpdates > 0; i-- )
{
if ( mVertexMap[i]->isSelected() )
{
if ( topologicalEditing )
{
// snap from current vertex
currentResultList.clear();
mVlayer->snapWithContext( mVertexMap[i]->point(), ZERO_TOLERANCE, currentResultList, QgsSnapper::SnapToVertex );
}
QgsVertexEntry *entry = mVertexMap.value( i, 0 );
if ( !entry || !entry->isSelected() )
continue;

mVlayer->moveVertex( mVertexMap[i]->point().x() + changeX, mVertexMap[i]->point().y() + changeY, mFeatureId, i );
if ( topologicalEditing )
{
// snap from current vertex
currentResultList.clear();
mVlayer->snapWithContext( entry->point(), ZERO_TOLERANCE, currentResultList, QgsSnapper::SnapToVertex );
}

mVertexMap[i]->moveCenter( changeX, changeY );
// only last update should trigger the geometry update
// as vertex selection gets lost on the update
if ( --nUpdates == 0 )
endGeometryChange();

if ( topologicalEditing )
{
QMultiMap<double, QgsSnappingResult>::iterator resultIt = currentResultList.begin();
QgsPoint p = entry->point() + v;
mVlayer->moveVertex( p.x(), p.y(), mFeatureId, i );

for ( ; resultIt != currentResultList.end(); ++resultIt )
{
// move all other
if ( mFeatureId != resultIt.value().snappedAtGeometry )
mVlayer->moveVertex( mVertexMap[i]->point().x(), mVertexMap[i]->point().y(),
resultIt.value().snappedAtGeometry, resultIt.value().snappedVertexNr );
}
}

QgsVertexEntry *entry = mVertexMap[i];
entry->setCenter( entry->point() );
entry->update();
if ( topologicalEditing )
{
QMultiMap<double, QgsSnappingResult>::iterator resultIt = currentResultList.begin();

if ( entry->equals() != -1 && !mVertexMap[ entry->equals()]->isSelected() )
for ( ; resultIt != currentResultList.end(); ++resultIt )
{
mVertexMap[ entry->equals()]->moveCenter( changeX, changeY );
mVertexMap[ entry->equals()]->update();
// for polygon delete both
// move all other
if ( mFeatureId != resultIt.value().snappedAtGeometry )
mVlayer->moveVertex( p.x(), p.y(),
resultIt.value().snappedAtGeometry, resultIt.value().snappedVertexNr );
}
}
}
Expand Down
5 changes: 2 additions & 3 deletions src/app/nodetool/qgsselectedfeature.h
Original file line number Diff line number Diff line change
Expand Up @@ -82,10 +82,9 @@ class QgsSelectedFeature: public QObject

/**
* Moves selected vertex
* @param changeX change in X coordinate
* @param changeY change in Y coordinate
* @param v translation vector
*/
void moveSelectedVertexes( double changeX, double changeY );
void moveSelectedVertexes( const QgsVector &v );

/**
* Inverts selection of vertex with number
Expand Down
6 changes: 0 additions & 6 deletions src/app/nodetool/qgsvertexentry.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -68,12 +68,6 @@ void QgsVertexEntry::setCenter( QgsPoint p )
}
}

void QgsVertexEntry::moveCenter( double x, double y )
{
mPoint += QgsVector( x, y );
setCenter( mPoint );
}

void QgsVertexEntry::setSelected( bool selected )
{
mSelected = selected;
Expand Down
1 change: 0 additions & 1 deletion src/app/nodetool/qgsvertexentry.h
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,6 @@ class QgsVertexEntry
bool isInRubberBand() const { return mInRubberBand; }

void setCenter( QgsPoint p );
void moveCenter( double x, double y );

void setEqual( int index ) { mEquals = index; }
void setSelected( bool selected = true );
Expand Down
14 changes: 8 additions & 6 deletions src/app/qgisapp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@
#include <QToolButton>
#include <QVBoxLayout>
#include <QWhatsThis>
#include <QThread>

#include <qgsnetworkaccessmanager.h>

Expand Down Expand Up @@ -317,7 +318,10 @@ static void setTitleBarText_( QWidget & qgisApp )
*/
static QgsMessageOutput *messageOutputViewer_()
{
return new QgsMessageViewer( QgisApp::instance() );
if ( QThread::currentThread() == QApplication::instance()->thread() )
return new QgsMessageViewer( QgisApp::instance() );
else
return new QgsMessageOutputConsole();
}

static void customSrsValidation_( QgsCoordinateReferenceSystem* srs )
Expand Down Expand Up @@ -6128,10 +6132,9 @@ void QgisApp::showStatusMessage( QString theMessage )
statusBar()->showMessage( theMessage );
}

// Show the maptip using tooltip
void QgisApp::showMapTip()

{
/* Show the maptip using tooltip */
// Stop the timer while we look for a maptip
mpMapTipsTimer->stop();

Expand All @@ -6141,7 +6144,6 @@ void QgisApp::showMapTip()
QPoint myPointerPos = mMapCanvas->mouseLastXY();

// Make sure there is an active layer before proceeding

QgsMapLayer* mypLayer = mMapCanvas->currentLayer();
if ( mypLayer )
{
Expand Down Expand Up @@ -6872,8 +6874,8 @@ bool QgisApp::addRasterLayers( QStringList const &theFileNameQStringList, bool g
QFileInfo myFileInfo( *myIterator );
// get the directory the .adf file was in
QString myDirNameQString = myFileInfo.path();
//extract basename with extension
QString myBaseNameQString = myFileInfo.completeBaseName() + "." + myFileInfo.suffix();
//extract basename
QString myBaseNameQString = myFileInfo.completeBaseName();
//only allow one copy of a ai grid file to be loaded at a
//time to prevent the user selecting all adfs in 1 dir which
//actually represent 1 coverage,
Expand Down
4 changes: 2 additions & 2 deletions src/app/qgsbrowserdockwidget.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -303,7 +303,7 @@ void QgsBrowserDockWidget::addLayer( QgsLayerItem *layerItem )
QgsDebugMsg( providerKey + " : " + uri );
if ( type == QgsMapLayer::VectorLayer )
{
QgisApp::instance()->addVectorLayer( uri, layerItem->name(), providerKey );
QgisApp::instance()->addVectorLayer( uri, layerItem->layerName(), providerKey );
}
if ( type == QgsMapLayer::RasterLayer )
{
Expand Down Expand Up @@ -333,7 +333,7 @@ void QgsBrowserDockWidget::addLayer( QgsLayerItem *layerItem )
QgsDebugMsg( "rasterLayerPath = " + rasterLayerPath );
QgsDebugMsg( "layers = " + layers.join( " " ) );

QgisApp::instance()->addRasterLayer( rasterLayerPath, layerItem->name(), providerKey, layers, styles, format, crs );
QgisApp::instance()->addRasterLayer( rasterLayerPath, layerItem->layerName(), providerKey, layers, styles, format, crs );
}
}

Expand Down
18 changes: 9 additions & 9 deletions src/app/qgscustomprojectiondialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -163,7 +163,7 @@ long QgsCustomProjectionDialog::getRecordCount()
int myResult;
long myRecordCount = 0;
//check the db is available
myResult = sqlite3_open( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -198,7 +198,7 @@ QString QgsCustomProjectionDialog::getProjectionFamilyName( QString theProjectio
int myResult;
QString myName;
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -229,7 +229,7 @@ QString QgsCustomProjectionDialog::getEllipsoidName( QString theEllipsoidAcronym
int myResult;
QString myName;
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -260,7 +260,7 @@ QString QgsCustomProjectionDialog::getProjectionFamilyAcronym( QString theProjec
int myResult;
QString myName;
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -291,7 +291,7 @@ QString QgsCustomProjectionDialog::getEllipsoidAcronym( QString theEllipsoidName
int myResult;
QString myName;
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -323,7 +323,7 @@ void QgsCustomProjectionDialog::on_pbnFirst_clicked()
sqlite3_stmt *myPreparedStatement;
int myResult;
//check the db is available
myResult = sqlite3_open( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -395,7 +395,7 @@ void QgsCustomProjectionDialog::on_pbnPrevious_clicked()
sqlite3_stmt *myPreparedStatement;
int myResult;
//check the db is available
myResult = sqlite3_open( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -468,7 +468,7 @@ void QgsCustomProjectionDialog::on_pbnNext_clicked()
sqlite3_stmt *myPreparedStatement;
int myResult;
//check the db is available
myResult = sqlite3_open( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -537,7 +537,7 @@ void QgsCustomProjectionDialog::on_pbnLast_clicked()
sqlite3_stmt *myPreparedStatement;
int myResult;
//check the db is available
myResult = sqlite3_open( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::qgisUserDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult != SQLITE_OK )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down
15 changes: 0 additions & 15 deletions src/app/qgshighlight.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,11 +69,6 @@ void QgsHighlight::paintPoint( QPainter *p, QgsPoint point )
{
QPolygonF r( 5 );

if ( mLayer )
{
point = mMapCanvas->mapRenderer()->layerToMapCoordinates( mLayer, point );
}

double d = mMapCanvas->extent().width() * 0.005;
r[0] = toCanvasCoordinates( point + QgsVector( -d, -d ) ) - pos();
r[1] = toCanvasCoordinates( point + QgsVector( d, -d ) ) - pos();
Expand All @@ -90,11 +85,6 @@ void QgsHighlight::paintLine( QPainter *p, QgsPolyline line )

for ( int i = 0; i < line.size(); i++ )
{
if ( mLayer )
{
line[i] = mMapCanvas->mapRenderer()->layerToMapCoordinates( mLayer, line[i] );
}

polygon[i] = toCanvasCoordinates( line[i] ) - pos();
}

Expand All @@ -115,11 +105,6 @@ void QgsHighlight::paintPolygon( QPainter *p, QgsPolygon polygon )

for ( int j = 0; j < polygon[i].size(); j++ )
{
if ( mLayer )
{
polygon[i][j] = mMapCanvas->mapRenderer()->layerToMapCoordinates( mLayer, polygon[i][j] );
}

ring[ j ] = toCanvasCoordinates( polygon[i][j] ) - pos();
}

Expand Down
6 changes: 3 additions & 3 deletions src/app/qgsoptions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -982,7 +982,7 @@ void QgsOptions::getEllipsoidList()

cmbEllipsoid->addItem( ELLIPS_FLAT_DESC );
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -1015,7 +1015,7 @@ QString QgsOptions::getEllipsoidAcronym( QString theEllipsoidName )
int myResult;
QString myName( ELLIPS_FLAT );
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down Expand Up @@ -1047,7 +1047,7 @@ QString QgsOptions::getEllipsoidName( QString theEllipsoidAcronym )
int myResult;
QString myName( ELLIPS_FLAT_DESC );
//check the db is available
myResult = sqlite3_open( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase );
myResult = sqlite3_open_v2( QgsApplication::srsDbFilePath().toUtf8().data(), &myDatabase, SQLITE_OPEN_READONLY, NULL );
if ( myResult )
{
QgsDebugMsg( QString( "Can't open database: %1" ).arg( sqlite3_errmsg( myDatabase ) ) );
Expand Down
3 changes: 3 additions & 0 deletions src/core/qgis.h
Original file line number Diff line number Diff line change
Expand Up @@ -186,6 +186,9 @@ const double MINIMUM_POINT_SIZE = 0.1;
const double DEFAULT_POINT_SIZE = 2.0;
const double DEFAULT_LINE_WIDTH = 0.26;

/** default snapping tolerance for segments (@note added in 1.8) */
const double DEFAULT_SEGMENT_EPSILON = 1e-8;

// FIXME: also in qgisinterface.h
#ifndef QGISEXTERN
#ifdef WIN32
Expand Down
4 changes: 3 additions & 1 deletion src/core/qgsapplication.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,9 @@ bool QgsApplication::event( QEvent * event )
bool QgsApplication::notify( QObject * receiver, QEvent * event )
{
bool done = false;
emit preNotify( receiver, event, &done );
// Crashes in customization (especially on Mac), if we're not in the main/UI thread, see #5597
if ( thread() == receiver->thread() )
emit preNotify( receiver, event, &done );

if ( done )
return true;
Expand Down
78 changes: 64 additions & 14 deletions src/core/qgscoordinatereferencesystem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,54 @@ bool QgsCoordinateReferenceSystem::createFromString( const QString theDefinition
return result;
}

bool QgsCoordinateReferenceSystem::createFromUserInput( const QString theDefinition )
{
QString theWkt;
char *wkt = NULL;
OGRSpatialReferenceH crs = OSRNewSpatialReference( NULL );

// make sure towgs84 parameter is loaded if using an ESRI definition and gdal >= 1.9
#if GDAL_VERSION_NUM >= 1900
if ( theDefinition.startsWith( "ESRI::" ) )
{
setupESRIWktFix();
}
#endif

if ( OSRSetFromUserInput( crs, theDefinition.toLocal8Bit().constData() ) == OGRERR_NONE )
{
if ( OSRExportToWkt( crs, &wkt ) == OGRERR_NONE )
{
theWkt = wkt;
OGRFree( wkt );
}
OSRDestroySpatialReference( crs );
}
//QgsDebugMsg( "theDefinition: " + theDefinition + " theWkt = " + theWkt );
return createFromWkt( theWkt );
}

void QgsCoordinateReferenceSystem::setupESRIWktFix( )
{
// make sure towgs84 parameter is loaded if gdal >= 1.9
// this requires setting GDAL_FIX_ESRI_WKT=GEOGCS (see qgis bug #5598 and gdal bug #4673)
#if GDAL_VERSION_NUM >= 1900
const char* configOld = CPLGetConfigOption( "GDAL_FIX_ESRI_WKT", "" );
const char* configNew = "GEOGCS";
// only set if it was not set, to let user change the value if needed
if ( strcmp( configOld, "" ) == 0 )
{
CPLSetConfigOption( "GDAL_FIX_ESRI_WKT", configNew );
if ( strcmp( configNew, CPLGetConfigOption( "GDAL_FIX_ESRI_WKT", "" ) ) != 0 )
QgsLogger::warning( QString( "GDAL_FIX_ESRI_WKT could not be set to %1 : %2"
).arg( configNew ).arg( CPLGetConfigOption( "GDAL_FIX_ESRI_WKT", "" ) ) ) ;
QgsDebugMsg( QString( "set GDAL_FIX_ESRI_WKT : %1" ).arg( configNew ) );
}
else
QgsDebugMsg( QString( "GDAL_FIX_ESRI_WKT was already set : %1" ).arg( configNew ) );
#endif
}

bool QgsCoordinateReferenceSystem::createFromOgcWmsCrs( QString theCrs )
{
QRegExp re( "urn:ogc:def:crs:([^:]+).+([^:]+)", Qt::CaseInsensitive );
Expand Down Expand Up @@ -423,12 +471,13 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
// +proj=lcc +lat_1=46.8 +lat_0=46.8 +lon_0=2.337229166666664 +k_0=0.99987742
// +x_0=600000 +y_0=2200000 +a=6378249.2 +b=6356515.000000472 +units=m +no_defs
//
QgsDebugMsg( "proj4: " + theProj4String );
QString myProj4String = theProj4String.trimmed();
QgsDebugMsg( "proj4: " + myProj4String );
mIsValidFlag = false;
mWkt.clear();

QRegExp myProjRegExp( "\\+proj=(\\S+)" );
int myStart = myProjRegExp.indexIn( theProj4String );
int myStart = myProjRegExp.indexIn( myProj4String );
if ( myStart == -1 )
{
QgsDebugMsg( "proj string supplied has no +proj argument" );
Expand All @@ -438,7 +487,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
mProjectionAcronym = myProjRegExp.cap( 1 );

QRegExp myEllipseRegExp( "\\+ellps=(\\S+)" );
myStart = myEllipseRegExp.indexIn( theProj4String );
myStart = myEllipseRegExp.indexIn( myProj4String );
if ( myStart == -1 )
{
QgsDebugMsg( "proj string supplied has no +ellps argument" );
Expand All @@ -450,7 +499,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
}

QRegExp myAxisRegExp( "\\+a=(\\S+)" );
myStart = myAxisRegExp.indexIn( theProj4String );
myStart = myAxisRegExp.indexIn( myProj4String );
if ( myStart == -1 )
{
QgsDebugMsg( "proj string supplied has no +a argument" );
Expand All @@ -471,7 +520,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
* - if the above does not match perform a whole text search on proj4 string (if not null)
*/
// QgsDebugMsg( "wholetext match on name failed, trying proj4string match" );
myRecord = getRecord( "select * from tbl_srs where parameters=" + quotedValue( theProj4String.trimmed() ) + " order by deprecated" );
myRecord = getRecord( "select * from tbl_srs where parameters=" + quotedValue( myProj4String ) + " order by deprecated" );
if ( myRecord.empty() )
{
// Ticket #722 - aaronr
Expand All @@ -485,20 +534,20 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
int myLength2 = 0;
QString lat1Str = "";
QString lat2Str = "";
myStart1 = myLat1RegExp.indexIn( theProj4String, myStart1 );
myStart2 = myLat2RegExp.indexIn( theProj4String, myStart2 );
myStart1 = myLat1RegExp.indexIn( myProj4String, myStart1 );
myStart2 = myLat2RegExp.indexIn( myProj4String, myStart2 );
if ( myStart1 != -1 && myStart2 != -1 )
{
myLength1 = myLat1RegExp.matchedLength();
myLength2 = myLat2RegExp.matchedLength();
lat1Str = theProj4String.mid( myStart1 + LAT_PREFIX_LEN, myLength1 - LAT_PREFIX_LEN );
lat2Str = theProj4String.mid( myStart2 + LAT_PREFIX_LEN, myLength2 - LAT_PREFIX_LEN );
lat1Str = myProj4String.mid( myStart1 + LAT_PREFIX_LEN, myLength1 - LAT_PREFIX_LEN );
lat2Str = myProj4String.mid( myStart2 + LAT_PREFIX_LEN, myLength2 - LAT_PREFIX_LEN );
}
// If we found the lat_1 and lat_2 we need to swap and check to see if we can find it...
if ( lat1Str != "" && lat2Str != "" )
{
// Make our new string to check...
QString theProj4StringModified = theProj4String;
QString theProj4StringModified = myProj4String;
// First just swap in the lat_2 value for lat_1 value
theProj4StringModified.replace( myStart1 + LAT_PREFIX_LEN, myLength1 - LAT_PREFIX_LEN, lat2Str );
// Now we have to find the lat_2 location again since it has potentially moved...
Expand All @@ -524,7 +573,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
// split on spaces followed by a plus sign (+) to deal
// also with parameters containing spaces (e.g. +nadgrids)
// make sure result is trimmed (#5598)
foreach( QString param, theProj4String.split( QRegExp( "\\s+(?=\\+)" ), QString::SkipEmptyParts ) )
foreach( QString param, myProj4String.split( QRegExp( "\\s+(?=\\+)" ), QString::SkipEmptyParts ) )
{
QString arg = QString( "' '||parameters||' ' LIKE %1" ).arg( quotedValue( QString( "% %1 %" ).arg( param.trimmed() ) ) );
if ( param.startsWith( "+datum=" ) )
Expand Down Expand Up @@ -563,7 +612,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
{
// Last ditch attempt to piece together what we know of the projection to find a match...
QgsDebugMsg( "globbing search for srsid from this proj string" );
setProj4String( theProj4String );
setProj4String( myProj4String );
mySrsId = findMatchingProj();
QgsDebugMsg( "globbing search for srsid returned srsid: " + QString::number( mySrsId ) );
if ( mySrsId > 0 )
Expand All @@ -580,7 +629,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString theProj4String
if ( !mIsValidFlag )
{
QgsDebugMsg( "Projection is not found in databases." );
setProj4String( theProj4String );
setProj4String( myProj4String );

// Is the SRS is valid now, we know it's a decent +proj string that can be entered into the srs.db
if ( mIsValidFlag )
Expand Down Expand Up @@ -842,7 +891,7 @@ void QgsCoordinateReferenceSystem::setProj4String( QString theProj4String )
OSRDestroySpatialReference( mCRS );
mCRS = OSRNewSpatialReference( NULL );
mIsValidFlag =
OSRImportFromProj4( mCRS, theProj4String.toLatin1().constData() )
OSRImportFromProj4( mCRS, theProj4String.trimmed().toLatin1().constData() )
== OGRERR_NONE;
mWkt.clear();
setMapUnits();
Expand Down Expand Up @@ -1543,6 +1592,7 @@ int QgsCoordinateReferenceSystem::syncDb()
if ( proj4.startsWith( input ) )
{
proj4 = proj4.mid( input.size() );
proj4 = proj4.trimmed();
}
}
else
Expand Down
26 changes: 26 additions & 0 deletions src/core/qgscoordinatereferencesystem.h
Original file line number Diff line number Diff line change
Expand Up @@ -171,6 +171,32 @@ class CORE_EXPORT QgsCoordinateReferenceSystem
*/
bool createFromString( const QString theDefinition );

/*! Set up this srs from a various text formats.
*
* Valid formats: WKT string, "EPSG:n", "EPSGA:n", "AUTO:proj_id,unit_id,lon0,lat0",
* "urn:ogc:def:crs:EPSG::n", PROJ.4 string, filename (with WKT, XML or PROJ.4 string),
* well known name (such as NAD27, NAD83, WGS84 or WGS72),
* ESRI::[WKT string] (directly or in a file), "IGNF:xxx"
*
* For more details on supported formats see OGRSpatialReference::SetFromUserInput()
* ( http://www.gdal.org/ogr/classOGRSpatialReference.html#aec3c6a49533fe457ddc763d699ff8796 )
* @note this function generates a WKT string using OSRSetFromUserInput() and
* passes it to createFromWkt() function.
* @param theDefinition A String containing a coordinate reference system definition.
*/
bool createFromUserInput( const QString theDefinition );

/*! Make sure that ESRI WKT import is done properly.
* This is required for proper shapefile CRS import when using gdal>= 1.9.
* @note This function is called by createFromUserInput() and QgsOgrProvider::crs(), there is usually
* no need to call it from elsewhere.
* @note This function sets CPL config option GDAL_FIX_ESRI_WKT to a proper value,
* unless it has been set by the user through the commandline or an environment variable.
* For more details refer to OGRSpatialReference::morphFromESRI() .
* @note added in 1.8
*/
static void setupESRIWktFix();

/*! Find out whether this CRS is correctly initialised and usable */
bool isValid() const;

Expand Down
2 changes: 2 additions & 0 deletions src/core/qgsdataitem.h
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,8 @@ class CORE_EXPORT QgsLayerItem : public QgsDataItem
static const QIcon &iconTable();
static const QIcon &iconRaster();
static const QIcon &iconDefault();

virtual QString layerName() const { return name(); }
};


Expand Down
Loading