为什么更改框的innerHTML会使我的按钮在Greasemonkey中停止工作? [英] Why does changing the innerHTML, of my box, make my button stop working in Greasemonkey?

查看:74
本文介绍了为什么更改框的innerHTML会使我的按钮在Greasemonkey中停止工作?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

因此,我编写了一个脚本,可以在一个新选项卡中一次加载一个图像...由于Brock通过

So, I wrote a script that loads images one at a time in a new tab... Got a stop button to work thanks to Brock over HERE...

然后我在等待该问题的答案的同时在我写的计数器中添加了它.

Then I broke it adding in the counter that I had written in while waiting for an answer to that question.

我看不出有什么原因应该破坏它的...请帮忙吗?

I can't see any reason that should have broke it... help please?

我的脚本:

var box = document.createElement ('div');
box.id = 'mySelectBox';
GM_addStyle (
    ' #mySelectBox {             ' +
    '    background: white;     ' +
    '    border: 2px solid red; ' +
    '    padding: 4px;          ' +
    //'    position: absolute;    ' +
    '    position: fixed;       ' +
    '    top: 8px; left: 8px;   ' +
    '    max-width: 400px;      ' +
    ' } '
);
document.body.appendChild (box);
box.innerHTML = '';

var searchButton = document.createElement ('div');
searchButton.className = 'mySearchButton';
searchButton.textContent = 'Open';

GM_addStyle (
    ' .mySearchButton {           ' +
    '    background: #aaa;       ' +
    '    border: 1px solid #777; ' +
    '    padding: 1px;           ' +
    '    margin-left: 8px;       ' +
    '    float: right;           ' +
    '    cursor: pointer;        ' +
    ' } '
);
box.insertBefore (searchButton, box.nextSibling);

var stopButton = document.createElement ('div');
stopButton.className = 'myStopButton';
stopButton.textContent = 'Stop';

GM_addStyle (
    ' .myStopButton {           ' +
    '    background: #aaa;       ' +
    '    border: 1px solid #777; ' +
    '    padding: 1px;           ' +
    '    margin-left: 8px;       ' +
    '    float: right;           ' +
    '    cursor: pointer;        ' +
    ' } '
);
box.insertBefore (stopButton, box.nextSibling);

var closeButton = document.createElement ('div');
closeButton.className = 'myCloseButton';
closeButton.textContent = 'X';

GM_addStyle (
    ' .myCloseButton {           ' +
    '    background: #aaa;       ' +
    '    border: 1px solid #777; ' +
    '    padding: 1px;           ' +
    '    margin-left: 8px;       ' +
    '    float: right;           ' +
    '    cursor: pointer;        ' +
    ' } '
);

box.insertBefore (closeButton, box.firstChild);
closeButton.addEventListener ('click', function () {
    box.parentNode.removeChild (box);
}, true);

var mytable = document.getElementById

    ('lair-sort-pets').getElementsByTagName ('img');

var linksToOpen = [];
var mywin2 = null;

var okayToOpenLinks = true;

searchButton.addEventListener ('click', openpics);
stopButton.addEventListener ('click', stopLinkSequence);

function openpics () {
    okayToOpenLinks = true;

    if (linksToOpen.length === 0) {
        for (var J = 0, L = mytable.length; J < L; J++) {

            linksToOpen.push (mytable[J].src); //-- Add URL to list
        }
    }

    openLinksInSequence ();
};

original = box.innerHTML

function stopLinkSequence () {
    okayToOpenLinks = false;
}

function openLinksInSequence () {
    k = linksToOpen.length - 1

    if (mywin2) {
        mywin2.close ();
        mywin2 = null;
    }

    if (okayToOpenLinks && linksToOpen.length) {
        var link = linksToOpen.shift ();
        mywin2 = window.open (link, "my_win2");

        box.innerHTML = '<center>Links left</center><br>' + '<center>' + k + '</center><br>' + original;

        mywin2.addEventListener ('load', openLinksInSequence, false);
    }
}


如果我注释掉这一行,它将再次起作用(没有状态计数器除外):

If I comment out this line it works again (except no status counter):

box.innerHTML = '<center>Links left</center><br>'+'<center>'+k+'</center><br>'+original;


为什么?

这里可能Greasemonkey脚本的目标页面.

HERE is a possible target page for the Greasemonkey script.

推荐答案

使用innerHTML(或outerHTML)更改元素的内容时,

When you change an element's contents using innerHTML (or outerHTML), it trashes any event handlers of anything that element contained. It can also help cause performance problems and memory leaks. Don't use innerHTML in userscripts except maybe for the initial creation of brand new nodes.

对于倒数/状态显示,只需创建一次HTML,然后只需更改数据内容和/或使用CSS即可更改显示.这样做并稍微消毒一下,该代码将变为:

For a countdown/status display, create the HTML once, then just alter the data content and/or use CSS to alter the display. Doing that, and sanitizing things a bit, that code becomes:

var box         = document.createElement ('div');
document.body.appendChild (box);    // Must append before set outerHTML
box.outerHTML   = multilineStr ( function () {/*!
    <div id="mySelectBox">
        <div id="myStatus">Links left<br>
            <span>86</span>
        </div>
        <div id="myCloseButton">X</div>
        <div id="mySearchButton">Open</div>
    </div>
*/} );

document.getElementById ("myCloseButton").addEventListener ('click', function () {
    var box = this.parentNode;
    box.parentNode.removeChild (box);
} );
var startStopBtn    = document.getElementById ("mySearchButton");
startStopBtn.addEventListener ('click', startStopPicsLoad);

var mytable         = document.querySelectorAll ('#lair-sort-pets img');
var linksToOpen     = [];
var mywin2          = null;
var okayToOpenLinks = true;

function startStopPicsLoad () {
    if (typeof startStopPicsLoad.isStartBtn === "undefined") {
        startStopPicsLoad.isStartBtn    = true;
    }
    if (startStopPicsLoad.isStartBtn) {
        //-- Change start button to stop button
        startStopBtn.textContent        = "Stop";
        startStopPicsLoad.isStartBtn    = false;

        if (linksToOpen.length === 0) {
            for (var J = 0, L = mytable.length; J < L; J++) {
                linksToOpen.push (mytable[J].src); //-- Add URL to list
            }

            //-- Display the status area.
            document.querySelector ('#myStatus').style.display = "block";
        }

        openLinksInSequence ();
    }
    else {
        //-- Change stop button to start button
        startStopBtn.textContent        = "Open";
        startStopPicsLoad.isStartBtn    = true;

        //-- Actually stop the sequence.
        okayToOpenLinks = false;
    }
};

function openLinksInSequence () {
    if (mywin2) {
        mywin2.close ();
        mywin2 = null;
    }

    if (okayToOpenLinks) {
        if (linksToOpen.length) {
            var k           = linksToOpen.length - 1;
            var statDisp    = document.querySelector ('#myStatus span');
            statDisp.textContent = k;

            var link        = linksToOpen.shift ();
            mywin2          = window.open (link, "my_win2");
            mywin2.addEventListener ('load', openLinksInSequence, false);
        }
    }
    else {
        //-- Sequence is now stopped, reset the state variable.
        okayToOpenLinks = true;
    }
}

GM_addStyle ( multilineStr ( function () {/*!
    #mySelectBox {
        background: white;
        border: 2px solid red;
        padding: 4px;
        //position: absolute;
        position: fixed;
        top: 8px; left: 8px;
        max-width: 400px;
    }
    #myStatus {
        text-align: center;
        display: none;
    }
    #myCloseButton {
        background: #aaa;
        border: 1px solid #777;
        padding: 1px;
        margin-left: 8px;
        float: right;
        cursor: pointer;
    }
    #mySearchButton {
        background: #aaa;
        border: 1px solid #777;
        padding: 1px;
        margin-left: 8px;
        float: right;
        cursor: pointer;
    }
*/} ) );

function multilineStr (dummyFunc) {
    var str = dummyFunc.toString ();
    str     = str.replace (/^[^\/]+\/\*!?/, '') // Strip function() { /*!
            .replace (/\s*\*\/\s*\}\s*$/, '')   // Strip */ }
            .replace (/\/\/.+$/gm, '') // Double-slash comments wreck CSS. Strip them.
            ;
    return str;
}

这篇关于为什么更改框的innerHTML会使我的按钮在Greasemonkey中停止工作?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