some UI improvements on planned sessions
This commit is contained in:
@@ -18,6 +18,7 @@ import pandas as pd
|
||||
import numpy as np
|
||||
|
||||
import dataprep
|
||||
from rowers.utils import geo_distance
|
||||
|
||||
ns = {'opengis': 'http://www.opengis.net/kml/2.2'}
|
||||
|
||||
@@ -25,6 +26,8 @@ ns = {'opengis': 'http://www.opengis.net/kml/2.2'}
|
||||
from rowers.models import (
|
||||
Rower, Workout,
|
||||
GeoPoint,GeoPolygon, GeoCourse,
|
||||
course_length,course_coord_center,course_coord_maxmin,
|
||||
polygon_coord_center
|
||||
)
|
||||
|
||||
# low level methods
|
||||
@@ -35,56 +38,6 @@ class InvalidTrajectoryError(Exception):
|
||||
def __str__(self):
|
||||
return repr(self.value)
|
||||
|
||||
def polygon_coord_center(polygon):
|
||||
|
||||
points = GeoPoint.objects.filter(polygon=polygon).order_by("order_in_poly")
|
||||
|
||||
latitudes = pd.Series([p.latitude for p in points])
|
||||
longitudes = pd.Series([p.longitude for p in points])
|
||||
|
||||
return latitudes.mean(), longitudes.mean()
|
||||
|
||||
def course_coord_center(course):
|
||||
|
||||
polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course")
|
||||
|
||||
latitudes = []
|
||||
longitudes = []
|
||||
|
||||
for p in polygons:
|
||||
latitude,longitude = polygon_coord_center(p)
|
||||
latitudes.append(latitude)
|
||||
longitudes.append(longitude)
|
||||
|
||||
latitude = pd.Series(latitudes).median()
|
||||
longitude = pd.Series(longitudes).median()
|
||||
|
||||
coordinates = pd.DataFrame({
|
||||
'latitude':latitudes,
|
||||
'longitude':longitudes,
|
||||
})
|
||||
|
||||
return latitude,longitude,coordinates
|
||||
|
||||
def course_coord_maxmin(course):
|
||||
|
||||
polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course")
|
||||
|
||||
latitudes = []
|
||||
longitudes = []
|
||||
|
||||
for p in polygons:
|
||||
latitude,longitude = polygon_coord_center(p)
|
||||
latitudes.append(latitude)
|
||||
longitudes.append(longitude)
|
||||
|
||||
lat_min = pd.Series(latitudes).min()
|
||||
lat_max = pd.Series(latitudes).max()
|
||||
long_min = pd.Series(longitudes).min()
|
||||
long_max = pd.Series(longitudes).max()
|
||||
|
||||
|
||||
return lat_min,lat_max,long_min,long_max
|
||||
|
||||
def polygon_to_path(polygon):
|
||||
points = GeoPoint.objects.filter(polygon=polygon).order_by("order_in_poly")
|
||||
|
||||
@@ -350,6 +350,79 @@ from utils import (
|
||||
defaultleft,defaultmiddle,landingpages
|
||||
)
|
||||
|
||||
from utils import geo_distance
|
||||
|
||||
def polygon_coord_center(polygon):
|
||||
|
||||
points = GeoPoint.objects.filter(polygon=polygon).order_by("order_in_poly")
|
||||
|
||||
latitudes = pd.Series([p.latitude for p in points])
|
||||
longitudes = pd.Series([p.longitude for p in points])
|
||||
|
||||
return latitudes.mean(), longitudes.mean()
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
def course_coord_center(course):
|
||||
|
||||
polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course")
|
||||
|
||||
latitudes = []
|
||||
longitudes = []
|
||||
|
||||
for p in polygons:
|
||||
latitude,longitude = polygon_coord_center(p)
|
||||
latitudes.append(latitude)
|
||||
longitudes.append(longitude)
|
||||
|
||||
latitude = pd.Series(latitudes).median()
|
||||
longitude = pd.Series(longitudes).median()
|
||||
|
||||
coordinates = pd.DataFrame({
|
||||
'latitude':latitudes,
|
||||
'longitude':longitudes,
|
||||
})
|
||||
|
||||
return latitude,longitude,coordinates
|
||||
|
||||
def course_coord_maxmin(course):
|
||||
|
||||
polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course")
|
||||
|
||||
latitudes = []
|
||||
longitudes = []
|
||||
|
||||
for p in polygons:
|
||||
latitude,longitude = polygon_coord_center(p)
|
||||
latitudes.append(latitude)
|
||||
longitudes.append(longitude)
|
||||
|
||||
lat_min = pd.Series(latitudes).min()
|
||||
lat_max = pd.Series(latitudes).max()
|
||||
long_min = pd.Series(longitudes).min()
|
||||
long_max = pd.Series(longitudes).max()
|
||||
|
||||
|
||||
return lat_min,lat_max,long_min,long_max
|
||||
|
||||
|
||||
def course_length(course):
|
||||
polygons = GeoPolygon.objects.filter(course=course).order_by("order_in_course")
|
||||
|
||||
totaldist = 0
|
||||
for i in range(len(polygons)-1):
|
||||
latitude1,longitude1 = polygon_coord_center(polygons[i])
|
||||
latitude2,longitude2 = polygon_coord_center(polygons[i+1])
|
||||
|
||||
dist = geo_distance(latitude1,longitude1,
|
||||
latitude2,longitude2,)
|
||||
|
||||
totaldist += 1000.*dist[0]
|
||||
|
||||
return int(totaldist)
|
||||
|
||||
# Extension of User with rowing specific data
|
||||
class Rower(models.Model):
|
||||
weightcategories = (
|
||||
@@ -677,7 +750,7 @@ class GeoCourse(models.Model):
|
||||
class GeoCourseEditForm(ModelForm):
|
||||
class Meta:
|
||||
model = GeoCourse
|
||||
fields = ['name','notes']
|
||||
fields = ['name','country','notes']
|
||||
|
||||
widgets = {
|
||||
'notes': forms.Textarea,
|
||||
@@ -941,6 +1014,11 @@ class PlannedSession(models.Model):
|
||||
self.sessionmode = 'distance'
|
||||
self.sessionunit = 'm'
|
||||
self.criterium = 'none'
|
||||
if self.course == None:
|
||||
self.course = GeoCourse.objects.all()[0]
|
||||
self.sessionvalue = course_length(self.course)
|
||||
elif self.sessiontype != 'coursetest':
|
||||
self.course = None
|
||||
|
||||
super(PlannedSession,self).save(*args, **kwargs)
|
||||
|
||||
@@ -977,8 +1055,7 @@ class PlannedSessionForm(ModelForm):
|
||||
|
||||
def __init__(self,*args,**kwargs):
|
||||
super(PlannedSessionForm, self).__init__(*args, **kwargs)
|
||||
if self.instance.sessiontype != 'coursetest':
|
||||
del self.fields['course']
|
||||
self.fields['course'].queryset = GeoCourse.objects.all().order_by("country","name")
|
||||
|
||||
class PlannedSessionFormSmall(ModelForm):
|
||||
|
||||
|
||||
@@ -336,7 +336,7 @@ def get_dates_timeperiod(timeperiod):
|
||||
elif timeperiod=='nextweek':
|
||||
today = date.today()
|
||||
enddate = today-timezone.timedelta(days=today.weekday())-timezone.timedelta(days=1)+timezone.timedelta(days=7)
|
||||
startdate = enddate-timezone.timedelta(days=13)
|
||||
startdate = enddate-timezone.timedelta(days=6)
|
||||
elif timeperiod=='lastmonth':
|
||||
today = date.today()
|
||||
startdate = today.replace(day=1)
|
||||
|
||||
@@ -145,6 +145,10 @@
|
||||
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
|
||||
<script>
|
||||
$(document).ready(function(){
|
||||
|
||||
$("td #id_course").hide();
|
||||
$("th label[for='id_course']").hide();
|
||||
|
||||
$("td #id_sessionmode").change(function() {
|
||||
|
||||
if (this.value == 'TRIMP') {
|
||||
@@ -179,6 +183,20 @@
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For Mandatory Tests, only distance or time are allowed.</p><p>For Mandatory Tests, the only criterium is 'Exactly'</p>");
|
||||
}
|
||||
if (this.value == 'coursetest') {
|
||||
$("th label[for='id_course']").show();
|
||||
$("td #id_course").show();
|
||||
$("td #id_criterium").prop("value","none");
|
||||
$("td #id_sessionmode").prop("value","distance");
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For OTW Tests, only distance is allowed.</p><p>The exact value is not relevant because it is calculated from the course.</p>");
|
||||
}
|
||||
|
||||
if (this.value != 'coursetest') {
|
||||
$("th label[for='id_course']").hide();
|
||||
$("td #id_course").hide();
|
||||
}
|
||||
|
||||
if (this.value == 'challenge') {
|
||||
$("td #id_criterium").prop("value","minimum");
|
||||
$('#id_guidance').html("<p>For Challenges, the default criterium is 'At Least'</p>");
|
||||
|
||||
@@ -144,6 +144,19 @@
|
||||
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
|
||||
<script>
|
||||
$(document).ready(function(){
|
||||
|
||||
var o = $("td #id_sessiontype").find(":selected").val();
|
||||
|
||||
if (o != 'coursetest') {
|
||||
$("td #id_course").hide();
|
||||
$("th label[for='id_course']").hide();
|
||||
} else {
|
||||
$("td #id_course").show();
|
||||
$("th label[for='id_course']").show();
|
||||
|
||||
}
|
||||
|
||||
|
||||
$("td #id_sessionmode").change(function() {
|
||||
|
||||
if (this.value == 'TRIMP') {
|
||||
@@ -178,6 +191,22 @@
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For Mandatory Tests, only distance or time are allowed.</p><p>For Mandatory Tests, the only criterium is 'Exactly'</p>");
|
||||
}
|
||||
|
||||
if (this.value == 'coursetest') {
|
||||
$("th label[for='id_course']").show();
|
||||
$("td #id_course").show();
|
||||
$("td #id_criterium").prop("value","none");
|
||||
$("td #id_sessionmode").prop("value","distance");
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For OTW Tests, only distance is allowed.</p><p>The exact value is not relevant because it is calculated from the course.</p>");
|
||||
}
|
||||
|
||||
if (this.value != 'coursetest') {
|
||||
$("th label[for='id_course']").hide();
|
||||
$("td #id_course").hide();
|
||||
}
|
||||
|
||||
|
||||
if (this.value == 'challenge') {
|
||||
$("td #id_criterium").prop("value","minimum");
|
||||
$('#id_guidance').html("<p>For Challenges, the default criterium is 'At Least'</p>");
|
||||
|
||||
@@ -137,7 +137,10 @@
|
||||
|
||||
|
||||
$(document).ready(function(){
|
||||
$("td #id_sessionmode").change(function() {
|
||||
$("td #id_course").hide();
|
||||
$("th label[for='id_course']").hide();
|
||||
|
||||
$("td #id_sessionmode").change(function() {
|
||||
|
||||
if (this.value == 'TRIMP') {
|
||||
$("td #id_sessionunit").prop("value","None");
|
||||
@@ -171,7 +174,23 @@
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For Mandatory Tests, only distance or time are allowed.</p><p>For Mandatory Tests, the only criterium is 'Exactly'</p>");
|
||||
}
|
||||
if (this.value == 'challenge') {
|
||||
|
||||
if (this.value == 'coursetest') {
|
||||
$("th label[for='id_course']").show();
|
||||
$("td #id_course").show();
|
||||
$("td #id_criterium").prop("value","none");
|
||||
$("td #id_sessionmode").prop("value","distance");
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For OTW Tests, only distance is allowed.</p><p>The exact value is not relevant because it is calculated from the course.</p>");
|
||||
}
|
||||
|
||||
if (this.value != 'coursetest') {
|
||||
$("th label[for='id_course']").hide();
|
||||
$("td #id_course").hide();
|
||||
}
|
||||
|
||||
|
||||
if (this.value == 'challenge') {
|
||||
$("td #id_criterium").prop("value","minimum");
|
||||
$('#id_guidance').html("<p>For Challenges, the default criterium is 'At Least'</p>");
|
||||
}
|
||||
|
||||
@@ -152,6 +152,19 @@
|
||||
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.4/jquery.min.js"></script>
|
||||
<script>
|
||||
$(document).ready(function(){
|
||||
|
||||
var o = $("td #id_sessiontype").find(":selected").val();
|
||||
|
||||
if (o != 'coursetest') {
|
||||
$("td #id_course").hide();
|
||||
$("th label[for='id_course']").hide();
|
||||
} else {
|
||||
$("td #id_course").show();
|
||||
$("th label[for='id_course']").show();
|
||||
|
||||
}
|
||||
|
||||
|
||||
$("td #id_sessionmode").change(function() {
|
||||
|
||||
if (this.value == 'TRIMP') {
|
||||
@@ -186,6 +199,22 @@
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For Mandatory Tests, only distance or time are allowed.</p><p>For Mandatory Tests, the only criterium is 'Exactly'</p>");
|
||||
}
|
||||
|
||||
if (this.value == 'coursetest') {
|
||||
$("th label[for='id_course']").show();
|
||||
$("td #id_course").show();
|
||||
$("td #id_criterium").prop("value","none");
|
||||
$("td #id_sessionmode").prop("value","distance");
|
||||
$("td #id_sessionunit").prop("value","m");
|
||||
$('#id_guidance').html("<p>Set mode to distance. For OTW Tests, only distance is allowed.</p><p>The exact value is not relevant because it is calculated from the course.</p>");
|
||||
}
|
||||
|
||||
if (this.value != 'coursetest') {
|
||||
$("th label[for='id_course']").hide();
|
||||
$("td #id_course").hide();
|
||||
}
|
||||
|
||||
|
||||
if (this.value == 'challenge') {
|
||||
$("td #id_criterium").prop("value","minimum");
|
||||
$('#id_guidance').html("<p>For Challenges, the default criterium is 'At Least'</p>");
|
||||
|
||||
@@ -224,13 +224,13 @@ def geo_distance(lat1,lon1,lat2,lon2):
|
||||
dlon = lon2 - lon1
|
||||
dlat = lat2 - lat1
|
||||
|
||||
a = sin(dlat / 2)**2 + cos(lat1) * cos(lat2) * sin(dlon / 2)**2
|
||||
c = 2 * atan2(sqrt(a), sqrt(1 - a))
|
||||
a = math.sin(dlat / 2)**2 + math.cos(lat1) * math.cos(lat2) * math.sin(dlon / 2)**2
|
||||
c = 2 * math.atan2(math.sqrt(a), math.sqrt(1 - a))
|
||||
|
||||
distance = R * c
|
||||
|
||||
tc1 = atan2(sin(lon2-lon1)*cos(lat2),
|
||||
cos(lat1)*sin(lat2)-sin(lat1)*cos(lat2)*cos(lon2-lon1))
|
||||
tc1 = math.atan2(math.sin(lon2-lon1)*math.cos(lat2),
|
||||
math.cos(lat1)*math.sin(lat2)-math.sin(lat1)*math.cos(lat2)*math.cos(lon2-lon1))
|
||||
|
||||
tc1 = tc1 % (2*pi)
|
||||
|
||||
@@ -238,6 +238,7 @@ def geo_distance(lat1,lon1,lat2,lon2):
|
||||
|
||||
return [distance,bearing]
|
||||
|
||||
|
||||
|
||||
def isbreakthrough(delta,cpvalues,p0,p1,p2,p3,ratio):
|
||||
pwr = abs(p0)/(1+(delta/abs(p2)))
|
||||
|
||||
@@ -8462,6 +8462,7 @@ def course_edit_view(request,id=0):
|
||||
form = GeoCourseEditForm(request.POST)
|
||||
if form.is_valid():
|
||||
name = form.cleaned_data['name']
|
||||
country = form.cleaned_data['country']
|
||||
notes = form.cleaned_data['notes']
|
||||
if isinstance(name,unicode):
|
||||
name = name.encode('utf8')
|
||||
@@ -8469,6 +8470,7 @@ def course_edit_view(request,id=0):
|
||||
name = name.decode('utf8')
|
||||
|
||||
course.name = name
|
||||
course.country = country
|
||||
course.notes = notes
|
||||
course.save()
|
||||
|
||||
@@ -11882,6 +11884,7 @@ def plannedsession_create_view(request,timeperiod='thisweek',rowerid=0):
|
||||
sessionvalue = cd['sessionvalue']
|
||||
sessionunit = cd['sessionunit']
|
||||
comment = cd['comment']
|
||||
course = cd['course']
|
||||
name = cd['name']
|
||||
|
||||
if sessionunit == 'min':
|
||||
@@ -11893,6 +11896,7 @@ def plannedsession_create_view(request,timeperiod='thisweek',rowerid=0):
|
||||
name=name,
|
||||
startdate=startdate,
|
||||
enddate=enddate,
|
||||
course=course,
|
||||
sessiontype=sessiontype,
|
||||
sessionmode=sessionmode,
|
||||
sessionvalue=sessionvalue,
|
||||
@@ -12074,6 +12078,7 @@ def plannedsession_teamcreate_view(request,timeperiod='thisweek',
|
||||
sessionvalue = cd['sessionvalue']
|
||||
sessionunit = cd['sessionunit']
|
||||
comment = cd['comment']
|
||||
course = cd['course']
|
||||
name = cd['name']
|
||||
|
||||
if sessionunit == 'min':
|
||||
@@ -12091,6 +12096,7 @@ def plannedsession_teamcreate_view(request,timeperiod='thisweek',
|
||||
sessionunit=sessionunit,
|
||||
comment=comment,
|
||||
criterium=criterium,
|
||||
course=course,
|
||||
manager=request.user)
|
||||
|
||||
ps.save()
|
||||
|
||||
Reference in New Issue
Block a user