`<इनपुट प्रकार = संख्या>` पर स्क्रॉल अक्षम करें


121

क्या इनपुट नंबर फ़ील्ड में नंबर बदलते हुए स्क्रॉल व्हील को अक्षम करना संभव है? मैंने स्पिनर को हटाने के लिए वेबकिट-विशिष्ट सीएसएस के साथ गड़बड़ की है, लेकिन मैं इस व्यवहार से पूरी तरह छुटकारा पाना चाहूंगा। मुझे type=numberयह पसंद है क्योंकि यह iOS पर एक अच्छा कीबोर्ड लाता है।


7
प्रकार = संख्या का उपयोग करने के बजाय इनपुट प्रकार tel (टाइप = "tel") का उपयोग करें। यह एक iOS संख्या कीबोर्ड को पॉपअप करेगा।
प्रवीण विजयन

जब आप onscrollइसमें सिर्फ एक हैंडलर जोड़ते हैं तो क्या होता event.preventDefault()है?
रॉबर्ट

14
मेरी विनम्र राय में, मुझे नहीं लगता कि यह एक विशेषता होनी चाहिए। अगर मुझे ब्राउज़र डेवलपमेंट में कोई बात आती तो मैं शायद इस फीचर को हटाने के लिए जोर देता। यह कष्टप्रद होने के अलावा कुछ भी नहीं है, और मैं किसी को भी नहीं जानता, जो वास्तव में इसका उपयोग करेगा।
किर्कलैंड

3
मैं आपसे पूरी तरह से सहमत हूँ किर्कलैंड। किसी प्रपत्र के साथ पृष्ठ को स्क्रॉल करना बुरा UX है और, जब आपके माउस के अंतर्गत एक नंबर इनपुट तत्व जाता है, तो यह वृद्धि करना शुरू कर देता है और पृष्ठ स्क्रॉल करना बंद कर देता है। पूरी तरह से भटकाव।
kjs3

3
@PraveenVijayan: फिर भी यह एक वर्कअराउंड है, यह नए html5 इनपुट प्रकारों का उपयोग करने के किसी भी कारण के खिलाफ जाता है। भविष्य में यह हो सकता है कि फोन आपको संपर्कों या किसी भी चीज़ से नंबर लेने की संभावना देंगे, जो कि बहुत ही अजीब लगेगा यदि आप इसका मतलब एक अलग तरह की संख्या से हैं।
विस्मय

जवाबों:


92

अन्य लोगों द्वारा सुझाए गए इनपुट-नंबर तत्वों पर मूसवेल इवेंट के डिफ़ॉल्ट व्यवहार को रोकें (कॉलिंग "ब्लर ()" आम तौर पर ऐसा करने का पसंदीदा तरीका नहीं होगा, क्योंकि ऐसा नहीं होगा, जो उपयोगकर्ता चाहता है)।

परंतु। मैं हर समय सभी इनपुट-संख्या तत्वों पर मूसवेल इवेंट के लिए सुनने से बचता हूं और केवल तब करता हूं, जब तत्व ध्यान में होता है (जब समस्या मौजूद है)। अन्यथा माउस पॉइंटर कहीं भी नहीं है जब उपयोगकर्ता इनपुट-संख्या तत्व पर पृष्ठ को स्क्रॉल नहीं कर सकता है

JQuery के लिए समाधान:

// disable mousewheel on a input number field when in focus
// (to prevent Cromium browsers change the value when scrolling)
$('form').on('focus', 'input[type=number]', function (e) {
  $(this).on('wheel.disableScroll', function (e) {
    e.preventDefault()
  })
})
$('form').on('blur', 'input[type=number]', function (e) {
  $(this).off('wheel.disableScroll')
})

(ध्यान केंद्रित घटनाओं को आसपास के फार्म तत्व में बदल दें - कई घटना श्रोताओं से बचने के लिए, जो प्रदर्शन के लिए खराब हैं।)


