चयन प्रकार / चयन इनपुट पर = क्रोम में = "संख्या" की अनुमति नहीं है


83

हमारा एप्लिकेशन इनपुट फ़ील्ड पर चयन स्टार्ट का उपयोग करता है यह निर्धारित करने के लिए कि क्या वे उपयोगकर्ता को अगले / पिछले क्षेत्र में ले जाते हैं जब वे तीर कुंजियों को दबाते हैं (यानी, जब चयन पाठ के अंत में होता है और उपयोगकर्ता दायां तीर दबाता है जिसे हम स्थानांतरित करते हैं अगला क्षेत्र, अन्यथा)

Chrome अब सेलेक्शनस्टार्ट को जहाँ = "नंबर" टाइप करने से रोकता है। अब यह अपवाद फेंकता है:

Failed to read the 'selectionStart' property from 'HTMLInputElement': The input element's type ('number') does not support selection.

निम्नलिखित देखें:

https://codereview.chromium.org/100433008/#ps60001

http://www.whatwg.org/specs/web-apps/current-work/multipage/the-input-element.html#do-not-apply

क्या टाइप = "संख्या" के इनपुट क्षेत्र में कैरेट के स्थान को निर्धारित करने का कोई तरीका है?


3
हम्म कोई अद्यतन नहीं। इस सुविधा को हटाने के लिए उत्सुक होने के कारण।
सेब

1
एक और उपयोग: यदि आप इनपुट प्रकार की संख्या के साथ jquery-maskmoney प्लगइन का उपयोग करते हैं, तो यही समस्या होती है
अलेक्जेंड्रे

क्या आप शायद इनपुट प्रकार को अस्थायी रूप से बदल textसकते हैं, कैरेट स्थिति की जांच कर सकते हैं, और फिर वापस प्रकार बदल सकते हैं number?
स्टेन

1
@ मुझे नहीं लगता कि स्वैपिंग प्रकार बहुत काम के होंगे, हालांकि मैंने अभी तक इसकी कोशिश नहीं की है।
स्टीवन

2
@ यह काम नहीं करता है, सिलेक्शनस्टार्ट / एंड हमेशा शून्य के रूप में वापस आता है: jsfiddle.net/Mottie/wMYKU
Mottie

जवाबों:


43

चयन केवल पाठ / खोज, URL, टेल और पासवर्ड के साथ अनुमत है । प्रकार संख्या के इनपुट के लिए चयन को अक्षम करने का संभावित कारण यह है कि कुछ उपकरणों पर, या कुछ परिस्थितियों में (उदाहरण के लिए, जब इनपुट को एक संक्षिप्त रूप में प्रस्तुत किया गया है list), तो कोई कैरेट नहीं हो सकता है। एकमात्र समाधान मैंने पाया है कि इनपुट प्रकार को पाठ में बदलना (इनपुट को प्रतिबंधित करने के लिए उपयुक्त पैटर्न के साथ)। मैं अभी भी इनपुट प्रकार को बदले बिना करने के लिए एक रास्ता ढूंढ रहा हूं और जब मुझे कुछ मिलेगा तो मैं एक अपडेट पोस्ट करूंगा।


6
मैं समझता हूं कि कुछ डिवाइस एक कैरेट प्रदर्शित नहीं कर सकते हैं लेकिन यह चीजों को जटिल करने के लिए लगता है। यदि हम हर चीज के लिए टाइप = "टेक्स्ट" का उपयोग करते हैं, तो वह टाइप होने के उद्देश्य को भी हरा देता है। यह फोन के लिए संख्यात्मक इनपुट आदि के लिए अलग-अलग कीबोर्ड दिखाने की क्षमता खो देता है। मैं इनपुट से चयन को हटाने के लिए उनकी पसंद से असहमत हूं, लेकिन मुझे यकीन नहीं है कि समाधान क्या है ...
स्टीवन

