Related Plugins and Tags

QGIS Planet

“Google Maps”-Style Road Maps in QGIS

This is a follow up post on “Guide to Advanced Labeling for OSM Roads”. This post covers how to create a map that looks similar to the classic Google Maps map based on OSM data.

Styling OSM road data is a bit tricky due to the many different possible options in OSM “type” tag. It takes some fiddling around to get results similar to Google. The easiest way to create such a style is using rule-based renderer with “Symbol levels” enabled.

I’ve excluded a number of road types from being rendered and labeled. This is done by NOT specifying a rule that fits those classes. That’s the reason why I don’t have a “no filter” rule. Instead, I’ve specified

type NOT IN ('footway','footpath','steps','cycleway','pedestrian','track','bridleway')

to cover all the roads I don’t want specifically highlighted but displayed using default style. This way I can make sure that footways and similar are neither drawn nor labeled.

Google-style rules for OSM with multiple zoom levels

Now, we can have a look at how to create those road shields Google uses:

Sample from Google Maps

Currently, it’s not possible to solve this using the labeling engine. And even after labels with “shields” will be implemented, there is still the problem that we want both road names and road numbers labeled – preferably without having to duplicate the layer.

For now, one possible solution for this is to create the shields using the “Marker lines” feature of new symbology. As the name suggests, you can put markers on lines. In this case, the marker will be our road shield. It basically has two parts: the colored shield plus the text. The shield can be created by putting two squares besides each other. (Adjust the offsets to move them besides each other.) Then we can put the text on top, one letter at a time.

Creating the road shield marker

Place the marker on the line once and deactivate “Rotate marker”.

A "road with shield" style

These styles can be assigned to every road you want to decorate with a shield. If you save the style, you just need to change the text next time.

And this is how the result can look like.

Zoomed-out result

Maybe the shields turned out a little too big compared with the original.

Zoomed in, more labels will be displayed and an additional layer with metro stations becomes visible. The metro symbol was created using the same technique described for the road shields.

Zoomed-in result

One disadvantage of creating road shields with this technique – besides the fact that it’s rather tedious – is that there is no collision detection between labels and shields. Nonetheless, it’s a viable solution that allows you to create high-resolution maps that look very similar to Google Maps using free OSM data.


Guide to Advanced Labeling for OSM Roads

Advanced labeling in QGIS new labeling engine is mostly about data-defined settings. Almost any property of the label can be controlled.

For this example, we will try to mimic the look of the classic Google map with it’s line and label styles. The data for this post is from the OpenStreetMap project provided as Shapefiles by Cloudmade.

After importing the roads into PostGIS using PostGIS Manager Plugin, we can create a view that will contain the necessary label style information. The trick here is to use CASE statements to distinguish between different label “classes”. Motorway labels will be bigger than the rest and the buffer color will be the same color as used for the corresponding lines.

drop view if exists v_osm_roads_styled ;

CREATE VIEW v_osm_roads_styled AS
SELECT *,
CASE WHEN type = 'motorway' THEN 9
     ELSE 8 END
     as font_size,
'black'::TEXT as font_color,
false as font_bold,
false as font_italic,
false as font_underline,
false as font_strikeout,
false as font_family,
1 as buffer_size,
CASE WHEN type = 'motorway' THEN '#fb9139'::TEXT
     WHEN type IN ( 'primary','primary_link','secondary','secondary_link') THEN '#fffb8b'::TEXT
     ELSE 'white'::TEXT END
     as buffer_color
from osm_roads;

In QGIS, we can then load the view and start styling. First, let’s get the line style ready. Using rule-based renderer, it’s easy to create complex styles. In this case, I’ve left it rather simple and don’t distinguish between different zoom levels. That’s a topic for another post :)

Google-style rules for OSM road data

Now for the labels! In “Data defined settings”, we can assign the special attributes created in the database view to the settings.

Completed "Data defined settings"

To achieve an even better look, go to “Advanced” tab and enable “curved” and “on line” placement. “Merge connected lines to avoid duplicate labels” option is very helpful too.

Finally – after adding some water objects (Cloudmade natural.shp) – this is what our result looks like:

Google-style OSM map

This solution can be improved considerably by adding multiple zoom levels with corresponding styles. One obvious difference between the original Google map and this look-alike is the lack of road numbers. Tim’s post on “shield labels” can be a starting point for adding road numbers the way Google does.


QGIS Time Manager Example: Visualizing Storm Data

Today, I’ve compiled a short video showcasing one of the possible uses of Time Manager plugin: Storm tracking. (Storm data can be downloaded from www.nhc.noaa.gov.)