2
बहुत बढ़िया जवाब। मुझे लगता है कि अगर मैं आज यह कर रहा होता तो मैं गैर-स्पर्श उपकरणों पर ईवेंट श्रोता को सशर्त रूप से लागू करने के लिए Modernizr.touch का उपयोग करता। मूल रूप से क्या user2863715 नीचे कहा गया है।
kjs3

शानदार उत्तर, लेकिन कम से कम वेबकिट में, यह विंडो को स्क्रॉल करने से रोकता है जबकि कर्सर इनपुट तत्व पर है। मैंने सोचा कि मूसवेल की घटनाओं को बबल भी माना जाता है।
रयान मैक्ग्रेनी

जब यह ध्यान में हो तो किसी तत्व में केवल निष्क्रिय स्क्रॉल फ़ंक्शन को लागू करना, यह स्क्रॉल को नहीं रोकना चाहिए, जब माउस इनपुट तत्व के ऊपर हो। लेकिन यह खिड़की को स्क्रॉल करने से रोकता है, जब तत्व ध्यान में होता है। और हाँ,
मूसलीवली

6
यह उस व्यवहार के लिए एक अच्छा समाधान है जो पहले स्थान पर मौजूद नहीं होना चाहिए।
जॉनी

यह अधिकांश यूनिक्स प्रकार के प्लेटफॉर्म gnome, osx, android (माउस के साथ) पर काम नहीं करता है क्योंकि स्क्रॉल व्यवहार के लिए इनपुट पर ध्यान केंद्रित करने की आवश्यकता नहीं होती है। वैकल्पिक रूप से, मैंने अभी-अभी पाठ प्रकार के इनपुट का उपयोग किया है और इसके लिए अपना नंबर प्रतिबंध रखा है (कुंजी शॉर्टकट को कम करना / लेकिन साथ ही js के साथ जोड़ा जा सकता है)
zeachco


20

एक घटना श्रोता उन सभी पर शासन करने के लिए

यह शुद्ध js में @Simon Perepelitsa के उत्तर के समान है , लेकिन थोड़ा सरल है, क्योंकि यह दस्तावेज़ तत्व पर एक ईवेंट श्रोता डालता है और जांचता है कि फ़ोकस किया गया तत्व एक नंबर इनपुट है या नहीं:

document.addEventListener("wheel", function(event){
    if(document.activeElement.type === "number"){
        document.activeElement.blur();
    }
});

यदि आप कुछ क्षेत्रों पर मूल्य स्क्रॉलिंग व्यवहार को बंद करना चाहते हैं, लेकिन अन्य लोग ऐसा नहीं करते हैं:

document.addEventListener("wheel", function(event){
    if(document.activeElement.type === "number" &&
       document.activeElement.classList.contains("noscroll"))
    {
        document.activeElement.blur();
    }
});

इसके साथ:

<input type="number" class="noscroll"/>

यदि इनपुट में noscroll वर्ग है तो यह स्क्रॉल पर परिवर्तन नहीं करेगा, अन्यथा सब कुछ समान रहता है।

यहां JSFiddle के साथ टेस्ट करें


मैं देख रहा हूं कि इसे डाउनवोट कर दिया गया है। यदि आपको कोई समस्या दिखाई देती है तो कृपया नीचे टिप्पणी के साथ एक टिप्पणी छोड़ दें। अगर मुझे कुछ याद आया तो मैं सीखना चाहूंगा कि यह क्या है। धन्यवाद।
पीटर रुक्मिणी

1
आधुनिक ब्राउज़र के लिए, कृपया wheelइसके बजाय ईवेंट का उपयोग करें mousewheel। संदर्भ: developer.mozilla.org/en-US/docs/Web/API/Element/wheel_event PS। मैं वह नहीं हूं, जो वोट कम करता है।
वी

19
input = document.getElementById("the_number_input")
input.addEventListener("mousewheel", function(event){ this.blur() })

http://jsfiddle.net/bQbDm/2/

JQuery के उदाहरण और क्रॉस-ब्राउज़र समाधान के लिए संबंधित प्रश्न देखें:

