एक तत्व में पाठ का चयन करना (अपने माउस से हाइलाइट करना)


424

मैं चाहूंगा कि उपयोगकर्ता किसी लिंक पर क्लिक करें, फिर वह दूसरे तत्व में HTML पाठ का चयन करता है ( इनपुट नहीं )।

"चयन करें" से मेरा मतलब है कि आप उसी तरह से अपने माउस को खींचकर पाठ का चयन करेंगे। यह अनुसंधान के लिए एक भालू रहा है क्योंकि हर कोई अन्य शब्दों में "चयन" या "हाइलाइट" के बारे में बात करता है।

क्या यह संभव है? मेरा कोड अब तक:

HTML:

<a href="javascript:" onclick="SelectText('xhtml-code')">Select Code</a>
<code id="xhtml-code">Some Code here </code>

जे एस:

function SelectText(element) {
    $("#" + element).select();
}

क्या मुझे कुछ स्पष्ट याद आ रहा है?


जवाबों:


612

सादा जावास्क्रिप्ट

function selectText(node) {
    node = document.getElementById(node);

    if (document.body.createTextRange) {
        const range = document.body.createTextRange();
        range.moveToElementText(node);
        range.select();
    } else if (window.getSelection) {
        const selection = window.getSelection();
        const range = document.createRange();
        range.selectNodeContents(node);
        selection.removeAllRanges();
        selection.addRange(range);
    } else {
        console.warn("Could not select text in node: Unsupported browser.");
    }
}

const clickable = document.querySelector('.click-me');
clickable.addEventListener('click', () => selectText('target'));
<div id="target"><p>Some text goes here!</p><p>Moar text!</p></div>
<p class="click-me">Click me!</p>

यहाँ एक कार्यशील डेमो है । आप में से एक jQuery प्लगइन की तलाश में हैं, मैंने उनमें से एक भी बनाया है


jQuery (मूल उत्तर)

मैंने इसके लिए इस सूत्र में एक उपाय खोजा है । मैं दी गई जानकारी को संशोधित करने में सक्षम था और किसी भी तत्व में पाठ का चयन करने के लिए पूरी तरह से भयानक फ़ंक्शन बनाने के लिए इसे jQuery के एक बिट के साथ मिलाया, ब्राउज़र की परवाह किए बिना:

function SelectText(element) {
    var text = document.getElementById(element);
    if ($.browser.msie) {
        var range = document.body.createTextRange();
        range.moveToElementText(text);
        range.select();
    } else if ($.browser.mozilla || $.browser.opera) {
        var selection = window.getSelection();
        var range = document.createRange();
        range.selectNodeContents(text);
        selection.removeAllRanges();
        selection.addRange(range);
    } else if ($.browser.safari) {
        var selection = window.getSelection();
        selection.setBaseAndExtent(text, 0, text, 1);
    }
}

jQuery समाधान मुझे देता है Uncaught TypeError: अनिर्धारित की संपत्ति 'MSIE' पढ़ा नहीं जा सकता
egmfrs

@egmfrs yea जब से यह उत्तर पोस्ट किया गया था, jquery ने अपने browserस्निफर को हटा दिया है ।
जेसन

127

यहाँ एक संस्करण है जिसमें कोई ब्राउज़र सूँघता नहीं है और jQuery पर निर्भरता नहीं है:

function selectElementText(el, win) {
    win = win || window;
    var doc = win.document, sel, range;
    if (win.getSelection && doc.createRange) {
        sel = win.getSelection();
        range = doc.createRange();
        range.selectNodeContents(el);
        sel.removeAllRanges();
        sel.addRange(range);
    } else if (doc.body.createTextRange) {
        range = doc.body.createTextRange();
        range.moveToElementText(el);
        range.select();
    }
}

selectElementText(document.getElementById("someElement"));
selectElementText(elementInIframe, iframe.contentWindow);

क्या कोई पाठ का चयन करने का कोई तरीका है div contentEditable='true'?
ओल्डबॉय

@PrimitiveNom: यह कोड एक संतोषप्रद तत्व पर काम करेगा, लेकिन आपको यह सुनिश्चित करना होगा कि इसमें पहले फोकस हो।
टिम डाउन

18

जेसन के कोड का उपयोग एक iframe के अंदर तत्वों के लिए नहीं किया जा सकता है (जैसा कि विंडो और दस्तावेज़ से गुंजाइश अलग है)। मैंने उस समस्या को ठीक किया और मैंने इसे किसी अन्य jQuery प्लगइन (चेनेबल) के रूप में उपयोग करने के लिए संशोधित किया:

