From 385254342d5fe636a572596b1d2cd92b17cf89ba Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Fri, 11 May 2018 16:41:56 +0200 Subject: [PATCH 1/6] first attempt --- rowers/.#plannedsessions.py | 1 - rowers/courses.py | 55 ++++++++++++++++++++++++++++++++++++- 2 files changed, 54 insertions(+), 2 deletions(-) delete mode 100644 rowers/.#plannedsessions.py diff --git a/rowers/.#plannedsessions.py b/rowers/.#plannedsessions.py deleted file mode 100644 index 25407209..00000000 --- a/rowers/.#plannedsessions.py +++ /dev/null @@ -1 +0,0 @@ -e408191@CZ27LT9RCGN72.63076:1525965015 \ No newline at end of file diff --git a/rowers/courses.py b/rowers/courses.py index 171e906e..06de3b98 100644 --- a/rowers/courses.py +++ b/rowers/courses.py @@ -31,6 +31,8 @@ from rowers.models import ( polygon_coord_center,PlannedSession ) +from utils import geo_distance + # low level methods class InvalidTrajectoryError(Exception): def __init__(self,value): @@ -39,6 +41,57 @@ class InvalidTrajectoryError(Exception): def __str__(self): return repr(self.value) +def get_dir_vector(polygon1,polygon2): + lat1,lon1 = polygon_coord_center(polygon1) + lat2,lon2 = polygon_coord_center(polygon2) + + return [[lat1,lon1],[lat2,lon2]] + +def get_delta(vector,polygon): + x = pd.Series(range(10000))/9999. + lat1 = vector[0][0] + lon1 = vector[0][1] + lat2 = vector[1][0] + lon2 = vector[1][0] + + lat = x.apply(lambda x:lat1+x*(lat2-lat1)) + lon = x.apply(lambda x:lon1+x*(lon2-lon1)) + + totdist,bearing = geo_distance(lat1,lon1,lat2,lon2) + + dist = x*totdist + + p = polygon_to_path(polygon) + + f = lambda x: coordinate_in_path(x['lat'],x['lon'],p) + + df = pd.DataFrame({'x':x, + 'lat':lat, + 'lon':lon, + 'dist':dist, + }) + + df['inpolygon'] = df.apply(f,axis=1) + + b = (~df['inpolygon']).shift(1)+df['inpolygon'] + + if len(df[b==2]): + return df[b==2]['dist'].min() + + else: + return 0 + + + + + +def get_delta_start(course): + polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") + vector = get_dir_vector(polygons[0],polygons[1]) + delta = get_delta(vector,polygons[0]) + + return delta + def get_course_timezone(course): polygons = GeoPolygon.objects.filter(course = course) points = GeoPoint.objects.filter(polygon = polygons[0]) @@ -293,7 +346,7 @@ def get_time_course(ws,course): rowdata = rowdata.resample('100ms',on='dt').mean() rowdata = rowdata.interpolate() - polygons = GeoPolygon.objects.filter(course=course) + polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") paths = [] for polygon in polygons: path = polygon_to_path(polygon) From c1b05a579b08161c5fabafb9b7885e76ec682901 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 14 May 2018 15:16:27 +0200 Subject: [PATCH 2/6] better page title virtualevent --- rowers/templates/virtualevent.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/rowers/templates/virtualevent.html b/rowers/templates/virtualevent.html index 8fe2c290..36d75779 100644 --- a/rowers/templates/virtualevent.html +++ b/rowers/templates/virtualevent.html @@ -2,7 +2,7 @@ {% load staticfiles %} {% load rowerfilters %} -{% block title %}New Virtual Race{% endblock %} +{% block title %}Rowsandall Virtual Race{% endblock %} {% block content %} From 22f412c85a0a8612b101ba1d929fb058dc2dae2a Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 14 May 2018 18:15:05 +0200 Subject: [PATCH 3/6] save --- rowers/courses.py | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/rowers/courses.py b/rowers/courses.py index 06de3b98..3f2b84e2 100644 --- a/rowers/courses.py +++ b/rowers/courses.py @@ -81,10 +81,7 @@ def get_delta(vector,polygon): else: return 0 - - - - + def get_delta_start(course): polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") vector = get_dir_vector(polygons[0],polygons[1]) From 34ccc51c37808a469902960925afd439f6f7cea4 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 14 May 2018 21:14:09 +0200 Subject: [PATCH 4/6] some improvements --- rowers/courses.py | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/rowers/courses.py b/rowers/courses.py index 3f2b84e2..a1532e98 100644 --- a/rowers/courses.py +++ b/rowers/courses.py @@ -45,19 +45,20 @@ def get_dir_vector(polygon1,polygon2): lat1,lon1 = polygon_coord_center(polygon1) lat2,lon2 = polygon_coord_center(polygon2) - return [[lat1,lon1],[lat2,lon2]] + return [lat2-lat1,lon2-lon1] def get_delta(vector,polygon): x = pd.Series(range(10000))/9999. - lat1 = vector[0][0] - lon1 = vector[0][1] - lat2 = vector[1][0] - lon2 = vector[1][0] + vlat = vector[0] + vlon = vector[1] - lat = x.apply(lambda x:lat1+x*(lat2-lat1)) - lon = x.apply(lambda x:lon1+x*(lon2-lon1)) + lat1,lon1 = polygon_coord_center(polygon) + + lat = x.apply(lambda x:lat1+x*vlat) + lon = x.apply(lambda x:lon1+x*vlon) - totdist,bearing = geo_distance(lat1,lon1,lat2,lon2) + totdist,bearing = geo_distance(lat1,lon1,lat1+vlat,lon1+vlat) + print totdist dist = x*totdist @@ -73,10 +74,12 @@ def get_delta(vector,polygon): df['inpolygon'] = df.apply(f,axis=1) - b = (~df['inpolygon']).shift(1)+df['inpolygon'] + + b = (~df['inpolygon']).shift(-1)+df['inpolygon'] + if len(df[b==2]): - return df[b==2]['dist'].min() + return 1.0e3*df[b==2]['dist'].min() else: return 0 From 2a73239bca215be533b2fe47fa966cb22119d941 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 14 May 2018 21:39:15 +0200 Subject: [PATCH 5/6] more precise course length --- rowers/courses.py | 66 ++------------------------------------ rowers/models.py | 80 +++++++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 80 insertions(+), 66 deletions(-) diff --git a/rowers/courses.py b/rowers/courses.py index a1532e98..16c3f7cd 100644 --- a/rowers/courses.py +++ b/rowers/courses.py @@ -28,7 +28,8 @@ from rowers.models import ( Rower, Workout, GeoPoint,GeoPolygon, GeoCourse, course_length,course_coord_center,course_coord_maxmin, - polygon_coord_center,PlannedSession + polygon_coord_center,PlannedSession, + polygon_to_path,coordinate_in_path ) from utils import geo_distance @@ -41,56 +42,6 @@ class InvalidTrajectoryError(Exception): def __str__(self): return repr(self.value) -def get_dir_vector(polygon1,polygon2): - lat1,lon1 = polygon_coord_center(polygon1) - lat2,lon2 = polygon_coord_center(polygon2) - - return [lat2-lat1,lon2-lon1] - -def get_delta(vector,polygon): - x = pd.Series(range(10000))/9999. - vlat = vector[0] - vlon = vector[1] - - lat1,lon1 = polygon_coord_center(polygon) - - lat = x.apply(lambda x:lat1+x*vlat) - lon = x.apply(lambda x:lon1+x*vlon) - - totdist,bearing = geo_distance(lat1,lon1,lat1+vlat,lon1+vlat) - print totdist - - dist = x*totdist - - p = polygon_to_path(polygon) - - f = lambda x: coordinate_in_path(x['lat'],x['lon'],p) - - df = pd.DataFrame({'x':x, - 'lat':lat, - 'lon':lon, - 'dist':dist, - }) - - df['inpolygon'] = df.apply(f,axis=1) - - - b = (~df['inpolygon']).shift(-1)+df['inpolygon'] - - - if len(df[b==2]): - return 1.0e3*df[b==2]['dist'].min() - - else: - return 0 - - -def get_delta_start(course): - polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") - vector = get_dir_vector(polygons[0],polygons[1]) - delta = get_delta(vector,polygons[0]) - - return delta def get_course_timezone(course): polygons = GeoPolygon.objects.filter(course = course) @@ -111,19 +62,6 @@ def get_course_timezone(course): return timezone_str -def polygon_to_path(polygon): - points = GeoPoint.objects.filter(polygon=polygon).order_by("order_in_poly") - s = [] - for point in points: - s.append([point.latitude,point.longitude]) - - p = path.Path(s[:-1]) - - return p - -def coordinate_in_path(latitude,longitude, p): - - return p.contains_points([(latitude,longitude)])[0] diff --git a/rowers/models.py b/rowers/models.py index bbcde970..2a8b8fcc 100644 --- a/rowers/models.py +++ b/rowers/models.py @@ -32,7 +32,7 @@ from collections import OrderedDict from timezonefinder import TimezoneFinder import types - +from matplotlib import path from rowsandall_app.settings import ( TWEET_ACCESS_TOKEN_KEY, @@ -363,6 +363,19 @@ def polygon_coord_center(polygon): +def polygon_to_path(polygon): + points = GeoPoint.objects.filter(polygon=polygon).order_by("order_in_poly") + s = [] + for point in points: + s.append([point.latitude,point.longitude]) + + p = path.Path(s[:-1]) + + return p + +def coordinate_in_path(latitude,longitude, p): + + return p.contains_points([(latitude,longitude)])[0] def course_coord_center(course): @@ -407,6 +420,62 @@ def course_coord_maxmin(course): return lat_min,lat_max,long_min,long_max +def get_dir_vector(polygon1,polygon2): + lat1,lon1 = polygon_coord_center(polygon1) + lat2,lon2 = polygon_coord_center(polygon2) + + return [lat2-lat1,lon2-lon1] + +def get_delta(vector,polygon): + x = pd.Series(range(10000))/9999. + vlat = vector[0] + vlon = vector[1] + + lat1,lon1 = polygon_coord_center(polygon) + + lat = x.apply(lambda x:lat1+x*vlat) + lon = x.apply(lambda x:lon1+x*vlon) + + totdist,bearing = geo_distance(lat1,lon1,lat1+vlat,lon1+vlon) + + dist = x*totdist + + p = polygon_to_path(polygon) + + f = lambda x: coordinate_in_path(x['lat'],x['lon'],p) + + df = pd.DataFrame({'x':x, + 'lat':lat, + 'lon':lon, + 'dist':dist, + }) + + df['inpolygon'] = df.apply(f,axis=1) + + + b = (~df['inpolygon']).shift(-1)+df['inpolygon'] + + + if len(df[b==2]): + return 1.0e3*df[b==2]['dist'].min() + + else: + return 0 + + +def get_delta_start(course): + polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") + vector = get_dir_vector(polygons[0],polygons[1]) + delta = get_delta(vector,polygons[0]) + + return delta + +def get_delta_finish(course): + polygons = GeoPolygon.objects.filter(course=course).order_by("-order_in_course") + vector = get_dir_vector(polygons[0],polygons[1]) + delta = get_delta(vector,polygons[0]) + + return delta def course_length(course): polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course") @@ -421,7 +490,14 @@ def course_length(course): totaldist += 1000.*dist[0] - return int(totaldist) + vector = get_dir_vector(polygons[0],polygons[1]) + deltastart = get_delta(vector,polygons[0]) + + polygons = polygons.reverse() + vector = get_dir_vector(polygons[0],polygons[1]) + deltafinish = get_delta(vector,polygons[0]) + + return int(totaldist-deltastart-deltafinish) sexcategories = ( ('male','male'), From 16754ca19057932cd69281d86f2239afcbd5cea7 Mon Sep 17 00:00:00 2001 From: Sander Roosendaal Date: Mon, 14 May 2018 21:46:42 +0200 Subject: [PATCH 6/6] added unicode method to GeoPolygon model --- rowers/models.py | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/rowers/models.py b/rowers/models.py index 2a8b8fcc..eb6bad4d 100644 --- a/rowers/models.py +++ b/rowers/models.py @@ -842,9 +842,10 @@ class GeoCourse(models.Model): name = self.name country = self.country - return u'{country} - {name}'.format( + return u'{country} - {name} - {d}m'.format( name=name, - country=country + country=country, + d = course_length(self) ) class GeoCourseEditForm(ModelForm): @@ -861,6 +862,16 @@ class GeoPolygon(models.Model): course = models.ForeignKey(GeoCourse, blank=True) order_in_course = models.IntegerField(default=0) + def __unicode__(self): + name = self.name + coursename = self.course.name + + return u'{coursename} - {name}'.format( + name=name, + course=coursename + ) + + # Need error checking to insert new polygons into existing course (all later polygons # increase there order_in_course number