]> git.wh0rd.org - tt-rss.git/blame - classes/pref_feeds.php
add Pref_Filters
[tt-rss.git] / classes / pref_feeds.php
CommitLineData
afcfe6ca
AD
1<?php
2class Pref_Feeds extends Handler {
3 function batch_edit_cbox($elem, $label = false) {
4 print "<input type=\"checkbox\" title=\"".__("Check to enable field")."\"
5 onchange=\"dijit.byId('feedEditDlg').toggleField(this, '$elem', '$label')\">";
6 }
7
8 function renamecat() {
9 $title = db_escape_string($_REQUEST['title']);
10 $id = db_escape_string($_REQUEST['id']);
11
12 if ($title) {
13 db_query($this->link, "UPDATE ttrss_feed_categories SET
14 title = '$title' WHERE id = '$id' AND owner_uid = " . $_SESSION["uid"]);
15 }
16 return;
17 }
18
19 function remtwitterinfo() {
20
21 db_query($this->link, "UPDATE ttrss_users SET twitter_oauth = NULL
22 WHERE id = " . $_SESSION['uid']);
23
24 return;
25 }
26
27 function getfeedtree() {
28
29 $search = $_SESSION["prefs_feed_search"];
30
31 if ($search) $search_qpart = " AND LOWER(title) LIKE LOWER('%$search%')";
32
33 $root = array();
34 $root['id'] = 'root';
35 $root['name'] = __('Feeds');
36 $root['items'] = array();
37 $root['type'] = 'category';
38
39 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
40
41 $result = db_query($this->link, "SELECT id, title FROM ttrss_feed_categories
42 WHERE owner_uid = " . $_SESSION["uid"] . " ORDER BY order_id, title");
43
44 while ($line = db_fetch_assoc($result)) {
45 $cat = array();
46 $cat['id'] = 'CAT:' . $line['id'];
47 $cat['bare_id'] = $feed_id;
48 $cat['name'] = $line['title'];
49 $cat['items'] = array();
50 $cat['checkbox'] = false;
51 $cat['type'] = 'category';
52
53 $feed_result = db_query($this->link, "SELECT id, title, last_error,
54 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
55 FROM ttrss_feeds
56 WHERE cat_id = '".$line['id']."' AND owner_uid = ".$_SESSION["uid"].
57 "$search_qpart ORDER BY order_id, title");
58
59 while ($feed_line = db_fetch_assoc($feed_result)) {
60 $feed = array();
61 $feed['id'] = 'FEED:' . $feed_line['id'];
62 $feed['bare_id'] = $feed_line['id'];
63 $feed['name'] = $feed_line['title'];
64 $feed['checkbox'] = false;
65 $feed['error'] = $feed_line['last_error'];
66 $feed['icon'] = getFeedIcon($feed_line['id']);
67 $feed['param'] = make_local_datetime($this->link,
68 $feed_line['last_updated'], true);
69
70 array_push($cat['items'], $feed);
71 }
72
73 $cat['param'] = T_sprintf('(%d feeds)', count($cat['items']));
74
75 if (count($cat['items']) > 0)
76 array_push($root['items'], $cat);
77
78 $root['param'] += count($cat['items']);
79 }
80
81 /* Uncategorized is a special case */
82
83 $cat = array();
84 $cat['id'] = 'CAT:0';
85 $cat['bare_id'] = 0;
86 $cat['name'] = __("Uncategorized");
87 $cat['items'] = array();
88 $cat['type'] = 'category';
89 $cat['checkbox'] = false;
90
91 $feed_result = db_query($this->link, "SELECT id, title,last_error,
92 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
93 FROM ttrss_feeds
94 WHERE cat_id IS NULL AND owner_uid = ".$_SESSION["uid"].
95 "$search_qpart ORDER BY order_id, title");
96
97 while ($feed_line = db_fetch_assoc($feed_result)) {
98 $feed = array();
99 $feed['id'] = 'FEED:' . $feed_line['id'];
100 $feed['bare_id'] = $feed_line['id'];
101 $feed['name'] = $feed_line['title'];
102 $feed['checkbox'] = false;
103 $feed['error'] = $feed_line['last_error'];
104 $feed['icon'] = getFeedIcon($feed_line['id']);
105 $feed['param'] = make_local_datetime($this->link,
106 $feed_line['last_updated'], true);
107
108 array_push($cat['items'], $feed);
109 }
110
111 $cat['param'] = T_sprintf('(%d feeds)', count($cat['items']));
112
113 if (count($cat['items']) > 0)
114 array_push($root['items'], $cat);
115
116 $root['param'] += count($cat['items']);
117 $root['param'] = T_sprintf('(%d feeds)', $root['param']);
118
119 } else {
120 $feed_result = db_query($this->link, "SELECT id, title, last_error,
121 ".SUBSTRING_FOR_DATE."(last_updated,1,19) AS last_updated
122 FROM ttrss_feeds
123 WHERE owner_uid = ".$_SESSION["uid"].
124 "$search_qpart ORDER BY order_id, title");
125
126 while ($feed_line = db_fetch_assoc($feed_result)) {
127 $feed = array();
128 $feed['id'] = 'FEED:' . $feed_line['id'];
129 $feed['bare_id'] = $feed_line['id'];
130 $feed['name'] = $feed_line['title'];
131 $feed['checkbox'] = false;
132 $feed['error'] = $feed_line['last_error'];
133 $feed['icon'] = getFeedIcon($feed_line['id']);
134 $feed['param'] = make_local_datetime($this->link,
135 $feed_line['last_updated'], true);
136
137 array_push($root['items'], $feed);
138 }
139
140 $root['param'] = T_sprintf('(%d feeds)', count($root['items']));
141
142 }
143
144 $fl = array();
145 $fl['identifier'] = 'id';
146 $fl['label'] = 'name';
147 $fl['items'] = array($root);
148
149 print json_encode($fl);
150 return;
151 }
152
153 function catsortreset() {
154 db_query($this->link, "UPDATE ttrss_feed_categories
155 SET order_id = 0 WHERE owner_uid = " . $_SESSION["uid"]);
156 return;
157 }
158
159 function feedsortreset() {
160 db_query($this->link, "UPDATE ttrss_feeds
161 SET order_id = 0 WHERE owner_uid = " . $_SESSION["uid"]);
162 return;
163 }
164
165 function savefeedorder() {
166 $data = json_decode($_POST['payload'], true);
167
168 if (is_array($data) && is_array($data['items'])) {
169 $cat_order_id = 0;
170
171 $data_map = array();
172
173 foreach ($data['items'] as $item) {
174
175 if ($item['id'] != 'root') {
176 if (is_array($item['items'])) {
177 if (isset($item['items']['_reference'])) {
178 $data_map[$item['id']] = array($item['items']);
179 } else {
180 $data_map[$item['id']] =& $item['items'];
181 }
182 }
183 }
184 }
185
186 foreach ($data['items'][0]['items'] as $item) {
187 $id = $item['_reference'];
188 $bare_id = substr($id, strpos($id, ':')+1);
189
190 ++$cat_order_id;
191
192 if ($bare_id > 0) {
193 db_query($this->link, "UPDATE ttrss_feed_categories
194 SET order_id = '$cat_order_id' WHERE id = '$bare_id' AND
195 owner_uid = " . $_SESSION["uid"]);
196 }
197
198 $feed_order_id = 0;
199
200 if (is_array($data_map[$id])) {
201 foreach ($data_map[$id] as $feed) {
202 $id = $feed['_reference'];
203 $feed_id = substr($id, strpos($id, ':')+1);
204
205 if ($bare_id != 0)
206 $cat_query = "cat_id = '$bare_id'";
207 else
208 $cat_query = "cat_id = NULL";
209
210 db_query($this->link, "UPDATE ttrss_feeds
211 SET order_id = '$feed_order_id',
212 $cat_query
213 WHERE id = '$feed_id' AND
214 owner_uid = " . $_SESSION["uid"]);
215
216 ++$feed_order_id;
217 }
218 }
219 }
220 }
221
222 return;
223 }
224
225 function removeicon() {
226 $feed_id = db_escape_string($_REQUEST["feed_id"]);
227
228 $result = db_query($this->link, "SELECT id FROM ttrss_feeds
229 WHERE id = '$feed_id' AND owner_uid = ". $_SESSION["uid"]);
230
231 if (db_num_rows($result) != 0) {
232 unlink(ICONS_DIR . "/$feed_id.ico");
233 }
234
235 return;
236 }
237
238 function uploadicon() {
239 $icon_file = $_FILES['icon_file']['tmp_name'];
240 $feed_id = db_escape_string($_REQUEST["feed_id"]);
241
242 if (is_file($icon_file) && $feed_id) {
243 if (filesize($icon_file) < 20000) {
244
245 $result = db_query($this->link, "SELECT id FROM ttrss_feeds
246 WHERE id = '$feed_id' AND owner_uid = ". $_SESSION["uid"]);
247
248 if (db_num_rows($result) != 0) {
249 unlink(ICONS_DIR . "/$feed_id.ico");
250 move_uploaded_file($icon_file, ICONS_DIR . "/$feed_id.ico");
251 $rc = 0;
252 } else {
253 $rc = 2;
254 }
255 } else {
256 $rc = 1;
257 }
258 } else {
259 $rc = 2;
260 }
261
262 print "<script type=\"text/javascript\">";
263 print "parent.uploadIconHandler($rc);";
264 print "</script>";
265 return;
266 }
267
268 function editfeed() {
269 global $purge_intervals;
270 global $update_intervals;
271 global $update_methods;
272
273 $feed_id = db_escape_string($_REQUEST["id"]);
274
275 $result = db_query($this->link,
276 "SELECT * FROM ttrss_feeds WHERE id = '$feed_id' AND
277 owner_uid = " . $_SESSION["uid"]);
278
279 $title = htmlspecialchars(db_fetch_result($result,
280 0, "title"));
281
282 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"id\" value=\"$feed_id\">";
283 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"op\" value=\"pref-feeds\">";
284 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"method\" value=\"editSave\">";
285
286 print "<div class=\"dlgSec\">".__("Feed")."</div>";
287 print "<div class=\"dlgSecCont\">";
288
289 /* Title */
290
291 print "<input dojoType=\"dijit.form.ValidationTextBox\" required=\"1\"
292 placeHolder=\"".__("Feed Title")."\"
293 style=\"font-size : 16px; width: 20em\" name=\"title\" value=\"$title\">";
294
295 /* Feed URL */
296
297 $feed_url = db_fetch_result($result, 0, "feed_url");
298 $feed_url = htmlspecialchars(db_fetch_result($result,
299 0, "feed_url"));
300
301 print "<hr/>";
302
303 print __('URL:') . " ";
304 print "<input dojoType=\"dijit.form.ValidationTextBox\" required=\"1\"
305 placeHolder=\"".__("Feed URL")."\"
306 regExp='^(http|https)://.*' style=\"width : 20em\"
307 name=\"feed_url\" value=\"$feed_url\">";
308
309 $last_error = db_fetch_result($result, 0, "last_error");
310
311 if ($last_error) {
312 print "&nbsp;<span title=\"".htmlspecialchars($last_error)."\"
313 class=\"feed_error\">(error)</span>";
314
315 }
316
317 /* Category */
318
319 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
320
321 $cat_id = db_fetch_result($result, 0, "cat_id");
322
323 print "<hr/>";
324
325 print __('Place in category:') . " ";
326
327 print_feed_cat_select($this->link, "cat_id", $cat_id,
328 'dojoType="dijit.form.Select"');
329 }
330
331 print "</div>";
332
333 print "<div class=\"dlgSec\">".__("Update")."</div>";
334 print "<div class=\"dlgSecCont\">";
335
336 /* Update Interval */
337
338 $update_interval = db_fetch_result($result, 0, "update_interval");
339
340 print_select_hash("update_interval", $update_interval, $update_intervals,
341 'dojoType="dijit.form.Select"');
342
343 /* Update method */
344
345 $update_method = db_fetch_result($result, 0, "update_method",
346 'dojoType="dijit.form.Select"');
347
348 print " " . __('using') . " ";
349 print_select_hash("update_method", $update_method, $update_methods,
350 'dojoType="dijit.form.Select"');
351
352 $purge_interval = db_fetch_result($result, 0, "purge_interval");
353
354
355 /* Purge intl */
356
357 print "<hr/>";
358 print __('Article purging:') . " ";
359
360 print_select_hash("purge_interval", $purge_interval, $purge_intervals,
361 'dojoType="dijit.form.Select" ' .
362 ((FORCE_ARTICLE_PURGE == 0) ? "" : 'disabled="1"'));
363
364 print "</div>";
365 print "<div class=\"dlgSec\">".__("Authentication")."</div>";
366 print "<div class=\"dlgSecCont\">";
367
368 $auth_login = htmlspecialchars(db_fetch_result($result, 0, "auth_login"));
369
370 print "<input dojoType=\"dijit.form.TextBox\" id=\"feedEditDlg_login\"
371 placeHolder=\"".__("Login")."\"
372 name=\"auth_login\" value=\"$auth_login\"><hr/>";
373
374 $auth_pass = htmlspecialchars(db_fetch_result($result, 0, "auth_pass"));
375
376 print "<input dojoType=\"dijit.form.TextBox\" type=\"password\" name=\"auth_pass\"
377 placeHolder=\"".__("Password")."\"
378 value=\"$auth_pass\">";
379
380 print "<div dojoType=\"dijit.Tooltip\" connectId=\"feedEditDlg_login\" position=\"below\">
381 ".__('<b>Hint:</b> you need to fill in your login information if your feed requires authentication, except for Twitter feeds.')."
382 </div>";
383
384 print "</div>";
385 print "<div class=\"dlgSec\">".__("Options")."</div>";
386 print "<div class=\"dlgSecCont\">";
387
388 $private = sql_bool_to_bool(db_fetch_result($result, 0, "private"));
389
390 if ($private) {
391 $checked = "checked=\"1\"";
392 } else {
393 $checked = "";
394 }
395
396 print "<input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" name=\"private\" id=\"private\"
397 $checked>&nbsp;<label for=\"private\">".__('Hide from Popular feeds')."</label>";
398
399 $rtl_content = sql_bool_to_bool(db_fetch_result($result, 0, "rtl_content"));
400
401 if ($rtl_content) {
402 $checked = "checked=\"1\"";
403 } else {
404 $checked = "";
405 }
406
407 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"rtl_content\" name=\"rtl_content\"
408 $checked>&nbsp;<label for=\"rtl_content\">".__('Right-to-left content')."</label>";
409
410 $include_in_digest = sql_bool_to_bool(db_fetch_result($result, 0, "include_in_digest"));
411
412 if ($include_in_digest) {
413 $checked = "checked=\"1\"";
414 } else {
415 $checked = "";
416 }
417
418 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"include_in_digest\"
419 name=\"include_in_digest\"
420 $checked>&nbsp;<label for=\"include_in_digest\">".__('Include in e-mail digest')."</label>";
421
422
423 $always_display_enclosures = sql_bool_to_bool(db_fetch_result($result, 0, "always_display_enclosures"));
424
425 if ($always_display_enclosures) {
426 $checked = "checked";
427 } else {
428 $checked = "";
429 }
430
431 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"always_display_enclosures\"
432 name=\"always_display_enclosures\"
433 $checked>&nbsp;<label for=\"always_display_enclosures\">".__('Always display image attachments')."</label>";
434
435
436 $cache_images = sql_bool_to_bool(db_fetch_result($result, 0, "cache_images"));
437
438 if ($cache_images) {
439 $checked = "checked=\"1\"";
440 } else {
441 $checked = "";
442 }
443
444 if (SIMPLEPIE_CACHE_IMAGES) {
445 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"cache_images\"
446 name=\"cache_images\"
447 $checked>&nbsp;<label for=\"cache_images\">".
448 __('Cache images locally (SimplePie only)')."</label>";
449 }
450
451 $mark_unread_on_update = sql_bool_to_bool(db_fetch_result($result, 0, "mark_unread_on_update"));
452
453 if ($mark_unread_on_update) {
454 $checked = "checked";
455 } else {
456 $checked = "";
457 }
458
459 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"mark_unread_on_update\"
460 name=\"mark_unread_on_update\"
461 $checked>&nbsp;<label for=\"mark_unread_on_update\">".__('Mark updated articles as unread')."</label>";
462
463 $update_on_checksum_change = sql_bool_to_bool(db_fetch_result($result, 0, "update_on_checksum_change"));
464
465 if ($update_on_checksum_change) {
466 $checked = "checked";
467 } else {
468 $checked = "";
469 }
470
471 print "<hr/><input dojoType=\"dijit.form.CheckBox\" type=\"checkbox\" id=\"update_on_checksum_change\"
472 name=\"update_on_checksum_change\"
473 $checked>&nbsp;<label for=\"update_on_checksum_change\">".__('Mark posts as updated on content change')."</label>";
474
475 print "</div>";
476
477 /* Icon */
478
479 print "<div class=\"dlgSec\">".__("Icon")."</div>";
480 print "<div class=\"dlgSecCont\">";
481
482 print "<iframe name=\"icon_upload_iframe\"
483 style=\"width: 400px; height: 100px; display: none;\"></iframe>";
484
485 print "<form style='display : block' target=\"icon_upload_iframe\"
486 enctype=\"multipart/form-data\" method=\"POST\"
487 action=\"backend.php\">
488 <input id=\"icon_file\" size=\"10\" name=\"icon_file\" type=\"file\">
489 <input type=\"hidden\" name=\"op\" value=\"pref-feeds\">
490 <input type=\"hidden\" name=\"feed_id\" value=\"$feed_id\">
491 <input type=\"hidden\" name=\"method\" value=\"uploadicon\">
492 <button dojoType=\"dijit.form.Button\" onclick=\"return uploadFeedIcon();\"
493 type=\"submit\">".__('Replace')."</button>
494 <button dojoType=\"dijit.form.Button\" onclick=\"return removeFeedIcon($feed_id);\"
495 type=\"submit\">".__('Remove')."</button>
496 </form>";
497
498 print "</div>";
499
500 $title = htmlspecialchars($title, ENT_QUOTES);
501
502 print "<div class='dlgButtons'>
503 <div style=\"float : left\">
504 <button dojoType=\"dijit.form.Button\" onclick='return unsubscribeFeed($feed_id, \"$title\")'>".
505 __('Unsubscribe')."</button>";
506
507 if (PUBSUBHUBBUB_ENABLED) {
508 $pubsub_state = db_fetch_result($result, 0, "pubsub_state");
509 $pubsub_btn_disabled = ($pubsub_state == 2) ? "" : "disabled=\"1\"";
510
511 print "<button dojoType=\"dijit.form.Button\" id=\"pubsubReset_Btn\" $pubsub_btn_disabled
512 onclick='return resetPubSub($feed_id, \"$title\")'>".__('Resubscribe to push updates').
513 "</button>";
514 }
515
516 print "</div>";
517
518 print "<div dojoType=\"dijit.Tooltip\" connectId=\"pubsubReset_Btn\" position=\"below\">".
519 __('Resets PubSubHubbub subscription status for push-enabled feeds.')."</div>";
520
521 print "<button dojoType=\"dijit.form.Button\" onclick=\"return dijit.byId('feedEditDlg').execute()\">".__('Save')."</button>
522 <button dojoType=\"dijit.form.Button\" onclick=\"return dijit.byId('feedEditDlg').hide()\">".__('Cancel')."</button>
523 </div>";
524
525 return;
526 }
527
528 function editfeeds() {
529 global $purge_intervals;
530 global $update_intervals;
531 global $update_methods;
532
533 $feed_ids = db_escape_string($_REQUEST["ids"]);
534
535 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"ids\" value=\"$feed_ids\">";
536 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"op\" value=\"pref-feeds\">";
537 print "<input dojoType=\"dijit.form.TextBox\" style=\"display : none\" name=\"method\" value=\"batchEditSave\">";
538
539 print "<div class=\"dlgSec\">".__("Feed")."</div>";
540 print "<div class=\"dlgSecCont\">";
541
542 /* Title */
543
544 print "<input dojoType=\"dijit.form.ValidationTextBox\"
545 disabled=\"1\" style=\"font-size : 16px; width : 20em;\" required=\"1\"
546 name=\"title\" value=\"$title\">";
547
548 $this->batch_edit_cbox("title");
549
550 /* Feed URL */
551
552 print "<br/>";
553
554 print __('URL:') . " ";
555 print "<input dojoType=\"dijit.form.ValidationTextBox\" disabled=\"1\"
556 required=\"1\" regExp='^(http|https)://.*' style=\"width : 20em\"
557 name=\"feed_url\" value=\"$feed_url\">";
558
559 $this->batch_edit_cbox("feed_url");
560
561 /* Category */
562
563 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
564
565 print "<br/>";
566
567 print __('Place in category:') . " ";
568
569 print_feed_cat_select($this->link, "cat_id", $cat_id,
570 'disabled="1" dojoType="dijit.form.Select"');
571
572 $this->batch_edit_cbox("cat_id");
573
574 }
575
576 print "</div>";
577
578 print "<div class=\"dlgSec\">".__("Update")."</div>";
579 print "<div class=\"dlgSecCont\">";
580
581 /* Update Interval */
582
583 print_select_hash("update_interval", $update_interval, $update_intervals,
584 'disabled="1" dojoType="dijit.form.Select"');
585
586 $this->batch_edit_cbox("update_interval");
587
588 /* Update method */
589
590 print " " . __('using') . " ";
591 print_select_hash("update_method", $update_method, $update_methods,
592 'disabled="1" dojoType="dijit.form.Select"');
593 $this->batch_edit_cbox("update_method");
594
595 /* Purge intl */
596
597 if (FORCE_ARTICLE_PURGE == 0) {
598
599 print "<br/>";
600
601 print __('Article purging:') . " ";
602
603 print_select_hash("purge_interval", $purge_interval, $purge_intervals,
604 'disabled="1" dojoType="dijit.form.Select"');
605
606 $this->batch_edit_cbox("purge_interval");
607 }
608
609 print "</div>";
610 print "<div class=\"dlgSec\">".__("Authentication")."</div>";
611 print "<div class=\"dlgSecCont\">";
612
613 print "<input dojoType=\"dijit.form.TextBox\"
614 placeHolder=\"".__("Login")."\" disabled=\"1\"
615 name=\"auth_login\" value=\"$auth_login\">";
616
617 $this->batch_edit_cbox("auth_login");
618
619 print "<br/><input dojoType=\"dijit.form.TextBox\" type=\"password\" name=\"auth_pass\"
620 placeHolder=\"".__("Password")."\" disabled=\"1\"
621 value=\"$auth_pass\">";
622
623 $this->batch_edit_cbox("auth_pass");
624
625 print "</div>";
626 print "<div class=\"dlgSec\">".__("Options")."</div>";
627 print "<div class=\"dlgSecCont\">";
628
629 print "<input disabled=\"1\" type=\"checkbox\" name=\"private\" id=\"private\"
630 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"private_l\" class='insensitive' for=\"private\">".__('Hide from Popular feeds')."</label>";
631
632 print "&nbsp;"; $this->batch_edit_cbox("private", "private_l");
633
634 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"rtl_content\" name=\"rtl_content\"
635 dojoType=\"dijit.form.CheckBox\">&nbsp;<label class='insensitive' id=\"rtl_content_l\" for=\"rtl_content\">".__('Right-to-left content')."</label>";
636
637 print "&nbsp;"; $this->batch_edit_cbox("rtl_content", "rtl_content_l");
638
639 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"include_in_digest\"
640 name=\"include_in_digest\"
641 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"include_in_digest_l\" class='insensitive' for=\"include_in_digest\">".__('Include in e-mail digest')."</label>";
642
643 print "&nbsp;"; $this->batch_edit_cbox("include_in_digest", "include_in_digest_l");
644
645 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"always_display_enclosures\"
646 name=\"always_display_enclosures\"
647 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"always_display_enclosures_l\" class='insensitive' for=\"always_display_enclosures\">".__('Always display image attachments')."</label>";
648
649 print "&nbsp;"; $this->batch_edit_cbox("always_display_enclosures", "always_display_enclosures_l");
650
651 if (SIMPLEPIE_CACHE_IMAGES) {
652 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"cache_images\"
653 name=\"cache_images\"
654 dojoType=\"dijit.form.CheckBox\">&nbsp;<label class='insensitive' id=\"cache_images_l\"
655 for=\"cache_images\">".
656 __('Cache images locally')."</label>";
657
658
659 print "&nbsp;"; $this->batch_edit_cbox("cache_images", "cache_images_l");
660 }
661
662 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"mark_unread_on_update\"
663 name=\"mark_unread_on_update\"
664 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"mark_unread_on_update_l\" class='insensitive' for=\"mark_unread_on_update\">".__('Mark updated articles as unread')."</label>";
665
666 print "&nbsp;"; $this->batch_edit_cbox("mark_unread_on_update", "mark_unread_on_update_l");
667
668 print "<br/><input disabled=\"1\" type=\"checkbox\" id=\"update_on_checksum_change\"
669 name=\"update_on_checksum_change\"
670 dojoType=\"dijit.form.CheckBox\">&nbsp;<label id=\"update_on_checksum_change_l\" class='insensitive' for=\"update_on_checksum_change\">".__('Mark posts as updated on content change')."</label>";
671
672 print "&nbsp;"; $this->batch_edit_cbox("update_on_checksum_change", "update_on_checksum_change_l");
673
674 print "</div>";
675
676 print "<div class='dlgButtons'>
677 <button dojoType=\"dijit.form.Button\"
678 onclick=\"return dijit.byId('feedEditDlg').execute()\">".
679 __('Save')."</button>
680 <button dojoType=\"dijit.form.Button\"
681 onclick=\"return dijit.byId('feedEditDlg').hide()\">".
682 __('Cancel')."</button>
683 </div>";
684
685 return;
686 }
687
688 function batchEditSave() {
689 return editsaveops(true);
690 }
691
692 function editSave() {
693 return editsaveops(false);
694 }
695
696 function editsaveops($batch) {
697
698 $feed_title = db_escape_string(trim($_POST["title"]));
699 $feed_link = db_escape_string(trim($_POST["feed_url"]));
700 $upd_intl = (int) db_escape_string($_POST["update_interval"]);
701 $purge_intl = (int) db_escape_string($_POST["purge_interval"]);
702 $feed_id = (int) db_escape_string($_POST["id"]); /* editSave */
703 $feed_ids = db_escape_string($_POST["ids"]); /* batchEditSave */
704 $cat_id = (int) db_escape_string($_POST["cat_id"]);
705 $auth_login = db_escape_string(trim($_POST["auth_login"]));
706 $auth_pass = db_escape_string(trim($_POST["auth_pass"]));
707 $private = checkbox_to_sql_bool(db_escape_string($_POST["private"]));
708 $rtl_content = checkbox_to_sql_bool(db_escape_string($_POST["rtl_content"]));
709 $include_in_digest = checkbox_to_sql_bool(
710 db_escape_string($_POST["include_in_digest"]));
711 $cache_images = checkbox_to_sql_bool(
712 db_escape_string($_POST["cache_images"]));
713 $update_method = (int) db_escape_string($_POST["update_method"]);
714
715 $always_display_enclosures = checkbox_to_sql_bool(
716 db_escape_string($_POST["always_display_enclosures"]));
717
718 $mark_unread_on_update = checkbox_to_sql_bool(
719 db_escape_string($_POST["mark_unread_on_update"]));
720
721 $update_on_checksum_change = checkbox_to_sql_bool(
722 db_escape_string($_POST["update_on_checksum_change"]));
723
724 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
725 if ($cat_id && $cat_id != 0) {
726 $category_qpart = "cat_id = '$cat_id',";
727 $category_qpart_nocomma = "cat_id = '$cat_id'";
728 } else {
729 $category_qpart = 'cat_id = NULL,';
730 $category_qpart_nocomma = 'cat_id = NULL';
731 }
732 } else {
733 $category_qpart = "";
734 $category_qpart_nocomma = "";
735 }
736
737 if (SIMPLEPIE_CACHE_IMAGES) {
738 $cache_images_qpart = "cache_images = $cache_images,";
739 } else {
740 $cache_images_qpart = "";
741 }
742
743 if ($method == "editSave") {
744
745 $result = db_query($this->link, "UPDATE ttrss_feeds SET
746 $category_qpart
747 title = '$feed_title', feed_url = '$feed_link',
748 update_interval = '$upd_intl',
749 purge_interval = '$purge_intl',
750 auth_login = '$auth_login',
751 auth_pass = '$auth_pass',
752 private = $private,
753 rtl_content = $rtl_content,
754 $cache_images_qpart
755 include_in_digest = $include_in_digest,
756 always_display_enclosures = $always_display_enclosures,
757 mark_unread_on_update = $mark_unread_on_update,
758 update_on_checksum_change = $update_on_checksum_change,
759 update_method = '$update_method'
760 WHERE id = '$feed_id' AND owner_uid = " . $_SESSION["uid"]);
761
762 } else if ($batch) {
763 $feed_data = array();
764
765 foreach (array_keys($_POST) as $k) {
766 if ($k != "op" && $k != "method" && $k != "ids") {
767 $feed_data[$k] = $_POST[$k];
768 }
769 }
770
771 db_query($this->link, "BEGIN");
772
773 foreach (array_keys($feed_data) as $k) {
774
775 $qpart = "";
776
777 switch ($k) {
778 case "title":
779 $qpart = "title = '$feed_title'";
780 break;
781
782 case "feed_url":
783 $qpart = "feed_url = '$feed_link'";
784 break;
785
786 case "update_interval":
787 $qpart = "update_interval = '$upd_intl'";
788 break;
789
790 case "purge_interval":
791 $qpart = "purge_interval = '$purge_intl'";
792 break;
793
794 case "auth_login":
795 $qpart = "auth_login = '$auth_login'";
796 break;
797
798 case "auth_pass":
799 $qpart = "auth_pass = '$auth_pass'";
800 break;
801
802 case "private":
803 $qpart = "private = '$private'";
804 break;
805
806 case "include_in_digest":
807 $qpart = "include_in_digest = '$include_in_digest'";
808 break;
809
810 case "always_display_enclosures":
811 $qpart = "always_display_enclosures = '$always_display_enclosures'";
812 break;
813
814 case "mark_unread_on_update":
815 $qpart = "mark_unread_on_update = '$mark_unread_on_update'";
816 break;
817
818 case "update_on_checksum_change":
819 $qpart = "update_on_checksum_change = '$update_on_checksum_change'";
820 break;
821
822 case "cache_images":
823 $qpart = "cache_images = '$cache_images'";
824 break;
825
826 case "rtl_content":
827 $qpart = "rtl_content = '$rtl_content'";
828 break;
829
830 case "update_method":
831 $qpart = "update_method = '$update_method'";
832 break;
833
834 case "cat_id":
835 $qpart = $category_qpart_nocomma;
836 break;
837
838 }
839
840 if ($qpart) {
841 db_query($this->link,
842 "UPDATE ttrss_feeds SET $qpart WHERE id IN ($feed_ids)
843 AND owner_uid = " . $_SESSION["uid"]);
844 print "<br/>";
845 }
846 }
847
848 db_query($this->link, "COMMIT");
849 }
850 return;
851 }
852
853 function resetPubSub() {
854
855 $ids = db_escape_string($_REQUEST["ids"]);
856
857 db_query($this->link, "UPDATE ttrss_feeds SET pubsub_state = 0 WHERE id IN ($ids)
858 AND owner_uid = " . $_SESSION["uid"]);
859
860 return;
861 }
862
863 function remove() {
864
865 $ids = split(",", db_escape_string($_REQUEST["ids"]));
866
867 foreach ($ids as $id) {
868 remove_feed($this->link, $id, $_SESSION["uid"]);
869 }
870
871 return;
872 }
873
874 function clear() {
875 $id = db_escape_string($_REQUEST["id"]);
876 clear_feed_articles($this->link, $id);
877 }
878
879 function rescore() {
880 $ids = split(",", db_escape_string($_REQUEST["ids"]));
881
882 foreach ($ids as $id) {
883
884 $filters = load_filters($this->link, $id, $_SESSION["uid"], 6);
885
886 $result = db_query($this->link, "SELECT
887 title, content, link, ref_id, author,".
888 SUBSTRING_FOR_DATE."(updated, 1, 19) AS updated
889 FROM
890 ttrss_user_entries, ttrss_entries
891 WHERE ref_id = id AND feed_id = '$id' AND
892 owner_uid = " .$_SESSION['uid']."
893 ");
894
895 $scores = array();
896
897 while ($line = db_fetch_assoc($result)) {
898
899 $tags = get_article_tags($this->link, $line["ref_id"]);
900
901 $article_filters = get_article_filters($filters, $line['title'],
902 $line['content'], $line['link'], strtotime($line['updated']),
903 $line['author'], $tags);
904
905 $new_score = calculate_article_score($article_filters);
906
907 if (!$scores[$new_score]) $scores[$new_score] = array();
908
909 array_push($scores[$new_score], $line['ref_id']);
910 }
911
912 foreach (array_keys($scores) as $s) {
913 if ($s > 1000) {
914 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
915 marked = true WHERE
916 ref_id IN (" . join(',', $scores[$s]) . ")");
917 } else if ($s < -500) {
918 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
919 unread = false WHERE
920 ref_id IN (" . join(',', $scores[$s]) . ")");
921 } else {
922 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s' WHERE
923 ref_id IN (" . join(',', $scores[$s]) . ")");
924 }
925 }
926 }
927
928 print __("All done.");
929
930 }
931
932 function rescoreAll() {
933
934 $result = db_query($this->link,
935 "SELECT id FROM ttrss_feeds WHERE owner_uid = " . $_SESSION['uid']);
936
937 while ($feed_line = db_fetch_assoc($result)) {
938
939 $id = $feed_line["id"];
940
941 $filters = load_filters($this->link, $id, $_SESSION["uid"], 6);
942
943 $tmp_result = db_query($this->link, "SELECT
944 title, content, link, ref_id, author,".
945 SUBSTRING_FOR_DATE."(updated, 1, 19) AS updated
946 FROM
947 ttrss_user_entries, ttrss_entries
948 WHERE ref_id = id AND feed_id = '$id' AND
949 owner_uid = " .$_SESSION['uid']."
950 ");
951
952 $scores = array();
953
954 while ($line = db_fetch_assoc($tmp_result)) {
955
956 $tags = get_article_tags($this->link, $line["ref_id"]);
957
958 $article_filters = get_article_filters($filters, $line['title'],
959 $line['content'], $line['link'], strtotime($line['updated']),
960 $line['author'], $tags);
961
962 $new_score = calculate_article_score($article_filters);
963
964 if (!$scores[$new_score]) $scores[$new_score] = array();
965
966 array_push($scores[$new_score], $line['ref_id']);
967 }
968
969 foreach (array_keys($scores) as $s) {
970 if ($s > 1000) {
971 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s',
972 marked = true WHERE
973 ref_id IN (" . join(',', $scores[$s]) . ")");
974 } else {
975 db_query($this->link, "UPDATE ttrss_user_entries SET score = '$s' WHERE
976 ref_id IN (" . join(',', $scores[$s]) . ")");
977 }
978 }
979 }
980
981 print __("All done.");
982
983 }
984
985 function add() {
986 $feed_url = db_escape_string(trim($_REQUEST["feed_url"]));
987 $cat_id = db_escape_string($_REQUEST["cat_id"]);
988 $p_from = db_escape_string($_REQUEST["from"]);
989
990 /* only read authentication information from POST */
991
992 $auth_login = db_escape_string(trim($_POST["auth_login"]));
993 $auth_pass = db_escape_string(trim($_POST["auth_pass"]));
994
995 if ($p_from != 'tt-rss') {
996 header("Content-Type: text/html");
997 print "<html>
998 <head>
999 <title>Tiny Tiny RSS</title>
1000 <link rel=\"stylesheet\" type=\"text/css\" href=\"utility.css\">
1001 </head>
1002 <body>
1003 <img class=\"floatingLogo\" src=\"images/ttrss_logo.png\"
1004 alt=\"Tiny Tiny RSS\"/>
1005 <h1>Subscribe to feed...</h1>";
1006 }
1007
1008 $rc = subscribe_to_feed($this->link, $feed_url, $cat_id, $auth_login, $auth_pass);
1009
1010 switch ($rc) {
1011 case 1:
1012 print_notice(T_sprintf("Subscribed to <b>%s</b>.", $feed_url));
1013 break;
1014 case 2:
1015 print_error(T_sprintf("Could not subscribe to <b>%s</b>.", $feed_url));
1016 break;
1017 case 3:
1018 print_error(T_sprintf("No feeds found in <b>%s</b>.", $feed_url));
1019 break;
1020 case 0:
1021 print_warning(T_sprintf("Already subscribed to <b>%s</b>.", $feed_url));
1022 break;
1023 case 4:
1024 print_notice("Multiple feed URLs found.");
1025
1026 $feed_urls = get_feeds_from_html($feed_url);
1027 break;
1028 case 5:
1029 print_error(T_sprintf("Could not subscribe to <b>%s</b>.<br>Can't download the Feed URL.", $feed_url));
1030 break;
1031 }
1032
1033 if ($p_from != 'tt-rss') {
1034
1035 if ($feed_urls) {
1036
1037 print "<form action=\"backend.php\">";
1038 print "<input type=\"hidden\" name=\"op\" value=\"pref-feeds\">";
1039 print "<input type=\"hidden\" name=\"quiet\" value=\"1\">";
1040 print "<input type=\"hidden\" name=\"method\" value=\"add\">";
1041
1042 print "<select name=\"feed_url\">";
1043
1044 foreach ($feed_urls as $url => $name) {
1045 $url = htmlspecialchars($url);
1046 $name = htmlspecialchars($name);
1047
1048 print "<option value=\"$url\">$name</option>";
1049 }
1050
1051 print "<input type=\"submit\" value=\"".__("Subscribe to selected feed").
1052 "\">";
1053
1054 print "</form>";
1055 }
1056
1057 $tp_uri = get_self_url_prefix() . "/prefs.php";
1058 $tt_uri = get_self_url_prefix();
1059
1060 if ($rc <= 2){
1061 $result = db_query($this->link, "SELECT id FROM ttrss_feeds WHERE
1062 feed_url = '$feed_url' AND owner_uid = " . $_SESSION["uid"]);
1063
1064 $feed_id = db_fetch_result($result, 0, "id");
1065 } else {
1066 $feed_id = 0;
1067 }
1068 print "<p>";
1069
1070 if ($feed_id) {
1071 print "<form method=\"GET\" style='display: inline'
1072 action=\"$tp_uri\">
1073 <input type=\"hidden\" name=\"tab\" value=\"feedConfig\">
1074 <input type=\"hidden\" name=\"method\" value=\"editFeed\">
1075 <input type=\"hidden\" name=\"methodparam\" value=\"$feed_id\">
1076 <input type=\"submit\" value=\"".__("Edit subscription options")."\">
1077 </form>";
1078 }
1079
1080 print "<form style='display: inline' method=\"GET\" action=\"$tt_uri\">
1081 <input type=\"submit\" value=\"".__("Return to Tiny Tiny RSS")."\">
1082 </form></p>";
1083
1084 print "</body></html>";
1085 return;
1086 }
1087 }
1088
1089 function categorize() {
1090 $ids = split(",", db_escape_string($_REQUEST["ids"]));
1091
1092 $cat_id = db_escape_string($_REQUEST["cat_id"]);
1093
1094 if ($cat_id == 0) {
1095 $cat_id_qpart = 'NULL';
1096 } else {
1097 $cat_id_qpart = "'$cat_id'";
1098 }
1099
1100 db_query($this->link, "BEGIN");
1101
1102 foreach ($ids as $id) {
1103
1104 db_query($this->link, "UPDATE ttrss_feeds SET cat_id = $cat_id_qpart
1105 WHERE id = '$id'
1106 AND owner_uid = " . $_SESSION["uid"]);
1107
1108 }
1109
1110 db_query($this->link, "COMMIT");
1111 }
1112
1113 function editCats() {
1114
1115 $action = $_REQUEST["action"];
1116
1117 if ($action == "save") {
1118
1119 $cat_title = db_escape_string(trim($_REQUEST["value"]));
1120 $cat_id = db_escape_string($_REQUEST["cid"]);
1121
1122 db_query($this->link, "BEGIN");
1123
1124 $result = db_query($this->link, "SELECT title FROM ttrss_feed_categories
1125 WHERE id = '$cat_id' AND owner_uid = ".$_SESSION["uid"]);
1126
1127 if (db_num_rows($result) == 1) {
1128
1129 $old_title = db_fetch_result($result, 0, "title");
1130
1131 if ($cat_title != "") {
1132 $result = db_query($this->link, "UPDATE ttrss_feed_categories SET
1133 title = '$cat_title' WHERE id = '$cat_id' AND
1134 owner_uid = ".$_SESSION["uid"]);
1135
1136 print $cat_title;
1137 } else {
1138 print $old_title;
1139 }
1140 } else {
1141 print $_REQUEST["value"];
1142 }
1143
1144 db_query($this->link, "COMMIT");
1145
1146 return;
1147
1148 }
1149
1150 if ($action == "add") {
1151
1152 $feed_cat = db_escape_string(trim($_REQUEST["cat"]));
1153
1154 if (!add_feed_category($this->link, $feed_cat))
1155 print_warning(T_sprintf("Category <b>$%s</b> already exists in the database.", $feed_cat));
1156
1157 }
1158
1159 if ($action == "remove") {
1160
1161 $ids = split(",", db_escape_string($_REQUEST["ids"]));
1162
1163 foreach ($ids as $id) {
1164 remove_feed_category($this->link, $id, $_SESSION["uid"]);
1165 }
1166 }
1167
1168 print "<div dojoType=\"dijit.Toolbar\">
1169 <input dojoType=\"dijit.form.ValidationTextBox\" required=\"1\" name=\"newcat\">
1170 <button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('feedCatEditDlg').addCategory()\">".
1171 __('Create category')."</button></div>";
1172
1173 $result = db_query($this->link, "SELECT title,id FROM ttrss_feed_categories
1174 WHERE owner_uid = ".$_SESSION["uid"]."
1175 ORDER BY title");
1176
1177 if (db_num_rows($result) != 0) {
1178
1179 print "<div class=\"prefFeedCatHolder\">";
1180
1181 print "<table width=\"100%\" class=\"prefFeedCatList\"
1182 cellspacing=\"0\" id=\"prefFeedCatList\">";
1183
1184 $lnum = 0;
1185
1186 while ($line = db_fetch_assoc($result)) {
1187
1188 $class = ($lnum % 2) ? "even" : "odd";
1189
1190 $cat_id = $line["id"];
1191 $this_row_id = "id=\"FCATR-$cat_id\"";
1192
1193 print "<tr class=\"\" $this_row_id>";
1194
1195 $edit_title = htmlspecialchars($line["title"]);
1196
1197 print "<td width='5%' align='center'><input
1198 onclick='toggleSelectRow2(this);' dojoType=\"dijit.form.CheckBox\"
1199 type=\"checkbox\"></td>";
1200
1201 print "<td>";
1202
1203 print "<span dojoType=\"dijit.InlineEditBox\"
1204 width=\"300px\" autoSave=\"false\"
1205 cat-id=\"$cat_id\">" . $edit_title .
1206 "<script type=\"dojo/method\" event=\"onChange\" args=\"item\">
1207 var elem = this;
1208 dojo.xhrPost({
1209 url: 'backend.php',
1210 content: {op: 'pref-feeds', method: 'editCats',
1211 action: 'save',
1212 value: this.value,
1213 cid: this.srcNodeRef.getAttribute('cat-id')},
1214 load: function(response) {
1215 elem.attr('value', response);
1216 updateFeedList();
1217 }
1218 });
1219 </script>
1220 </span>";
1221
1222 print "</td></tr>";
1223
1224 ++$lnum;
1225 }
1226
1227 print "</table>";
1228 print "</div>";
1229
1230 } else {
1231 print "<p>".__('No feed categories defined.')."</p>";
1232 }
1233
1234 print "<div class='dlgButtons'>
1235 <div style='float : left'>
1236 <button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('feedCatEditDlg').removeSelected()\">".
1237 __('Remove selected categories')."</button>
1238 </div>";
1239
1240 print "<button dojoType=\"dijit.form.Button\" onclick=\"dijit.byId('feedCatEditDlg').hide()\">".
1241 __('Close this window')."</button></div>";
1242
1243 return;
1244
1245 }
1246
1247 function index() {
1248
1249 print "<div dojoType=\"dijit.layout.AccordionContainer\" region=\"center\">";
1250 print "<div id=\"pref-feeds-feeds\" dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Feeds')."\">";
1251
1252 $result = db_query($this->link, "SELECT COUNT(id) AS num_errors
1253 FROM ttrss_feeds WHERE last_error != '' AND owner_uid = ".$_SESSION["uid"]);
1254
1255 $num_errors = db_fetch_result($result, 0, "num_errors");
1256
1257 if ($num_errors > 0) {
1258
1259 $error_button = "<button dojoType=\"dijit.form.Button\"
1260 onclick=\"showFeedsWithErrors()\" id=\"errorButton\">" .
1261 __("Feeds with errors") . "</button>";
1262 }
1263
1264 if (DB_TYPE == "pgsql") {
1265 $interval_qpart = "NOW() - INTERVAL '3 months'";
1266 } else {
1267 $interval_qpart = "DATE_SUB(NOW(), INTERVAL 3 MONTH)";
1268 }
1269
1270 $result = db_query($this->link, "SELECT COUNT(*) AS num_inactive FROM ttrss_feeds WHERE
1271 (SELECT MAX(updated) FROM ttrss_entries, ttrss_user_entries WHERE
1272 ttrss_entries.id = ref_id AND
1273 ttrss_user_entries.feed_id = ttrss_feeds.id) < $interval_qpart AND
1274 ttrss_feeds.owner_uid = ".$_SESSION["uid"]);
1275
1276 $num_inactive = db_fetch_result($result, 0, "num_inactive");
1277
1278 if ($num_inactive > 0) {
1279 $inactive_button = "<button dojoType=\"dijit.form.Button\"
1280 onclick=\"showInactiveFeeds()\">" .
1281 __("Inactive feeds") . "</button>";
1282 }
1283
1284 $feed_search = db_escape_string($_REQUEST["search"]);
1285
1286 if (array_key_exists("search", $_REQUEST)) {
1287 $_SESSION["prefs_feed_search"] = $feed_search;
1288 } else {
1289 $feed_search = $_SESSION["prefs_feed_search"];
1290 }
1291
1292 print '<div dojoType="dijit.layout.BorderContainer" gutters="false">';
1293
1294 print "<div region='top' dojoType=\"dijit.Toolbar\">"; #toolbar
1295
1296 print "<div style='float : right; padding-right : 4px;'>
1297 <input dojoType=\"dijit.form.TextBox\" id=\"feed_search\" size=\"20\" type=\"search\"
1298 value=\"$feed_search\">
1299 <button dojoType=\"dijit.form.Button\" onclick=\"updateFeedList()\">".
1300 __('Search')."</button>
1301 </div>";
1302
1303 print "<div dojoType=\"dijit.form.DropDownButton\">".
1304 "<span>" . __('Select')."</span>";
1305 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1306 print "<div onclick=\"dijit.byId('feedTree').model.setAllChecked(true)\"
1307 dojoType=\"dijit.MenuItem\">".__('All')."</div>";
1308 print "<div onclick=\"dijit.byId('feedTree').model.setAllChecked(false)\"
1309 dojoType=\"dijit.MenuItem\">".__('None')."</div>";
1310 print "</div></div>";
1311
1312 print "<div dojoType=\"dijit.form.DropDownButton\">".
1313 "<span>" . __('Feeds')."</span>";
1314 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1315 print "<div onclick=\"quickAddFeed()\"
1316 dojoType=\"dijit.MenuItem\">".__('Subscribe to feed')."</div>";
1317 print "<div onclick=\"editSelectedFeed()\"
1318 dojoType=\"dijit.MenuItem\">".__('Edit selected feeds')."</div>";
1319 print "<div onclick=\"resetFeedOrder()\"
1320 dojoType=\"dijit.MenuItem\">".__('Reset sort order')."</div>";
1321 print "</div></div>";
1322
1323 if (get_pref($this->link, 'ENABLE_FEED_CATS')) {
1324 print "<div dojoType=\"dijit.form.DropDownButton\">".
1325 "<span>" . __('Categories')."</span>";
1326 print "<div dojoType=\"dijit.Menu\" style=\"display: none;\">";
1327 print "<div onclick=\"editFeedCats()\"
1328 dojoType=\"dijit.MenuItem\">".__('Edit categories')."</div>";
1329 print "<div onclick=\"resetCatOrder()\"
1330 dojoType=\"dijit.MenuItem\">".__('Reset sort order')."</div>";
1331 print "</div></div>";
1332
1333 }
1334
1335 print $error_button;
1336 print $inactive_button;
1337
1338 print "<button dojoType=\"dijit.form.Button\" onclick=\"removeSelectedFeeds()\">"
1339 .__('Unsubscribe')."</button dojoType=\"dijit.form.Button\"> ";
1340
1341 if (defined('_ENABLE_FEED_DEBUGGING')) {
1342
1343 print "<select id=\"feedActionChooser\" onchange=\"feedActionChange()\">
1344 <option value=\"facDefault\" selected>".__('More actions...')."</option>";
1345
1346 if (FORCE_ARTICLE_PURGE == 0) {
1347 print
1348 "<option value=\"facPurge\">".__('Manual purge')."</option>";
1349 }
1350
1351 print "
1352 <option value=\"facClear\">".__('Clear feed data')."</option>
1353 <option value=\"facRescore\">".__('Rescore articles')."</option>";
1354
1355 print "</select>";
1356
1357 }
1358
1359 print "</div>"; # toolbar
1360
1361 //print '</div>';
1362 print '<div dojoType="dijit.layout.ContentPane" region="center">';
1363
1364 print "<div id=\"feedlistLoading\">
1365 <img src='images/indicator_tiny.gif'>".
1366 __("Loading, please wait...")."</div>";
1367
1368 print "<div dojoType=\"fox.PrefFeedStore\" jsId=\"feedStore\"
1369 url=\"backend.php?op=pref-feeds&method=getfeedtree\">
1370 </div>
1371 <div dojoType=\"lib.CheckBoxStoreModel\" jsId=\"feedModel\" store=\"feedStore\"
1372 query=\"{id:'root'}\" rootId=\"root\" rootLabel=\"Feeds\"
1373 childrenAttrs=\"items\" checkboxStrict=\"false\" checkboxAll=\"false\">
1374 </div>
1375 <div dojoType=\"fox.PrefFeedTree\" id=\"feedTree\"
1376 dndController=\"dijit.tree.dndSource\"
1377 betweenThreshold=\"5\"
1378 model=\"feedModel\" openOnClick=\"false\">
1379 <script type=\"dojo/method\" event=\"onClick\" args=\"item\">
1380 var id = String(item.id);
1381 var bare_id = id.substr(id.indexOf(':')+1);
1382
1383 if (id.match('FEED:')) {
1384 editFeed(bare_id);
1385 } else if (id.match('CAT:')) {
1386 editCat(bare_id, item);
1387 }
1388 </script>
1389 <script type=\"dojo/method\" event=\"onLoad\" args=\"item\">
1390 Element.hide(\"feedlistLoading\");
1391 </script>
1392 </div>";
1393
1394 print "<div dojoType=\"dijit.Tooltip\" connectId=\"feedTree\" position=\"below\">
1395 ".__('<b>Hint:</b> you can drag feeds and categories around.')."
1396 </div>";
1397
1398 print '</div>';
1399 print '</div>';
1400
1401 print "</div>"; # feeds pane
1402
1403 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('OPML')."\">";
1404
1405 print "<p>" . __("Using OPML you can export and import your feeds and Tiny Tiny RSS settings.") . " ";
1406
1407 print "<span class=\"insensitive\">" . __("Note: Only main settings profile can be migrated using OPML.") . "</span>";
1408
1409 print "</p>";
1410
1411 print "<h3>" . __("Import") . "</h3>";
1412
1413 print "<br/><iframe id=\"upload_iframe\"
1414 name=\"upload_iframe\" onload=\"opmlImportComplete(this)\"
1415 style=\"width: 400px; height: 100px; display: none;\"></iframe>";
1416
1417 print "<form name=\"opml_form\" style='display : block' target=\"upload_iframe\"
1418 enctype=\"multipart/form-data\" method=\"POST\"
1419 action=\"backend.php\">
1420 <input id=\"opml_file\" name=\"opml_file\" type=\"file\">&nbsp;
1421 <input type=\"hidden\" name=\"op\" value=\"dlg\">
1422 <input type=\"hidden\" name=\"id\" value=\"importOpml\">
1423 <button dojoType=\"dijit.form.Button\" onclick=\"return opmlImport();\" type=\"submit\">" .
1424 __('Import') . "</button>";
1425
1426 print "<h3>" . __("Export") . "</h3>";
1427
1428 print "<p>" . __('Filename:') .
1429 " <input type=\"text\" id=\"filename\" value=\"TinyTinyRSS.opml\" />&nbsp;" .
1430 __('Include settings') . "<input type=\"checkbox\" id=\"settings\" CHECKED />" .
1431
1432 "<button dojoType=\"dijit.form.Button\"
1433 onclick=\"gotoExportOpml(document.opml_form.filename.value, document.opml_form.settings.checked)\" >" .
1434 __('Export') . "</button></p></form>";
1435
1436 print "<h3>" . __("Publish") . "</h3>";
1437
1438 print "<p>".__('Your OPML can be published publicly and can be subscribed by anyone who knows the URL below.') . " ";
1439
1440 print "<span class=\"insensitive\">" . __("Note: Published OPML does not include your Tiny Tiny RSS settings, feeds that require authentication or feeds hidden from Popular feeds.") . "</span>" . "</p>";
1441
1442 print "<button dojoType=\"dijit.form.Button\" onclick=\"return displayDlg('pubOPMLUrl')\">".
1443 __('Display URL')."</button> ";
1444
1445
1446 print "</div>"; # pane
1447
1448 if (strpos($_SERVER['HTTP_USER_AGENT'], "Firefox") !== false) {
1449
1450 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Firefox integration')."\">";
1451
1452 print "<p>" . __('This Tiny Tiny RSS site can be used as a Firefox Feed Reader by clicking the link below.') . "</p>";
1453
1454 print "<p>";
1455
1456 print "<button onclick='window.navigator.registerContentHandler(" .
1457 "\"application/vnd.mozilla.maybe.feed\", " .
1458 "\"" . add_feed_url() . "\", " . " \"Tiny Tiny RSS\")'>" .
1459 __('Click here to register this site as a feed reader.') .
1460 "</button>";
1461
1462 print "</p>";
1463
1464 print "</div>"; # pane
1465 }
1466
1467 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Subscribing using bookmarklet')."\">";
1468
1469 print "<p>" . __("Drag the link below to your browser toolbar, open the feed you're interested in in your browser and click on the link to subscribe to it.") . "</p>";
1470
1471 $bm_subscribe_url = str_replace('%s', '', add_feed_url());
1472
1473 $confirm_str = __('Subscribe to %s in Tiny Tiny RSS?');
1474
1475 $bm_url = htmlspecialchars("javascript:{if(confirm('$confirm_str'.replace('%s',window.location.href)))window.location.href='$bm_subscribe_url'+window.location.href}");
1476
1477 print "<a href=\"$bm_url\" class='bookmarklet'>" . __('Subscribe in Tiny Tiny RSS'). "</a>";
1478
1479 print "</div>"; #pane
1480
1481 print "<div dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Published & shared articles and generated feeds')."\">";
1482
1483 print "<h3>" . __("Published articles and generated feeds") . "</h3>";
1484
1485 print "<p>".__('Published articles are exported as a public RSS feed and can be subscribed by anyone who knows the URL specified below.')."</p>";
1486
1487 $rss_url = '-2::' . htmlspecialchars(get_self_url_prefix() .
1488 "/public.php?op=rss&id=-2&view-mode=all_articles");;
1489
1490 print "<button dojoType=\"dijit.form.Button\" onclick=\"return displayDlg('generatedFeed', '$rss_url')\">".
1491 __('Display URL')."</button> ";
1492
1493 print "<button dojoType=\"dijit.form.Button\" onclick=\"return clearFeedAccessKeys()\">".
1494 __('Clear all generated URLs')."</button> ";
1495
1496 print "<h3>" . __("Articles shared by URL") . "</h3>";
1497
1498 print "<p>" . __("You can disable all articles shared by unique URLs here.") . "</p>";
1499
1500 print "<button dojoType=\"dijit.form.Button\" onclick=\"return clearArticleAccessKeys()\">".
1501 __('Unshare all articles')."</button> ";
1502
1503 print "</div>"; #pane
1504
1505 if (defined('CONSUMER_KEY') && CONSUMER_KEY != '') {
1506
1507 print "<div id=\"pref-feeds-twitter\" dojoType=\"dijit.layout.AccordionPane\" title=\"".__('Twitter')."\">";
1508
1509 $result = db_query($this->link, "SELECT COUNT(*) AS cid FROM ttrss_users
1510 WHERE twitter_oauth IS NOT NULL AND twitter_oauth != '' AND
1511 id = " . $_SESSION['uid']);
1512
1513 $is_registered = db_fetch_result($result, 0, "cid") != 0;
1514
1515 if (!$is_registered) {
1516 print_notice(__('Before you can update your Twitter feeds, you must register this instance of Tiny Tiny RSS with Twitter.com.'));
1517 } else {
1518 print_notice(__('You have been successfully registered with Twitter.com and should be able to access your Twitter feeds.'));
1519 }
1520
1521 print "<button dojoType=\"dijit.form.Button\" onclick=\"window.location.href = 'twitter.php?op=register'\">".
1522 __("Register with Twitter.com")."</button>";
1523
1524 print " ";
1525
1526 print "<button dojoType=\"dijit.form.Button\"
1527 onclick=\"return clearTwitterCredentials()\">".
1528 __("Clear stored credentials")."</button>";
1529
1530 print "</div>"; # pane
1531
1532 }
1533
1534 print "</div>"; #container
1535
1536 }
1537}
1538?>