उदाहरण 1: सभी पाठों का चयन <code> टैग पर एकल क्लिक के साथ और "चयनित" वर्ग जोड़ें:

$(function() {
    $("code").click(function() {
        $(this).selText().addClass("selected");
    });
});

उदाहरण 2: बटन पर क्लिक करने पर, iframe के अंदर एक तत्व चुनें:

$(function() {
    $("button").click(function() {
        $("iframe").contents().find("#selectme").selText();
    });
});

नोट: याद रखें कि iframe स्रोत को सुरक्षा त्रुटियों को रोकने के लिए उसी डोमेन में रहना चाहिए।

jQuery प्लगइन:

jQuery.fn.selText = function() {
    var obj = this[0];
    if ($.browser.msie) {
        var range = obj.offsetParent.createTextRange();
        range.moveToElementText(obj);
        range.select();
    } else if ($.browser.mozilla || $.browser.opera) {
        var selection = obj.ownerDocument.defaultView.getSelection();
        var range = obj.ownerDocument.createRange();
        range.selectNodeContents(obj);
        selection.removeAllRanges();
        selection.addRange(range);
    } else if ($.browser.safari) {
        var selection = obj.ownerDocument.defaultView.getSelection();
        selection.setBaseAndExtent(obj, 0, obj, 1);
    }
    return this;
}

मैंने इसे IE8, फ़ायरफ़ॉक्स, ओपेरा, सफारी, क्रोम (वर्तमान संस्करण) में परीक्षण किया। मुझे यकीन नहीं है कि यह पुराने IE संस्करणों में काम करता है (ईमानदारी से मुझे परवाह नहीं है)।


3
$ .browser को अब हटा दिया गया है / हटा दिया गया है - इसके लिए फिर से लिखने की ज़रूरत है
जेम्स मैककॉर्मैक

2
@JamesMcCormack: हाँ। मुझे यकीन नहीं है कि अगर यह फिर से लिखा जाएगा तो यह लायक होगा क्योंकि यहां अन्य समाधान पोस्ट किए गए हैं जिनमें $ .browser शामिल नहीं है।
लेप

16

यह धागा में वास्तव में अद्भुत सामग्री है। लेकिन मैं "सुरक्षा त्रुटि" के कारण FF 3.5b99 + FireBug का उपयोग करके इस पृष्ठ पर इसे ठीक से करने में सक्षम नहीं हूं।

Yipee !! मैं इस कोड के साथ पूरे दाहिने हाथ के साइडबार का चयन करने में सक्षम था आशा है कि यह आपकी मदद करता है:

    var r = document.createRange();
    var w=document.getElementById("sidebar");  
    r.selectNodeContents(w);  
    var sel=window.getSelection(); 
    sel.removeAllRanges(); 
    sel.addRange(r); 

PS: - मैं jquery चयनकर्ताओं द्वारा लौटाए गए ऑब्जेक्ट का उपयोग करने में सक्षम नहीं था जैसे कि

   var w=$("div.welovestackoverflow",$("div.sidebar"));

   //this throws **security exception**

   r.selectNodeContents(w);

2
आपको jQuery से तत्व प्राप्त करने की आवश्यकता है, जैसा कि आप एक jQuery ऑब्जेक्ट का चयन करने की कोशिश कर रहे हैं: var w = $ ("div.welovestackoverflow", $ ("div.sidebar"))। Get (0);
ब्लिक्स

काम नहीं करता ... मुझे एक त्रुटि मिलती है "ऑब्जेक्ट इस पद्धति का समर्थन नहीं करता है" और यह पहली पंक्ति पर प्रकाश डालता है। मैंने कुछ खुदाई की और पाया कि एक "document.body.createTextRange ()" है, लेकिन फिर "selectNodeContents" काम नहीं करता है .... और यह IE में है
जेसन

मैंने वह धागा पढ़ा जो आपने पाया ... अद्भुत ... मैं उस जानकारी से एक फ़ंक्शन बनाने में सक्षम था जो सभी ब्राउज़रों पर काम करता है। आपको बहुत - बहुत धन्यवाद! मेरा समाधान पोस्ट किया गया है
जेसन

6

आप किसी भी तत्व की सामग्री का चयन करने के लिए निम्न फ़ंक्शन का उपयोग कर सकते हैं:

