Monday 19 September 2016

Trains: Station House for Sale in Hurva

Slightly less than a 30 minutes bus ride  from Malmö (unfortunately the rails were removed long ago), a old railway station is for sale. The house has been a B&B in the past and has been for salequite recently:

Image acquired from Wikipedia (CC BY-SA 3.0) 
It will take some passion, work and time (and tracks) to make the house a station again.

The station was built 1865 as a part of YEJ (Ystad to Eslövs Järnväg) that closed 1981.
The blue line indicates the tracks that once were connecting Eslöv with Bjärsjölagård, Tomelilla and finally Ystad.


My refusal to give real estate agents free marketing prevents me from posting the housing ad on the blog. Real estate agents are welcome to post on their own blogs.

Links:

Tuesday 26 July 2016

TrafficControl: MapQuest/OSM needs API Key

For the last time, I've been working experimenting with maps using QML and MapQuest/Open Street Maps. The application logic is still in C++ but the map handling is in QML, where the map is rendered. Unfortunately, API keys are needed for applications using OSM  since July 11th this year.

The consequence of this is that the map tiles applications get from OSM contains no useful map information:
Before, the center of Malmö was shown


The issue is also affecting the default Qt examples, and there is a bug report addressing this issue: https://bugreports.qt.io/browse/QTBUG-5459. Currently, it isn't clear how to add that API key in Qt/QML programs. For the Qt version 5.6, API keys aren't supported, but hopefully the Qt developers may provide a patch for that.

I assume that OSM has introduced this API key requirement to reduce traffic to the servers and to have some control of which software packages that can access the servers. Providing servers and storage for maps are very resource demanding.

For my program, I can still investigate the implementation, where I'm trying to figure out how to add tracks to QML dynamically when the program reads the KML file. I am considering some C++ model that is interacting with a QML view.

Update:
The lesson of this is that software depending on external parties needs to be revised on a regular basis, since there will be changes to external interfaces.

Saturday 9 July 2016

TrafficControl: Calculating Distances between Coordinates on the Surface of a Sphere

Distance calculations will be essential for the TrafficControl program. In a flat world, Pythagoras theorem would do just fine, but the calculations will be done on the surface of a sphere.

Starting from Paris, moving 2000 km north and after that 1000 km to the east, you will end up close to Rovaniemi, Finland. Moving 1000 km east from Paris and then 2000 km north, you will end up south of the national park of Sarek, 400 km off. This happens as the distance around the world along a certain latitude is smaller when moving away from the equator.

The Haversine formula takes all this into account. The implementation I use is:

def haversine(lon1, lat1, lon2, lat2):  #From rosettacode.org

  R = 6372.8 # Earth radius in kilometers
  dLat = radians(lat2 - lat1)
  dLon = radians(lon2 - lon1)
  lat1 = radians(lat1)
  lat2 = radians(lat2)

  a = sin(dLat/2)**2 + cos(lat1)*cos(lat2)*sin(dLon/2)**2
  c = 2*asin(sqrt(a))

  return R * c

Here, the distance between the coordinates (lon1, lat1) and (lon2, lat2) is R*c.

Keep in mind to check whether the coordinates are sent with longitude first and latitude last or the other way around. That will reduce the risk of tricky bugs.

Saturday 14 May 2016

TrafficControl: Mapping Stations to Tracks from a KML File

The longlat coordinates for several existing and closed tracks and stations in Skåne, Sweden are stored in a KML file from Google Earth (blog post here). That file had some 420 tracks and stations.

The script scans the file for all stations and saves that information to a two-dimensional array that contains station name and coordinates.

After that, the script scans the file for all tracks and calculates the total distance of the tracks using the Haversine formula (Pythagoras' theorem won't do as the coordinate system is on the surface of a sphere). The name of the track, the length and the start and end coordinates are saved to a two-dimensional array. For each track, the station that is closest to the start and end points are found. If those candidates are closer than a predefined distance (in my case 100 meters), the track is connected to that station.

Finally, the script printed out the ADD STATION statements, ADD TRACK statements and CONNECT statements for the found connections.

The result file will look like:
ADD STATION Lund_C COORDINATES 55.70606862405453 13.18645933296118
ADD STATION Stångby COORDINATES 55.75072435969958 13.19996121860929
ADD TRACK dLun-StaN 5159 COORDINATES  55.70646523436889 13.18632710260987 55.71072132192893 13.18584908014066 55.71279148452389 13.18540683116051 55.71523576518295 13.18491978947624 55.71697139241737 13.18451423725925 55.71820550069631 13.18422078540084 55.71863549188491 13.18410509912514 55.72015263051769 13.18387805907402 55.72100614423973 13.18374645589791 55.72250595277901 13.18351438987617 55.72459782468813 13.18323899923316 55.72555794818392 13.18311356441235 55.72702138992866 13.18290315672957 55.72790621390291 13.18281900842842 55.72871601698184 13.18290611634804 55.72962139952958 13.18317702257096 55.7303726493431 13.18355658336061 55.73124798036218 13.18419008179007 55.73260471604188 13.18527763612758 55.73399029217104 13.18644576538502 55.7352346199416 13.18742225161641 55.73714017430663 13.18899079381876 55.73972705840463 13.19107073602017 55.74120631439643 13.19228528053877 55.74469495391181 13.19510449129269 55.75071735799666 13.19995102503562
ADD TRACK dLun-StaS 5159 COORDINATES 55.75071735799666 13.19995102503562 55.74469495391181 13.19510449129269 55.74120631439643 13.19228528053877 55.73972705840463 13.19107073602017 55.73714017430663 13.18899079381876 55.7352346199416 13.18742225161641 55.73399029217104 13.18644576538502 55.73260471604188 13.18527763612758 55.73124798036218 13.18419008179007 55.7303726493431 13.18355658336061 55.72962139952958 13.18317702257096 55.72871601698184 13.18290611634804 55.72790621390291 13.18281900842842 55.72702138992866 13.18290315672957 55.72555794818392 13.18311356441235 55.72459782468813 13.18323899923316 55.72250595277901 13.18351438987617 55.72100614423973 13.18374645589791 55.72015263051769 13.18387805907402 55.71863549188491 13.18410509912514 55.71820550069631 13.18422078540084 55.71697139241737 13.18451423725925 55.71523576518295 13.18491978947624 55.71279148452389 13.18540683116051 55.71072132192893 13.18584908014066 55.70646523436889 13.18632710260987 
CONNECT TRACK dLun-StaN FROM Lund_C TO Stångby DEFAULT
CONNECT TRACK dLun-StaN FROM Stångby TO Lund_C
CONNECT TRACK dLun-StaS FROM Stångby TO Lund_C DEFAULT
CONNECT TRACK dLun-StaS FROM Lund_C TO Stångby

The python scripts are available in the scripts section in my Gtihub repo: