首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何像承诺的那样使用showModal完全阻止外部内容?

如何像承诺的那样使用showModal完全阻止外部内容?
EN

Stack Overflow用户
提问于 2017-04-03 11:52:03
回答 1查看 562关注 0票数 0

我正在尝试用javascript:书签修改页面行为,因为在我当前的环境中,我无法制作插件(或其他任何东西)。

几乎所有东西都正常工作,除了某些页面中的预期enter键外,这些页面包含了某种全局捕获。就像这样发生的事:

代码语言:javascript
复制
(function(){
    window.dialog = dialog
    function dialog (title, callback, value) {
        let alertDialog = document.getElementById('alertDialog')
        if (alertDialog) alertDialog.remove()
        let htmlDiv = document.createElement('div')
        let html = `<div>dummy</div>
        <dialog id="alertDialog">
          <form method="dialog">
            <section>
              <p>
                <label for="value">${title}</label>
                <br />
                <input type="text" name="value" value="${value}">
              </p>
            </section>
            <menu>
              <button id="cancel" type="reset">cancel</button>
              &nbsp;
              <button type="submit">ok</button>
            </menu>
          </form>
        </dialog>
        <style>dialog#alertDialog input { width: 100%; } dialog#alertDialog menu { text-align: center; }</style>`
        htmlDiv.innerHTML = html.replace(/^\s*</gm,'<').replace(/[\n\r\t\0\f\v]/g,'') // "minify" else append child fails, although...
            .replace('> <', '><') // ...after jscompress minifies this and we paste into bookmark, it adds those spaces which would yield to append child error
        alertDialog = htmlDiv.childNodes[1]
        document.querySelector('body').appendChild(alertDialog)
        let cancelButton = alertDialog.querySelector('#cancel')
        if (cancelButton) cancelButton.addEventListener('click', function() { alertDialog.close() })
        let input = alertDialog.querySelector('input')
        if (typeof callback === 'function') {
            alertDialog.onsubmit = function(){ callback(input ? input.value : true) }
            alertDialog.oncancel = function(){ callback(false) }
        }

        if (value !== undefined) {
            alertDialog.showModal() // prompt
        } else {
            alertDialog.querySelector('input').remove()
            if (title.substr(-1) === '?') {
                alertDialog.showModal() // confirm
            } else {
                alertDialog.querySelector('#cancel').remove()
                alertDialog.showModal() // alert
            }
        }
        return null
    }

//    dialog('foo!')
}())
代码语言:javascript
复制
<body onkeypress="handle(event)">
<form action="#">
    <input type="text" name="txt" />
    <a href="javascript:window.dialog('foo!')">modal</a>
</form>

<script>
    function handle(e){
        if(e.keyCode === 13){
            e.preventDefault(); // Ensure it is only this code that rusn
            alert("Enter was pressed was presses");
        }
    }
</script>
</body>

如果我能够更改这个DOM并将onkeypressbody移动到form,那么问题就解决了。但我甚至不知道enter capture事件在我试图修改的页面中的位置。

除了使用alertconfirm和/或prompt之外,是否有一种通用方法来解决这个问题?在那里呆了一个小时,我认为使用承诺或让步可能会有帮助,但没有帮助。

我想继续使用(或者至少使用所有特性,包括简单性和小代码),因为它为我解决了许多其他问题。

医生们承诺:

showModal()方法的HTMLDialogElement接口显示对话框作为一个模式,在任何其他对话框的顶部可能存在。它显示在顶层,以及一个:背景伪元素。对话框外的交互被阻塞,外部的内容被渲染为惰性。

但现在不是完全正确了,对吧?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-04-04 13:42:00

终于来了!这个成功了。

首先,我认为“让我们尝试重写onkeypress",但是当它在这个单独的实例中工作时,它不在我的环境中。最后,我想“哦,也许是在按下键”。事实也是如此。:)

所以,说到底,这句话并不完全是假的。这并不能阻止其他事件的传播,很可能是每个设计,因为如果需要的话,有资源可以这样做。(即,在本例中为stopPropagation)。

代码语言:javascript
复制
(function(){
    window.overrideEnter = overrideEnter
    function overrideEnter (event) {
        if (event.keyCode == 13) {
            event.stopPropagation()
        }
    }
    window.dialog = dialog
    function dialog (title, callback, value) {
        let alertDialog = document.getElementById('alertDialog')
        if (alertDialog) alertDialog.remove()
        let htmlDiv = document.createElement('div')
        let html = `<div>dummy</div>
        <dialog id="alertDialog">
          <form method="dialog" onkeypress="return window.overrideEnter(event)" onkeydown="return window.overrideEnter(event)" onkeyup="return window.overrideEnter(event)">
            <section>
              <p>
                <label for="value">${title}</label>
                <br />
                <input type="text" name="value" value="${value}">
              </p>
            </section>
            <menu>
              <button type="submit">ok</button>
              &nbsp;
              <button id="cancel" type="reset">cancel</button>
            </menu>
          </form>
        </dialog>
        <style>dialog#alertDialog input { width: 100%; } dialog#alertDialog menu { text-align: center; }</style>`
        htmlDiv.innerHTML = html.replace(/^\s*</gm,'<').replace(/[\n\r\t\0\f\v]/g,'') // "minify" else append child fails, although...
            .replace('> <', '><') // ...after jscompress minifies this and we paste into bookmark, it adds those spaces which would yield to append child error
        alertDialog = htmlDiv.childNodes[1]
        document.querySelector('body').appendChild(alertDialog)
        let cancelButton = alertDialog.querySelector('#cancel')
        cancelButton.addEventListener('click', function(){ alertDialog.close(); callback(false) })
        let input = alertDialog.querySelector('input')
        //console.log(input)
        if (typeof callback === 'function') {
            alertDialog.onsubmit = function(){ callback(input ? input.value : true) }
            alertDialog.oncancel = function(){ callback(false) }
            alertDialog.onclose = function(){}
        }

        document.onkeydown = function(event) {
            event = event || window.event
            if (event.keyCode == 13) {
                event.stopPropagation()
            }
        }
        if (value !== undefined) {
            alertDialog.showModal() // prompt
        } else {
            input.remove()
            input = undefined
            if (title.substr(-1) === '?') {
                alertDialog.showModal() // confirm
            } else {
                cancelButton.remove()
                alertDialog.showModal() // alert
            }
        }
        return null
    }
}())
代码语言:javascript
复制
<body onkeypress="handle(event)">
<form action="#">
    <input type="text" name="txt" />
    <a href="javascript:window.dialog('foo?', result => console.log(result))">modal</a>
</form>

<script>
    function handle(e){
        if(e.keyCode === 13){
            e.preventDefault()
            alert("Enter was pressed was pressed")
        }
        return true
    }
</script>
</body>

票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/43183930

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档