View difference between Paste ID: 1LcKAz54 and wbn6MtLb
SHOW: | | - or go back to the newest paste.
1
/*
2
 * q.js v2018.3-6.1
3
 * http://anonsw.github.io/8chjs/
4
 */
5
6
//IMAGE BLACKLIST CODING
7
var imageBlacklist = [] ;
8
function loadImageBlacklist() { JSON.parse(localStorage.imageBlacklist || "[]").forEach(addToImageBlaclist); }
9
function saveImageBlacklist() { localStorage.imageBlacklist = JSON.stringify(imageBlacklist); }
10
function addToImageBlaclist(md5) { if (md5 && -1 === imageBlacklist.indexOf(md5)) imageBlacklist.push(md5); }
11
function blacklistPostImages(post) { $(post).find('img.post-image').each(function (i, el) { var md5 = el.getAttribute('data-md5'); addToImageBlaclist(md5); el.remove(); }); }
12
function removeBlacklistedImages() { var removed = 0; $('img.post-image').each(function (i, el) { if (-1 !== imageBlacklist.indexOf(el.getAttribute('data-md5'))) { el.remove(); removed += 1; } }); return removed; }
13
function onNopeClicked(event) { event.preventDefault(); event.stopPropagation(); loadImageBlacklist(); var post = $(event.target).closest('.post'); blacklistPostImages(post); removeBlacklistedImages(); saveImageBlacklist(); }
14
function addNopeButtons() { $('.post').each(function(i, post) { if ($(post).find('.nope').length === 0) { $(post).prepend("<input type='button' class='nope' onClick='onNopeClicked(event)' value='Nope'></input>"); } }) }
15
16
setInterval(function () { loadImageBlacklist(); removeBlacklistedImages(); addNopeButtons(); }, 500);
17
18
19
/* Display a replies counter overlay in the top right corner */
20
$(function(){
21
  $('head').append('<style>#thread_stats_posts_ovl { '+
22
  'position:fixed;top:35px;right:35px;'+
23
  'font:38px sans-serif;opacity:0.5;color:#f60;}</style>');
24
  $('body').append('<div id="thread_stats_posts_ovl"/>');
25
  function copyStats() { $('#thread_stats_posts_ovl').
26
    text($('#thread_stats_posts').text());}
27
  $(document).on('new_post',copyStats); copyStats();});