HTML5 इवेंट श्रोता संख्या इनपुट स्क्रॉल के लिए - केवल क्रोम


2
धन्यवाद सेमोन, मैं इसे jQuery के साथ सभी नंबर इनपुट के लिए इस तरह से करने में कामयाब रहा: $(':input[type=number]' ).live('mousewheel',function(e){ $(this).blur(); });मैंने डिफ़ॉल्ट को रोकने के बजाय धब्बा का उपयोग किया ताकि यह स्क्रॉल करने से पृष्ठ को अवरुद्ध न करे!
थिबुत कोल्सन

कलंक के बारे में अच्छा, मुझे नहीं पता था कि आप अभी भी पेज स्क्रॉलिंग की अनुमति दे सकते हैं। मैंने अपना उत्तर अपडेट कर दिया है।
साइमन पेरेपेलित्सा

13
FYI करें, live()पदावनत किया जाता है। अब, आप का उपयोग करना चाहिए on():$(':input[type=number]').on('mousewheel',function(e){ $(this).blur(); });
Saeid Zebardast

3
@SaeidZebardast आपकी टिप्पणी का जवाब देने के लिए योग्य हैं
नमकीन

आधुनिक ब्राउज़र के लिए, कृपया wheelइसके बजाय ईवेंट का उपयोग करें mousewheel। संदर्भ: developer.mozilla.org/en-US/docs/Web/API/Element/wheel_event
vee

16

आप बस HTML onwheel विशेषता का उपयोग कर सकते हैं ।

इस विकल्प का पेज के अन्य तत्वों पर स्क्रॉल करने पर कोई प्रभाव नहीं पड़ता है।

और सभी निविष्टियों के लिए एक श्रोता जोड़ें इनपुट में काम नहीं करते गतिशील रूप से बनाए गए।

सशर्त, आप CSS के साथ इनपुट तीर निकाल सकते हैं।

input[type="number"]::-webkit-outer-spin-button, 
input[type="number"]::-webkit-inner-spin-button {
    -webkit-appearance: none;
    margin: 0;
}
input[type="number"] {
    -moz-appearance: textfield;
}
<input type="number" onwheel="this.blur()" />


1
धन्यवाद भाई!! इसने एंगुलर - मैटेरियल 6
नसीरुद्दीन सैय्यद


हम इस CSS को कई स्रोतों में पा सकते हैं। वैसे भी, CSS केवल एक बोनस है। प्रश्न का वास्तविक समाधान HTML ऑनव्हील विशेषता है। ;-)
Maikon Matheus

5
मुझे यह समाधान पसंद है! धन्यवाद। मेरे मामले में, onBlur()अपेक्षा के अनुरूप नहीं था। मैं return falseवास्तव में "व्हील पर कुछ नहीं करता" के बजाय एक सरल सेटअप करता हूं । <input type="number" onwheel="return false;">
डैनियल

14

@ शिमोन Perepelitsa

इसके लिए एक बेहतर उपाय है। ब्लर इनपुट से फोकस हटाता है और यह एक साइड इफेक्ट है जो आप नहीं चाहते हैं। आपको इसके बजाय evt.preventDefault का उपयोग करना चाहिए। उपयोगकर्ता द्वारा स्क्रॉल किए जाने पर यह इनपुट के डिफ़ॉल्ट व्यवहार को रोकता है। यहाँ कोड है:

input = document.getElementById("the_number_input")
input.addEventListener("mousewheel", function(evt){ evt.preventDefault(); })

6
यह काम करता है, लेकिन घटना बुलबुला नहीं होगी, इसलिए पृष्ठ स्क्रॉल नहीं करेगा। क्या बिना ब्लोअर के डिफ़ॉल्ट व्यवहार (पेज स्क्रॉल) रखने का कोई तरीका है?
GuiGS

आधुनिक ब्राउज़र के लिए, कृपया wheelइसके बजाय ईवेंट का उपयोग करें mousewheel। संदर्भ: developer.mozilla.org/en-US/docs/Web/API/Element/wheel_event
vee