jQuery.fn.selectText = function(){
    this.find('input').each(function() {
        if($(this).prev().length == 0 || !$(this).prev().hasClass('p_copy')) { 
            $('<p class="p_copy" style="position: absolute; z-index: -1;"></p>').insertBefore($(this));
        }
        $(this).prev().html($(this).val());
    });
    var doc = document;
    var element = this[0];
    console.log(this, element);
    if (doc.body.createTextRange) {
        var range = document.body.createTextRange();
        range.moveToElementText(element);
        range.select();
    } else if (window.getSelection) {
        var selection = window.getSelection();        
        var range = document.createRange();
        range.selectNodeContents(element);
        selection.removeAllRanges();
        selection.addRange(range);
    }
};

इस समारोह को इस प्रकार कहा जा सकता है:

$('#selectme').selectText();

5

मैं उसी चीज की तलाश कर रहा था, मेरा समाधान यह था:

$('#el-id').focus().select();

3
आप focus()एक गैर-इनपुट पर उपयोग नहीं कर सकते , जो कि यह सवाल है।
जेसन

4
लेकिन आप इसे एक textarea तत्व पर उपयोग कर सकते हैं - जो कि मुझे यहां पहुंचने के लिए समस्या थी। सभी तरह से प्रश्न को न पढ़ने के लिए मेरी गलती है।
ऑस्टन

4

मुझे कुछ चीजों को छोड़कर लेप का जवाब पसंद आया:

  1. ब्राउज़र-सूँघना, jQuery या नहीं इष्टतम नहीं है
  2. सूखी
  3. IE8 में काम नहीं करता है अगर obj के माता पिता createTextRange का समर्थन नहीं करता है
  4. Chrome का सेटबेस उपयोग करने की क्षमता का लाभ जाना चाहिए (IMO)
  5. कई DOM तत्वों ("चयनित" तत्व के भीतर तत्व) में फैले पाठ का चयन नहीं करेंगे। दूसरे शब्दों में, यदि आप कई स्पेल तत्वों वाले div पर selText कहते हैं, तो यह उन तत्वों में से प्रत्येक के पाठ का चयन नहीं करेगा । यह मेरे लिए, YMMV के लिए एक डील-ब्रेकर था।

यहाँ मैं प्रेरणा के लिए लेप के जवाब के लिए एक इशारा के साथ आया था। मुझे यकीन है कि मेरा उपहास किया जाएगा क्योंकि यह शायद थोड़ा भारी-भरकम है (और वास्तव में मोरेसो हो सकता है लेकिन मैं पचाता हूं)। लेकिन यह काम करता है और ब्राउज़र-सूँघने से बचता है और यही बात है

selectText:function(){

    var range,
        selection,
        obj = this[0],
        type = {
            func:'function',
            obj:'object'
        },
        // Convenience
        is = function(type, o){
            return typeof o === type;
        };

    if(is(type.obj, obj.ownerDocument)
        && is(type.obj, obj.ownerDocument.defaultView)
        && is(type.func, obj.ownerDocument.defaultView.getSelection)){

        selection = obj.ownerDocument.defaultView.getSelection();

        if(is(type.func, selection.setBaseAndExtent)){
            // Chrome, Safari - nice and easy
            selection.setBaseAndExtent(obj, 0, obj, $(obj).contents().size());
        }
        else if(is(type.func, obj.ownerDocument.createRange)){

            range = obj.ownerDocument.createRange();

            if(is(type.func, range.selectNodeContents)
                && is(type.func, selection.removeAllRanges)
                && is(type.func, selection.addRange)){
                // Mozilla
                range.selectNodeContents(obj);
                selection.removeAllRanges();
                selection.addRange(range);
            }
        }
    }
    else if(is(type.obj, document.body) && is(type.obj, document.body.createTextRange)) {

        range = document.body.createTextRange();

        if(is(type.obj, range.moveToElementText) && is(type.obj, range.select)){
            // IE most likely
            range.moveToElementText(obj);
            range.select();
        }
    }

    // Chainable
    return this;
}

बस। जो कुछ आप देखते हैं वह पठनीयता और / या सुविधा के लिए है। ओपेरा, सफारी, क्रोम, फ़ायरफ़ॉक्स और IE के नवीनतम संस्करणों में मैक पर परीक्षण किया गया। IE8 में भी परीक्षण किया गया। इसके अलावा, मैं आमतौर पर कोड ब्लॉक के अंदर जरूरत पड़ने पर केवल चर घोषित करता हूं, लेकिन jslint ने सुझाव दिया कि वे सभी को शीर्ष घोषित किया जाएगा। ठीक है jslint

संपादित करें मैं इसे op के कोड में कैसे शामिल करना भूल गया:

function SelectText(element) {
    $("#" + element).selectText();
}

चियर्स