49
यह वास्तव में बेकार है। मैंने इस पर WHAT-WG से संपर्क किया है क्योंकि मुझे लगता है कि यह एक बड़ी गलती है। 99.9% उपयोगकर्ता एजेंट एक <input type="number"/>फ़ील्ड को एक टेक्स्ट फ़ील्ड के रूप में प्रस्तुत करते हैं जो डिफॉल्ट ऑन-स्क्रीन कीबोर्ड (यदि उपलब्ध हो) को संख्यात्मक कीबोर्ड पर सेट करता है लेकिन फिर भी फ़ील्ड को "टेक्स्ट इनपुट" फ़ील्ड के रूप में प्रस्तुत करता है। क्षेत्र के लिए एक कैलकुलेटर या इसी तरह के मूल्य हेरफेर की सुविधा को जोड़ने के लिए किसी भी मौजूदा / भविष्य के प्रयास अब बेकार हो गए हैं जब तक कि हम फ़ील्ड को वापस पाठ पर मजबूर नहीं करते हैं और उपयोगकर्ता अनुभव को बर्बाद कर देते हैं।
स्क्यूलिफ

3
मैं आप दोनों से सहमत हूं। जैसा कि मैं इस पोस्ट में इंगित करता हूं , मुझे लगता है कि मूल्य आईडीएल विशेषता में हमेशा एक पाठ प्रतिपादन होना चाहिए जिसमें इनपुट शामिल हो। इसके अलावा, यदि उपयोगकर्ता एजेंट चयन की अनुमति देता है, तो चयनस्टार्ट / एंड उपलब्ध होना चाहिए।
पैट्रिस चालिन

6
Whaaaaat o_0 क्रोम ने इंटरनेट को तोड़ दिया .. और मेरे परीक्षण। अधिक गंभीर नोट पर मुझे तर्क नहीं मिलते। एक उपयोगकर्ता को अपना ईमेल पता या नंबर चुनने में सक्षम क्यों नहीं होना चाहिए? stackoverflow.com/questions/22171694/…
पीटर

22

मुझे इसके लिए एक साधारण वर्कअराउंड (क्रोम पर परीक्षण किया गया) मिला है setSelectionRange()। आप बस उपयोग typeकरने textसे पहले बदल सकते हैं setSelectionRange()और फिर इसे वापस बदल सकते हैं number

यहां jquery के साथ एक सरल उदाहरण दिया गया है, जो जब भी आप इनपुट पर क्लिक करते हैं, तो इनपुट में नंबर 4 में स्थिति को ध्यान में रखेगा। व्यवहार को देखने के लिए इनपुट में 5 से अधिक संख्या जोड़ें)

डुबो देना


यह दृष्टिकोण emailइनपुट के लिए भी काम करता है (जो कि इस पृष्ठ पर समाप्त हो गया है यह सोचकर कि क्यों setSelectionRange()IE11 (!) और क्रोम में काम नहीं किया गया है)।
jdunning

यह jQuery के बिना काम करता है, शुद्ध जावास्क्रिप्ट के रूप में obj.type = "text"; फिर obj.type = "नंबर" पर लौटें;
जकौ

लेकिन प्लंकर अब उपयोगकर्ता को माउस के साथ चयन करने की अनुमति नहीं देता है।
मिस्टर लिस्टर

1
मेरे लिए (क्रोम संस्करण 80 में) यह अब काम नहीं करता है क्योंकि अगर मैं इनपुट प्रकार को "टेक्स्ट" का उपयोग करके सेट करता हूं input.type = 'text', तो क्रोम इनपुट से फ़ोकस हटाता है, और कर्सर गायब हो जाता है ताकि input.selectionStartआदि शून्य हो जाएं।
आनंद मसरी

16

वर्तमान में एकमात्र तत्व जो पाठ चयन को सुरक्षित रूप से अनुमति देते हैं:

<input type="text|search|password|tel|url">जैसा कि इसमें वर्णित है:
whatwg: SelectionStart विशेषता

आप इनपुट तत्वों का बारीकी से अवलोकन करने के लिए HTMLInputElement इंटरफ़ेस के लिए प्रलेखन भी पढ़ सकते हैं।

इस "मुद्दे" को सुरक्षित रूप से दूर करने के लिए, अब के लिए सबसे अच्छा एक के साथ सौदा है <input type="text">और एक मुखौटा / बाधा लागू करें जो केवल संख्याओं को स्वीकार करते हैं। आवश्यकता को पूरा करने वाले कुछ प्लगइन्स हैं:

आप यहां पिछले प्लग इन में से एक का लाइव डेमो देख सकते हैं:

यदि आप सुरक्षित रूप से उपयोग करना चाहते हैं selectionStart, तो आप उन तत्वों की जांच कर सकते हैं जो इसका समर्थन करते हैं ( इनपुट प्रकार विशेषताएँ देखें )

