3 var _active_feed_id = false;
4 var _active_feed_offset = false;
5 var _update_timeout = false;
6 var _feedlist_expanded = false;
8 function catchup_feed(feed_id, callback) {
11 var fn = find_feed(last_feeds, feed_id).title;
13 if (confirm(__("Mark all articles in %s as read?").replace("%s", fn))) {
17 if (feed_id == -4) is_cat = "true";
19 var query = "?op=rpc&subop=catchupFeed&feed_id=" +
20 feed_id + "&is_cat=" + is_cat;
22 new Ajax.Request("backend.php", {
24 onComplete: function(transport) {
25 if (callback) callback(transport);
32 exception_error("catchup_article", e);
37 function catchup_article(article_id, callback) {
39 var query = "?op=rpc&subop=catchupSelected" +
40 "&cmode=0&ids=" + article_id;
42 new Ajax.Request("backend.php", {
44 onComplete: function(transport) {
45 if (callback) callback(transport);
49 exception_error("catchup_article", e);
53 function set_selected_feed(feed_id) {
55 var feeds = $("feeds-content").getElementsByTagName("LI");
57 for (var i = 0; i < feeds.length; i++) {
58 if (feeds[i].id == "F-" + feed_id)
59 feeds[i].className = "selected";
61 feeds[i].className = "";
64 _active_feed_id = feed_id;
67 exception_error("mark_selected_feed", e);
71 function zoom(article_id) {
73 var elem = $('A-' + article_id);
76 var divs = elem.getElementsByTagName('DIV');
78 for (var i = 0; i < divs.length; i++) {
79 if (divs[i].className == 'excerpt')
80 Element.hide(divs[i]);
82 if (divs[i].className == 'content')
83 Element.show(divs[i]);
87 catchup_article(article_id,
88 function() { update(); });
91 exception_error("zoom", e);
95 function load_more() {
97 viewfeed(_active_feed_id, _active_feed_offset + 10);
99 exception_error("load_more", e);
105 console.log('updating feeds...');
107 window.clearTimeout(_update_timeout);
109 new Ajax.Request("backend.php", {
110 parameters: "?op=rpc&subop=digest-init",
111 onComplete: function(transport) {
112 fatal_error_check(transport);
113 parse_feeds(transport);
114 set_selected_feed(_active_feed_id);
117 _update_timeout = window.setTimeout('update()', 5*1000);
119 exception_error("update", e);
123 function remove_headline_entry(article_id) {
125 var elem = $('A-' + article_id);
128 elem.parentNode.removeChild(elem);
132 exception_error("remove_headline_entry", e);
136 function view(article_id, dismiss_only) {
138 remove_headline_entry(article_id);
140 catchup_article(article_id,
141 function() { update(); });
143 return dismiss_only != true;
145 exception_error("view", e);
149 function viewfeed(feed_id, offset) {
152 if (!feed_id) feed_id = _active_feed_id;
157 offset = _active_feed_offset + offset;
160 var query = "backend.php?op=rpc&subop=digest-update&feed_id=" + feed_id +
163 new Ajax.Request("backend.php", {
165 onComplete: function(transport) {
166 fatal_error_check(transport);
167 parse_headlines(transport, offset == 0);
168 set_selected_feed(feed_id);
169 _active_feed_offset = offset;
173 exception_error("view", e);
177 function find_article(articles, article_id) {
179 for (var i = 0; i < articles.length; i++) {
180 if (articles[i].id == article_id)
187 exception_error("find_article", e);
191 function find_feed(feeds, feed_id) {
193 for (var i = 0; i < feeds.length; i++) {
194 if (feeds[i].id == feed_id)
201 exception_error("find_feed", e);
205 function get_feed_icon(feed) {
208 return 'icons/' + feed.id + '.ico';
211 return 'images/mark_set.png';
214 return 'images/pub_set.png';
217 return 'images/fresh.png';
220 return 'images/tag.png';
223 return 'images/label.png';
225 return 'images/blank_icon.gif';
228 exception_error("get_feed_icon", e);
232 function add_feed_entry(feed) {
236 icon_part = "<img src='" + get_feed_icon(feed) + "'/>";
238 var tmp_html = "<li id=\"F-"+feed.id+"\" " +
239 "onmouseover=\"feed_mi(this)\" onmouseout=\"feed_mo(this)\">" +
241 "<a href=\"#\" onclick=\"viewfeed("+feed.id+")\">" + feed.title + "</a>" +
242 "<div class='unread-ctr'>" +
243 "<img onclick=\"catchup_feed("+feed.id+")\" title=\"Dismiss\" class=\"dismiss\" style='display : none' src=\"images/digest_checkbox.png\">" +
244 "<span class=\"unread\">" + feed.unread + "</span>" +
248 $("feeds-content").innerHTML += tmp_html;
251 exception_error("add_feed_entry", e);
255 function add_headline_entry(article, feed) {
260 icon_part = "<img class='icon' src='" + get_feed_icon(feed) + "'/>";
262 var tmp_html = "<li id=\"A-"+article.id+"\">" +
264 "<div class='digest-check'>" +
265 "<img title='Set starred' onclick=\"toggleMark(this, "+article.id+")\" src='images/mark_unset.png'>" +
266 "<img title='Set published' onclick=\"togglePub(this, "+article.id+")\" src='images/pub_unset.png'>" +
267 "<img title='Dismiss' onclick=\"view("+article.id+", true)\" class='digest-check' src='images/digest_checkbox.png'>" +
269 "<a target=\"_blank\" href=\""+article.link+"\""+
270 "onclick=\"return view("+article.id+")\" class='title'>" +
271 article.title + "</a>" +
272 "<div class='body'>" +
273 "<div title=\"Click to expand article\" onclick=\"zoom("+article.id+")\" class='excerpt'>" +
274 article.excerpt + "</div>" +
275 "<div style='display : none' class='content'>" +
276 article.content + "</div>" +
277 "<div class='info'><a href=\#\" onclick=\"viewfeed("+feed.id+")\">" +
278 feed.title + "</a> " + " @ " +
279 new Date(article.updated * 1000) + "</div>" +
282 $("headlines-content").innerHTML += tmp_html;
285 exception_error("add_headline_entry", e);
289 function expand_feeds() {
291 _feedlist_expanded = true;
293 redraw_feedlist(last_feeds);
296 exception_error("expand_feeds", e);
300 function redraw_feedlist(feeds) {
303 $('feeds-content').innerHTML = "";
307 if (_feedlist_expanded) limit = feeds.length;
309 for (var i = 0; i < Math.min(limit, feeds.length); i++) {
310 add_feed_entry(feeds[i]);
313 if (feeds.length > limit) {
314 $('feeds-content').innerHTML += "<li id='F-MORE-PROMPT'>" +
315 "<img src='images/blank_icon.gif'>" +
316 "<a href=\"#\" onclick=\"expand_feeds()\">" +
317 __("%d more...").replace("%d", feeds.length-10) +
322 exception_error("redraw_feedlist", e);
326 function parse_feeds(transport) {
329 if (!transport.responseXML) return;
331 var feeds = transport.responseXML.getElementsByTagName('feeds')[0];
334 feeds = eval("(" + feeds.firstChild.nodeValue + ")");
336 feeds.sort( function (a,b)
338 if (b.unread != a.unread)
339 return (b.unread - a.unread)
341 if (a.title > b.title)
343 else if (a.title < b.title)
351 redraw_feedlist(feeds);
355 exception_error("parse_feeds", e);
359 function parse_headlines(transport, replace) {
361 if (!transport.responseXML) return;
363 var headlines = transport.responseXML.getElementsByTagName('headlines')[0];
366 headlines = eval("(" + headlines.firstChild.nodeValue + ")");
368 if (replace) $('headlines-content').innerHTML = '';
370 var pr = $('H-MORE-PROMPT');
372 if (pr) pr.parentNode.removeChild(pr);
374 for (var i = 0; i < headlines.length; i++) {
376 if (!$('A-' + headlines[i].id)) {
377 add_headline_entry(headlines[i],
378 find_feed(last_feeds, headlines[i].feed_id));
383 $('headlines-content').appendChild(pr);
385 $('headlines-content').innerHTML += "<li id='H-MORE-PROMPT'>" +
386 "<div class='body'><a href=\"javascript:load_more()\">" +
387 __("More articles...") + "</a></div></li>";
390 new Effect.Appear('headlines-content');
394 exception_error("parse_headlines", e);
401 new Ajax.Request("backend.php", {
402 parameters: "backend.php?op=rpc&subop=digest-init",
403 onComplete: function(transport) {
404 parse_feeds(transport);
405 window.setTimeout('viewfeed(-4)', 100);
406 _update_timeout = window.setTimeout('update()', 5*1000);
410 exception_error("digest_init", e);
414 function tMark_afh_off(effect) {
416 var elem = effect.effects[0].element;
418 console.log("tMark_afh_off : " + elem.id);
421 elem.src = elem.src.replace("mark_set", "mark_unset");
422 elem.alt = __("Star article");
427 exception_error("tMark_afh_off", e);
431 function tPub_afh_off(effect) {
433 var elem = effect.effects[0].element;
435 console.log("tPub_afh_off : " + elem.id);
438 elem.src = elem.src.replace("pub_set", "pub_unset");
439 elem.alt = __("Publish article");
444 exception_error("tPub_afh_off", e);
448 function toggleMark(mark_img, id) {
452 var query = "?op=rpc&id=" + id + "&subop=mark";
454 query = query + "&afid=" + _active_feed_id;
455 query = query + "&omode=c";
457 if (!mark_img) return;
459 if (mark_img.src.match("mark_unset")) {
460 mark_img.src = mark_img.src.replace("mark_unset", "mark_set");
461 mark_img.alt = __("Unstar article");
462 query = query + "&mark=1";
464 mark_img.alt = __("Please wait...");
465 query = query + "&mark=0";
467 mark_img.src = mark_img.src.replace("mark_set", "mark_unset");
468 mark_img.alt = __("Star article");
471 new Ajax.Request("backend.php", {
473 onComplete: function(transport) {
478 exception_error("toggleMark", e);
482 function togglePub(mark_img, id, note) {
486 var query = "?op=rpc&id=" + id + "&subop=publ";
488 query = query + "&afid=" + _active_feed_id;
490 if (note != undefined) {
491 query = query + "¬e=" + param_escape(note);
493 query = query + "¬e=undefined";
496 query = query + "&omode=c";
498 if (!mark_img) return;
500 if (mark_img.src.match("pub_unset") || note != undefined) {
501 mark_img.src = mark_img.src.replace("pub_unset", "pub_set");
502 mark_img.alt = __("Unpublish article");
503 query = query + "&pub=1";
506 mark_img.alt = __("Please wait...");
507 query = query + "&pub=0";
509 mark_img.src = mark_img.src.replace("pub_set", "pub_unset");
510 mark_img.alt = __("Publish article");
513 new Ajax.Request("backend.php", {
515 onComplete: function(transport) {
520 exception_error("togglePub", e);
524 function fatal_error(code, msg) {
528 window.location.href = "digest.php";
529 } else if (code == 5) {
530 window.location.href = "update.php";
533 if (msg == "") msg = "Unknown error";
535 console.error("Fatal error: " + code + "\n" +
541 exception_error("fatalError", e);
545 function fatal_error_check(transport) {
547 if (transport.responseXML) {
548 var error = transport.responseXML.getElementsByTagName("error")[0];
551 var code = error.getAttribute("error-code");
552 var msg = error.getAttribute("error-msg");
554 fatal_error(code, msg);
560 exception_error("fatal_error_check", e);
565 function feed_mi(elem) {
567 var imgs = elem.getElementsByTagName('IMG');
568 var spans = elem.getElementsByTagName('SPAN');
570 for (var i = 0; i < imgs.length; i++) {
571 if (imgs[i].className == "dismiss")
572 Element.show(imgs[i]);
575 for (var i = 0; i < spans.length; i++) {
576 if (spans[i].className == "unread")
577 Element.hide(spans[i]);
582 exception_error("feed_mi", e);
586 function feed_mo(elem) {
588 var imgs = elem.getElementsByTagName('IMG');
589 var spans = elem.getElementsByTagName('SPAN');
591 for (var i = 0; i < imgs.length; i++) {
592 if (imgs[i].className == "dismiss")
593 Element.hide(imgs[i]);
596 for (var i = 0; i < spans.length; i++) {
597 if (spans[i].className == "unread")
598 Element.show(spans[i]);
602 exception_error("feed_mo", e);