हाँ, यह मुझे भारी लगता है, हालाँकि यह सही प्रतीत होता है। मेरा मुख्य सार यह है कि गैर-मानक का उपयोग करना setBaseAndExtent()सिर्फ इसलिए कि यह मेरे लिए व्यर्थ लगता है जब आप बस उस शाखा को हटा सकते हैं और सब कुछ ठीक उसी तरह और मानक-आधारित तरीके से काम करता है। फीचर का पता लगाना अच्छा है, लेकिन मैं हर चीज को परख कर थक जाता हूं जो बहुत जल्दी पूरी हो जाती है।
टिम डाउन

खैर @TimDown का लाभ उठाने setBaseAndExtentकी बात यह है कि यह काफी अधिक कुशल है, और यहां तक ​​कि जोड़ा ifराज्य के साथ अभी भी कहीं अधिक है अगर आप "उस शाखा को हटा दें"। मुझे वास्तव में "मैं थक गया हूँ .." की टिप्पणी समझ में नहीं आती है? इसे लिखें और इसे भूल जाएं, आपको केवल यही करना है कि फ़ंक्शन को कॉल करें, इसे न लिखें। :)
Madbreaks

@ मैडब्रेक्स मैं आश्चर्यचकित होता अगर setBaseAndExtentइससे अधिक प्रदर्शन होता addRange। ऐसा क्यों होगा? मेरी अन्य टिप्पणी आपकी विशेषता परीक्षण लोकाचार से संबंधित सभी DOM इंटरैक्शन के लिए विस्तारित थी: इसका उपयोग करने से पहले हर एक DOM विधि और संपत्ति का परीक्षण करने के लिए यह एक बहुत बड़ा कोड है। मैं निराश नहीं करता; मैं लाइन खींचने और अपने कोड में कुछ और धारणा बनाने के लिए खुश हूं।
टिम डाउन

4

क्रोम में काम करने वाला अपडेटेड संस्करण:

function SelectText(element) {
    var doc = document;
    var text = doc.getElementById(element);    
    if (doc.body.createTextRange) { // ms
        var range = doc.body.createTextRange();
        range.moveToElementText(text);
        range.select();
    } else if (window.getSelection) {
        var selection = window.getSelection();
        var range = doc.createRange();
        range.selectNodeContents(text);
        selection.removeAllRanges();
        selection.addRange(range);

    }
}

$(function() {
    $('p').click(function() {
        SelectText("selectme");

    });
});

http://jsfiddle.net/KcX6A/326/


3

किसी भी टैग के लिए कोई भी उस छोटे और सरल कोड के द्वारा उस टैग के अंदर सभी पाठ का चयन कर सकता है। यह पीले रंग के साथ पूरे टैग क्षेत्र को उजागर करेगा और सिंगल क्लिक पर इसके अंदर पाठ का चयन करेगा।

document.onclick = function(event) {
    var range, selection;
event.target.style.backgroundColor = 'yellow';
        selection = window.getSelection();
        range = document.createRange();
        range.selectNodeContents(event.target);
        selection.removeAllRanges();
        selection.addRange(range);
};

2

lepe - यह मेरे लिए बहुत काम करता है धन्यवाद! मैंने आपका कोड एक प्लगइन फ़ाइल में डाला, फिर इसे प्रत्येक कथन के साथ संयोजन में उपयोग किया ताकि आप एक पृष्ठ पर कई पूर्व टैग और एकाधिक "सभी का चयन करें" लिंक कर सकें और यह हाइलाइट करने के लिए सही पूर्व चुनता है:

<script type="text/javascript" src="../js/jquery.selecttext.js"></script>
<script type="text/javascript">
  $(document).ready(function() { 
        $(".selectText").each(function(indx) {
                $(this).click(function() {                 
                    $('pre').eq(indx).selText().addClass("selected");
                        return false;               
                    });
        });
  });


1

चयन ऑब्जेक्ट (गेको इंजन) और टेक्स्टरेंज ऑब्जेक्ट (ट्राइडेंट इंजन) पर एक नज़र डालें । मुझे किसी भी जावास्क्रिप्ट चौखटे के बारे में नहीं पता है जिसके लिए इसे लागू करने के लिए क्रॉस-ब्राउज़र समर्थन है, लेकिन मैंने कभी भी इसकी तलाश नहीं की है, इसलिए यह संभव है कि jQuery के पास भी हो।


0

टिम का तरीका मेरे मामले के लिए पूरी तरह से काम करता है - निम्न कथन को प्रतिस्थापित करने के बाद IE और FF दोनों के लिए div में पाठ का चयन करना:

range.moveToElementText(text);

