用戶在瀏覽網頁的過程當中,執行復制操做的場景是很是多的,例如:複製連接地址、複製分享文案等等。前端
而前端經過模擬用戶的複製操做,能夠減小操做的步驟,進而優化用戶體驗。git
複製操做主要分爲如下兩部分:github
首先,讀者須要明白,不是全部的文本均可以被選中的(後續會提到),筆者這裏先介紹幾個能夠選中文本的狀況:瀏覽器
因爲 input 元素的工做方式因其類型屬性的值而有很大的差別,因此這裏只討論 text 的狀況。app
由於 JavaScript 提供了 HTTMLInputElement.select() 方法,因此選中 textarea 和 input 中的內容就變得很是簡單:post
document.querySelector('input').select()
複製代碼
若是 input 和 textarea 元素附加了 disabled 屬性,那麼其內容是沒法被選中的,這種狀況最好是將 disabled 替換爲 readonly 。優化
div 元素並無開箱即用的 select() 方法,這就須要讀者瞭解一個新的對象: Selection 。ui
Selection 對象表示用戶選擇文本的範圍以及光標的範圍。關於 Selection 對象,讀者須要瞭解如下幾個術語:spa
與 Selection 對象息息相關的還有一個 Range 對象,它主要用來自定義選區。對於這兩個對象不瞭解的讀者,能夠查看文末給出的參考文獻,接下來,利用 Selection 和 Range 對象實現上述 select() 方法:操作系統
function select (element) {
const selection = window.getSelection()
const range = document.createRange()
range.selectNodeContents(element)
selection.removeAllRanges()
selection.addRange(range)
}
複製代碼
document 暴露的 execCommand 方法,能夠用來運行操做系統提供的命令,而且這些命令大部分做用於 Selection 對象。
該方法返回的布爾值表示操做是否被支持或者是否被啓用,可是調用一個命令以前,不能嘗試使用返回值去校驗瀏覽器的兼容性。
function copyText () {
let success = true
try {
success = document.execCommand('copy')
} catch (e) {
success = false
}
return success
}
複製代碼
經過 execCommand 執行 copy 命令,能夠將上述選中的文本添加到系統剪貼板中,接下來用戶只須要在使用的地方按下 Ctrl(command) + V 便可粘貼該內容。
上述方案基本上能夠應對大部分的狀況,可是在 HTML 中,部分元素中的文本是沒法被選中的,例如:
<select id="js-select">
<option value="apple">apple</option>
<option value="banana">banana</option>
<option value="peach">peach</option>
</select>
複製代碼
既然 select 元素中的文本沒法被選中,那麼就沒法調用 execCommand 方法,又何談模擬用戶複製該文本呢?
這裏就須要採用如下套路:
首先獲取到須要複製的文本內容,對於 select 元素,其文本內容能夠根據 value 屬性獲取:
const element = document.getElementById('js-select')
const text = element.value
複製代碼
前面提到的 input、textarea 等元素都是能夠被選中的,因此這裏筆者選擇建立一個透明的 textarea 來實現接下來的功能:
function createFakerElement (text) {
const fakerElement = document.createElement('textarea')
fakerElement.style.position = 'absolute'
fakerElement.style.left = '-9999px'
fakerElement.value = text
document.body.appendChild(fakerElement)
return fakerElement
}
複製代碼
前面也提到選中文本有兩種方式:
因爲上述建立的是 textarea,這裏直接調用 select 方法:
function selectInput (element) {
return element.select()
}
複製代碼
前文已經說起,這裏再也不贅述。
接下來只要按照順序執行這些操做便可:
document.getElementById('js-button').addEventListener('click', () => {
const element = document.getElementById('js-select')
// 一、獲取須要的文本內容
const text = element.value
// 二、建立透明的 textarea 元素
const fakerElement = createFakerElement(text)
// 三、選中相應的文本
selectInput(fakerElement)
// 四、執行操做系統剪貼板的 copy 命令
const success = copyText()
if (success) {
console.log('複製成功')
} else {
console.log('複製失敗')
}
document.body.removeChild(fakerElement)
}, false)
複製代碼
由上文可知,前端模擬用戶的複製操做主要涉及兩方面的知識:
其中 document.execCommand 方法主要做用於 Selection 對象,因此當元素沒法被選中時,該複製命令則沒法達到預期的效果。
前面也到了 disabled 屬性以及 select 元素這樣的特例,相比較下,經過建立一個透明的 textarea 來模擬複製操做的方案可用性更高。
參考文獻
相關文章推薦
寫在最後
若是本文對您有幫助,點個贊吧!也歡迎小夥伴們關注個人訂閱號 漫談大前端