jQuery

>

jQuery 表示エリアをクリックでコピー

公開日 : 2024/02/07

最終更新日時 : 2024/03/08 14:44:15

下記のように表示エリアをクリックしただけでコピーできる機能を実装してみる。

コピーさせたい内容

WordPress での実装を前提に進めていく。
 

jQuery でコピー機能を作成 (clipboard.js)

jQuery(function(){
    
    resizeDisplay();
    
    function resizeDisplay(){
        
        // とりあえず 49 タグに対応
        for (let i = 1; i < 50; i++) {
           if($('.pre' + i).length){
               guidDisplay('.pre' + i, '.dguid' + i, '.sguid' + i);
           }
        }
    }
    
    // 画面サイズの変更に対応
    $(window).resize(function(){
        resizeDisplay();
    });
    
    function guidDisplay(obj, dclass, sclass) {
        
        let divclass = dclass.replace('.', '');
        let spanclass = sclass.replace('.', '');
        
        // コピー案内用のタグ生成
        $(obj).after(`<div class="${divclass}"><span class="${spanclass}">Area click to copy</span></div>`);
        
        // div タグの CSS 設定
        $(dclass).css({
            width: "170px",
            height: "7px",
            textAlign: "right",
            zIndex: "999",
            visibility: "hidden",
        });
        
        // span タグの CSS 設定
        $(sclass).css({
            color: "white",
            fontSize: "1.4rem",
            opacity: "0.3",
        });
        
        // pre タグの位置を取得
        var offset = $(obj).offset();
        var y = offset.top + 3;
        var left = offset.left;
        var w = $(obj).width() - 161;
        var x = left + w;
        
        // 案内表示位置の設定
        $(dclass).offset({
            top: y,
            left: x
        });
        // Area click to copy 案内表示
        console.log('Copy 案内表示');
        $(dclass).css({
            visibility: "visible"
        });
    }
    
    // 表示エリアのクリックイベント
    for (let i = 1; i < 50; i++) {
        if($('.pre' + i).length){
            $('.pre' + i).click(function(){
                selectDomElm(this, '.dguid' + i, '.sguid' + i);
            });
        }
    }
    
    function selectDomElm(obj, dclass, sclass) {
        
        // コピーした旨の表示
        $(sclass).text('Copied!');
        
        var range = document.createRange();
        range.selectNodeContents(obj);
        
    // クリップボードへのコピー
        var copyText = $(obj).text();
        navigator.clipboard
            .writeText(copyText)
            .then(
              (success) => console.log('Success'),
              (error) => console.log('Fail')
            );
        
        var selection = window.getSelection();
        selection.removeAllRanges();
        selection.addRange(range);
        
        setTimeout(function(){
            //選択解除
            if (selection) {
                selection.removeAllRanges();
            }
            // 表示を Area click to copy に戻す
            $(sclass).text('Area click to copy');
        }, 2800); // 一定時間経過したら選択を解除する
        
    }
});

jQuery を使っていてこんなこと言うのもなんだが、document.execCommand(‘copy’) はオワコンに近いのでクリップボードへのコピーは navigator.clipboard.writeText を使用する。
コピー要素は pre タグで囲みます。pre タグをいくつ設置するかはさだかでないので、とりあえず 49 を上限として存在する分だけ作成されるようにしている。それに伴いコピー案内表示も作成されていく。
pre 自体のデザインは使用テーマの CSS ファイル で好きなように設定すればいい。

functions.php で clipboard.js を読み込ませる

function new_scripts() {

    wp_enqueue_script('new-jquery-3-7-1', get_template_directory_uri() . '/js/jquery-3.7.1.min.js', array('jquery'), '3.7.1');

    // clipboard.js 追加
    wp_enqueue_script('new-clipboard', get_template_directory_uri() . '/js/clipboard.js', array('jquery'), '1.0');

}
add_action('wp_enqueue_scripts', 'new_scripts');

上記はテーマディレクトリ内にある js ディレクトリにある clipboard.js を読み込ませる例。
jquery-3.7.1 等、jquery 本体が読み込まれているのが前提。既に js ファイルを読み込ませているブロック内に clipboard のインクルード構文だけ追加してもいい。

 

投稿欄での使用方法

コピーさせたい内容を pre タグで囲むだけ。

<pre class="pre1">
コピーさせたい内容
</pre>

class 名に pre1 を指定します。
pre タグを増やしていくにつれ pre2、pre3 のようにクラス名を変えて指定していきます。

 

スクリプトタグ込みでスクリプトコードを表示させたい

スクリプトコードなどを表示させてコピー機能を実装させたいならプラグインを利用するのが手っ取り早い。
それでもコピーアイコンではなく表示エリアクリックでコピーできるようにしたい場合はスクリプトコードを表示できるプラグインと上で導入した clipboard.js を連携させる必要がある。
 

Enlighter – Customizable Syntax Highlighter プラグインを導入して連携させる

ビジュアルモードで任意の場所に任意のコードを挿入する。

テキストモードに切り替え下記のようになっている pre タグのクラス名部分を

<pre class="EnlighterJSRAW" data-enlighter-language="generic">
&lt;!DOCTYPE html&gt;
&lt;html lang="ja"&gt;
&lt;head&gt;
&lt;meta charset="UTF-8"&gt;
&lt;meta name="viewport" content="width=device-width, initial-scale=1.0"&gt;
&lt;title&gt;Ajax Python データ送受信&lt;/title&gt;
&lt;script src="https://ajax.googleapis.com/ajax/libs/jquery/3.6.3/jquery.min.js"&gt;&lt;/script&gt;
&lt;script&gt;
$(function(){
    $.ajax({
            ⌇
            ⌇
            ⌇
</pre>

下記のようにクラス名を追加するとエリアクリックコピー機能を連携させることができる。

<pre class="EnlighterJSRAW pre1" data-enlighter-language="generic">

ここまでやるならいっそのことプラグインを自作したほうがいいかも。