]> git.wh0rd.org Git - tt-rss.git/blob - prefs.js
preselect active feed cat on edit
[tt-rss.git] / prefs.js
1 var xmlhttp = false;
2
3 var active_feed_cat = false;
4 var active_label = false;
5 var active_tab = false;
6 var feed_to_expand = false;
7
8 var piggie_top = -400;
9 var piggie_fwd = true;
10
11 var xmlhttp = Ajax.getTransport();
12
13 var init_params = new Array();
14
15 function expand_feed_callback() {
16         if (xmlhttp.readyState == 4) {
17                 try {   
18                         var container = document.getElementById("BRDET-" + feed_to_expand);     
19                         container.innerHTML=xmlhttp.responseText;
20                         container.style.display = "block";
21 //                      p_notify("");
22                 } catch (e) {
23                         exception_error("expand_feed_callback", e);
24                 }
25         }
26 }
27
28 function feedlist_callback() {
29         if (xmlhttp.readyState == 4) {
30                 try {   
31                         var container = document.getElementById('prefContent'); 
32                         container.innerHTML=xmlhttp.responseText;
33                         selectTab("feedConfig", true);
34                         notify("");
35                 } catch (e) {
36                         exception_error("feedlist_callback", e);
37                 }
38         }
39 }
40
41 function filterlist_callback() {
42         var container = document.getElementById('prefContent');
43         if (xmlhttp.readyState == 4) {
44                 container.innerHTML=xmlhttp.responseText;
45                 notify("");
46         }
47 }
48
49 function labellist_callback() {
50         var container = document.getElementById('prefContent');
51         if (xmlhttp.readyState == 4) {
52                 closeInfoBox();
53                 container.innerHTML=xmlhttp.responseText;
54                 if (active_label) {
55                         var row = document.getElementById("LILRR-" + active_label);
56                         if (row) {
57                                 if (!row.className.match("Selected")) {
58                                         row.className = row.className + "Selected";
59                                 }               
60                         }
61                         var checkbox = document.getElementById("LICHK-" + active_label);
62                         
63                         if (checkbox) {
64                                 checkbox.checked = true;
65                         }
66                 }
67                 notify("");
68         }
69 }
70
71 function labeltest_callback() {
72         var container = document.getElementById('label_test_result');
73         if (xmlhttp.readyState == 4) {
74                 container.innerHTML=xmlhttp.responseText;
75                 notify("");
76         }
77 }
78
79 function feed_browser_callback() {
80         var container = document.getElementById('prefContent');
81         if (xmlhttp.readyState == 4) {
82                 container.innerHTML=xmlhttp.responseText;
83                 notify("");
84         }
85 }
86
87 function userlist_callback() {
88         var container = document.getElementById('prefContent');
89         if (xmlhttp.readyState == 4) {
90                 container.innerHTML=xmlhttp.responseText;
91                 notify("");
92         }
93 }
94
95 function prefslist_callback() {
96         var container = document.getElementById('prefContent');
97         if (xmlhttp.readyState == 4) {
98
99                 container.innerHTML=xmlhttp.responseText;
100                 
101                 notify("");
102         }
103 }
104
105 function gethelp_callback() {
106         var container = document.getElementById('prefHelpBox');
107         if (xmlhttp.readyState == 4) {
108
109                 container.innerHTML = xmlhttp.responseText;
110                 container.style.display = "block";
111
112         }
113 }
114
115
116 function notify_callback() {
117         var container = document.getElementById('notify');
118         if (xmlhttp.readyState == 4) {
119                 container.innerHTML=xmlhttp.responseText;
120         }
121 }
122
123 function updateFeedList(sort_key) {
124
125         if (!xmlhttp_ready(xmlhttp)) {
126                 printLockingError();
127                 return
128         }
129
130 //      document.getElementById("prefContent").innerHTML = "Loading feeds, please wait...";
131
132 //      p_notify("Loading, please wait...");
133
134         var feed_search = document.getElementById("feed_search");
135         var search = "";
136         if (feed_search) { search = feed_search.value; }
137
138         xmlhttp.open("GET", "backend.php?op=pref-feeds" +
139                 "&sort=" + param_escape(sort_key) + 
140                 "&search=" + param_escape(search), true);
141         xmlhttp.onreadystatechange=feedlist_callback;
142         xmlhttp.send(null);
143
144 }
145
146 function updateUsersList(sort_key) {
147
148         if (!xmlhttp_ready(xmlhttp)) {
149                 printLockingError();
150                 return
151         }
152
153 //      document.getElementById("prefContent").innerHTML = "Loading feeds, please wait...";
154
155 //      p_notify("Loading, please wait...");
156
157         xmlhttp.open("GET", "backend.php?op=pref-users&sort="
158                 + param_escape(sort_key), true);
159         xmlhttp.onreadystatechange=userlist_callback;
160         xmlhttp.send(null);
161
162 }
163
164 function addLabel() {
165
166         if (!xmlhttp_ready(xmlhttp)) {
167                 printLockingError();
168                 return
169         }
170
171         var form = document.forms['label_edit_form'];
172
173         var sql_exp = form.sql_exp.value;
174         var description = form.description.value;
175
176         if (sql_exp == "") {
177                 alert("Can't create label: missing SQL expression.");
178                 return false;
179         }
180
181         if (description == "") {
182                 alert("Can't create label: missing caption.");
183                 return false;
184         }
185
186         var query = Form.serialize("label_edit_form");
187
188         xmlhttp.open("GET", "backend.php?op=pref-labels&subop=add&" + query, true);                     
189         xmlhttp.onreadystatechange=infobox_submit_callback;
190         xmlhttp.send(null);
191 }
192
193 function addFeed() {
194
195         if (!xmlhttp_ready(xmlhttp)) {
196                 printLockingError();
197                 return
198         }
199
200         var link = document.getElementById("fadd_link");
201
202         if (link.value.length == 0) {
203                 alert("Error: No feed URL given.");
204         } else if (!isValidURL(link.value)) {
205                 alert("Error: Invalid feed URL.");
206         } else {
207                 notify("Adding feed...");
208
209                 xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=add&feed_url=" +
210                         param_escape(link.value), true);
211                 xmlhttp.onreadystatechange=feedlist_callback;
212                 xmlhttp.send(null);
213
214                 link.value = "";
215
216         }
217
218 }
219
220 function addFeedCat() {
221
222         if (!xmlhttp_ready(xmlhttp)) {
223                 printLockingError();
224                 return
225         }
226
227         var cat = document.getElementById("fadd_cat");
228
229         if (cat.value.length == 0) {
230                 alert("Can't add category: no name specified.");
231         } else {
232                 notify("Adding feed category...");
233
234                 xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editCats&action=add&cat=" +
235                         param_escape(cat.value), true);
236                 xmlhttp.onreadystatechange=infobox_callback;
237                 xmlhttp.send(null);
238
239                 link.value = "";
240
241         }
242
243 }
244 function addUser() {
245
246         if (!xmlhttp_ready(xmlhttp)) {
247                 printLockingError();
248                 return
249         }
250
251         var sqlexp = document.getElementById("uadd_box");
252
253         if (sqlexp.value.length == 0) {
254                 alert("Can't add user: no login specified.");
255         } else {
256                 notify("Adding user...");
257
258                 xmlhttp.open("GET", "backend.php?op=pref-users&subop=add&login=" +
259                         param_escape(sqlexp.value), true);                      
260                         
261                 xmlhttp.onreadystatechange=userlist_callback;
262                 xmlhttp.send(null);
263
264                 sqlexp.value = "";
265         }
266
267 }
268
269 function editLabel(id) {
270
271         if (!xmlhttp_ready(xmlhttp)) {
272                 printLockingError();
273                 return
274         }
275
276         document.getElementById("label_create_btn").disabled = true;
277
278         active_label = id;
279
280         selectTableRowsByIdPrefix('prefLabelList', 'LILRR-', 'LICHK-', false);
281         selectTableRowById('LILRR-'+id, 'LICHK-'+id, true);
282
283         xmlhttp.open("GET", "backend.php?op=pref-labels&subop=edit&id=" +
284                 param_escape(id), true);
285         xmlhttp.onreadystatechange=infobox_callback;
286         xmlhttp.send(null);
287
288 }
289
290 function editUser(id) {
291
292         if (!xmlhttp_ready(xmlhttp)) {
293                 printLockingError();
294                 return
295         }
296
297         selectTableRowsByIdPrefix('prefUserList', 'UMRR-', 'UMCHK-', false);
298         selectTableRowById('UMRR-'+id, 'UMCHK-'+id, true);
299
300         xmlhttp.open("GET", "backend.php?op=pref-users&subop=edit&id=" +
301                 param_escape(id), true);
302         xmlhttp.onreadystatechange=infobox_callback;
303         xmlhttp.send(null);
304
305 }
306
307 function editFilter(id) {
308
309         if (!xmlhttp_ready(xmlhttp)) {
310                 printLockingError();
311                 return
312         }
313
314         document.getElementById("create_filter_btn").disabled = true;
315
316         selectTableRowsByIdPrefix('prefFilterList', 'FILRR-', 'FICHK-', false);
317         selectTableRowById('FILRR-'+id, 'FICHK-'+id, true);
318
319         xmlhttp.open("GET", "backend.php?op=pref-filters&subop=edit&id=" + param_escape(id), true);
320         xmlhttp.onreadystatechange=infobox_callback;
321         xmlhttp.send(null);
322 }
323
324 function editFeed(feed) {
325
326 //      notify("Editing feed...");
327
328         if (!xmlhttp_ready(xmlhttp)) {
329                 printLockingError();
330                 return
331         }
332
333         // clean selection from all rows & select row being edited
334         selectTableRowsByIdPrefix('prefFeedList', 'FEEDR-', 'FRCHK-', false);
335         selectTableRowById('FEEDR-'+feed, 'FRCHK-'+feed, true);
336
337         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editfeed&id=" +
338                 param_escape(feed), true);
339
340         xmlhttp.onreadystatechange=infobox_callback;
341         xmlhttp.send(null);
342
343 }
344
345 function editFeedCat(cat) {
346
347         if (!xmlhttp_ready(xmlhttp)) {
348                 printLockingError();
349                 return
350         }
351
352         active_feed_cat = cat;
353
354         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editCats&action=edit&id=" +
355                 param_escape(cat), true);
356         xmlhttp.onreadystatechange=infobox_callback;
357         xmlhttp.send(null);
358
359 }
360
361 function getSelectedLabels() {
362         return getSelectedTableRowIds("prefLabelList", "LILRR");
363 }
364
365 function getSelectedUsers() {
366         return getSelectedTableRowIds("prefUserList", "UMRR");
367 }
368
369 function getSelectedFeeds() {
370         return getSelectedTableRowIds("prefFeedList", "FEEDR");
371 }
372
373 function getSelectedFilters() {
374         return getSelectedTableRowIds("prefFilterList", "FILRR");
375 }
376
377 function getSelectedFeedCats() {
378         return getSelectedTableRowIds("prefFeedCatList", "FCATR");
379 }
380
381 function getSelectedFeedsFromBrowser() {
382
383         var list = document.getElementById("browseFeedList");
384         if (!list) list = document.getElementById("browseBigFeedList");
385
386         var selected = new Array();
387         
388         for (i = 0; i < list.childNodes.length; i++) {
389                 var child = list.childNodes[i];
390                 if (child.id && child.id.match("FBROW-")) {
391                         var id = child.id.replace("FBROW-", "");
392                         
393                         var cb = document.getElementById("FBCHK-" + id);
394
395                         if (cb.checked) {
396                                 selected.push(id);
397                         }
398                 }
399         }
400
401         return selected;
402 }
403
404 function removeSelectedLabels() {
405
406         if (!xmlhttp_ready(xmlhttp)) {
407                 printLockingError();
408                 return
409         }
410
411         var sel_rows = getSelectedLabels();
412
413         if (sel_rows.length > 0) {
414
415                 var ok = confirm("Remove selected labels?");
416
417                 if (ok) {
418                         notify("Removing selected labels...");
419         
420                         xmlhttp.open("GET", "backend.php?op=pref-labels&subop=remove&ids="+
421                                 param_escape(sel_rows.toString()), true);
422                         xmlhttp.onreadystatechange=labellist_callback;
423                         xmlhttp.send(null);
424                 }
425         } else {
426                 alert("No labels are selected.");
427         }
428
429         return false;
430 }
431
432 function removeSelectedUsers() {
433
434         if (!xmlhttp_ready(xmlhttp)) {
435                 printLockingError();
436                 return
437         }
438
439         var sel_rows = getSelectedUsers();
440
441         if (sel_rows.length > 0) {
442
443                 var ok = confirm("Remove selected users?");
444
445                 if (ok) {
446                         notify("Removing selected users...");
447         
448                         xmlhttp.open("GET", "backend.php?op=pref-users&subop=remove&ids="+
449                                 param_escape(sel_rows.toString()), true);
450                         xmlhttp.onreadystatechange=userlist_callback;
451                         xmlhttp.send(null);
452                 }
453
454         } else {
455                 alert("No users are selected.");
456         }
457
458         return false;
459 }
460
461 function removeSelectedFilters() {
462
463         if (!xmlhttp_ready(xmlhttp)) {
464                 printLockingError();
465                 return
466         }
467
468         var sel_rows = getSelectedFilters();
469
470         if (sel_rows.length > 0) {
471
472                 var ok = confirm("Remove selected filters?");
473
474                 if (ok) {
475                         notify("Removing selected filters...");
476         
477                         xmlhttp.open("GET", "backend.php?op=pref-filters&subop=remove&ids="+
478                                 param_escape(sel_rows.toString()), true);
479                         xmlhttp.onreadystatechange=filterlist_callback;
480                         xmlhttp.send(null);
481                 }
482         } else {
483                 alert("No filters are selected.");
484         }
485
486         return false;
487 }
488
489
490 function removeSelectedFeeds() {
491
492         if (!xmlhttp_ready(xmlhttp)) {
493                 printLockingError();
494                 return
495         }
496
497         var sel_rows = getSelectedFeeds();
498
499         if (sel_rows.length > 0) {
500
501                 var ok = confirm("Unsubscribe from selected feeds?");
502
503                 if (ok) {
504
505                         notify("Unsubscribing from selected feeds...");
506         
507                         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=remove&ids="+
508                                 param_escape(sel_rows.toString()), true);
509                         xmlhttp.onreadystatechange=feedlist_callback;
510                         xmlhttp.send(null);
511                 }
512
513         } else {
514
515                 alert("No feeds are selected.");
516
517         }
518         
519         return false;
520 }
521
522 function removeSelectedFeedCats() {
523
524         if (!xmlhttp_ready(xmlhttp)) {
525                 printLockingError();
526                 return
527         }
528
529         var sel_rows = getSelectedFeedCats();
530
531         if (sel_rows.length > 0) {
532
533                 var ok = confirm("Remove selected categories?");
534
535                 if (ok) {
536                         notify("Removing selected categories...");
537         
538                         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editCats&action=remove&ids="+
539                                 param_escape(sel_rows.toString()), true);
540                         xmlhttp.onreadystatechange=infobox_callback;
541                         xmlhttp.send(null);
542                 }
543
544         } else {
545
546                 alert("No categories are selected.");
547
548         }
549
550         return false;
551 }
552
553 function feedEditCancel() {
554
555         if (!xmlhttp_ready(xmlhttp)) {
556                 printLockingError();
557                 return
558         }
559
560         closeInfoBox();
561
562         selectPrefRows('feed', false); // cleanup feed selection
563
564         return false;
565 }
566
567 function feedCatEditCancel() {
568
569         if (!xmlhttp_ready(xmlhttp)) {
570                 printLockingError();
571                 return
572         }
573
574         active_feed_cat = false;
575
576 //      notify("Operation cancelled.");
577
578         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editCats", true);
579         xmlhttp.onreadystatechange=infobox_callback;
580         xmlhttp.send(null);
581
582         return false;
583 }
584
585 function feedEditSave() {
586
587         try {
588         
589                 if (!xmlhttp_ready(xmlhttp)) {
590                         printLockingError();
591                         return
592                 }
593
594                 // FIXME: add parameter validation
595
596                 var query = Form.serialize("edit_feed_form");
597
598                 notify("Saving feed...");
599
600                 xmlhttp.open("POST", "backend.php", true);
601                 xmlhttp.onreadystatechange=feedlist_callback;
602                 xmlhttp.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
603                 xmlhttp.send(query);
604
605                 closeInfoBox();
606
607                 return false;
608
609         } catch (e) {
610                 exception_error("feedEditSave", e);
611         } 
612 }
613
614 function feedCatEditSave() {
615
616         if (!xmlhttp_ready(xmlhttp)) {
617                 printLockingError();
618                 return
619         }
620
621         notify("Saving category...");
622
623         var query = Form.serialize("feed_cat_edit_form");
624
625         xmlhttp.open("GET", "backend.php?" + query, true);
626         xmlhttp.onreadystatechange=infobox_callback;
627         xmlhttp.send(null);
628
629         active_feed_cat = false;
630
631         return false;
632 }
633
634
635 function labelTest() {
636
637         var container = document.getElementById('label_test_result');
638         container.style.display = "block";
639         container.innerHTML = "<p>Loading, please wait...</p>";
640
641         var form = document.forms['label_edit_form'];
642
643         var sql_exp = form.sql_exp.value;
644         var description = form.description.value;
645
646         xmlhttp.open("GET", "backend.php?op=pref-labels&subop=test&expr=" +
647                 param_escape(sql_exp) + "&descr=" + param_escape(description), true);
648
649         xmlhttp.onreadystatechange=labeltest_callback;
650         xmlhttp.send(null);
651
652         return false;
653 }
654
655 function displayHelpInfobox(topic_id) {
656
657         xmlhttp.open("GET", "backend.php?op=help&tid=" +
658                 param_escape(topic_id) + "&noheaders=1", true);
659
660         xmlhttp.onreadystatechange=infobox_callback;
661         xmlhttp.send(null);
662
663 }
664
665 function labelEditCancel() {
666
667         if (!xmlhttp_ready(xmlhttp)) {
668                 printLockingError();
669                 return
670         }
671
672         document.getElementById("label_create_btn").disabled = false;
673
674         active_label = false;
675
676         selectPrefRows('label', false); // cleanup feed selection
677         closeInfoBox();
678
679         return false;
680 }
681
682 function userEditCancel() {
683
684         if (!xmlhttp_ready(xmlhttp)) {
685                 printLockingError();
686                 return
687         }
688
689         selectPrefRows('user', false); // cleanup feed selection
690         closeInfoBox();
691
692         return false;
693 }
694
695 function filterEditCancel() {
696
697         if (!xmlhttp_ready(xmlhttp)) {
698                 printLockingError();
699                 return
700         }
701
702         document.getElementById("create_filter_btn").disabled = false;
703         
704         selectPrefRows('filter', false); // cleanup feed selection
705         closeInfoBox();
706
707         return false;
708 }
709
710 function labelEditSave() {
711
712         var label = active_label;
713
714         if (!xmlhttp_ready(xmlhttp)) {
715                 printLockingError();
716                 return
717         }
718
719 /*      if (!is_opera()) {
720
721                 var sql_exp = document.forms["label_edit_form"].sql_exp.value;
722                 var description = document.forms["label_edit_form"].description.value;
723         
724                 if (sql_exp.length == 0) {
725                         alert("SQL Expression cannot be blank.");
726                         return false;
727                 }
728         
729                 if (description.length == 0) {
730                         alert("Caption field cannot be blank.");
731                         return false;
732                 }
733         } */
734
735         closeInfoBox();
736
737         notify("Saving label...");
738
739         active_label = false;
740
741         query = Form.serialize("label_edit_form");
742
743         xmlhttp.open("GET", "backend.php?" + query, true);              
744         xmlhttp.onreadystatechange=labellist_callback;
745         xmlhttp.send(null);
746
747         return false;
748 }
749
750 function userEditSave() {
751
752         if (!xmlhttp_ready(xmlhttp)) {
753                 printLockingError();
754                 return
755         }
756
757         var login = document.forms["user_edit_form"].login.value;
758
759         if (login.length == 0) {
760                 alert("Login field cannot be blank.");
761                 return;
762         }
763         
764         notify("Saving user...");
765
766         closeInfoBox();
767
768         var query = Form.serialize("user_edit_form");
769         
770         xmlhttp.open("GET", "backend.php?" + query, true);                      
771         xmlhttp.onreadystatechange=userlist_callback;
772         xmlhttp.send(null);
773
774         return false;
775 }
776
777
778 function filterEditSave() {
779
780         if (!xmlhttp_ready(xmlhttp)) {
781                 printLockingError();
782                 return
783         }
784
785 /*      if (!is_opera()) {
786                 var reg_exp = document.forms["filter_edit_form"].reg_exp.value;
787         
788                 if (reg_exp.length == 0) {
789                         alert("Filter expression field cannot be blank.");
790                         return;
791                 }
792         } */
793
794         notify("Saving filter...");
795
796         var query = Form.serialize("filter_edit_form");
797
798         closeInfoBox();
799
800         document.getElementById("create_filter_btn").disabled = false;
801
802         xmlhttp.open("GET", "backend.php?" + query, true);
803         xmlhttp.onreadystatechange=filterlist_callback;
804         xmlhttp.send(null);
805
806         return false;
807 }
808
809 function editSelectedLabel() {
810         var rows = getSelectedLabels();
811
812         if (rows.length == 0) {
813                 alert("No labels are selected.");
814                 return;
815         }
816
817         if (rows.length > 1) {
818                 alert("Please select only one label.");
819                 return;
820         }
821
822         notify("");
823
824         editLabel(rows[0]);
825
826 }
827
828 function editSelectedUser() {
829         var rows = getSelectedUsers();
830
831         if (rows.length == 0) {
832                 alert("No users are selected.");
833                 return;
834         }
835
836         if (rows.length > 1) {
837                 alert("Please select only one user.");
838                 return;
839         }
840
841         notify("");
842
843         editUser(rows[0]);
844 }
845
846 function resetSelectedUserPass() {
847         var rows = getSelectedUsers();
848
849         if (rows.length == 0) {
850                 alert("No users are selected.");
851                 return;
852         }
853
854         if (rows.length > 1) {
855                 alert("Please select only one user.");
856                 return;
857         }
858
859         var ok = confirm("Reset password of selected user?");
860
861         if (ok) {
862                 notify("Resetting password for selected user...");
863         
864                 var id = rows[0];
865         
866                 xmlhttp.open("GET", "backend.php?op=pref-users&subop=resetPass&id=" +
867                         param_escape(id), true);
868                 xmlhttp.onreadystatechange=userlist_callback;
869                 xmlhttp.send(null);
870         }
871 }
872
873 function selectedUserDetails() {
874
875         if (!xmlhttp_ready(xmlhttp)) {
876                 printLockingError();
877                 return
878         }
879
880         var rows = getSelectedUsers();
881
882         if (rows.length == 0) {
883                 alert("No users are selected.");
884                 return;
885         }
886
887         if (rows.length > 1) {
888                 alert("Please select only one user.");
889                 return;
890         }
891
892         var id = rows[0];
893
894         notify("");
895
896         xmlhttp.open("GET", "backend.php?op=user-details&id=" + id, true);
897         xmlhttp.onreadystatechange=infobox_callback;
898         xmlhttp.send(null);
899
900 }
901
902 function selectedFeedDetails() {
903
904         if (!xmlhttp_ready(xmlhttp)) {
905                 printLockingError();
906                 return
907         }
908
909         var rows = getSelectedFeeds();
910
911         if (rows.length == 0) {
912                 alert("No feeds are selected.");
913                 return;
914         }
915
916         if (rows.length > 1) {
917                 notify("Please select only one feed.");
918                 return;
919         }
920
921 //      var id = rows[0];
922
923         notify("");
924
925         xmlhttp.open("GET", "backend.php?op=feed-details&id=" + 
926                 param_escape(rows.toString()), true);
927         xmlhttp.onreadystatechange=infobox_callback;
928         xmlhttp.send(null);
929
930 }
931
932 function editSelectedFilter() {
933         var rows = getSelectedFilters();
934
935         if (rows.length == 0) {
936                 alert("No filters are selected.");
937                 return;
938         }
939
940         if (rows.length > 1) {
941                 alert("Please select only one filter.");
942                 return;
943         }
944
945         notify("");
946
947         editFilter(rows[0]);
948
949 }
950
951
952 function editSelectedFeed() {
953         var rows = getSelectedFeeds();
954
955         if (rows.length == 0) {
956                 notify("No feeds are selected.");
957                 return;
958         }
959
960         if (rows.length > 1) {
961                 notify("Please select one feed.");
962                 return;
963         }
964
965         notify("");
966
967         editFeed(rows[0]);
968
969 }
970
971 function editSelectedFeedCat() {
972         var rows = getSelectedFeedCats();
973
974         if (rows.length == 0) {
975                 alert("No categories are selected.");
976                 return;
977         }
978
979         if (rows.length > 1) {
980                 alert("Please select only one category.");
981                 return;
982         }
983
984         notify("");
985
986         editFeedCat(rows[0]);
987
988 }
989
990 function piggie_callback() {
991         var piggie = document.getElementById("piggie");
992
993         piggie.style.top = piggie_top;
994         piggie.style.backgroundColor = "white";
995         piggie.style.borderWidth = "1px";
996
997         if (piggie_fwd && piggie_top < 0) {
998                 setTimeout("piggie_callback()", 50);
999                 piggie_top = piggie_top + 10;
1000         } else if (piggie_fwd && piggie_top >= 0) {
1001                 piggie_fwd = false;
1002                 setTimeout("piggie_callback()", 50);
1003         } else if (!piggie_fwd && piggie_top > -400) {
1004                 setTimeout("piggie_callback()", 50);
1005                 piggie_top = piggie_top - 10;
1006         } else if (!piggie_fwd && piggie_top <= -400) {
1007                 piggie.style.display = "none";
1008                 piggie_fwd = true;
1009         }
1010 }
1011
1012 var piggie_opacity = 0;
1013
1014 function piggie2_callback() {
1015         var piggie = document.getElementById("piggie");
1016         piggie.style.top = 0;
1017         piggie.style.opacity = piggie_opacity;
1018         piggie.style.backgroundColor = "transparent";
1019         piggie.style.borderWidth = "0px";
1020
1021         if (piggie_fwd && piggie_opacity < 1) {
1022                 setTimeout("piggie2_callback()", 50);
1023                 piggie_opacity = piggie_opacity + 0.03;
1024         } else if (piggie_fwd && piggie_opacity >= 1) {
1025                 piggie_fwd = false;
1026                 setTimeout("piggie2_callback()", 50);
1027         } else if (!piggie_fwd && piggie_opacity > 0) {
1028                 setTimeout("piggie2_callback()", 50);
1029                 piggie_opacity = piggie_opacity - 0.03;
1030         } else if (!piggie_fwd && piggie_opacity <= 0) {
1031                 piggie.style.display = "none";
1032                 piggie_fwd = true;
1033         }
1034 }
1035
1036 function localPiggieFunction(enable) {
1037         if (enable) {
1038                 debug("I LOVEDED IT!");
1039                 var piggie = document.getElementById("piggie");
1040                 piggie.style.display = "block";
1041
1042                 if (navigator.userAgent.match("Gecko") && Math.random(1) > 0.5) {       
1043                         piggie2_callback();
1044                 } else {
1045                         piggie_callback();
1046                 }
1047         }
1048 }
1049
1050 function validateOpmlImport() {
1051         
1052         var opml_file = document.getElementById("opml_file");
1053
1054         if (opml_file.value.length == 0) {
1055                 alert("No OPML file to upload.");
1056                 return false;
1057         } else {
1058                 return true;
1059         }
1060 }
1061
1062 function updateFilterList(sort_key) {
1063
1064         if (!xmlhttp_ready(xmlhttp)) {
1065                 printLockingError();
1066                 return
1067         }
1068
1069 //      document.getElementById("prefContent").innerHTML = "Loading filters, please wait...";
1070
1071 //      p_notify("Loading, please wait...");
1072
1073         xmlhttp.open("GET", "backend.php?op=pref-filters&sort=" + 
1074                 param_escape(sort_key), true);
1075         xmlhttp.onreadystatechange=filterlist_callback;
1076         xmlhttp.send(null);
1077
1078 }
1079
1080 function updateLabelList(sort_key) {
1081
1082         if (!xmlhttp_ready(xmlhttp)) {
1083                 printLockingError();
1084                 return
1085         }
1086
1087 //      p_notify("Loading, please wait...");
1088
1089 //      document.getElementById("prefContent").innerHTML = "Loading labels, please wait...";
1090
1091         xmlhttp.open("GET", "backend.php?op=pref-labels&sort=" + 
1092                 param_escape(sort_key), true);
1093         xmlhttp.onreadystatechange=labellist_callback;
1094         xmlhttp.send(null);
1095 }
1096
1097 function updatePrefsList() {
1098
1099         if (!xmlhttp_ready(xmlhttp)) {
1100                 printLockingError();
1101                 return
1102         }
1103
1104 //      p_notify("Loading, please wait...");
1105
1106         xmlhttp.open("GET", "backend.php?op=pref-prefs", true);
1107         xmlhttp.onreadystatechange=prefslist_callback;
1108         xmlhttp.send(null);
1109
1110 }
1111
1112 function selectTab(id, noupdate) {
1113
1114 //      alert(id);
1115
1116         if (!id) id = active_tab;
1117
1118         try {
1119
1120                 if (!xmlhttp_ready(xmlhttp)) {
1121                         printLockingError();
1122                         return
1123                 }
1124
1125                 if (!noupdate) {
1126
1127                         debug("selectTab: " + id + "(NU: " + noupdate + ")");
1128         
1129 //                      notify("Loading, please wait...", true);
1130         
1131                         // close active infobox if needed
1132                         closeInfoBox();
1133         
1134                         // clean up all current selections, just in case
1135                         active_feed_cat = false;
1136                         active_label = false;
1137         
1138                         if (id == "feedConfig") {
1139                                 updateFeedList();
1140                         } else if (id == "filterConfig") {
1141                                 updateFilterList();
1142                         } else if (id == "labelConfig") {
1143                                 updateLabelList();
1144                         } else if (id == "genConfig") {
1145                                 updatePrefsList();
1146                         } else if (id == "userConfig") {
1147                                 updateUsersList();
1148                         } else if (id == "feedBrowser") {
1149                                 updateBigFeedBrowser();
1150                         }
1151                 }
1152         
1153                 var tab = document.getElementById(active_tab + "Tab");
1154         
1155                 if (tab) {
1156                         if (tab.className.match("Selected")) {
1157                                 tab.className = "prefsTab";
1158                         }
1159                 }
1160         
1161                 tab = document.getElementById(id + "Tab");
1162         
1163                 if (tab) {
1164                         if (!tab.className.match("Selected")) {
1165                                 tab.className = tab.className + "Selected";
1166                         }
1167                 }
1168         
1169                 if (active_tab != id) {
1170                         storeInitParam("prefs_active_tab", id);
1171                 }
1172         
1173                 active_tab = id;
1174
1175         } catch (e) {
1176                 exception_error("selectTab", e);
1177         }
1178 }
1179
1180 function backend_sanity_check_callback() {
1181
1182         if (xmlhttp.readyState == 4) {
1183
1184                 try {
1185                 
1186                         if (!xmlhttp.responseXML) {
1187                                 fatalError(3, "[D001, Received reply is not XML]: " + xmlhttp.responseText);
1188                                 return;
1189                         }
1190         
1191                         var reply = xmlhttp.responseXML.firstChild.firstChild;
1192         
1193                         if (!reply) {
1194                                 fatalError(3, "[D002, Invalid RPC reply]: " + xmlhttp.responseText);
1195                                 return;
1196                         }
1197         
1198                         var error_code = reply.getAttribute("error-code");
1199                 
1200                         if (error_code && error_code != 0) {
1201                                 return fatalError(error_code, reply.getAttribute("error-msg"));
1202                         }
1203         
1204                         debug("sanity check ok");
1205
1206                         var params = reply.nextSibling;
1207
1208                         if (params) {
1209                                 debug('reading init-params...');
1210                                 var param = params.firstChild;
1211
1212                                 while (param) {
1213                                         var k = param.getAttribute("key");
1214                                         var v = param.getAttribute("value");
1215                                         debug(k + " => " + v);
1216                                         init_params[k] = v;                                     
1217                                         param = param.nextSibling;
1218                                 }
1219                         }
1220
1221                         init_second_stage();
1222
1223                 } catch (e) {
1224                         exception_error("backend_sanity_check_callback", e);
1225                 }
1226         } 
1227 }
1228
1229 function init_second_stage() {
1230
1231         try {
1232                 active_tab = getInitParam("prefs_active_tab");
1233                 if (!active_tab) active_tab = "genConfig";
1234
1235                 document.onkeydown = pref_hotkey_handler;
1236
1237                 if (navigator.userAgent.match("Opera")) {       
1238                         setTimeout("selectTab()", 500);
1239                 } else {
1240                         selectTab(active_tab);
1241                 }
1242                 notify("");
1243         } catch (e) {
1244                 exception_error("init_second_stage", e);
1245         }
1246 }
1247
1248 function init() {
1249
1250         try {
1251         
1252                 if (arguments.callee.done) return;
1253                 arguments.callee.done = true;           
1254
1255                 if (getURLParam('debug')) {
1256                         document.getElementById('debug_output').style.display = 'block';
1257                         debug('debug mode activated');
1258                 }
1259
1260                 // IE kludge
1261                 if (!xmlhttp) {
1262                         document.getElementById("prefContent").innerHTML = 
1263                                 "<b>Fatal error:</b> This program needs XmlHttpRequest " + 
1264                                 "to function properly. Your browser doesn't seem to support it.";
1265                         return;
1266                 }
1267
1268                 xmlhttp.open("GET", "backend.php?op=rpc&subop=sanityCheck", true);
1269                 xmlhttp.onreadystatechange=backend_sanity_check_callback;
1270                 xmlhttp.send(null);
1271
1272         } catch (e) {
1273                 exception_error("init", e);
1274         }
1275 }
1276
1277 function categorizeSelectedFeeds() {
1278
1279         if (!xmlhttp_ready(xmlhttp)) {
1280                 printLockingError();
1281                 return
1282         }
1283
1284         var sel_rows = getSelectedFeeds();
1285
1286         var cat_sel = document.getElementById("sfeed_set_fcat");
1287         var cat_id = cat_sel[cat_sel.selectedIndex].value;
1288
1289         if (sel_rows.length > 0) {
1290
1291                 notify("Changing category of selected feeds...");
1292
1293                 xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=categorize&ids="+
1294                         param_escape(sel_rows.toString()) + "&cat_id=" + param_escape(cat_id), true);
1295                 xmlhttp.onreadystatechange=feedlist_callback;
1296                 xmlhttp.send(null);
1297
1298         } else {
1299
1300                 alert("No feeds are selected.");
1301
1302         }
1303
1304 }
1305
1306 function validatePrefsReset() {
1307         return confirm("Reset to defaults?");
1308 }
1309
1310 function browseFeeds(limit) {
1311
1312         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=browse", true);
1313         xmlhttp.onreadystatechange=infobox_callback;
1314         xmlhttp.send(null);
1315
1316 }
1317
1318 function feedBrowserSubscribe() {
1319         try {
1320
1321                 var selected = getSelectedFeedsFromBrowser();
1322
1323                 if (selected.length > 0) {
1324                         closeInfoBox();
1325                         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=massSubscribe&ids="+
1326                                 param_escape(selected.toString()), true);
1327                         xmlhttp.onreadystatechange=feedlist_callback;
1328                         xmlhttp.send(null);
1329                 } else {
1330                         alert("No feeds are selected.");
1331                 }
1332
1333         } catch (e) {
1334                 exception_error("feedBrowserSubscribe", e);
1335         }
1336 }
1337
1338 function updateBigFeedBrowser(limit) {
1339
1340         if (!xmlhttp_ready(xmlhttp)) {
1341                 printLockingError();
1342                 return
1343         }
1344
1345 //      p_notify("Loading, please wait...");
1346
1347         var query = "backend.php?op=pref-feed-browser";
1348
1349         var limit_sel = document.getElementById("feedBrowserLimit");
1350
1351         if (limit_sel) {
1352                 var limit = limit_sel[limit_sel.selectedIndex].value;
1353                 query = query + "&limit=" + param_escape(limit);
1354         }
1355
1356         xmlhttp.open("GET", query, true);
1357         xmlhttp.onreadystatechange=feed_browser_callback;
1358         xmlhttp.send(null);
1359 }
1360
1361 function browserToggleExpand(id) {
1362         try {
1363 /*              if (feed_to_expand && feed_to_expand != id) {
1364                         var d = document.getElementById("BRDET-" + feed_to_expand);
1365                         d.style.display = "none";
1366                 } */
1367
1368                 if (!xmlhttp_ready(xmlhttp)) {
1369                         printLockingError();
1370                         return
1371                 }
1372
1373                 var d = document.getElementById("BRDET-" + id);
1374
1375                 if (d.style.display == "block") {               
1376                         d.style.display = "none";
1377                         
1378                 } else {
1379         
1380                         feed_to_expand = id;
1381
1382                         d.style.display = "block";
1383                         d.innerHTML = "Loading, please wait...";
1384
1385                         xmlhttp.open("GET", "backend.php?op=pref-feed-browser&subop=details&id="
1386                                 + param_escape(id), true);
1387                         xmlhttp.onreadystatechange=expand_feed_callback;
1388                         xmlhttp.send(null);
1389                 }
1390
1391         } catch (e) {
1392                 exception_error("browserExpand", e);
1393         }
1394 }
1395
1396 function validateNewPassword(form) {
1397         if (form.OLD_PASSWORD.value == "") {
1398                 alert("Old password cannot be blank");
1399                 return false;
1400         }
1401         if (form.NEW_PASSWORD.value == "") {
1402                 alert("New password cannot be blank");
1403                 return false;
1404         }
1405         return true;
1406 }
1407
1408 function selectPrefRows(kind, select) {
1409
1410         if (kind) {
1411                 var opbarid = false;    
1412                 var nchk = false;
1413                 var nrow = false;
1414                 var lname = false;
1415
1416                 if (kind == "feed") {
1417                         opbarid = "feedOpToolbar";
1418                         nrow = "FEEDR-";
1419                         nchk = "FRCHK-";                        
1420                         lname = "prefFeedList";
1421                 } else if (kind == "fcat") {
1422                         opbarid = "catOpToolbar";
1423                         nrow = "FCATR-";
1424                         nchk = "FCCHK-";
1425                         lname = "prefFeedCatList";
1426                 } else if (kind == "filter") {
1427                         opbarid = "filterOpToolbar";
1428                         nrow = "FILRR-";
1429                         nchk = "FICHK-";
1430                         lname = "prefFilterList";
1431                 } else if (kind == "label") {
1432                         opbarid = "labelOpToolbar";
1433                         nrow = "LILRR-";
1434                         nchk = "LICHK-";
1435                         lname = "prefLabelList";
1436                 } else if (kind == "user") {
1437                         opbarid = "userOpToolbar";
1438                         nrow = "UMRR-";
1439                         nchk = "UMCHK-";
1440                         lname = "prefUserList";
1441                 }
1442
1443                 if (opbarid) {
1444                         selectTableRowsByIdPrefix(lname, nrow, nchk, select);
1445                         disableContainerChildren(opbarid, !select);
1446                 }
1447
1448         } 
1449 }
1450
1451
1452 function toggleSelectPrefRow(sender, kind) {
1453
1454         toggleSelectRow(sender);
1455
1456         if (kind) {
1457                 var opbarid = false;    
1458                 var nsel = -1;
1459                 
1460                 if (kind == "feed") {
1461                         opbarid = "feedOpToolbar";
1462                         nsel = getSelectedFeeds();
1463                 } else if (kind == "fcat") {
1464                         opbarid = "catOpToolbar";
1465                         nsel = getSelectedFeedCats();
1466                 } else if (kind == "filter") {
1467                         opbarid = "filterOpToolbar";
1468                         nsel = getSelectedFilters();
1469                 } else if (kind == "label") {
1470                         opbarid = "labelOpToolbar";
1471                         nsel = getSelectedLabels();
1472                 } else if (kind == "user") {
1473                         opbarid = "userOpToolbar";
1474                         nsel = getSelectedUsers();
1475                 }
1476
1477                 if (opbarid && nsel != -1) {
1478                         disableContainerChildren(opbarid, nsel == false);
1479                 }
1480
1481         } 
1482 }
1483
1484 function toggleSelectFBListRow(sender) {
1485         toggleSelectListRow(sender);
1486         disableContainerChildren("fbrOpToolbar", getSelectedFeedsFromBrowser() == 0);
1487 }
1488
1489 var seq = "";
1490
1491 function pref_hotkey_handler(e) {
1492         try {
1493
1494                 var keycode;
1495         
1496                 if (!hotkeys_enabled) return;
1497         
1498                 if (window.event) {
1499                         keycode = window.event.keyCode;
1500                 } else if (e) {
1501                         keycode = e.which;
1502                 }
1503         
1504                 if (keycode == 13 || keycode == 27) {
1505                         seq = "";
1506                 } else {
1507                         seq = seq + "" + keycode;
1508                 }
1509
1510
1511         if (document.getElementById("piggie")) {
1512         
1513                 if (seq.match("807371717369")) {
1514                         seq = "";
1515                         localPiggieFunction(true);
1516                 } else {
1517                         localPiggieFunction(false);
1518                 }
1519         }
1520
1521         } catch (e) {
1522                 exception_error("pref_hotkey_handler", e);
1523         }
1524 }
1525
1526 function userSwitch() {
1527         var chooser = document.getElementById("userSwitch");
1528         var user = chooser[chooser.selectedIndex].value;
1529         window.location = "prefs.php?swu=" + user;
1530 }
1531
1532 function editFeedCats() {
1533         if (!xmlhttp_ready(xmlhttp)) {
1534                 printLockingError();
1535                 return
1536         }
1537
1538         xmlhttp.open("GET", "backend.php?op=pref-feeds&subop=editCats", true);
1539         xmlhttp.onreadystatechange=infobox_callback;
1540         xmlhttp.send(null);
1541 }