7

सबसे पहले आप या तो द्वारा mewewheel घटना को रोकना चाहिए:

  1. इसके साथ अक्षम करना mousewheel.disableScroll
  2. इससे इंटरसेप्ट कर रहा है e.preventDefault();
  3. तत्व से ध्यान हटाकर el.blur();

पहले दो दृष्टिकोण खिड़की को स्क्रॉल करने से रोकते हैं और अंतिम तत्व से ध्यान हटाता है; दोनों ही अवांछनीय परिणाम हैं।

एक el.blur()देरी के बाद तत्व का उपयोग करना और उसे रोकना है:

$('input[type=number]').on('mousewheel', function(){
  var el = $(this);
  el.blur();
  setTimeout(function(){
    el.focus();
  }, 10);
});

3
एक अच्छा दिखने वाला समाधान, लेकिन परीक्षण में मैंने पाया कि इस समाधान का फोकस चोरी करने का दुष्प्रभाव था। मैंने इसे इस बात के लिए टाल दिया: एक परीक्षण यह देखने के लिए कि क्या तत्व में फ़ोकस था: var hadFocus = el.is(':focus');धुंधला होने से पहले, और फिर एक गार्ड केवल टाइमआउट सेट करने के लिए था अगर हैफोकस सच था।
रॉब डॉसन

2

प्रदान किए गए उत्तर फ़ायरफ़ॉक्स (क्वांटम) में काम नहीं करते हैं। इवेंट श्रोता को मूसवेल से व्हील में बदलना होगा:

$(':input[type=number]').on('wheel',function(e){ $(this).blur(); });

यह कोड फ़ायरफ़ॉक्स क्वांटम और क्रोम पर काम करता है।


2

प्रतिक्रिया के साथ काम करने वाले और समाधान की तलाश में किसी के लिए भी। मुझे पता चला है कि इनपुट घटक में onWheelCapture प्रोप का उपयोग करना सबसे आसान तरीका है:

onWheelCapture={e => { e.target.blur() }}


2

प्रकार विविधता

टाइपस्क्रिप्ट को यह जानना होगा कि आप टाइप सुरक्षा के लिए HTMLElement के साथ काम कर रहे हैं, अन्यथा आपको बहुत Property 'type' does not exist on type 'Element'प्रकार की त्रुटियां दिखाई देंगी ।

document.addEventListener("mousewheel", function(event){
  let numberInput = (<HTMLInputElement>document.activeElement);
  if (numberInput.type === "number") {
    numberInput.blur();
  }
});

1

अपने लिए इसे हल करने की कोशिश करते हुए, मैंने देखा कि पृष्ठ के स्क्रॉलिंग को बनाए रखना संभव है और इनपुट के फ़ोकस को बनाए रखना है जबकि पकड़े गए इवेंट के मूल तत्व पर फिर से आग लगाने का प्रयास करके नंबर परिवर्तन को अक्षम करना, जिस <input type="number"/>पर इसे पकड़ा गया था। , बस इस तरह से:

e.target.parentElement.dispatchEvent(e);

हालाँकि, यह ब्राउज़र कंसोल में त्रुटि का कारण बनता है, और संभवतः हर जगह काम करने की गारंटी नहीं है (मैं केवल फ़ायरफ़ॉक्स पर परीक्षण किया गया), क्योंकि यह जानबूझकर अमान्य कोड है।

एक अन्य समाधान जो कम से कम फ़ायरफ़ॉक्स और क्रोमियम पर अच्छी तरह से काम करता है, अस्थायी रूप से इस तरह से <input>तत्व बनाने के लिए है readOnly:

function handleScroll(e) {
  if (e.target.tagName.toLowerCase() === 'input'
    && (e.target.type === 'number')
    && (e.target === document.activeElement)
    && !e.target.readOnly
  ) {
      e.target.readOnly = true;
      setTimeout(function(el){ el.readOnly = false; }, 0, e.target);
  }
}
document.addEventListener('wheel', function(e){ handleScroll(e); });

