I'm working on a Track & Share Module for Pilots, the app is build with AngularJS within Ionic and Cordova framework. I'm currently developting and testing for android only.
The case:
There are four buttons, first checks if gps is enabled, second starts the tracking, third stops the tracking, fourth send the trackdata to the web-API if internet connection is stable. I can't guarantee 100% connectivity up in the air, so I can't send the trackdata on every tracked waypoint direct to the api - I have to store it until the aircraft is on the ground again.
The problem:
The tracked waypoints are (1) temporally/timely highly variable (I can't get any pattern on my test-tracks) and (2) the tracked altitude/heading/speed data isn't recorded on some trackpoints.
My flown test-route is about 40 minutes. I'm tracking every 60 seconds. So I must get at least minimum 35-40 trackpoints. But: I just get between 9 and 15 trackpoints on that route..
Trackpoints:
1442050712218|51.4514495|6.8892898|null|null|null; 12.9.2015 11:38:32
1442051327924|51.5183441|6.8183962|null|null|null; 12.9.2015 11:48:48
1442051511529|51.8569473|6.8611548|null|null|null; 12.9.2015 11:51:52
1442051732401|51.9828794|6.9063169|null|null|null; 12.9.2015 11:55:32
1442051912503|52.0233909|6.9596959|1300|64|52.25; 12.9.2015 11:58:33
1442052014828|52.0400627|7.0322238|1332|75|51.25; 12.9.2015 12:00:15
1442052517583|52.1472176|7.3813409|1307|70|51.5; 12.9.2015 12:08:38
1442052746410|52.1859082|7.5392811|1217|68|53; 12.9.2015 12:12:26
1442053119338|52.224271|7.874347|null|null|null; 12.9.2015 12:18:39
1442053401324|52.2677044|7.9679879|null|null|null; 12.9.2015 12:23:21
.service('TrackingFunctions', ['$interval', '$rootScope', '$localstorage', function($interval, $rootScope, $localstorage) {
// Erstellt einmalige "global" Referenz, dass immer die selbe Instanz angesprochen wird
var tracker;
this.doTracking = function(execTracking){
if(!execTracking){ // if no tracker start new
$localstorage.TRACKDATA = [];
return $interval(function(){
$localstorage.isTrackerActive = true;
var geo_options = {
enableHighAccuracy: true,
maximumAge: 30000,
timeout: 20000
};
function geo_success(position) {
console.log(position);
var tsmp = position.timestamp;
var lat = position.coords.latitude;
var lng = position.coords.longitude;
var alt = position.coords.altitude;
var hdg = position.coords.heading;
var spd = position.coords.speed;
var ARRAYDATA = tsmp + "|" + lat + "|" + lng + "|" + alt + "|" +hdg + "|" + spd + ";";
$localstorage.TRACKDATA.push(ARRAYDATA);
}
function geo_error() {
//$scope.alt = "Fehler " + error.message + ' Error Code: ' + error.code;
}
var wpid = navigator.geolocation.getCurrentPosition(geo_success, geo_error, geo_options);
},60000); // getrackt wird alle 60 Sekunden
} else { // if tracker cancel
$interval.cancel(execTracking);
console.log("tracker deaktiviert!");
}
};
}])
How can I fix that the app tracks every 60 seconds and the missing data will be recorded, too? The function is crucial fot the app and webservice for flight-training for solo-flights of the student pilot.
Thank you.
Just an idea:
The timeout is not a accurate task, that means, timeout is working when all other tasks are done. It's more like: You should run every 60 seconds.
In your case, I would save the position continuous and would write a «clock/timer», called every second. In your script you calculate the exact starttime, e.g.: 09:27:16. After starttime + x * 60 seconds you trigger in your clock the final saving of the position.
If this is not working, I would test it by using a Web Worker.
Related
I want to make cooldown on a command, cooldown has to work for everyone.
//Start of code or something
var cooldowns = {}
var minute = 60000;
var hour = minute * 24;
//Set cooldown
cooldowns[message.author.id] = Date.now() + hour * 24; //Set a 24 hour cooldown
//At command check
if(cooldowns[message.author.id]){
if(cooldowns[message.author.id] > Date.now()) delete cooldowns[message.author.id];
else console.log("user still has " + Math.round((cooldowns[message.author.id] - Date.now)/minute) + " minutes left"
}
You can use Discord.collection for this
This guide, describes how yo set cooldown per user, but all whats you need its channge message.author.id to message.guild.id
I'd like to start by stating I have very little experience with Angular as this is the first project I've worked on that uses it.
Within the controller I make an AJAX call which returns a json. One of the json objects is minutes in the following format: 1385
I'd like to convert this number into something like this: 8d 15h 0m using an Angular filter
Im wondering how this would be possible?
Answer
Yes. It is 100% possible. Create a filter like below and add your specific date calculation
inside the filter.
How to do the date calculation:
In terms of the actual date calculation, it will be nothing more than regular JavaScript logic. Here you have a few options:
The native Date() object will expose various .getSomething()
functions
MomentJS is also good, as its a library designed for these things specifically
Manual calculation
If you'd like to know how to do this manually. Conceptually the calculation is something like below... the idea is, a rolling calculation where you get the higher time unit, then keep subtracting it from the next calculation, carrying the leftover time along.
Input = Original Minute value
Days = Input / 60 [mins in an hour] / 24 [total hours in day]
Hours = Leftover / 60 [mins in an hour]
Mins = Leftover
A quick search on SO yielded this solution for a custom calculation of sorts. I used the linked calculation on my sample below.
Example
var app = angular.module('app', []);
app.controller('MainCtrl', function($scope) {})
.filter('myDateFilter', ['$filter',
function($filter) {
return function(input) {
// set minutes to seconds
var seconds = input * 60
// calculate (and subtract) whole days
var days = Math.floor(seconds / 86400);
seconds -= days * 86400;
// calculate (and subtract) whole hours
var hours = Math.floor(seconds / 3600) % 24;
seconds -= hours * 3600;
// calculate (and subtract) whole minutes
var minutes = Math.floor(seconds / 60) % 60;
return days + 'd ' + hours + 'h ' + minutes + 'm ';
}
}
]);
<!DOCTYPE html>
<html ng-app="app">
<head>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.25/angular.min.js"></script>
</head>
<body ng-controller="MainCtrl">
1385 minutes = {{ 1385 | myDateFilter }}
</body>
</html>
I suggest a slightly shorter version as an alternative, that uses new Date() object and gets its components individually with predefined methods. It works the same way and uses less computations.
Here is a demo:
var app = angular.module('app', []);
app.controller('MainCtrl', function($scope) {});
app.filter('myDateFilter', ['$filter',
function($filter) {
return function(input) {
var inp = new Date(0, 0, 0, 0, input, 0); // assumes minutes as an input
var m = inp.getMinutes();
var h = inp.getHours();
var d = inp.getDay();
return d + 'd ' + h + 'h ' + m + 'm ';
}
}
]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.25/angular.min.js"></script>
<div ng-app="app" ng-controller="MainCtrl">
1385 minutes = {{ 1385 | myDateFilter }}
</div>
Here is a pipe you can copy/paste for angular 6+. I made it a bit more robust too:
import { Pipe, PipeTransform } from '#angular/core';
/**
* Format a value in minutes as [x(d| days)] y(h| hours) z(m| minutes)
*
* Usage:
* value | hoursMinutes // 0d 3h 20m
* value | hoursMinutes: 'long':false // 3 hours 20 minutes
*/
#Pipe({
name: 'hoursMinutes'
})
export class HoursMinutesPipe implements PipeTransform {
transform(minutes: number, format = 'short', includeDays = true): any {
let formatted = '';
// set minutes to seconds
let seconds = minutes * 60;
// calculate (and subtract) whole days
let days = 0;
if (includeDays) {
days = Math.floor(seconds / 86400);
seconds -= days * 86400;
formatted = `${days}d `;
}
// calculate (and subtract) whole hours
const hours = Math.floor(seconds / 3600) % 24;
seconds -= hours * 3600;
// calculate (and subtract) whole minutes
const min = Math.floor(seconds / 60) % 60;
formatted += `${hours}h ${min}m`;
if ('long' === format) {
formatted = formatted.replace('d', ' days');
formatted = formatted.replace('h', ' hours');
formatted = formatted.replace('m', ' minutes');
}
return formatted;
}
}
I have used $cookieStore in angularjs with expiration time but expiration time is not working.
Look at this code...
var today = new Date();
var expiresValue = new Date(today);
//Set 'expires' option in (365 x 24 x 60 x 60) = 31536000 seconds = 1 year
expiresValue.setSeconds(today.getSeconds() + 31536000);
// Setting a cookie
$cookieStore.put('STYPE', response.data.type, {'expires' : expiresValue});
How can i set expiration time in angularjs.
$cookieStore is depricated. Instead of using $cookieStore use $cookies
https://docs.angularjs.org/api/ngCookies/service/$cookies
$cookies.put('STYPE', response.data.type, {expires : expiresValue});
I am implementing a function to have a countdown in Angular form current time - existing time in future. If the time has elapsed then display a message. Timer ran out in ..... HH:MM:SS
The end time. Lets call it endTime eg:
9/15/2016 9:16:00 PM
Current time. Time current moment we live.
Lets call it currentTime.
The goal is to get a timer that is Current time - end time. Save it to a Variable TotalHours.
Then calculate the time remaining for NOW to total hours. For example TotalHours = 5. And NOW is 9/14/2016 1:16:00 PM then FinalCountDown = 6:16:00 PM. That is the timer I want running...
Here is how I am doing it...
if (info.endTime) {
var CurrentTime = new Date().toLocaleString('en-US');
moment.locale(); // en
var TotalHours = moment.utc(moment(info.diffTime, "DD/MM/YYYY HH:mm:ss").diff(moment(CurrentTime, "DD/MM/YYYY HH:mm:ss"))).format("HH:mm:ss");
info.finalCountDown= TotalHours;
};
The issue here is the following:
Case 1:
endTime = 9/15/2016 9:16:00 AM
currentTime = 9/15/2016 1:21:00 PM
TotalHours = 4:05:00
But... if its after next 2 days...
Case 2:
endTime = 9/17/2016 9:16:00 AM
currentTime = 9/15/2016 1:21:00 PM
TotalHours = 4:05:00
Total hours is still the same...
I need it to add 24hours + 24 hours + extra time = 48 + 4:05:00 = 52:05:00
also I want it to display as: 52h:05m:00s
Please let me know how to solve this...
A quick and dirty solution would be to simply convert the difference between the two date/time objects to milliseconds and then do some math on the milliseconds and format the output as follows:
var currentTime = new Date("9-15-2016 13:21:00");
var endTime = new Date("9-17-2016 09:16:00");
var ms = (endTime - currentTime); // ms of difference
var days = Math.round(ms/ 86400000);
var hrs = Math.round((ms% 86400000) / 3600000);
var mins = Math.round(((ms% 86400000) % 3600000) / 60000);
$scope.finalCountdown = (days + "d:" + hrs + " h:" + mins + "m left");
You could add in a calculation for the seconds if you needed and you can do some formatting of the numbers to have leading zeros.
However, doing this doesn't account for issues such as leap-years and other data and time anomalies. A better suggestion would be to use angular-moment which utilizes Moment.js as it can handle differences and formatting with ease.
I'm using the Jquery TimeCircles plug in (https://github.com/wimbarelds/TimeCircles) as a timer on my application, but I would like to have it so that there is only one circle with the minutes and seconds in the middle, like 15:40. I would like the seconds to keep ticking down, but the circle should animate according to the minutes only. Currently I have two circles showing the minutes and seconds.
I would like to start the timer at 50 minutes, and then countdown to 0 minutes and 0 seconds. Is there any way I can have the time display in the format MM:SS inside the one circle, and have the number of seconds ticking down, and the circle animating to the number of minutes ticking down only?
Thank you so much!
I actually had a fairly similar request the other day on github:
https://github.com/wimbarelds/TimeCircles/issues/68
You could change it to something like:
var $container = $('#DateCountdown .textDiv_Minutes');
$container.find('h4').text('Time left');
var $original = $container.find('span');
var $clone = $original.clone().appendTo($container);
$original.hide();
$('#DateCountdown').TimeCircles().addListener(function(unit, value, total) {
total = Math.abs(total);
var minutes = Math.floor(total / 60) % 60;
var seconds = total % 60;
if(seconds < 10) seconds = "0" + seconds;
$clone.text(minutes + ':' + seconds);
}, "all");
You'd need to use the TimeCircles options that make it only display the Minutes circle.