所以我有一个按钮,它应该创建一个奇特的共享URL,使用goo.gl缩短它,然后将其复制到剪贴板。好消息是,我已经成功完成了所有这些,但不是一次全部。
问题源于规范:
从document.execCommand()触发的复制命令只会影响真实剪贴板的内容,前提是从用户信任和触发的事件调度事件,或者实现配置为允许此事件。如何配置实现以允许对剪贴板的写访问超出了本规范的范围。
execCommand Unofficial W3C Spec
所以看起来这可能不起作用......
你看,为了缩短网址,我需要进行一次AJAX调用。我只在用户点击共享按钮时才这样做,因为我每天有1,000,000个限制缩短(如果我每次更改页面时生成一个新的共享URL,那么一个用户很容易就会有1,000个新的URL,所以我和# 39; d限制为最多1,000个最终用户:不是最佳选择)。但这意味着我必须从发起事件的线程以外的线程中侦听AJAX事件,从而有效地失去execCommand('copy')
所需的这种祝福状态。
有没有办法让一个单一按钮同时生成goo.gl网址,然后将所说短网址复制到剪贴板?
供参考,here's what I wrote (Kotlin/JS)和here's the JavaScript output。
以下是a SSCCE that illustrates how it seems like it should work, but does not(基于陈杨华's answer)。
答案 0 :(得分:3)
有两种解决方案可行,但两者都存在缺陷。只有当您的请求少于一个seconde且其中一个被弃用时才有效,因此不应在生产环境中使用它。
首先要使用 setTimeout ,这是少数几个不会丢失 execCommand “权限”的异步函数之一。但它没有失去被认为是等于或小于1000毫秒。因此,如果您的请求少于此,那么您很高兴,但如果没有,那么您就会出错。如果将它与某种超时处理相结合,它可以工作,但如果请求通常需要超过1秒,那么它可能不够好。像这样举例如:
var toCopy;
const buttonClick = () => {
setTimeout(function() {
if (toCopy) {
// strangely, this execCommand will work
console.log(document.execCommand('copy'));
}
}, 1000);
var client = new XMLHttpRequest();
client.onload = function(data) {
toCopy = this.responseText;
};
// by setting your timeout on your request
// with the same duration as the setTiemout
// you make sure it either works or throws an error
client.ontimeout = function(data) {
console.log('timeout');
};
client.timeout = 1000;
client.open("GET", "https://www.random.org/integers/?num=1&min=1&max=100&col=1&base=10&format=plain");
client.send();
}
$(() => {
$("button").click(buttonClick)
})
document.addEventListener('copy', function(e) {
e.preventDefault();
e.clipboardData.setData('text/plain', toCopy);
});
https://jsfiddle.net/8md4Ltu2/4/
还有另一种方法可以使它工作,但它已被弃用,因此不能使用。但是,为了彻底,我会把它放在这里。您可以将XMLHttpRequest的异步标志设置为false。请求将是同步的,因此execCommand的处理非常简单。但是这个同步标志已被弃用,如果你试图使用它,那么指南是抛出一个错误,因此不能使用它。请参阅:https://xhr.spec.whatwg.org/#synchronous-flag
var toCopy;
const buttonClick = () => {
var client = new XMLHttpRequest();
client.onload = function(data) {
toCopy = this.responseText;
console.log(document.execCommand('copy'));
};
client.open("GET", "https://www.random.org/integers/?num=1&min=1&max=100&col=1&base=10&format=plain", false);
client.send();
}
$(() => {
$("button").click(buttonClick)
})
document.addEventListener('copy', function(e) {
e.preventDefault();
e.clipboardData.setData('text/plain', toCopy);
});