एक साइड इफ़ेक्ट जो मैंने देखा है, वह यह है कि यदि आप फ़ील्ड के लिए अलग-अलग स्टाइल रखते readOnlyहैं, तो स्प्लिट-सेकंड के लिए फ़ील्ड फ़्लिकर कर सकता है , लेकिन कम से कम मेरे मामले के लिए, यह एक मुद्दा नहीं लगता है।

इसी तरह, (जैसा कि जेम्स के उत्तर में समझाया गया है) readOnlyसंपत्ति को संशोधित करने के बजाय , आप blur()क्षेत्र और फिर focus()इसे वापस कर सकते हैं , लेकिन फिर, उपयोग में शैलियों के आधार पर, कुछ टिमटिमा सकता है।

वैकल्पिक रूप से, जैसा कि यहां अन्य टिप्पणियों में बताया गया है, आप केवल preventDefault()इसके बजाय घटना पर कॉल कर सकते हैं । यह मानते हुए कि आप केवल wheelउन संख्याओं की घटनाओं को संभालते हैं, जो फोकस में हैं और माउस कर्सर के तहत (जो कि तीन स्थितियों से ऊपर है), उपयोगकर्ता के अनुभव पर नकारात्मक प्रभाव किसी के भी करीब नहीं होगा।


1

यदि आप ऐसा समाधान चाहते हैं जिसमें जावास्क्रिप्ट की आवश्यकता न हो, तो सीएसएस छद्म तत्व के साथ कुछ एचटीएमएल कार्यक्षमता को जोड़कर यह चाल चली जाती है:

span {
  position: relative;
  display: inline-block; /* Fit around contents */
}

span::after {
  content: "";
  position: absolute;
  top: 0; right: 0; bottom: 0; left: 0; /* Stretch over containing block */
  cursor: text; /* restore I-beam cursor */
}

/* Restore context menu while editing */
input:focus {
  position: relative;
  z-index: 1;
}
<label>How many javascripts can u fit in u mouth?
  <span><input type="number" min="0" max="99" value="1"></span>
</label>

यह काम करता है क्योंकि <label>फॉर्म फ़ील्ड के साथ संबद्ध सामग्री पर क्लिक करने से फ़ील्ड फ़ोकस होगी। हालाँकि, क्षेत्र के ऊपर छद्म तत्व का "विंडोपैन" मौसमी घटनाओं को उस तक पहुँचने से रोक देगा।

दोष यह है कि ऊपर / नीचे स्पिनर बटन अब काम नहीं करते हैं, लेकिन आपने कहा कि आपने वैसे भी हटा दिए थे।


सिद्धांत रूप में, किसी को इनपुट मेनू की आवश्यकता के बिना संदर्भ मेनू को पहले ध्यान केंद्रित करने के लिए पुनर्स्थापित किया जा सकता है: उपयोगकर्ता स्क्रॉल करते समय :hoverशैलियों को आग नहीं देना चाहिए , क्योंकि ब्राउज़र प्रदर्शन कारणों से स्क्रॉल करने के दौरान उन्हें पुनर्गणना करने से बचते हैं, लेकिन मैंने पूरी तरह से क्रॉस-ब्राउज़र / डिवाइस नहीं बनाया है यह परीक्षण किया।


0
function fixNumericScrolling() {
$$( "input[type=number]" ).addEvent( "mousewheel", function(e) {
    stopAll(e);     
} );
}

function stopAll(e) {
if( typeof( e.preventDefault               ) != "undefined" ) e.preventDefault();
if( typeof( e.stopImmediatePropagation     ) != "undefined" ) e.stopImmediatePropagation();
if( typeof( event ) != "undefined" ) {
    if( typeof( event.preventDefault           ) != "undefined" ) event.preventDefault();
    if( typeof( event.stopImmediatePropagation ) != "undefined" ) event.stopImmediatePropagation();
}

return false;
}

0

सबसे आसान समाधान onWheel={ event => event.currentTarget.blur() }}इनपुट पर ही जोड़ना है।

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