कार्यान्वयन

// Fix: failed to read the 'selectionStart' property from 'HTMLInputElement'
// The @fn parameter provides a callback to execute additional code
var _fixSelection = (function() {
    var _SELECTABLE_TYPES = /text|password|search|tel|url/;
    return function fixSelection (dom, fn) {
        var validType = _SELECTABLE_TYPES.test(dom.type),
            selection = {
                start: validType ? dom.selectionStart : 0,
                end: validType ? dom.selectionEnd : 0
            };
        if (validType && fn instanceof Function) fn(dom);
        return selection;
    };
}());

// Gets the current position of the cursor in the @dom element
function getCaretPosition (dom) {
    var selection, sel;
    if ('selectionStart' in dom) {
        return _fixSelection(dom).start;
    } else { // IE below version 9
        selection = document.selection;
        if (selection) {
            sel = selection.createRange();
            sel.moveStart('character', -dom.value.length);
            return sel.text.length;
        }
    }
    return -1;
}

प्रयोग

// If the DOM element does not support `selectionStart`,
// the returned object sets its properties to -1.
var box = document.getElementById("price"),
    pos = getCaretPosition(box);
console.log("position: ", pos);

उपरोक्त उदाहरण यहां पाया जा सकता है: jsu.fnGetCaretPosition ()


नमस्ते, पोस्ट के लिए धन्यवाद। क्या आप केवल यह समझा सकते हैं कि 'केवल संख्या को स्वीकार करने में बाधा' से आपका क्या मतलब है?
पेटारएमि

1
हाय @PetarMI, बाधा से मेरा मतलब है कि एक <इनपुट> तत्व केवल संख्यात्मक वर्णों को स्वीकार कर सकता है, और यह जावास्क्रिप्ट के माध्यम से किया जाता है, ऐसा इसलिए है क्योंकि सभी ब्राउज़र नए एचटीएमएल 5 <इनपुट> टैग के साथ ठीक से काम नहीं करते हैं।
jherax

5

JQuery न्यूमेरिक प्लगइन, संस्करण 1.3.x का उपयोग करते समय यह हमारे लिए हो रहा था, इसलिए लपेटकर selectionStartऔर हम selectionEndएक try...catch{}त्रुटि को दबाने में सक्षम थे।

स्रोत: https://github.com/joaquingatica/jQuery-Plugins/commit/a53f82044759d29ff30bac698b09e3202b456545


5

एक काम के आसपास के रूप में, type="tel"इनपुट प्रकार type="number"क्रोम में बहुत समान कार्यक्षमता प्रदान करता है और इसमें यह सीमा नहीं है (जैसा कि पैट्रिस द्वारा बताया गया है)।


fwiw यह एंड्रॉइड पर एक टेलीफोन विशिष्ट नंबरपैड देता है जबकि संख्या एक अलग numpad देता है
patrick

5

Chrome पर इसे पूरा करने का एक तरीका है (और शायद कुछ अन्य ब्राउज़र, लेकिन Chrome यहां बड़ा अपराधी है)। window.getSelection()वर्तमान इनपुट से चयन ऑब्जेक्ट को पुनः प्राप्त करने के लिए उपयोग करें और फिर चयन को पीछे की ओर (या आगे की ओर) बढ़ाएं और देखें कि क्या toString()चयन का मान बदलता है। यदि ऐसा नहीं होता है, तो कर्सर इनपुट के अंत में है और आप अपने अगले इनपुट पर जा सकते हैं। यदि ऐसा होता है, तो आपको चयन को पूर्ववत करने के लिए ऑपरेशन को उल्टा करना होगा।

s = window.getSelection();
len = s.toString().length;
s.modify('extend', 'backward', 'character');
if (len < s.toString().length) {
    // It's not at the beginning of the input, restore previous selection
    s.modify('extend', 'forward', 'character');
} else {
    // It's at the end, you can move to the previous input
}

मुझे यह विचार इस SO उत्तर से मिला: https://stackoverflow.com/a/24247942


3

क्या हम इस तरह से समर्थित तत्वों को शामिल करने के लिए केवल तत्व जांच को उल्टा नहीं कर सकते, जैसे:

