diff options
| -rwxr-xr-x | lib/Travelynx.pm | 1 | ||||
| -rwxr-xr-x | lib/Travelynx/Controller/Traveling.pm | 14 | ||||
| -rw-r--r-- | public/static/js/travelynx-actions.js | 17 | ||||
| -rw-r--r-- | public/static/js/travelynx-actions.min.js | 2 | ||||
| l--------- | public/static/v7 (renamed from public/static/v5) | 0 | ||||
| -rw-r--r-- | templates/_cancelled.html.ep | 27 | ||||
| -rw-r--r-- | templates/_checked_in.html.ep | 85 | ||||
| -rw-r--r-- | templates/_checked_out.html.ep | 12 | ||||
| -rw-r--r-- | templates/departures.html.ep | 13 | ||||
| -rw-r--r-- | templates/landingpage.html.ep | 88 | ||||
| -rw-r--r-- | templates/layouts/default.html.ep | 2 | 
11 files changed, 160 insertions, 101 deletions
| diff --git a/lib/Travelynx.pm b/lib/Travelynx.pm index c11f175..63faafd 100755 --- a/lib/Travelynx.pm +++ b/lib/Travelynx.pm @@ -1505,6 +1505,7 @@ sub startup {  	);  	$authed_r->get('/account')->to('account#account'); +	$authed_r->get('/ajax/status_card.html')->to('traveling#status_card');  	$authed_r->get('/cancelled')->to('traveling#cancelled');  	$authed_r->get('/change_password')->to('account#password_form');  	$authed_r->get('/export.json')->to('account#json_export'); diff --git a/lib/Travelynx/Controller/Traveling.pm b/lib/Travelynx/Controller/Traveling.pm index d8e5e03..73a079c 100755 --- a/lib/Travelynx/Controller/Traveling.pm +++ b/lib/Travelynx/Controller/Traveling.pm @@ -19,6 +19,20 @@ sub homepage {  	}  } +sub status_card { +	my ($self) = @_; +	my $status = $self->get_user_status; + +	delete $self->stash->{layout}; + +	if ( $status->{checked_in} ) { +		$self->render( '_checked_in', status => $status ); +	} +	else { +		$self->render( '_checked_out', status => $status ); +	} +} +  sub geolocation {  	my ($self) = @_; diff --git a/public/static/js/travelynx-actions.js b/public/static/js/travelynx-actions.js index 583c806..b1e4d43 100644 --- a/public/static/js/travelynx-actions.js +++ b/public/static/js/travelynx-actions.js @@ -17,7 +17,16 @@ function tvly_run(link, req, err_callback) {  		}  	});  } -$(document).ready(function() { +function tvly_update() { +	$.get('/ajax/status_card.html', function(data) { +		$('.statuscol').html(data); +		tvly_reg_handlers(); +		setTimeout(tvly_update, 15000); +	}).fail(function() { +		setTimeout(tvly_update, 15000); +	}); +} +function tvly_reg_handlers() {  	$('.action-checkin').click(function() {  		var link = $(this);  		var req = { @@ -78,4 +87,10 @@ $(document).ready(function() {  			tvly_run(link, req);  		}  	}); +} +$(document).ready(function() { +	tvly_reg_handlers(); +	if ($('.statuscol .autorefresh').length) { +		setTimeout(tvly_update, 15000); +	}  }); diff --git a/public/static/js/travelynx-actions.min.js b/public/static/js/travelynx-actions.min.js index db9fa1b..4dafe2f 100644 --- a/public/static/js/travelynx-actions.min.js +++ b/public/static/js/travelynx-actions.min.js @@ -1 +1 @@ -function tvly_run(t,n,a){var c='<i class="material-icons">error</i>',i=$('<div class="progress"><div class="indeterminate"></div></div>');t.hide(),t.after(i),$.post("/action",n,function(n){n.success?$(location).attr("href",n.redirect_to):(M.toast({html:c+" "+n.error}),i.remove(),a&&a(),t.append(" "+c),t.show())})}$(document).ready(function(){$(".action-checkin").click(function(){var t=$(this);tvly_run(t,{action:"checkin",station:t.data("station"),train:t.data("train")})}),$(".action-checkout").click(function(){var t=$(this),n={action:"checkout",station:t.data("station"),force:t.data("force")};tvly_run(t,n,function(){t.append(" – Ohne Echtzeitdaten auschecken?"),t.data("force",!0)})}),$(".action-undo").click(function(){var t=$(this);tvly_run(t,{action:"undo",undo_id:t.data("id")})}),$(".action-cancelled-from").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_from",station:t.data("station"),train:t.data("train")})}),$(".action-cancelled-to").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_to",station:t.data("station"),force:!0})}),$(".action-delete").click(function(){var t=$(this),n={action:"delete",id:t.data("id"),checkin:t.data("checkin"),checkout:t.data("checkout")};really_delete=confirm("Diese Zugfahrt wirklich löschen? Der Eintrag wird sofort aus der Datenbank entfernt und kann nicht wiederhergestellt werden."),really_delete&&tvly_run(t,n)})}); +function tvly_run(t,a,n){var e='<i class="material-icons">error</i>',c=$('<div class="progress"><div class="indeterminate"></div></div>');t.hide(),t.after(c),$.post("/action",a,function(a){a.success?$(location).attr("href",a.redirect_to):(M.toast({html:e+" "+a.error}),c.remove(),n&&n(),t.append(" "+e),t.show())})}function tvly_update(){$.get("/ajax/status_card.html",function(t){$(".statuscol").html(t),tvly_reg_handlers(),setTimeout(tvly_update,15e3)}).fail(function(){setTimeout(tvly_update,15e3)})}function tvly_reg_handlers(){$(".action-checkin").click(function(){var t=$(this);tvly_run(t,{action:"checkin",station:t.data("station"),train:t.data("train")})}),$(".action-checkout").click(function(){var t=$(this),a={action:"checkout",station:t.data("station"),force:t.data("force")};tvly_run(t,a,function(){t.append(" – Ohne Echtzeitdaten auschecken?"),t.data("force",!0)})}),$(".action-undo").click(function(){var t=$(this);tvly_run(t,{action:"undo",undo_id:t.data("id")})}),$(".action-cancelled-from").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_from",station:t.data("station"),train:t.data("train")})}),$(".action-cancelled-to").click(function(){var t=$(this);tvly_run(t,{action:"cancelled_to",station:t.data("station"),force:!0})}),$(".action-delete").click(function(){var t=$(this),a={action:"delete",id:t.data("id"),checkin:t.data("checkin"),checkout:t.data("checkout")};really_delete=confirm("Diese Zugfahrt wirklich löschen? Der Eintrag wird sofort aus der Datenbank entfernt und kann nicht wiederhergestellt werden."),really_delete&&tvly_run(t,a)})}$(document).ready(function(){tvly_reg_handlers(),$(".statuscol .autorefresh").length&&setTimeout(tvly_update,15e3)}); diff --git a/public/static/v5 b/public/static/v7 index 945c9b4..945c9b4 120000 --- a/public/static/v5 +++ b/public/static/v7 diff --git a/templates/_cancelled.html.ep b/templates/_cancelled.html.ep new file mode 100644 index 0000000..d35c849 --- /dev/null +++ b/templates/_cancelled.html.ep @@ -0,0 +1,27 @@ +<div class="card yellow lighten-4"> +	<div class="card-content"> +		<span class="card-title">Zugausfall dokumentieren</span> +		<p>Prinzipiell wärest du nun eingecheckt in +			<%= $status->{train_type} %> <%= $status->{train_no} %> +			ab <%= $status->{station_name} %>, doch dieser Zug fällt aus. +			</p> +		<p>Falls du den Zugausfall z.B. für ein Fahrgastrechteformular +			dokumentieren möchtest, wähle bitte jetzt deine geplante +			Zielstation aus. Achtung: Momentan wird dabei keine +			Soll-Ankunftszeit gespeichert, das zu beheben steht auf +			der Todoliste.</p> +		<table> +			<tbody> +				% my $is_after = 0; +				% for my $station (@{$status->{route_after}}) { +					<tr><td><a class="action-cancelled-to" data-station="<%= $station %>"><%= $station %></a></td></tr> +				% } +			</tbody> +		</table> +	</div> +	<div class="card-action"> +		<a class="action-undo" data-id="in_transit"> +			<i class="material-icons">undo</i> Checkinversuch Rückgängig? +		</a> +	</div> +</div> diff --git a/templates/_checked_in.html.ep b/templates/_checked_in.html.ep new file mode 100644 index 0000000..e4afeda --- /dev/null +++ b/templates/_checked_in.html.ep @@ -0,0 +1,85 @@ +<div class="card green darken-4 autorefresh"> +	<div class="card-content white-text"> +		<span class="card-title">Eingecheckt</span> +		<p> +			In <b><%= $status->{train_type} %> <%= $status->{train_no} %></b> +			% if ($status->{arr_name}) { +				von <b><%= $status->{dep_name} %></b> nach <b><%= $status->{arr_name} %></b>. +			% } +			% else { +				ab <b><%= $status->{dep_name} %></b>. +			% } +		</p> +		<p> +			<b><%= $status->{real_departure}->strftime('%H:%M') %></b> +			% if ($status->{real_departure}->epoch != $status->{sched_departure}->epoch) { +				(<%= sprintf('%+d', ($status->{real_departure}->epoch - $status->{sched_departure}->epoch)/60) %>) +			% } +			→ +			% if ($status->{real_arrival}->epoch) { +				<b><%= $status->{real_arrival}->strftime('%H:%M') %></b> +				% if ($status->{real_arrival}->epoch != $status->{sched_arrival}->epoch) { +					(<%= sprintf('%+d', ($status->{real_arrival}->epoch - $status->{sched_arrival}->epoch)/60) %>) +				% } +			% } +			% else { +				unbekannt +			% } +		</p> +		<p> +			<div class="center"> +				% if ($status->{departure_countdown} > 120) { +					Abfahrt in <%= int($status->{departure_countdown} / 60) %> Minuten +				% } +				% elsif ($status->{arrival_countdown}) { +					% if ($status->{arrival_countdown} > 0) { +						Ankunft in <%= int($status->{arrival_countdown} / 60) %> +						Minute<%= int($status->{arrival_countdown} / 60) == 1 ? '' : 'n' %> +					% } +					% else { +						Ziel erreicht +					% } +				% } +				% elsif ($status->{arr_name}) { +					Ankunft in mehr als zwei Stunden +				% } +			</div> +			<div class="progress green darken-3" style="height: 1ex;"> +				<div class="determinate white" style="width: <%= sprintf('%.2f', 100 * $status->{journey_completion}); %>%;"></div> +			</div> +		</p> +		% if ($status->{arr_name}) { +			<p>Zielstation ändern?</p> +		% } +		% else { +			<p>Zielstation wählen:</p> +		% } +		<table> +			<tbody> +				% my $is_after = 0; +				% for my $station (@{$status->{route_after}}) { +					% if ($status->{arr_name} and $station eq $status->{arr_name}) { +						<tr><td><b><a class="action-checkout" data-station="<%= $station %>"><%= $station %></a></b></td></tr> +					% } +					% else { +						<tr><td><a class="action-checkout" data-station="<%= $station %>"><%= $station %></a></td></tr> +					% } +				% } +			</tbody> +		</table> +		% if ($status->{arr_name}) { +			<p> +				Falls das Backend ausgefallen ist oder der Zug aus anderen +				Gründen verloren ging: <a class="action-checkout" +				data-force="1" data-station="<%= $status->{arr_name} +				%>">Ohne Echtzeitdaten in <%= $status->{arr_name} %> +				auschecken</a>. +			</p> +		% } +	</div> +	<div class="card-action"> +		<a class="action-undo" data-id="in_transit"> +			<i class="material-icons">undo</i> Checkin Rückgängig? +		</a> +	</div> +</div> diff --git a/templates/_checked_out.html.ep b/templates/_checked_out.html.ep new file mode 100644 index 0000000..cec61bc --- /dev/null +++ b/templates/_checked_out.html.ep @@ -0,0 +1,12 @@ +<div class="card grey darken-4"> +	<div class="card-content white-text"> +		<span class="card-title">Ausgecheckt</span> +		<p>Aus <%= $status->{train_type} %> <%= $status->{train_no} %> +			bis <%= $status->{arr_name} %></p> +	</div> +	<div class="card-action"> +		<a class="action-undo" data-id="<%= $status->{journey_id} %>"> +			<i class="material-icons">undo</i> Rückgängig? +		</a> +	</div> +</div> diff --git a/templates/departures.html.ep b/templates/departures.html.ep index 7d33417..32a4336 100644 --- a/templates/departures.html.ep +++ b/templates/departures.html.ep @@ -16,18 +16,7 @@  			</div>  		% }  		% elsif ($status->{timestamp_delta} < 180) { -			<div class="card grey darken-4"> -				<div class="card-content white-text"> -					<span class="card-title">Ausgecheckt</span> -					<p>Aus <%= $status->{train_type} %> <%= $status->{train_no} %> -						bis <%= $status->{arr_name} %></p> -				</div> -				<div class="card-action"> -					<a class="action-undo" data-id="<%= $status->{journey_id} %>"> -						<i class="material-icons">undo</i> Rückgängig? -					</a> -				</div> -			</div> +			%= include '_checked_out', status => $status;  		% }  	</div>  </div> diff --git a/templates/landingpage.html.ep b/templates/landingpage.html.ep index 84514c5..83b8303 100644 --- a/templates/landingpage.html.ep +++ b/templates/landingpage.html.ep @@ -12,94 +12,10 @@  		</div>  	% }  	<div class="row"> -		<div class="col s12"> +		<div class="col s12 statuscol">  			% my $status = get_user_status();  			% if ($status->{checked_in}) { -				<div class="card green darken-4"> -					<div class="card-content white-text"> -						<span class="card-title">Eingecheckt</span> -						<p> -							In <b><%= $status->{train_type} %> <%= $status->{train_no} %></b> -							% if ($status->{arr_name}) { -								von <b><%= $status->{dep_name} %></b> nach <b><%= $status->{arr_name} %></b>. -							% } -							% else { -								ab <b><%= $status->{dep_name} %></b>. -							% } -						</p> -						<p> -							<b><%= $status->{real_departure}->strftime('%H:%M') %></b> -							% if ($status->{real_departure}->epoch != $status->{sched_departure}->epoch) { -								(<%= sprintf('%+d', ($status->{real_departure}->epoch - $status->{sched_departure}->epoch)/60) %>) -							% } -							→ -							% if ($status->{real_arrival}->epoch) { -								<b><%= $status->{real_arrival}->strftime('%H:%M') %></b> -								% if ($status->{real_arrival}->epoch != $status->{sched_arrival}->epoch) { -									(<%= sprintf('%+d', ($status->{real_arrival}->epoch - $status->{sched_arrival}->epoch)/60) %>) -								% } -							% } -							% else { -								unbekannt -							% } -						</p> -						<p> -							<div class="center"> -								% if ($status->{departure_countdown} > 120) { -									Abfahrt in <%= int($status->{departure_countdown} / 60) %> Minuten -								% } -								% elsif ($status->{arrival_countdown}) { -									% if ($status->{arrival_countdown} > 0) { -										Ankunft in <%= int($status->{arrival_countdown} / 60) %> -										Minute<%= int($status->{arrival_countdown} / 60) == 1 ? '' : 'n' %> -									% } -									% else { -										Ziel erreicht -									% } -								% } -								% elsif ($status->{arr_name}) { -									Ankunft in mehr als zwei Stunden -								% } -							</div> -							<div class="progress green darken-3" style="height: 1ex;"> -								<div class="determinate white" style="width: <%= sprintf('%.2f', 100 * $status->{journey_completion}); %>%;"></div> -							</div> -						</p> -						% if ($status->{arr_name}) { -							<p>Zielstation ändern?</p> -						% } -						% else { -							<p>Zielstation wählen:</p> -						% } -						<table> -							<tbody> -								% my $is_after = 0; -								% for my $station (@{$status->{route_after}}) { -									% if ($status->{arr_name} and $station eq $status->{arr_name}) { -										<tr><td><b><a class="action-checkout" data-station="<%= $station %>"><%= $station %></a></b></td></tr> -									% } -									% else { -										<tr><td><a class="action-checkout" data-station="<%= $station %>"><%= $station %></a></td></tr> -									% } -								% } -							</tbody> -						</table> -						% if ($status->{arr_name}) { -							<p> -								Falls das Backend ausgefallen ist oder der Zug aus anderen -								Gründen verloren ging: <a class="action-checkout" -								data-force="1" data-station="<%= $status->{arr_name} -								%>">Ohne Echtzeitdaten in <%= $status->{arr_name} %> -								auschecken</a>. -							</p> -						% } -					</div> -					<div class="card-action"> -						<a class="action-undo" data-id="in_transit"> -							<i class="material-icons">undo</i> Checkin Rückgängig? -						</a> -					</div> -				</div> +				%= include '_checked_in', status => $status;  			% }  			% elsif ($status->{cancelled}) {  				<div class="card yellow lighten-4"> diff --git a/templates/layouts/default.html.ep b/templates/layouts/default.html.ep index cdd624a..a2a5648 100644 --- a/templates/layouts/default.html.ep +++ b/templates/layouts/default.html.ep @@ -5,7 +5,7 @@  	<meta charset="utf-8">  	<meta name="viewport" content="width=device-width, initial-scale=1.0">  	<meta name="theme-color" content="#673ab7"> -	% my $av = 'v6'; # asset version +	% my $av = 'v7'; # asset version  	%= stylesheet "/static/${av}/css/materialize.min.css"  	%= stylesheet "/static/${av}/css/material-icons.css"  	%= stylesheet "/static/${av}/css/local.css" | 