Point size shows storm class, labels read maximum speed in mph.

If you are using Time Manager for your work, I’d love to hear about it.


Editing Labels in QGIS SVG Output using Inkscape

If you are planning to tweak the labels in SVG output from QGIS, you should use the old labeling engine. Labels create with the old engine are written into the SVG file as text objects whereas labels from the new engine end up as paths for some reason.

Let’s see how it works using the climate Shapefile from QGIS sample data. I just created an empty map, loaded the points and labeled them before exporting the map to SVG using Print Composer. Now, we can manipulate the SVG file in Inkscape: Select one of the labels and and start the XML Editor (Edit menu – XML Editor or through the toolbar button).

Find the "XML tree" button for full control of the labels

If you selected a label before opening XML Editor, one of the entires in the tree should be highlighted. Expanding the element reveals that it’s a text featuring a series of attributes QGIS exported. From here, you can change both the looks and the text of all labels in your map. Of course, you are not limited to the XML Editor but can change to the GUI – which is certainly recommended for experimenting with all the different settings.

Here you have full control over how the label looks like


Visualizing Global Connections

Today, I’ve been experimenting with data from OpenFlights.org. They offer airport, airline and route data for download. The first idea that came to mind was to connect airports on a shared route by lines. This kind of visualization just looks much nicer if the connections are curved instead of simple straight lines.

Luckily, that’s pretty easy to do using PostGIS. After loading airport positions and route data, we can create the connection lines like this (based on [postgis-users] Great circle as a linestring):

UPDATE experimental.airroutes
SET the_geom =
(SELECT ST_Transform(ST_Segmentize(ST_MakeLine(
       ST_Transform(a.the_geom, 953027),
       ST_Transform(b.the_geom, 953027)
     ), 100000 ), 4326 )
 FROM experimental.airports a, experimental.airports b
 WHERE a.id = airroutes.source_id
   AND b.id = airroutes.dest_id
);

The CRS used in the query is not available in PostGIS by default. You can add it like this (source: spatialreference.org):

INSERT into spatial_ref_sys (srid, auth_name, auth_srid, proj4text, srtext) values ( 953027, 'esri', 53027, '+proj=eqdc +lat_0=0 +lon_0=0 +lat_1=60 +lat_2=60 +x_0=0 +y_0=0 +a=6371000 +b=6371000 +units=m +no_defs ', 'PROJCS["Sphere_Equidistant_Conic",GEOGCS["GCS_Sphere",DATUM["Not_specified_based_on_Authalic_Sphere",SPHEROID["Sphere",6371000,0]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]],PROJECTION["Equidistant_Conic"],PARAMETER["False_Easting",0],PARAMETER["False_Northing",0],PARAMETER["Central_Meridian",0],PARAMETER["Standard_Parallel_1",60],PARAMETER["Standard_Parallel_2",60],PARAMETER["Latitude_Of_Origin",0],UNIT["Meter",1],AUTHORITY["EPSG","53027"]]');

This is an example visualization (done in QGIS) showing only flight routes starting from Vienna International Airport:

Flight routes from Vienna International

Connections crossing the date line are currently more problematic. Lines would have to be split, otherwise this is what you’ll get:

Date line trouble


How to create a Table with Geometry Column in PostGIS

Do you need to create a table with a geometry column in PostGIS from scratch?
Can’t remember the syntax of AddGeometryColumn(varchar catalog_name, varchar schema_name, varchar table_name, varchar column_name, integer srid, varchar type, integer dimension)? I can’t. ;)

Let’s make our lives easier: QGIS PostGIS Manager offers a convenient GUI for creating tables with geometry columns:

PostGIS Manager Create Table dialog

The dialog works a lot like what you’re probably used to in pgAdmin – with the added nicety of supporting Geometry columns.

