I am using a custom angular.js filter for datetime objects:
我正在为datetime对象使用自定义angular.js过滤器:
function relativeTimeFilter()
{
return function (dateObj) {
return getRelativeDateTimeString(dateObj);
};
}
function getRelativeDateTimeString(dt)
{
if(!dt) return "undefined ago";
var delta = dt.getSeconds();
if (delta < 0) return "not yet";
if (delta < 1 * 60) return delta == 1 ? "one second ago" : delta + " seconds ago";
if (delta < 2 * 60) return "a minute ago";
if (delta < 45 * 60) return Math.floor(delta/60) + " minutes ago";
if (delta < 90 * 60) return "an hour ago";
if (delta < 24 * (60*60)) return Math.floor(delta/60/60) + " hours ago";
if (delta < 48 * (60*60)) return "yesterday";
if (delta < 30 * (24 * (60*60))) return Math.floor(delta/60/60/24) + " days ago";
if (delta < 12 * (30 * (24 * (60*60))))
{
var months = Math.floor(delta/60/60/24/30);
return (months <= 1) ? "one month ago" : (months + " months ago");
}
else
{
var years = Math.floor(delta/60/60/24/365);
return (years <= 1) ? "one year ago" : (years + " years ago");
}
}
module.filter("relativetime", relativeTimeFilter);
At this point, it is not so important which filter I use (I think). The filter receives a Datetime object. The relative time declaration is only valid one second. Meaning one second ago
must be updated after a second to 2 seconds ago
and so on.
在这一点上,我使用的过滤器(我认为)并不重要。过滤器接收Datetime对象。相对时间声明仅有效一秒钟。一秒前的含义必须在一秒钟到2秒之后更新,依此类推。
When I apply the filter, this only happens once. So how do I trigger the filter appliance in a regular interval?
当我应用过滤器时,这只发生一次。那么如何定期触发过滤设备呢?
I tried the following:
我尝试了以下方法:
setInterval(function() {$scope.$apply()}, 1000) // placed in controller function
...with no success.
......没有成功
Any ideas?
有任何想法吗?
2 个解决方案
#1
7
I don't think you are going to be able to achieve this with a filter. The reason $scope.$apply()
doesn't work is because it is watching for changes on the data. Since the data didn't actually change, the filter never gets called again.
我不认为你能够通过过滤器实现这一目标。 $ scope。$ apply()不起作用的原因是因为它正在监视数据的变化。由于数据实际上没有改变,因此永远不会再次调用过滤器。
Instead, you need to adjust the data that is being viewed in your controller. Use $timeout
instead of setInterval
because it is built into the digestion lifecycle.
相反,您需要调整控制器中正在查看的数据。使用$ timeout而不是setInterval,因为它内置于消化生命周期中。
I'd consider using a directive to do this.
我会考虑使用指令来做到这一点。
app.directive('relativeTime', function($timeout) {
function update(scope, element) {
element.text(getRelativeDateTimeString(scope.actualTime));
$timeout(function() { update(scope, element); }, 1000);
}
return {
scope: {
actualTime: '=relativeTime'
},
link: function(scope, element) {
update(scope, element);
}
};
});
So you can use the directive like this:
所以你可以使用这样的指令:
<div relative-time="theDate"></div>
Also, I found a flaw in your getRelativeDateTimeString
function. You need to base your delta off of the current time. getSeconds
just gives you the seconds of the given time:
另外,我在你的getRelativeDateTimeString函数中发现了一个缺陷。您需要将delta与当前时间相关联。 getSeconds只给出给定时间的秒数:
var delta = parseInt(((new Date().getTime()) - dt.getTime()) / 1000);
Here is a working CodePen.
这是一个有效的CodePen。
#2
2
Below is the working jsfiddle uses directive to update the time, I think you are looking for similar code..
下面是工作jsfiddle使用指令来更新时间,我想你正在寻找类似的代码..
http://jsfiddle.net/vishalvasani/xRg3j/
http://jsfiddle.net/vishalvasani/xRg3j/
it uses
它用
$timeout
#1
7
I don't think you are going to be able to achieve this with a filter. The reason $scope.$apply()
doesn't work is because it is watching for changes on the data. Since the data didn't actually change, the filter never gets called again.
我不认为你能够通过过滤器实现这一目标。 $ scope。$ apply()不起作用的原因是因为它正在监视数据的变化。由于数据实际上没有改变,因此永远不会再次调用过滤器。
Instead, you need to adjust the data that is being viewed in your controller. Use $timeout
instead of setInterval
because it is built into the digestion lifecycle.
相反,您需要调整控制器中正在查看的数据。使用$ timeout而不是setInterval,因为它内置于消化生命周期中。
I'd consider using a directive to do this.
我会考虑使用指令来做到这一点。
app.directive('relativeTime', function($timeout) {
function update(scope, element) {
element.text(getRelativeDateTimeString(scope.actualTime));
$timeout(function() { update(scope, element); }, 1000);
}
return {
scope: {
actualTime: '=relativeTime'
},
link: function(scope, element) {
update(scope, element);
}
};
});
So you can use the directive like this:
所以你可以使用这样的指令:
<div relative-time="theDate"></div>
Also, I found a flaw in your getRelativeDateTimeString
function. You need to base your delta off of the current time. getSeconds
just gives you the seconds of the given time:
另外,我在你的getRelativeDateTimeString函数中发现了一个缺陷。您需要将delta与当前时间相关联。 getSeconds只给出给定时间的秒数:
var delta = parseInt(((new Date().getTime()) - dt.getTime()) / 1000);
Here is a working CodePen.
这是一个有效的CodePen。
#2
2
Below is the working jsfiddle uses directive to update the time, I think you are looking for similar code..
下面是工作jsfiddle使用指令来更新时间,我想你正在寻找类似的代码..
http://jsfiddle.net/vishalvasani/xRg3j/
http://jsfiddle.net/vishalvasani/xRg3j/
it uses
它用
$timeout