timeline_setter 0.3.0 → 0.3.1
Sign up to get free protection for your applications and to get access to all the features.
- data/Rakefile +4 -4
- data/doc/doc.markdown +50 -27
- data/doc/timeline-setter.html +170 -119
- data/doc/twitter-demo.html +4 -57
- data/documentation/TimelineSetter/CLI.html +87 -78
- data/documentation/TimelineSetter/Parser.html +45 -31
- data/documentation/TimelineSetter/Timeline.html +70 -48
- data/documentation/TimelineSetter.html +6 -4
- data/documentation/_index.html +4 -4
- data/documentation/css/full_list.css +2 -0
- data/documentation/css/style.css +12 -10
- data/documentation/file.README.html +22 -18
- data/documentation/frames.html +1 -1
- data/documentation/index.html +22 -18
- data/documentation/js/app.js +4 -4
- data/documentation/js/full_list.js +29 -6
- data/documentation/method_list.html +19 -19
- data/documentation/top-level-namespace.html +5 -3
- data/index.html +42 -15
- data/lib/timeline_setter/cli.rb +2 -1
- data/lib/timeline_setter/timeline.rb +1 -1
- data/lib/timeline_setter/version.rb +1 -1
- data/public/javascripts/timeline-setter.js +117 -57
- data/public/javascripts/vendor/jquery-min.js +4 -16
- data/public/javascripts/vendor/jquery.js +9404 -0
- data/public/javascripts/vendor/underscore-min.js +26 -21
- data/public/javascripts/vendor/underscore.js +999 -0
- data/spec/test_data.csv +3 -3
- data/spec/timeline-debug.html +19 -0
- data/templates/timeline-markup.erb +25 -1
- data/timeline_setter.gemspec +11 -10
- metadata +9 -8
@@ -5,7 +5,7 @@
|
|
5
5
|
var TimelineSetter = window.TimelineSetter = (window.TimelineSetter || {});
|
6
6
|
|
7
7
|
// Current version of `TimelineSetter`
|
8
|
-
TimelineSetter.VERSION = "0.3.
|
8
|
+
TimelineSetter.VERSION = "0.3.1";
|
9
9
|
|
10
10
|
// Mixins
|
11
11
|
// ------
|
@@ -81,7 +81,7 @@
|
|
81
81
|
drag = {x: e.pageX};
|
82
82
|
e.type = "dragstart";
|
83
83
|
obj.el.trigger(e);
|
84
|
-
}
|
84
|
+
}
|
85
85
|
|
86
86
|
// The user is interacting; capture the offset and trigger a `dragging` event.
|
87
87
|
function mousemove(e){
|
@@ -93,7 +93,7 @@
|
|
93
93
|
});
|
94
94
|
drag = { x: (e.pageX || e.touches[0].pageX) };
|
95
95
|
obj.el.trigger(e);
|
96
|
-
}
|
96
|
+
}
|
97
97
|
|
98
98
|
// We're done tracking the movement set drag back to `null` for the next event.
|
99
99
|
function mouseup(e){
|
@@ -101,7 +101,7 @@
|
|
101
101
|
drag = null;
|
102
102
|
e.type = "dragend";
|
103
103
|
obj.el.trigger(e);
|
104
|
-
}
|
104
|
+
}
|
105
105
|
|
106
106
|
if (!touchInit) {
|
107
107
|
// Bind on mouse events if we have a mouse...
|
@@ -123,7 +123,7 @@
|
|
123
123
|
|
124
124
|
obj.el.bind("touchmove", mousemove);
|
125
125
|
obj.el.bind("touchend", mouseup);
|
126
|
-
}
|
126
|
+
}
|
127
127
|
};
|
128
128
|
|
129
129
|
|
@@ -140,11 +140,11 @@
|
|
140
140
|
if (safari){
|
141
141
|
var negative = delta < 0 ? -1 : 1;
|
142
142
|
delta = Math.log(Math.abs(delta)) * negative * 2;
|
143
|
-
}
|
143
|
+
}
|
144
144
|
e.type = "scrolled";
|
145
145
|
e.deltaX = delta;
|
146
146
|
obj.el.trigger(e);
|
147
|
-
}
|
147
|
+
}
|
148
148
|
|
149
149
|
obj.el.bind("mousewheel DOMMouseScroll", mousewheel);
|
150
150
|
};
|
@@ -221,6 +221,14 @@
|
|
221
221
|
Intervals.dateStr = function(timestamp, interval) {
|
222
222
|
var d = new Intervals.dateFormats(timestamp);
|
223
223
|
switch (interval) {
|
224
|
+
case "Millennium":
|
225
|
+
return d.year;
|
226
|
+
case "Quincentenary":
|
227
|
+
return d.year;
|
228
|
+
case "Century":
|
229
|
+
return d.year;
|
230
|
+
case "HalfCentury":
|
231
|
+
return d.year;
|
224
232
|
case "Decade":
|
225
233
|
return d.year;
|
226
234
|
case "Lustrum":
|
@@ -235,6 +243,10 @@
|
|
235
243
|
return d.date;
|
236
244
|
case "Hours":
|
237
245
|
return d.hourWithMinutes;
|
246
|
+
case "HalfHour":
|
247
|
+
return d.hourWithMinutes;
|
248
|
+
case "QuarterHour":
|
249
|
+
return d.hourWithMinutes;
|
238
250
|
case "Minutes":
|
239
251
|
return d.hourWithMinutes;
|
240
252
|
case "Seconds":
|
@@ -245,19 +257,51 @@
|
|
245
257
|
Intervals.prototype = {
|
246
258
|
// Sane estimates of date ranges for the `isAtLeastA` test.
|
247
259
|
INTERVALS : {
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
|
256
|
-
|
260
|
+
Millennium : 69379200000000, // 2200 years is the trigger
|
261
|
+
Quincentenary : 34689600000000, // 1100 years is the trigger
|
262
|
+
Century : 9460800000000, // 300 years is the trigger
|
263
|
+
HalfCentury : 3153600000000, // 100 years is the trigger
|
264
|
+
Decade : 315360000000,
|
265
|
+
Lustrum : 157680000000,
|
266
|
+
FullYear : 31536000000,
|
267
|
+
Month : 2592000000,
|
268
|
+
Week : 604800000,
|
269
|
+
Date : 86400000,
|
270
|
+
Hours : 3600000,
|
271
|
+
HalfHour : 1800000,
|
272
|
+
QuarterHour : 900000,
|
273
|
+
Minutes : 60000,
|
274
|
+
Seconds : 1000 // 1,000 millliseconds equals on second
|
257
275
|
},
|
258
276
|
|
259
277
|
// The order used when testing where exactly a timespan falls.
|
260
|
-
INTERVAL_ORDER : [
|
278
|
+
INTERVAL_ORDER : [
|
279
|
+
'Seconds',
|
280
|
+
'Minutes',
|
281
|
+
'QuarterHour',
|
282
|
+
'HalfHour',
|
283
|
+
'Hours',
|
284
|
+
'Date',
|
285
|
+
'Week',
|
286
|
+
'Month',
|
287
|
+
'FullYear',
|
288
|
+
'Lustrum',
|
289
|
+
'Decade',
|
290
|
+
'HalfCentury',
|
291
|
+
'Century',
|
292
|
+
'Quincentenary',
|
293
|
+
'Millennium'
|
294
|
+
],
|
295
|
+
|
296
|
+
// The year adjustment used for supra-year intervals.
|
297
|
+
YEAR_FRACTIONS : {
|
298
|
+
Millenium : 1000,
|
299
|
+
Quincentenary : 500,
|
300
|
+
Century : 100,
|
301
|
+
HalfCentury : 50,
|
302
|
+
Decade : 10,
|
303
|
+
Lustrum : 5
|
304
|
+
},
|
261
305
|
|
262
306
|
// A test to find the appropriate range of intervals, for example if a range of
|
263
307
|
// timestamps only spans hours this will return true when called with `"Hours"`.
|
@@ -278,22 +322,16 @@
|
|
278
322
|
return this.INTERVALS[this.INTERVAL_ORDER[this.idx]];
|
279
323
|
},
|
280
324
|
|
281
|
-
//
|
282
|
-
|
283
|
-
|
284
|
-
|
285
|
-
// And if you pass in the year 2010 or 2015 you'll get 2010 back.
|
286
|
-
getDecade : function(date) {
|
287
|
-
return (date.getFullYear() / 10 | 0) * 10;
|
325
|
+
// Floor the year to a given epoch.
|
326
|
+
getYearFloor : function(date, intvl){
|
327
|
+
var fudge = this.YEAR_FRACTIONS[intvl] || 1;
|
328
|
+
return (date.getFullYear() / fudge | 0) * fudge;
|
288
329
|
},
|
289
330
|
|
290
|
-
//
|
291
|
-
|
292
|
-
|
293
|
-
|
294
|
-
// And if you pass in the year 1997 you'll get 1995 back.
|
295
|
-
getLustrum : function(date) {
|
296
|
-
return (date.getFullYear() / 5 | 0) * 5;
|
331
|
+
// Return a date with the year set to the next interval in a given epoch.
|
332
|
+
getYearCeil : function(date, intvl){
|
333
|
+
if(this.YEAR_FRACTIONS[intvl]) return this.getYearFloor(date, intvl) + this.YEAR_FRACTIONS[intvl];
|
334
|
+
return date.getFullYear();
|
297
335
|
},
|
298
336
|
|
299
337
|
// Return a Date object rounded down to the previous Sunday, a.k.a. the first day of the week.
|
@@ -310,6 +348,23 @@
|
|
310
348
|
return thisDate;
|
311
349
|
},
|
312
350
|
|
351
|
+
// Return the half of the hour this date belongs to. Anything before 30 min.
|
352
|
+
// past the hour comes back as zero. Anything after comes back as 30.
|
353
|
+
getHalfHour: function(date) {
|
354
|
+
return date.getMinutes() > 30 ? 30 : 0;
|
355
|
+
},
|
356
|
+
|
357
|
+
// Return the quarter of the hour this date belongs to. Anything before 15 min.
|
358
|
+
// past the hour comes back as zero; 15-30 comes back as 15; 30-45 as 30;
|
359
|
+
// 45-60 as 45.
|
360
|
+
getQuarterHour: function(date) {
|
361
|
+
var minutes = date.getMinutes();
|
362
|
+
if (minutes < 15) return 0;
|
363
|
+
if (minutes < 30) return 15;
|
364
|
+
if (minutes < 45) return 30;
|
365
|
+
return 45;
|
366
|
+
},
|
367
|
+
|
313
368
|
// Zero out a date from the current interval down to seconds.
|
314
369
|
floor : function(ts){
|
315
370
|
var date = new Date(ts);
|
@@ -319,22 +374,22 @@
|
|
319
374
|
idx;
|
320
375
|
|
321
376
|
// Zero the special extensions, and adjust as idx necessary.
|
377
|
+
date.setFullYear(this.getYearFloor(date, intvl));
|
322
378
|
switch(intvl){
|
323
|
-
case 'Decade':
|
324
|
-
date.setFullYear(this.getDecade(date));
|
325
|
-
break;
|
326
|
-
case 'Lustrum':
|
327
|
-
date.setFullYear(this.getLustrum(date));
|
328
|
-
break;
|
329
379
|
case 'Week':
|
330
380
|
date.setDate(this.getWeekFloor(date).getDate());
|
331
381
|
idx = _.indexOf(this.INTERVAL_ORDER, 'Week');
|
382
|
+
case 'HalfHour':
|
383
|
+
date.setMinutes(this.getHalfHour(date));
|
384
|
+
case 'QuarterHour':
|
385
|
+
date.setMinutes(this.getQuarterHour(date));
|
332
386
|
}
|
333
387
|
|
334
388
|
// Zero out the rest
|
335
389
|
while(idx--){
|
336
390
|
intvl = this.INTERVAL_ORDER[idx];
|
337
|
-
if(
|
391
|
+
if (!(_.include(['Week', 'HalfHour', 'QuarterHour'].concat(_.keys(this.YEAR_FRACTIONS)), intvl)))
|
392
|
+
date["set" + intvl](intvl === "Date" ? 1 : 0);
|
338
393
|
}
|
339
394
|
|
340
395
|
return date.getTime();
|
@@ -344,18 +399,21 @@
|
|
344
399
|
ceil : function(ts){
|
345
400
|
var date = new Date(this.floor(ts));
|
346
401
|
var intvl = this.INTERVAL_ORDER[this.idx];
|
402
|
+
|
403
|
+
date.setFullYear(this.getYearCeil(date, intvl));
|
347
404
|
switch(intvl){
|
348
|
-
case 'Decade':
|
349
|
-
date.setFullYear(this.getDecade(date) + 10);
|
350
|
-
break;
|
351
|
-
case 'Lustrum':
|
352
|
-
date.setFullYear(this.getLustrum(date) + 5);
|
353
|
-
break;
|
354
405
|
case 'Week':
|
355
406
|
date.setTime(this.getWeekCeil(date).getTime());
|
356
407
|
break;
|
408
|
+
case 'HalfHour':
|
409
|
+
date.setMinutes(this.getHalfHour(date) + 30);
|
410
|
+
break;
|
411
|
+
case 'QuarterHour':
|
412
|
+
date.setMinutes(this.getQuarterHour(date) + 15);
|
413
|
+
break;
|
357
414
|
default:
|
358
|
-
|
415
|
+
if (!(_.include(['Week', 'HalfHour', 'QuarterHour'].concat(_.keys(this.YEAR_FRACTIONS)), intvl)))
|
416
|
+
date["set" + intvl](date["get" + intvl]() + 1);
|
359
417
|
}
|
360
418
|
return date.getTime();
|
361
419
|
},
|
@@ -470,9 +528,9 @@
|
|
470
528
|
// are the formatters we override.
|
471
529
|
//
|
472
530
|
// formatter : function(d, defaults) {
|
473
|
-
// defaults.months = ['enero', 'febrero', 'marzo',
|
474
|
-
// 'abril', 'mayo', 'junio', 'julio',
|
475
|
-
// 'agosto', 'septiembre', 'octubre',
|
531
|
+
// defaults.months = ['enero', 'febrero', 'marzo',
|
532
|
+
// 'abril', 'mayo', 'junio', 'julio',
|
533
|
+
// 'agosto', 'septiembre', 'octubre',
|
476
534
|
// 'noviembre', 'diciembre'];
|
477
535
|
// return defaults;
|
478
536
|
// }
|
@@ -540,12 +598,12 @@
|
|
540
598
|
this.series.push(this.bySid[card.series]);
|
541
599
|
}
|
542
600
|
var series = this.bySid[card.series];
|
543
|
-
series.add(card);
|
601
|
+
var crd = series.add(card);
|
544
602
|
|
545
603
|
this.bounds.extend(series.max());
|
546
604
|
this.bounds.extend(series.min());
|
547
605
|
|
548
|
-
this.trigger('cardAdd', card);
|
606
|
+
this.trigger('cardAdd', card, crd);
|
549
607
|
}
|
550
608
|
});
|
551
609
|
|
@@ -663,6 +721,7 @@
|
|
663
721
|
add : function(card){
|
664
722
|
var crd = new Card(card, this);
|
665
723
|
this.cards.push(crd);
|
724
|
+
return crd;
|
666
725
|
},
|
667
726
|
|
668
727
|
// The comparing function for `max` and `min`.
|
@@ -715,12 +774,13 @@
|
|
715
774
|
this.series.bind("hideNotch", this.toggleNotch);
|
716
775
|
this.series.bind("showNotch", this.toggleNotch);
|
717
776
|
this.timeline.bind("render", this.render);
|
718
|
-
this.timeline.bar.bind("
|
777
|
+
this.timeline.bar.bind("move", this.flip);
|
719
778
|
this.id = [
|
720
779
|
this.get('timestamp'),
|
721
780
|
this.get('description').split(/ /)[0].replace(/[^a-zA-Z\-]/g,"")
|
722
781
|
].join("-");
|
723
782
|
this.timeline.cards.push(this);
|
783
|
+
this.template = window.JST.card;
|
724
784
|
};
|
725
785
|
|
726
786
|
Card.prototype = _.extend(Card.prototype, {
|
@@ -750,7 +810,7 @@
|
|
750
810
|
var tRightEdge = this.timeline.$(".timeline_setter").offset().left + this.timeline.$(".timeline_setter").width();
|
751
811
|
var margin = this.el.css("margin-left") === this.originalMargin;
|
752
812
|
var flippable = this.$(".TS-item").width() < this.timeline.$(".timeline_setter").width() / 2;
|
753
|
-
var offTimeline = this.el.
|
813
|
+
var offTimeline = (this.el.offset().left - this.el.parent().offset().left) - this.$(".TS-item").width() < 0;
|
754
814
|
|
755
815
|
// If the card's right edge is more than the timeline's right edge and
|
756
816
|
// it's never been flipped before and it won't go off the timeline when
|
@@ -775,7 +835,7 @@
|
|
775
835
|
var that = this;
|
776
836
|
this.hideActiveCard();
|
777
837
|
if (!this.el) {
|
778
|
-
this.el = $(
|
838
|
+
this.el = $(this.template({card: this}));
|
779
839
|
|
780
840
|
// create a `this.$` scoped to its card.
|
781
841
|
queryable(this, this.el);
|
@@ -931,7 +991,7 @@
|
|
931
991
|
|
932
992
|
// The TimelineSetter JS API allows you to listen to certain
|
933
993
|
// timeline events, and activate cards programmatically.
|
934
|
-
// To take advantage of it, assign the timeline boot function to a variable
|
994
|
+
// To take advantage of it, assign the timeline boot function to a variable
|
935
995
|
// like so:
|
936
996
|
//
|
937
997
|
// var currentTimeline = TimelineSetter.Timeline.boot(
|
@@ -940,7 +1000,7 @@
|
|
940
1000
|
//
|
941
1001
|
// then call methods on the `currentTimeline.api` object
|
942
1002
|
//
|
943
|
-
// currentTimeline.api.onLoad(function() {
|
1003
|
+
// currentTimeline.api.onLoad(function() {
|
944
1004
|
// console.log("I'm ready");
|
945
1005
|
// });
|
946
1006
|
//
|
@@ -1006,8 +1066,8 @@
|
|
1006
1066
|
// and a formatter function for dates. All of these are optional.
|
1007
1067
|
//
|
1008
1068
|
// We also initialize a new API object for each timeline, accessible via the
|
1009
|
-
// timeline variable's `api` method (e.g. `currentTimeline.api`) and look for
|
1010
|
-
// how many timelines are globally on the page for keydown purposes. We'll only
|
1069
|
+
// timeline variable's `api` method (e.g. `currentTimeline.api`) and look for
|
1070
|
+
// how many timelines are globally on the page for keydown purposes. We'll only
|
1011
1071
|
// bind keydowns globally if there's only one timeline on the page.
|
1012
1072
|
Timeline.boot = function(data, config) {
|
1013
1073
|
var timeline = TimelineSetter.timeline = new Timeline(data, config || {});
|