28
29
// User Settings
30
var anonsw = {
31
    qflair: '', // Examples: REAL, &rarr;
32-
    qcolor: '#99d6ff',
32+
    qcolor: '#9fd8e0',
33-
    youcolor: '#F3D74D',
33+
    youcolor: '#9fd8e0',
34
    scrollcolor: 'rgba(153, 153, 153, 0.6)',
35
    scrollbackcolor: '#333',
36
    scrolltime: 400, // ms
37
    updateDelay: 200, // ms
38
    sidenavWidth: 30, // px
39
40
    floodEnabled: false,
41
    floodThreshold: 15, // min # posts before beginning fade
42
    floodVanish: 25, // max # posts before completed fade/hide
43
    floodBehavior: 'fade', // hide, fade
44
    fadenametripregex: /^(Anon(ymous)?-.*|.*-!!mG7VJxZNCI)$/i,
45
    fadenametripfloodvalue: -1, // Effective post count for fading, or -1 for auto of floodThreshold+post count
46
    strikeThroughNameFags: true,
47
48
    rateHistoryLen: 50, // Data points on chart
49
    rateAvgLen: 10 // Number of data points to average for instantaneous rate
50
51
    // Suggestions from 589388.html#590283
52
    //    ...shill detection features, such as
53
    //          easily knowing the proportion of posts from a user that don't link.
54
    //          I'd want to know any ID that was posting > 1/3 posts targetting noone.
55
56
    // TODO: Behavior for post hover should be to show original post visual before all q.js mods
57
    // TODO: Add flags to turn on/off features
58
    // TODO: Custom-regex -> post color/fade (auto-filter by selecting text and choosing new menu item?)
59
    //       Examples: daily reminder, guys, check this out, shill, get out, filtered, tell us more, archive everything
60
    // TODO: Manual shade
61
    // TODO: remove Q trip codes from post content?
62
    // TODO: remove Q from end of post content if not a Q post?
63
    // TODO: recognize all of known Q trip codes? (make to sure to exclude known comps)
64
    // TODO: Links to reset on current Q/(you) post
65
    // TODO: Link to go to latest post (end key doesn't always work, but try capturing that as well?)
66
    // TODO: Keyboard shortcuts for navigation
67
    // TODO: Current/Total overall post navigation
68
    // TODO: Remap end key to always go to end of page
69
    // TODO: Check box for each post to mark as "read", "spam", ?
70
    // TODO: Autocorrect all-caps posts (50% threshold)?
71
    // TODO: Correct broken links but remove referral when clicked?
72
    // TODO: Make flood post fading non-linear to give leniency to posters just passing flood threshold
73
    // TODO: Penalize reposts in flood detection (if id's different, merge?) ?
74
    // TODO: Scorecard of posters ordered by post count (post rate, reply count, ...)?
75
    // TODO: Color/shade posts where there are no references and no question marks
76
    // TODO: If Q or trip used in name field, strike them out or replace with Anonymous?
77
    // TODO: embedded posts in Q posts don't have background-color and inherit Q color, fix?
78
};
79
80
(function( anonsw_main, $, undefined ) {
81
    // House keeping variables
82
    var qposts = [];
83
    var allqposts = [];
84
    var currq = -1;
85
    var youposts = [];
86
    var curryou = -1;
87
    var qnavposts = [];
88
    var younavposts = [];
89
    var ctx;
90
    var	borderSz;
91
    var	scrollWd;
92
    var minheight;
93
    var ratehistory = [];
94
95
    // On scroll stop. SO #9144560
96
    (function ($) {
97
        var on = $.fn.on, timer;
98
        $.fn.on = function () {
99
            var args = Array.apply(null, arguments);
100
            var last = args[args.length - 1];
101
102
            if (isNaN(last) || (last === 1 && args.pop())) return on.apply(this, args);
103
104
            var delay = args.pop();
105
            var fn = args.pop();
106
107
            args.push(function () {
108
                var self = this, params = arguments;
109
                clearTimeout(timer);
110
                timer = setTimeout(function () {
111
                    fn.apply(self, params);
112
                }, delay);
113
            });
114
115
            return on.apply(this, args);
116
        };
117
    }(this.jQuery || this.Zepto));
118
119
    // Case insensitive contains selector for finding yous. SO #8746882
120
    $.expr[":"].icontains = jQuery.expr.createPseudo(function (arg) {
121
        return function (elem) {
122
            return jQuery(elem).text().toUpperCase().indexOf(arg.toUpperCase()) >= 0;
123
        };
124
    });
125
126
    // Get non-child text. SO #3442394
127
    function immediateText(el) {
128
        return el.contents().not(el.children()).text();
129
    }
130
131
    // Scroll to element
132
    function myScrollTo(el) {
133
        $('html, body').animate({
134
            scrollTop: $(el).offset().top - $('div.boardlist').height()
135
        }, anonsw.scrolltime);
136
    }
137
138
    // Highlight (you) posts/references
139
    function highlightYous() {
140
        $(youposts).each(function() {
141
            $(this).css('background-color', anonsw.youcolor);
142
        });
143
        return $.Deferred().resolve();
144
    }
145
146
    // Remove invalid (you)'s
147
    function removeInvalidYous() {
148
        $('div.body:icontains("(You)")').each(function() {
149
            $(this).find(':not(small)').contents().filter(function() { return this.nodeType == 3 }).each(function() {
150
                this.textContent = this.textContent.replace(/\(+ *You *\)+/ig, "you");
151
            });
152
        });
153
        return $.Deferred().resolve();
154
    }
155
156
    // Highlight Q posts
157
    function highlightQ() {
158
        $(allqposts).each(function(idx,val) {
159
            if($(val).css('background-color') !== anonsw.qcolor) {
160
                if(anonsw.qflair !== "") {
161
                    $(val).find('p.intro > label > span.trip').first().prepend(anonsw.qflair + " ");
162
                }
163
                $(val).css('background-color', anonsw.qcolor);
164
            }
165
        });
166
        return $.Deferred().resolve();
167
    }
168
169
    // Scroll to next Q
170
    anonsw_main.nextq = function() {
171
        if(qposts.length > 0) {
172
            if(currq < qposts.length-1) {
173
                currq++;
174
            }
175
            myScrollTo($(qposts).get(currq));
176
        }
177
    };
178
179
    // Scroll to last Q
180
    anonsw_main.lastq = function() {
181
        if(qposts.length > 0) {
182
            currq = qposts.length - 1;
183
            myScrollTo($(qposts).get(currq));
184
        }
185
    };
186
187
    // Scroll to previous Q
188
    anonsw_main.prevq = function() {
189
        if(qposts.length > 0) {
190
            if(currq > 0) {
191
                currq--;
192
            }
193
            myScrollTo($(qposts).get(currq));
194
        }
195
    };
196
197
    // Scroll to first Q
198
    anonsw_main.firstq = function() {
199
        if(qposts.length > 0) {
200
            currq = 0;
201
            myScrollTo($(qposts).get(currq));
202
        }
203
    };
204
205
    // Scroll to next (You)
206
    anonsw_main.nextyou = function() {
207
        if(youposts.length > 0) {
208
            if(curryou < youposts.length-1) {
209
                curryou++;
210
            }
211
            myScrollTo($(youposts).get(curryou));
212
        }
213
    };
214
215
    // Scroll to last (You)
216
    anonsw_main.lastyou = function() {
217
        if(youposts.length > 0) {
218
            curryou = youposts.length - 1;
219
            myScrollTo($(youposts).get(curryou));
220
        }
221
    };
222
223
    // Scroll to previous (You)
224
    anonsw_main.prevyou = function() {
225
        if(youposts.length > 0) {
226
            if(curryou > 0) {
227
                curryou--;
228
            }
229
            myScrollTo($(youposts).get(curryou));
230
        }
231
    };
232
233
    // Scroll to first (You)
234
    anonsw_main.firstyou = function() {
235
        if(youposts.length > 0) {
236
            curryou = 0;
237
            myScrollTo($(youposts).get(curryou));
238
        }
239
    };
240
241
    // Inserts Q navigation links
242
    function qnav() {
243
        $('div.boardlist').append('<span>[ <a href="javascript:anonsw_main.firstq();"><i class="fa fa-step-backward"></i></a> <a href="javascript:anonsw_main.prevq();"><i class="fa fa-backward"></i></a> <span style="filter:brightness(70%);">Q</span> <span class="qcount">(?:?)</span> <a href="javascript:anonsw_main.nextq();"><i class="fa fa-forward"></i></a> <a href="javascript:anonsw_main.lastq();"><i class="fa fa-step-forward"></i></a> ]</span>');
244
    }
245
246
    // Inserts (You) navigation links
247
    function younav() {
248
        $('div.boardlist').append('<span>[ <a href="javascript:anonsw_main.firstyou();"><i class="fa fa-step-backward"></i></a> <a href="javascript:anonsw_main.prevyou();"><i class="fa fa-backward"></i></a> <span style="filter:brightness(70%);">(You)</span> <span class="youcount">(?:?)</span> </span><a href="javascript:anonsw_main.nextyou();"><i class="fa fa-forward"></i></a> <a href="javascript:anonsw_main.lastyou();"><i class="fa fa-step-forward"></i></a> ]</span>');
249
    }
250
251
    // Inserts feature toggle links
252
    function togglenav() {
253
        $('div.boardlist').append('<span>[ <a href="javascript:anonsw_main.toggleFlood();">Turn Post Fading <span class="toggleFloodState">Off</span></a> ]</span>')
254
    }
255
256
    // Inserts post rate count/chart
257
    function postratenav() {
258
        var height = $('div.boardlist').height() - 1;
259
        $('div.boardlist').append('<span>[ Post Rate: <span class="postRate">0</span> posts/min <canvas class="postRateChart"></canvas>]</span>')
260
        $('.postRate').css('color', $('div.boardlist a').css('color'));
261
        var charts = $('.postRateChart');
262
        $(charts).each(function() {
263
            $(this).css('width', '100px');
264
            $(this).css('height', height);
265
            $(this).css('vertical-align', 'middle');
266
            //$(this).css('border', '1px solid');
267
            //$(this).css('border-color', $('div.boardlist').css('color'));
268
            var gctx = $(this).get(0).getContext('2d');
269
            gctx.canvas.height = 20;
270
            gctx.canvas.width = 100;
271
        });
272
    }
273
274
    // Inserts side navigation (bird's eye)
275
    function sidenav() {
276
        $('body').append('<canvas id="sidenav"></canvas>');
277
        var nav = $('#sidenav');
278
        $(nav).css('position', 'fixed');
279
        $(nav).css('top', $('div.boardlist').height());
280
        $(nav).css('right', 0);
281
        $(nav).css('width', anonsw.sidenavWidth);
282
        $(nav).css('height', $(window).height() - $('div.boardlist').height());
283
        $(nav).css('background-color', anonsw.scrollbackcolor);
284
        $('body').css('margin-right', anonsw.sidenavWidth);
285
        ctx = $('#sidenav').get(0).getContext('2d');
286
        //ctx.canvas.height = $(document).height() - $('div.boardlist').height();
287
        ctx.canvas.height = 2048;
288
        ctx.canvas.width = anonsw.sidenavWidth;
289
        borderSz = 1;
290
        scrollWd = ctx.canvas.width / 2;
291
    }
292
293
    // Update navigation counts
294
    function updateNavCounts() {
295
        var fontSize = -1;
296
        var lineHeight;
297
298
        if(currq > qposts.length) { currq = qposts.length; }
299
        if(curryou > youposts.length) { curryou = youposts.length; }
300
301
        for(i=0; i<qposts.length; i++) {
302
            var el = $(qposts).get(i);
303
            if(fontSize == -1) {
304
                fontSize = $(el).css('font-size');
305
                lineHeight = Math.floor(parseInt(fontSize.replace('px', '')) * 1.5);
306
            }
307
            if(($(el).offset().top + $(el).height() - 2.25*lineHeight) > $(window).scrollTop()) {
308
                currq = i;
309
                break;
310
            }
311
        }
312
313
        for(i=0; i<youposts.length; i++) {
314
            var el = $(youposts).get(i);
315
            if(fontSize == -1) {
316
                fontSize = $(el).css('font-size');
317
                lineHeight = Math.floor(parseInt(fontSize.replace('px', '')) * 1.5);
318
            }
319
            if(($(el).offset().top + $(el).height() - 2.25*lineHeight) > $(window).scrollTop()) {
320
                curryou = i;
321
                break;
322
            }
323
        }
324
325
        // TODO: check for duplicates and remove from counts
326
        $('.qcount').text("(" + (currq+1) + ":" + qposts.length + ")");
327
        $('.youcount').text("(" + (curryou+1) + ":" + youposts.length + ")");
328
    }
329
330
    // Update navigation graphics
331
    function updateNavGraphics() {
332
        var sidenav = $('#sidenav');
333
        if(sidenav.length) {
334
            $(sidenav).css('height', $(window).height() - $('div.boardlist').height());
335
            minheight = ctx.canvas.height / ($(window).height() - $('div.boardlist').height()); // 1px
336
            ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);
337
338
            // Draw nav q posts
339
            qnavposts = [];
340
            ctx.fillStyle = anonsw.qcolor;
341
            for (i = 0; i < qposts.length; i++) {
342
                // TODO: check if we have already added post, don't draw it again
343
                var el = $(qposts).get(i);
344
                var height = $(el).height() / $(document).height() * ctx.canvas.height;
345
                if(height < minheight) height = minheight;
346
                qnavposts[i] = {
347
                    x : borderSz,
348
                    y : $(el).offset().top / $(document).height() * ctx.canvas.height,
349
                    width : ctx.canvas.width - borderSz*2,
350
                    height : height
351
                };
352
                ctx.fillRect(qnavposts[i].x, qnavposts[i].y, qnavposts[i].width, qnavposts[i].height);
353
            }
354
355
            // Draw nav you posts
356
            younavposts = [];
357
            ctx.fillStyle = anonsw.youcolor;
358
            for (i = 0; i < youposts.length; i++) {
359
                // TODO: check if we have already added post, don't add it again
360
                var el = $(youposts).get(i);
361
                var height = $(el).height() / $(document).height() * ctx.canvas.height;
362
                if(height < minheight) height = minheight;
363
                younavposts[i] = {
364
                    x : borderSz,
365
                    y : $(el).offset().top / $(document).height() * ctx.canvas.height,
366
                    width : ctx.canvas.width - borderSz*2,
367
                    height : height
368
                };
369
                ctx.fillRect(younavposts[i].x, younavposts[i].y, younavposts[i].width, younavposts[i].height);
370
            }
371
372
            // Update nav window
373
            ctx.fillStyle = anonsw.scrollcolor;
374
            ctx.fillRect(
375
                scrollWd / 2,
376
                $(window).scrollTop() / $(document).height() * ctx.canvas.height,
377
                scrollWd,
378
                $(window).height() / $(document).height() * ctx.canvas.height
379
            );
380
381
            // Add red marker at bottom of >750 posts
382
            if($('#thread_stats_posts').text() > 750) {
383
                var barHeight = (4 * 2048) / ($(window).height() - $('div.boardlist').height());
384
                ctx.fillStyle = '#f66';
385
                ctx.fillRect(
386
                    0,
387
                    ctx.canvas.height - barHeight,
388
                    ctx.canvas.width,
389
                    barHeight
390
                );
391
            }
392
        }
393
    }
394
395
    // Updates post rate count/chart
396
    function updateNavPostRate() {
397
        var posts = $('div.post').not('.post-hover');
398
        var startPost = posts.length - (anonsw.rateHistoryLen + anonsw.rateAvgLen) + 1;
399
        if(startPost < 1) startPost = 1;
400
        var start = $($($(posts).get(0)).find('.intro time').get(0)).attr('unixtime'); //$('div.post:first .intro time').attr('unixtime');
401
        ratehistory = [];
402
        timehistory = [];
403
        for(var i=startPost; i<posts.length; i++) {
404
            // TODO: check if we have already added post, don't add it again
405
            var step = $($($(posts).get(i)).find('.intro time').get(0)).attr('unixtime'); //$($('div.post .intro time').get(i)).attr('unixtime');
406
            timehistory[timehistory.length] = step;
407
            if(timehistory.length - anonsw.rateAvgLen - 1 >= 0) {
408
                var avgend = timehistory[timehistory.length - 1];
409
                var avgstart = timehistory[timehistory.length - anonsw.rateAvgLen - 1];
410
                ratehistory[ratehistory.length] = anonsw.rateAvgLen / ((avgend - avgstart) / 60);
411
            } else {
412
                ratehistory[ratehistory.length] = 0;
413
            }
414
        }
415
        //console.log(ratehistory);
416
417
        $('.postRate').text(ratehistory[ratehistory.length-1].toFixed(1));
418
419
        if(ratehistory.length > anonsw.rateAvgLen) {
420
            var maxRate = Math.max.apply(null, ratehistory);
421
            var minRate = Math.min.apply(null, ratehistory);
422
            //console.log("Max: " + maxRate);
423
            //console.log("Min: " + minRate);
424
            if(minRate > (maxRate - 0.5)) {
425
                minRate = maxRate - 0.5;
426
                maxRate = maxRate + 0.5;
427
            }
428
            if(minRate < 0) {
429
                minRate = 0;
430
            }
431
            var maxTime = timehistory[timehistory.length-1];
432
            var minTime = timehistory[anonsw.rateAvgLen];
433
            $('.postRateChart').each(function() {
434
                var gctx = $(this).get(0).getContext('2d');
435
                gctx.clearRect(0, 0, gctx.canvas.width, gctx.canvas.height);
436
                gctx.strokeStyle = $('div.boardlist a').css('color');
437
                gctx.beginPath();
438
                var x = 0;
439
                var y = gctx.canvas.height - (ratehistory[anonsw.rateAvgLen] - minRate)/(maxRate - minRate) * gctx.canvas.height;
440
                gctx.moveTo(x, y);
441
                for(var i=anonsw.rateAvgLen+1; i<ratehistory.length; i++) {
442
                    x = (timehistory[i] - minTime)/(maxTime - minTime) * gctx.canvas.width;
443
                    y = gctx.canvas.height - (ratehistory[i] - minRate)/(maxRate - minRate) * gctx.canvas.height;
444
                    gctx.lineTo(x, y);
445
                }
446
                gctx.stroke();
447
                gctx.closePath();
448
            });
449
        }
450
    }
451
452
    // Update navigation
453
    function updateNav() {
454
        updateNavCounts();
455
        updateNavGraphics();
456
        updateNavPostRate();
457
    }
458
459
    // Update nav when scrolling stops
460
    $(window).on('scroll', function(e) {
461
        updateNavCounts();
462
        updateNavGraphics();
463
    }, anonsw.updateDelay);
464
465
    // Update nav when resize stops
466
    $(window).on('resize', function(e) {
467
        updateNav();
468
    }, anonsw.updateDelay);
469
470
    // Set which posts are Q posts
471
    function setQPosts() {
472
        qposts = $.map($('div.post:not(.post-hover) > p.intro > label > span.trip:contains("!!mG7VJxZNCI")'), function(el) {
473
            return $(el).closest('div.post');
474
        });
475
        allqposts = $.map($('div.post:not(.post-hover) > p.intro > label > span.trip:contains("!!mG7VJxZNCI")'), function(el) {
476
            return $(el).closest('div.post');
477
        });
478
        return $.Deferred().resolve();
479
    }
480
481
    // Set which posts are (you) posts
482
    function setYouPosts() {
483
        youposts = $.map($('div.post:not(.post-hover) > p.intro > label span.name > span.own_post, div.post:not(.post-hover) > div.body > p.body-line > small:icontains("(You)")'), function(el) {
484
            return $(el).closest('div.post');
485
        });
486
        return $.Deferred().resolve();
487
    }
488
489
    // Set flood posts
490
    function setFloodPosts() {
491
        if(anonsw.floodEnabled) {
492
            var stats = {};
493
            var firstId = null;
494
            //console.log("==[ Name Fags ]=================================================");
495
            var posts = $('div.post:not(.post-hover)').not('.you');
496
            $(posts).each(function () {
497
                var id = $(this).find('p > span.poster_id').first().text();
498
                if(firstId != null) {
499
                    if (!(id in stats)) {
500
                        stats[id] = {count: 0, namefag: false, floodcount: 0};
501
                    }
502
                    stats[id].count++;
503
                    if(!stats[id].namefag) {
504
                        var name = immediateText($(this).find('p > label span.name').first());
505
                        var trip = $(this).find('p > label > span.trip').first().text();
506
                        stats[id].namefag = !anonsw.fadenametripregex.test(name+'-'+trip);
507
                        //if(stats[id].namefag) {
508
                        //	console.log(id + '=' + stats[id].namefag + ', ' + name + ', ' + trip);
509
                        //}
510
                    }
511
                    if(stats[id].namefag) {
512
                        if(anonsw.fadenametripfloodvalue < 0) {
513
                            stats[id].floodcount = anonsw.floodThreshold + stats[id].count;
514
                        } else {
515
                            stats[id].floodcount = anonsw.fadenametripfloodvalue;
516
                        }
517
                    } else {
518
                        stats[id].floodcount = stats[id].count;
519
                    }
520
                }
521
                if (firstId == null) {
522
                    firstId = id;
523
                }
524
            });
525
            $.each(stats, function (key, value) {
526
                if (key !== firstId) {
527
                    var ids = $('span.poster_id:contains("' + key + '")');
528
                    if (value.floodcount > anonsw.floodThreshold || value.namefag) {
529
                        if(anonsw.strikeThroughNameFags && value.namefag) {
530
                            $(ids).each(function() {
531
                                $(this).closest('div.post').find('p > label span.name').first().css('text-decoration','line-through');
532
                            });
533
                        }
534
                        if (anonsw.floodBehavior === 'fade') {
535
                            var intensity = value.floodcount;
536
                            if (intensity > anonsw.floodVanish) {
537
                                intensity = anonsw.floodVanish;
538
                            }
539
                            intensity = ((anonsw.floodVanish - anonsw.floodThreshold) - (intensity - anonsw.floodThreshold)) / (anonsw.floodVanish - anonsw.floodThreshold);
540
                            if (intensity < 0.1) {
541
                                intensity = 0.1;
542
                            }
543
                            $(ids).each(function () {
544
                                $(this).closest('div.post').css('opacity', intensity);
545
                                $(this).closest('div.post').hover(function () {
546
                                    $(this).animate({opacity: 1.0}, anonsw.updateDelay);
547
                                }, function () {
548
                                    $(this).animate({opacity: intensity}, anonsw.updateDelay);
549
                                });
550
                            });
551
                        } else if (anonsw.floodBehavior === 'hide') {
552
                            if (value.count >= anonsw.floodVanish) {
553
                                $(ids).each(function () {
554
                                    $(this).closest('div.post').hide();
555
                                });
556
                            }
557
                        }
558
                    } else {
559
                        $(ids).each(function () {
560
                            $(this).closest('div.post').css('opacity', 1.0);
561
                        });
562
                    }
563
                }
564
            });
565
        }
566
        return $.Deferred().resolve();
567
    }
568
569
    // Toggle post flooding
570
    anonsw_main.toggleFlood = function() {
571
        if(anonsw.floodEnabled) {
572
            anonsw.floodEnabled = false;
573
            $('.toggleFloodState').text('On');
574
            if(anonsw.floodBehavior === 'fade') {
575
                $('span.poster_id').each(function () {
576
                    $(this).closest('div.post').css('opacity', 1);
577
                    $(this).closest('div.post').off('mouseenter mouseleave');
578
                });
579
            } else if(anonsw.floodBehavior === 'hide') {
580
                $(this).closest('div.post').show();
581
            }
582
        } else {
583
            anonsw.floodEnabled = true;
584
            $('.toggleFloodState').text('Off');
585
            runq()
586
        }
587
    };
588
589
    // Helper to run snippets in the right order
590
    function runq() {
591
        setQPosts()
592
            .done(highlightQ)
593
            .done(removeInvalidYous)
594
            .done(setYouPosts)
595
            .done(highlightYous)
596
            .done(setFloodPosts)
597
            .done(updateNav);
598
    }
599
600
    anonsw_main.Q = function() {
601
        qnav();
602
        younav();
603
        togglenav();
604
        postratenav();
605
        sidenav();
606
        runq();
607
608
        // Select the node that will be observed for mutations
609
        var targetNode = $('div.thread')[0];
610
611
        // Options for the observer (which mutations to observe)
612
        var config = { childList: true };
613
614
        // Callback function to execute when mutations are observed
615
        var callback = function(mutationsList) {
616
            for(var mutation in mutationsList) {
617
                if (mutationsList[mutation].type == 'childList') {
618
                    runq();
619
                    break;
620
                }
621
            }
622
        };
623
624
        // Create an observer instance linked to the callback function
625
        var observer = new MutationObserver(callback);
626
627
        // Start observing the target node for configured mutations
628
        observer.observe(targetNode, config);
629
    };
630
}( window.anonsw_main = window.anonsw_main || {}, jQuery ));
631
632
// Attach snippets to ready/change events
633
$(document).ready(anonsw_main.Q);