if (deviceIsIOS &&
    targetElement.setSelectionRange &&
    (
        targetElement.type === 'text' ||
        targetElement.type === 'search' ||
        targetElement.type === 'password' ||
        targetElement.type === 'url' ||
        targetElement.type === 'tel'
    )
) {

इसके अलावा:

if (deviceIsIOS && 
    targetElement.setSelectionRange && 
    targetElement.type.indexOf('date') !== 0 && 
    targetElement.type !== 'time' && 
    targetElement.type !== 'month'
) {

1

हालांकि इस प्रकार के प्रपत्र फ़ील्ड के लिए हटाए गए ईवेंट के साथ समस्या अभी भी प्रासंगिक हो सकती है, जहां तक ​​मैं देख सकता हूं, इस तरह के फ़ील्ड को "परिवर्तन" इवेंट के साथ हमेशा की तरह सुना जा सकता है।

इस प्रकार के क्षेत्र के लिए घटनाओं के मुद्दे का जवाब ढूंढते हुए मुझे यह लेख यहां मिला, लेकिन इसका परीक्षण करते समय, मैंने पाया कि मैं केवल उल्लेखित "परिवर्तन" घटना पर भरोसा कर सकता हूं।


1

मुझे यह त्रुटि कोणीयज वेबसाइट में प्राप्त हुई।

मैंने एक इनपुट पर एक कस्टम डेटा विशेषता बनाई थी और एनजी-ब्लर ($ घटना के साथ) का भी उपयोग कर रहा था।

जब मेरे कॉलबैक को कॉल किया गया तो मैं 'डेटा-आईडी' मान को एक्सेस करने की कोशिश कर रहा था:

var id = $event.target.attributes["data-id"]

और यह इस तरह होना चाहिए था:

var id = $event.target.attributes["data-id"].value

इस त्रुटि के बारे में कहीं भी बहुत अधिक प्रतीत नहीं होता है इसलिए मैं इसे यहां छोड़ रहा हूं।


0

मुझे पता है कि यह उत्तर बहुत देर से आता है, लेकिन यहाँ एक प्लग-इन है जो सभी प्रकार के तत्वों के लिए चयन को आरंभ करता है, अधिकांश ब्राउज़रों (पुराने और नए) के लिए:

https://github.com/adelriosantiago/caret

मैंने इसे type="number"@ncohen के उत्तर का उपयोग करके समस्या से निपटने के लिए अद्यतन किया है ।


0

Failed to read the 'selectionStart' property from 'HTMLInputElement': The input element's type ('number') does not support selection.निम्नानुसार हल करें :

var checkFocus = false;
var originalValue = "";
$(document).ready(function() {
  $("input").focus(function() {
    var that = this;
    if ($('#' + $(this).context.id).attr("type") == "text") {
      setTimeout(function() {
        if (that.selectionStart != null || that.selectionEnd != null) {
          that.selectionStart = that.selectionEnd = 10000;
        }
      }, 0);
    } else if ($('#' + $(this).context.id).attr("type") == "number") {
      if (checkFocus) {
        moveCursorToEnd($('#' + $(this).context.id), $(this).context.id);
        checkValue($('#' + $(this).context.id))
        checkFocus = false;
      } else {
        $('#' + $(this).context.id).blur();
      }
    }
  });
});

function FocusTextBox(id) {
  checkFocus = true;
  document.getElementById(id).focus();
}

function checkValue(input) {
  if ($(input).val() == originalValue || $(input).val() == "") {
    $(input).val(originalValue)
  }
}

function moveCursorToEnd(input, id) {
  originalValue = input.val();
  input.val('');
  document.getElementById(id).focus();
  return originalValue;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.4.2/jquery.min.js"></script>
<button onclick="FocusTextBox('textid')">
   <input id="textid" type="number" value="1234" > 
</button>


0

यदि क्रोम उपकरण परीक्षण मोड का उपयोग कर रहे हैं तो इस पर कोणीय में झूठे सकारात्मक के लिए देखें।

तो यह स्पष्ट रूप से क्रोम है और वास्तविक iPhone नहीं है - फिर भी त्रुटि अभी भी उठती है क्योंकि _platform.IOSरिटर्न सही है और फिर setSelectionRangeबाद में विफल हो जाता है।

यह कोणीय है - लेकिन अन्य फ्रेमवर्क / वातावरण में समान मुद्दे मौजूद हो सकते हैं।

यहाँ छवि विवरण दर्ज करें

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