निम्नलिखित के साथ:

range.moveToElementText(el);

निम्नलिखित jQuery फ़ंक्शन के साथ क्लिक करके div में पाठ का चयन किया जाता है:

$(function () {
    $("#divFoo").click(function () {
        selectElementText(document.getElementById("divFoo"));
    })
});

0

स्ट्रिंग के रूप में चयनित पाठ प्राप्त करने के लिए यहां एक और सरल उपाय है, आप अपने कोड में एक दिव्य तत्व के बच्चे को जोड़ने के लिए आसानी से इस स्ट्रिंग का उपयोग कर सकते हैं:

var text = '';

if (window.getSelection) {
    text = window.getSelection();

} else if (document.getSelection) {
    text = document.getSelection();

} else if (document.selection) {
    text = document.selection.createRange().text;
}

text = text.toString();

यह हाइलाइट किए गए टेक्स्ट को वापस करने के लिए है, हाइलाइट बनाने के लिए नहीं।
एमकेएन वेब सॉल्यूशंस

0

मेरा विशेष उपयोग-मामला एक संपादन योग्य अवधि तत्व के अंदर एक पाठ रेंज का चयन कर रहा था, जो कि जहाँ तक मैं देख सकता था, यहाँ किसी भी उत्तर में वर्णित नहीं है।

मुख्य अंतर यह है कि आपको ऑब्जेक्ट के प्रकार Textका एक नोड पास करना होगा Range, जैसा कि Range.setStart () के प्रलेखन में वर्णित है :

यदि startNode पाठ, टिप्पणी, या CDATASection का एक नोड प्रकार है , तो startOffset प्रारंभनोड के प्रारंभ से वर्णों की संख्या है। अन्य नोड प्रकारों के लिए, स्टार्टऑनसेट प्रारंभ के प्रारंभ के बीच चाइल्ड नोड्स की संख्या है।

Textनोड, किसी स्पान तत्व के पहले चाइल्ड नोड है, इसलिए इसे पाने के लिए, का उपयोगchildNodes[0] अवधि तत्व की। बाकी सभी उत्तरों के समान ही है।

यहाँ एक कोड उदाहरण है:

var startIndex = 1;
var endIndex = 5;
var element = document.getElementById("spanId");
var textNode = element.childNodes[0];

var range = document.createRange();
range.setStart(textNode, startIndex);
range.setEnd(textNode, endIndex);

var selection = window.getSelection();
selection.removeAllRanges();
selection.addRange(range);

अन्य प्रासंगिक दस्तावेज:
रेंज
चयन
दस्तावेज़।
रिट्रीरेन्ज () Window.getSelection ()


-1

jQuery.browser.webkitChrome के लिए "और यदि" में जोड़ा गया । क्रोम 23 में यह काम नहीं कर सका।

एक <pre>टैग में सामग्री का चयन करने के लिए नीचे इस स्क्रिप्ट को बनाया class="code"

jQuery( document ).ready(function() {
    jQuery('pre.code').attr('title', 'Click to select all');
    jQuery( '#divFoo' ).click( function() {
        var refNode = jQuery( this )[0];
        if ( jQuery.browser.msie ) {
            var range = document.body.createTextRange();
            range.moveToElementText( refNode );
            range.select();
        } else if ( jQuery.browser.mozilla || jQuery.browser.opera  || jQuery.browser.webkit ) {
            var selection = refNode.ownerDocument.defaultView.getSelection();
            console.log(selection);
            var range = refNode.ownerDocument.createRange();
            range.selectNodeContents( refNode );
            selection.removeAllRanges();
            selection.addRange( range );
        } else if ( jQuery.browser.safari ) {
            var selection = refNode.ownerDocument.defaultView.getSelection();
            selection.setBaseAndExtent( refNode, 0, refNode, 1 );
        }
    } );
} );

-1

के jQuery प्रलेखन के अनुसार select():

प्रत्येक मिलान किए गए तत्व की चुनिंदा घटना को ट्रिगर करें। यह उन सभी फ़ंक्शंस का कारण बनता है जो उस चयनित ईवेंट के लिए बाध्य किए गए हैं, और मिलान तत्व (ओं) पर ब्राउज़र की डिफ़ॉल्ट चयन कार्रवाई को कॉल करता है।

select()इस मामले में jQuery काम नहीं करेगा क्यों आपकी व्याख्या है ।


4
मैं एक सीएसएस शैली के साथ पाठ को उजागर करने की कोशिश नहीं कर रहा हूं। मैं चाहता हूं कि पाठ का चयन किया जाए।
जेसन
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.