最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - How can I prevent trailing decimal point from displaying in number inputs after losing focus? - Stack Overflow

programmeradmin4浏览0评论

When using number inputs with the step attribute for decimal values, I noticed that when I type "1.2" and then delete the "2" to leave "1.", the trailing decimal point remains visible in the input even after the input loses focus. The actual value is "1" (without the decimal), but the display still shows "1.".

Here is a React example but it happens in plain HTML input as well. How can I fix this visual inconsistency?

function Example() {
  const [value, setValue] = React.useState('');
  const [focused, setFocused] = React.useState(false);
  
  return (
    <div>
      
      <label>
        Enter a decimal number <br/>(try typing "1.2" then delete the "2" and then lose focus):
       <br/><br/>
        <input
          type="number"
          step="0.01"
          value={value}
          onChange={(e) => {
            console.log("onChange value:", e.target.value);
            setValue(e.target.value);
          }}
          onFocus={() => setFocused(true)}
          onBlur={() => setFocused(false)}
          style={{padding: '5px', margin: '5px 0'}}
        />
      </label>
      
      <div style={{marginTop: '10px'}}>
        <p><strong>Input is currently:</strong> {focused ? 'Focused' : 'Blurred'}</p>
        <p><strong>Value in state:</strong> "{value}"</p>
      </div>
    </div>
  );
}

// Render it
ReactDOM.render(
  <Example />,
  document.getElementById('root')
);
<script src=".3.1/umd/react.production.min.js"></script>
<script src=".3.1/umd/react-dom.production.min.js"></script>
<div id="root"></div>

When using number inputs with the step attribute for decimal values, I noticed that when I type "1.2" and then delete the "2" to leave "1.", the trailing decimal point remains visible in the input even after the input loses focus. The actual value is "1" (without the decimal), but the display still shows "1.".

Here is a React example but it happens in plain HTML input as well. How can I fix this visual inconsistency?

function Example() {
  const [value, setValue] = React.useState('');
  const [focused, setFocused] = React.useState(false);
  
  return (
    <div>
      
      <label>
        Enter a decimal number <br/>(try typing "1.2" then delete the "2" and then lose focus):
       <br/><br/>
        <input
          type="number"
          step="0.01"
          value={value}
          onChange={(e) => {
            console.log("onChange value:", e.target.value);
            setValue(e.target.value);
          }}
          onFocus={() => setFocused(true)}
          onBlur={() => setFocused(false)}
          style={{padding: '5px', margin: '5px 0'}}
        />
      </label>
      
      <div style={{marginTop: '10px'}}>
        <p><strong>Input is currently:</strong> {focused ? 'Focused' : 'Blurred'}</p>
        <p><strong>Value in state:</strong> "{value}"</p>
      </div>
    </div>
  );
}

// Render it
ReactDOM.render(
  <Example />,
  document.getElementById('root')
);
<script src="https://cdnjs.cloudflare/ajax/libs/react/18.3.1/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare/ajax/libs/react-dom/18.3.1/umd/react-dom.production.min.js"></script>
<div id="root"></div>

Share Improve this question asked Mar 22 at 13:05 JulianJulian 236 bronze badges 1
  • It looks like a trailing dot or comma isn't a valid number in Chrome Mobile for Android. AFAIK, there isn't much you can do with invalid text in a number input field. You can't access the raw text and the browser returns an empty string for invalid input. Consider using a text input field instead. valueAsNumber returns NaN for input 1.. See How to get the raw value an <input type="number"> field? – jabaa Commented Mar 23 at 0:16
Add a comment  | 

1 Answer 1

Reset to default 2

The answer works for most browser, but fails for e.g. Chrome Mobile for Android. The reason:

It looks like a trailing dot or comma isn't a valid number in Chrome Mobile for Android. AFAIK, there isn't much you can do with invalid text in a number input field. You can't access the raw text and the browser returns an empty string or NaN for invalid input. Consider using a text input field instead if you have to support these browsers. valueAsNumber returns NaN and value returns an empty string for input 1.. See How to get the raw value an field?

This means that your code doesn't work in these browser even without my answer. The answer that works for most browsers:

You can remove the trailing decimal point the the onBlur handler:

function Example() {
  const [value, setValue] = React.useState('');
  const [focused, setFocused] = React.useState(false);
  
  return (
    <div>
      <label>
        Enter a decimal number <br/>(try typing "1.2" then delete the "2" and then lose focus):
       <br/><br/>
        <input
          type="number"
          step="0.01"
          value={value}
          onChange={(e) => {
            console.log("onChange value:", e.target.value);
            setValue(e.target.value);
          }}
          onFocus={() => setFocused(true)}
          onBlur={(e) => {e.target.valueAsNumber = e.target.valueAsNumber; return setFocused(false);}}
          style={{padding: '5px', margin: '5px 0'}}
        />
      </label>
      
      <div style={{marginTop: '10px'}}>
        <p><strong>Input is currently:</strong> {focused ? 'Focused' : 'Blurred'}</p>
        <p><strong>Value in state:</strong> "{value}"</p>
      </div>
    </div>
  );
}

// Render it
ReactDOM.render(
  <Example />,
  document.getElementById('root')
);
<script src="https://cdnjs.cloudflare/ajax/libs/react/18.3.1/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare/ajax/libs/react-dom/18.3.1/umd/react-dom.production.min.js"></script>
<div id="root"></div>

A number input field only stores the numerical value, not the textual representation with trailing dot.

e.target.valueAsNumber is a getter and a setter. When you read the value, you get the numerical value as number. When you set the value, the text in the input field is refreshed with the textual representation of the number without trailing dot.

与本文相关的文章

发布评论

评论列表(0)

  1. 暂无评论