Private
Public Access
1
0

Added slider and improved behavior of video analysis

This commit is contained in:
Sander Roosendaal
2019-11-07 17:55:02 +01:00
parent 8fdca8a1f6
commit e35b3fd7b1
5 changed files with 110 additions and 27 deletions

View File

@@ -1899,6 +1899,9 @@ def leaflet_chart_video(lat,lon,name=""):
"Nautical": nautical,
}},{{
"Navionics":navionics,
}},
{{
position:'topleft'
}}).addTo(mymap);
var marker = L.marker([{latbegin}, {longbegin}]).addTo(mymap);

View File

@@ -15,15 +15,54 @@
{% block main %}
<style>
.slidecontainer {
width: 100%; /* Width of the outside container */
}
/* The slider itself */
.slider {
-webkit-appearance: none; /* Override default CSS styles */
appearance: none;
width: 100%; /* Full-width */
height: 25px; /* Specified height */
background: #d3d3d3; /* Grey background */
outline: none; /* Remove outline */
opacity: 0.7; /* Set transparency (for mouse-over effects on hover) */
-webkit-transition: .2s; /* 0.2 seconds transition on hover */
transition: opacity .2s;
}
/* Mouse-over effects */
.slider:hover {
opacity: 1; /* Fully shown on mouse-over */
}
/* The slider handle (use -webkit- (Chrome, Opera, Safari, Edge) and -moz- (Firefox) to override default look) */
.slider::-webkit-slider-thumb {
-webkit-appearance: none; /* Override default look */
appearance: none;
width: 25px; /* Set a specific slider handle width */
height: 25px; /* Slider handle height */
background: #4CAF50; /* Green background */
cursor: pointer; /* Cursor on hover */
}
.slider::-moz-range-thumb {
width: 25px; /* Set a specific slider handle width */
height: 25px; /* Slider handle height */
background: #4CAF50; /* Green background */
cursor: pointer; /* Cursor on hover */
}
</style>
{% language 'en' %}
<h1>Video Analysis for {{ workout.name }}</h1>
<ul class="main-content">
<li class="grid_4">
<div style="height:100%" id="theplot" class="flexplot mapdiv">
{{ mapdiv | safe}}
</div>
<li>
Data Time
<span id="datatime">
</span> seconds
</li>
<li>
Video Time
@@ -40,11 +79,21 @@
<span id="speed">
</span> m/s
</li>
<li class="grid_4">
<li class="grid_2">
<div style="height:100%" id="theplot" class="flexplot mapdiv">
{{ mapdiv | safe}}
</div>
<div class="slidecontainer">
<input type="range" min="0" max="{{ maxtime }}" value="{{ analysis.delay }}" class="slider" id="myRange">
</div>
</li>
<li class="grid_2">
<div id="player"></div>
<script>
// 1. Code for the map
{{ mapscript | safe }}
// 2. This code loads the IFrame Player API code asynchronously.
var tag = document.createElement('script');
@@ -75,16 +124,20 @@
// 4. The API will call this function when the video player is ready.
function onPlayerReady(event) {
event.target.playVideo();
// event.target.playVideo();
function updateTime() {
var oldTime = videotime;
if(player && player.getCurrentTime) {
videotime = player.getCurrentTime();
velo = boatspeed[Math.round(videotime)];
lat = latitude[Math.round(videotime)];
lon = longitude[Math.round(videotime)];
strokerate = spm[Math.round(videotime)];
var delay = document.getElementById("myRange").value;
var datatime = parseFloat(videotime)+parseFloat(delay);
velo = boatspeed[Math.round(datatime)];
lat = latitude[Math.round(datatime)];
lon = longitude[Math.round(datatime)];
strokerate = spm[Math.round(datatime)];
document.getElementById("time").innerHTML = Math.round(videotime);
document.getElementById("datatime").innerHTML = Math.round(datatime);
document.getElementById("speed").innerHTML = velo;
document.getElementById("spm").innerHTML = strokerate;
var newLatLng = new L.LatLng(lat, lon);
@@ -99,9 +152,6 @@
// when the time changes, this will be called.
function onProgress(currentTime) {
if(currentTime > 20) {
console.log("the video reached 20 seconds!");
}
}
function stopVideo() {
@@ -143,6 +193,26 @@
{% endif %}
</li>
</ul>
<script>
// slider
var slider = document.getElementById("myRange");
{% if analysis and user.is_authenticated and user == rower.user %}
document.getElementById("myRange").style.display = "block";
{% else %}
document.getElementById("myRange").style.display = "none";
{% endif %}
var output = document.getElementById("id_delay");
output.value = slider.value; // Display the default slider value
// Update the current slider value (each time you drag the slider handle)
slider.oninput = function() {
output.value = this.value;
}
output.oninput = function() {
slider.value = this.value;
}
</script>
{% endlanguage %}
{% endblock %}

View File

@@ -45,6 +45,11 @@
<i class="fas fa-balance-scale fa-fw"></i>&nbsp;Compare
</a>
</li>
<li id="video-analysis">
<a href="/rowers/workout/{{ workout.id|encode }}/video/">
<i class="fas fa-video-plus fa-fw"></i>&nbsp;Video Analysis
</a>
</li>
{% if user.is_authenticated and workout|may_edit:request %}
<li id="chart-image">
<a href="/rowers/workout/{{ workout.id|encode }}/image/">
@@ -74,11 +79,6 @@
<i class="fas fa-map-marked-alt fa-fw"></i>&nbsp;Map
</a>
</li>
<li id="video-analysis">
<a href="/rowers/workout/{{ workout.id|encode }}/video/">
<i class="fas fa-video-plus fa-fw"></i>&nbsp;Video Analysis
</a>
</li>
<li id="chart-empower">
<a href="/rowers/workout/{{ workout.id|encode }}/forcecurve/">
<i class="fas fa-dumbbell fa-fw"></i>&nbsp;Force Curve

View File

@@ -173,6 +173,7 @@ $('#id_workouttype').change();
{% endfor %}
{% for video in videos %}
<li>
<div>{{ video.name }}</div>
<a href="/rowers/video/{{ video.id|encode }}/">
<img src="https://img.youtube.com/vi/{{ video.video_id }}/hqdefault.jpg"/>
</a>

View File

@@ -69,6 +69,10 @@ def workout_video_view(request,id=''):
form = VideoAnalysisCreateForm(request.POST)
if form.is_valid():
video_id = form.cleaned_data['url']
try:
video_id = get_video_id(form.cleaned_data['url'])
except (TypeError,ValueError):
pass
delay = form.cleaned_data['delay']
if 'save_button' in request.POST:
analysis.name = form.cleaned_data['name']
@@ -101,8 +105,8 @@ def workout_video_view(request,id=''):
df2 = df.resample('1s').mean().interpolate()
mask = df2['time'] < delay
df2 = df2.mask(mask).dropna()
#mask = df2['time'] < delay
#df2 = df2.mask(mask).dropna()
df2['time'] = (df2['time']-df2['time'].min())
boatspeed = (100*df2['velo']).astype(int)/100.
@@ -112,8 +116,8 @@ def workout_video_view(request,id=''):
coordinates.set_index(pd.to_timedelta(coordinates['time'],unit='s'),inplace=True)
coordinates = coordinates.resample('1s').mean().interpolate()
mask = coordinates['time'] < delay
coordinates = coordinates.mask(mask).dropna()
#mask = coordinates['time'] < delay
#coordinates = coordinates.mask(mask).dropna()
coordinates['time'] = coordinates['time']-coordinates['time'].min()
latitude = coordinates['latitude']
longitude = coordinates['longitude']
@@ -158,6 +162,7 @@ def workout_video_view(request,id=''):
'form':form,
'breadcrumbs':breadcrumbs,
'analysis':analysis,
'maxtime':coordinates['time'].max(),
})
@@ -206,8 +211,8 @@ def workout_video_create_view(request,id=0):
df2 = df.resample('1s').mean().interpolate()
mask = df2['time'] < delay
df2 = df2.mask(mask).dropna()
#mask = df2['time'] < delay
#df2 = df2.mask(mask).dropna()
df2['time'] = (df2['time']-df2['time'].min())
boatspeed = (100*df2['velo']).astype(int)/100.
@@ -217,8 +222,8 @@ def workout_video_create_view(request,id=0):
coordinates.set_index(pd.to_timedelta(coordinates['time'],unit='s'),inplace=True)
coordinates = coordinates.resample('1s').mean().interpolate()
mask = coordinates['time'] < delay
coordinates = coordinates.mask(mask).dropna()
#mask = coordinates['time'] < delay
#coordinates = coordinates.mask(mask).dropna()
coordinates['time'] = coordinates['time']-coordinates['time'].min()
latitude = coordinates['latitude']
longitude = coordinates['longitude']
@@ -251,6 +256,8 @@ def workout_video_create_view(request,id=0):
]
analysis = {'delay':delay}
return render(request,
'embedded_video.html',
{
@@ -261,7 +268,9 @@ def workout_video_create_view(request,id=0):
'mapdiv': mapdiv,
'video_id': video_id,
'form':form,
'analysis':analysis,
'breadcrumbs':breadcrumbs,
'maxtime':coordinates['time'].max()
})
# Show the EMpower Oarlock generated Stroke Profile