In my opinion, this is the fastest way so far to create a spatially enabled table. It provides a much better user experience than telling users (especially new ones) to use AddGeometryColumn(…


Creating a Gradient Fill for Polygons in QGIS

QGIS styling options have advanced a lot in the last releases. But there’s always something more we would love to have … Greedy users!

Inkscape and other graphics programs can do it: Gradient fills.

Inspired by a question on gis.stackexchange, I tried to create something as close to a gradient fill as possible.

What I came up with is a symbol consisting out of multiple stacked “simple line” layers. The top-most layer is the dark outer border and every following layer is getting lighter and growing towards the center of the polygon (using a positive offset value). Important options are flat cap styles for all line layers and – of course – enabled symbol levels.

A "gradient" fill in QGIS

As you can see, the gradient looks quite fine inside the polygons. For the edges, it would be necessary to add a mask hiding the unclean rendering. Or maybe there is another solution which I just couldn’t think of?

Nicer map using a mask

This is the symbol source if you want to try it. Paste it into your symbology-ng-style.xml document.

    <symbol outputUnit="MM" alpha="1" type="fill" name="gradient">
      <layer pass="0" class="SimpleFill" locked="0">
        <prop k="color" v="255,255,255,255"/>
        <prop k="color_border" v="0,0,0,255"/>
        <prop k="offset" v="0,0"/>
        <prop k="style" v="solid"/>
        <prop k="style_border" v="solid"/>
        <prop k="width_border" v="1"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="240,240,240,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="6"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="6"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="220,220,220,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="5.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="5.5"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="200,200,200,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="5"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="180,180,180,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="4.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="4.5"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="160,160,160,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="4"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="4"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="140,140,140,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="3.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="3.5"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="120,120,120,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="3"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="3"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="100,100,100,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="2.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="2.5"/>
      </layer>
      <layer pass="0" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="80,80,80,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="2"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="2"/>
      </layer>
      <layer pass="1" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="60,60,60,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="1.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="1.5"/>
      </layer>
      <layer pass="2" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="40,40,40,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="1"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="1"/>
      </layer>
      <layer pass="3" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="20,20,20,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="0.5"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="1"/>
      </layer>
      <layer pass="4" class="SimpleLine" locked="0">
        <prop k="capstyle" v="flat"/>
        <prop k="color" v="10,10,10,255"/>
        <prop k="customdash" v="5;2"/>
        <prop k="joinstyle" v="bevel"/>
        <prop k="offset" v="0"/>
        <prop k="penstyle" v="solid"/>
        <prop k="use_custom_dash" v="0"/>
        <prop k="width" v="0.5"/>
      </layer>
    </symbol>

Open Government Data Wien in QGIS

Vienna’s Open Government Data initiative is publishing an increasing amount of Geodata and the best thing is: They’re publishing it via open standardized services! Both WMS and WFS are available and ready to be used in QGIS.

Let’s see how we can use the data available through their WFS using the district information layer “Bezirksgrenzen” as an example. The page lists a GML and a GeoJSON version of WFS. For now, we’ll use GeoJSON.

In QGIS, the layer can be loaded using “Add vector layer” – “Protocol” and inserting the GeoJSON url there. The encoding should be changed to ISO8859-15 to account for “Umlaute”.

The loaded GeoJSON layer "Bezirksgrenzen"

Now, we have geodata. Let’s add some attribute data too! Attribute data is available in CSV format. After downloading e.g. some information on the district population, check the file content and remove excessive header lines so that there is only one header line containing attribute names left. Then, you can load the CSV file into QGIS too (“Add vector layer”).

Last step: Joining geodata and attribute data! Go to the vector layer’s properties – Join tab and add the following join relation:

Joining GeoJSON and attribute layer

Now, the attribute table of the vector layer contains the additional CSV attributes – ready for further analysis. If you want to classify based on numerical CSV attributes, you’ll have to create a .csvt file first otherwise all fields are interpreted as texts.

Works great. Thumbs up for this great initiative!


QGIS 1.7 Released!

QGIS 1.7 has landed. After some delays due to a major infrastructure overhaul, a new version of QGIS is available for download. For a list of what’s new in 1.7 check the release announcement.


Browsing Spatial Data with QGIS Browser

QGIS trunk now comes with a separate tool called “QGIS Browser”. It enables the user to browse through all spatial data files on the system as well as all WMS configured in QGIS. Both files and WMS layers are listed in a tree widget on the left side while metadata, attributes and a preview can be seen on the right.

WMS preview in QGIS Browser

This is a great way for example to check through all layers of a WMS fast and without having to go through the “Add WMS Layer” dialog in QGIS all the time.


Multi-line Labels in QGIS

Ever wondered how to create multi-line labels in QGIS? The new labeling engine has a “Multiline labels” option but it’s not so obvious how to create a usable labeling attribute. Here is how it works (credits to @nhopton on QGIS forum):

  1. Create a big enough text field (if the data doesn’t contain any yet).
  2. In Layer Properties – Fields, chose a “Text edit” edit widget for the label field.
  3. Enter the multi-line text into the label field. You can do this using Attribute Table or Feature Form.

    A feature form with "Text edit" widget

  4. Activate labeling. You’ll have to tick “Multiline labels” option in Layer Labeling Settings – Advanced – Options. That’s it:

    Simple multi-line label example

A common use case is the wish to show multiple attribute values in a feature’s label. Using Field Calculator, you can combine them into multi-line labels. All you need is to combine the fields with the || operator and add ‘\n’ (newline) wherever there should be a line break:

Field1 || '\n' || Field2

Populating a multi-line label field using Field Calculator

And finally, the result:

Multi-line labels displaying city name and population


A First Glimpse at the QGIS Processing Framework

The aim of QGIS Processing Framework developed by Polymeris is to provide a generic framework for accessing existing geo-processing functionality of e.g. SAGA, GRASS, Orfeo Toolbox, etc. This should enable users to script their geo-processing work in python console and allow development of a tool to graphically build workflows using VisTrails an “open-source scientific workflow and provenance management system”.

For a first impression, Polymeris has published some screenshots of QGIS with SAGA modules loaded: [1],[2]

This project is big and if it turns out well, QGIS will profit enormously from it. Both scriptable geoprocessing functionality and a graphic workflow builder can improve user experience a lot if they are implemented well. You can follow further development on the project homepage on GitHub.


Converting MXD to QGIS Project File

On Wednesday, Allan Maungu – geoscripting.blogspot.com announced MXD2QGS, a converter that exports layers from an Arcmap 10 document into a Quantum GIS project file. The tool is built as an ArcToolbox and can be downloaded from the blog.

I’d be very interested to hear whether this tool works for you.


Fast SQL Layer for QGIS

For everyone working with spatial databases in QGIS there comes a time when “Add PostGIS/SpatiaLite Layer” and “RT Sql Layer” start to be annoying. You always have to retype or copy-paste your SQL queries into the user interface if you need to change the tiniest thing in the layer’s definition.

This is where “Fast SQL Layer” can be a real time saver. Fast SQL Layer is a new plugin for QGIS by Pablo T. Carreira. It basically adds an SQL console for loading layers from PostGIS/SpatiaLite into QGIS. And it even comes with syntax highlighting!

Installation

Fast SQL Layer comes with one dependency: Pygments, which is used for syntax highlighting.

On Ubuntu, all you have to do is install it with apt-get:

sudo apt-get install python-pygments

For Windows with OSGeo4W, @Mike_Toews posted this on gis.stackexchange:

I downloaded and extracted Pygments-1.4.tar.gz, then in an OSGeo4W shell within the Pygments-1.4 directory, type python setup.py build then python setup.py install

Usage

When you activate the plugin in plugin manager, a dock widget will appear which contains the console and some fields for specifying the database connection that should be used. Then, you can simply write your SQL query and load the results with one click.

Fast SQL plugin

In this example, I renamed “gid” to “id”, but you can actually edit the values in the drop down boxes to adjust the column names for id and geometry:

A second layer loaded using Fast SQL plugin

It certainly needs some polishing on the user interface side but I really like it.


Catchment Areas with pgRouting driving_distance()

In a previous post, I’ve described how to create catchment areas with pgRouting shortest_path() function. The solution described there calculates costs from the starting node (aka vertex) to all other nodes in the network. Depending on the network size, this can take a long time. Especially, if you are only interested in relatively small catchment areas (e.g. 50 km around a node in a network covering 10,000 km) there is a lot of unnecessary calculation going on. This is where you might want to use driving_distance() instead.

Driving_distance() offers a parameter for maximum distance/cost and will stop calculations when the costs exceed this limit. But let’s start at the beginning: installing the necessary functions.

Installation

If you have followed my guide to installing pgRouting, you already have some routing functions installed – but not driving_distance(). Weirdly, the necessary SQL scripts are not shipped with the .zip file available on pgRouting’s download page. You need:

routing_dd.sql
routing_dd_wrappers.sql

Both are available through the project repository at Github. Get them and execute them in your pgRouting-enabled database. Now, you should be ready.

Calculating driving distances

To calculate driving distances, we need a query very similar to shortest_path():

CREATE OR REPLACE FUNCTION driving_distance(
sql text,
source_id integer,
distance float8,
directed boolean,
has_reverse_cost boolean)
RETURNS SETOF path_result

The only new value is “distance”. That’s the maximum distance/cost you want to be contained in the result set. “distance” has to be specified in the same units as the cost attribute (which is specified in the “sql” text parameter).

Note: In my opinion, the name “(driving) distance” is misleading. While you can use distance as a cost attribute, you’re not limited to distances. You can use any cost attribute you like, e.g. travel time, fuel consumption, co2 emissions, …

The actual query for a catchment area of 100 km around node # 2000 looks like this:

SELECT * FROM driving_distance('
      SELECT gid AS id,
          start_id::int4 AS source,
          end_id::int4 AS target,
          shape_leng::float8 AS cost
      FROM network',
      2000,
      100000,
      false,
      false)

Interpreting the result

These are the first lines of the result set:

vertex_id;edge_id;cost
294;7262;97400.433506144
297;7236;98012.620979231
335;1095;96849.456306244
347;7263;93617.693852324
364;7098;93573.849081386
366;2551;92702.443434779
378;7263;91994.328368081

The cost attribute contains the total cost of travel from the starting node to the vertex_id node.
We will only be using vertex_id and cost. The use of edge_id is a mystery to me.

Visualizing the result

The easiest way to visualize driving_distance() results is using RT Sql Layer plugin. We need to join the results of driving_distance() with the table containing node geometries:

SELECT *
   FROM node
   JOIN
   (SELECT * FROM driving_distance('
      SELECT gid AS id,
          start_id::int4 AS source,
          end_id::int4 AS target,
          shape_leng::float8 AS cost
      FROM network',
      2000,
      100000,
      false,
      false)) AS route
   ON
   node.id = route.vertex_id

If you color the nodes based on the cost attribute, it will look something like this:

result of pgRouting driving_distance() visualized in QGIS


QGIS Video Tutorials

QGIS wiki now has it’s own section listing QGIS video tutorials.
If you know of any tutorials not listed yet, leave a comment and I’ll add them.

Together with the newly started “How to I do that in QGIS” tutorial collection, this will hopefully become the number one reference for both new users doing their first GIS-related work and advanced uses interested in the latest QGIS features.


QGIS is now on Twitter!

Follow @qgis on twitter.com/qgis.


How to do X in QGIS

A great new initiative has been started on QGIS wiki: “How to do X in QGIS” aims at providing step-by-step tutorials for various tasks based on the latest versions of QGIS. This new knowledge base is meant to complement the existing documentation and to replace some of the outdated tutorials available all over the web.

Feel free to contribute tutorials or tutorial ideas, it’s a wiki!


How to Label Only Selected Features in QGIS

The aim of this post is to describe a method for labeling of a subset of features within a layer using new labeling functionality.

The problem

Often, we want to label only a few features in a layer. Of course we can export those features to a new layer and label them that way, but that requires creation of additional files and layers within your project. Things will start to get messy fast.

Another approach is to delete unwanted label texts from the attribute table. This either means that you have to duplicate a “name” attribute and then start deleting from the newly created attribute table column or that you actually delete values in the original column. Both approaches are problematic. Either you produce redundancy that gets difficult to maintain (two attributes have to be updated if the name of a feature changes) or you loose information from the attribute table.

The suggested solution

Let me present a different approach using new labeling tools. The idea is based on moving unwanted labels out of view. This approach avoids duplication of features and duplication/deletion of label texts. And this is the workflow:

  1. Select the features you want to label
  2. Open attribute table
  3. If you don’t have label attributes ready yet: Add two type “real” columns called e.g. “label_x” and “label_y”
  4. Invert the selection (3rd button in attribute table window)
  5. Open field calculator and fill “label_x” and “label_y” fields of the selected features with 0 values (or any coordinates outside your map extent)
  6. Close field calculator and attribute table
  7. Save your edits
  8. Open the labeling dialog and set “data defined settings” – “x coordinate” and “y coordinate”
  9. Enable “Label this layer” and specify the label field
  10. Done

If you change your mind about a feature and want to label it later on: Simply delete the values in “label_x” and “label_y” fields (so they read NULL).

This works quite well for me but I’m aware that it’s still not optimal. Another “data defined setting” like “show this label (true/false)” would be more intuitive.

Have you found better solutions to this problem? Please, post them!


How to Specify Data Types of CSV Columns for Use in QGIS

If you load .csv files through “Add vector layer”, all columns are interpreted as strings. That’s most likely not what you want, but it’s OGR’s default behaviour:

The OGR CSV driver returns all attribute columns with a type of string if no field type information file (with .csvt extension) is available.

Let’s create a .csvt file then!

The .csvt file has to have the same name as the .csv file it describes. (Same concept used in shapefiles.) It enables definition of the following data types: Integer, Real, String, Date (YYYY-MM-DD), Time (HH:MM:SS+nn) and DateTime (YYYY-MM-DD HH:MM:SS+nn).

A .csvt file contains only one line and the types for each column have to be quoted and comma separated, e.g.

"Integer","Real","String"

You can even specify width and precision of each column, e.g.

"Integer(6)","Real(5.5)","String(22)"

Read more at: www.gdal.org/ogr/drv_csv.html


Back to Top

Sustaining Members