Faabass
Faabass

Reputation: 1164

Angular2 show two decimals in input

I have an angular2 app that needs to show ALWAYS two decimals in inputs after some calculations. But although in the component I force to have two decimals, in the input it shows it with zero decinmal, one decimal or the decimals that the number has but what I need is to show always two.

In the controller I force to have two decimals in this way

return +(this.getCost() * this.getQuantity()).toFixed(2);

But when I show that, the result can have different decimals size

<input name="number" pattern="^[0-9]+(\.[0-9]{1,2})?" step="0.01" formControlName="number" type="button" class="form-control" id="number" >

Adding that I;m using TypeScript and the field type is number (which I think is causing the rounded)

Upvotes: 10

Views: 28896

Answers (8)

JuanDM
JuanDM

Reputation: 1330

I would suggest you to use a mask on the input field there is a package text-mask that i've used before and works!

Note: take a look at you html input type, you said that is number, but actually in your question the type is button

To use the package:

  1. Install the packages

    npm i angular2-text-mask text-mask-addons --save

  2. Import it in you app-module file

    import { TextMaskModule } from 'angular2-text-mask';
    
    @NgModule({
      imports: [
        /* ... */
        TextMaskModule
      ]
      /* ... */
    })
    export class AppModule { }
    
  3. In you component.ts

    import createNumberMask from 'text-mask-addons/dist/createNumberMask';
    
    @Component({   
      selector: 'app-my-component',   
      templateUrl: './my-component.html',   
      styleUrls: ['./my.component.scss'] }) 
    
      export class MyComponent implements OnInit { 
      public price = 0;
    
      private currencyMask = createNumberMask({
        prefix: '',
        suffix: '',
        includeThousandsSeparator: true,
        thousandsSeparatorSymbol: ',',
        allowDecimal: true,
        decimalSymbol: '.',
        decimalLimit: 2,
        integerLimit: null,
        requireDecimal: false,
        allowNegative: false,
        allowLeadingZeroes: false
      });
    
    }
    
  4. In your component.html

    <input type="text" [textMask]="{mask: currencyMask}" name="receivedName" id="received" class="form-control" maxlength="50" [(ngModel)]="price"/>
    

Upvotes: 19

Faabass
Faabass

Reputation: 1164

At the end I did't find the right answer...

What I did was to create the following function

fixDecimals(value : string){
    value = "" + value;
    value = value.trim();
    value = parseFloat(value).toFixed(2);
    return value;
  }

And I changed the input type to text (instead of number).

And I'm calling this function in the ngOnInit so, I'm always showing the number with to decimals to the user. The only pending thing is that if the user change the value and remove the decimals, the number won't be completed with the corresponding 00.

I tried with the onChange, but the prompt goes to the end of the input (which is very awkard for the user)

Upvotes: 3

Ali Shawky
Ali Shawky

Reputation: 104

DecimalPipe

DecimalPipe is an angular Pipe API and belongs to CommonModule. DecimalPipe is used to format a number as decimal number according to locale rules. It uses number keyword with pipe operator. Find the syntax.

number_expression | number[:digitInfo]

Finally we get a decimal number as text. Find the description. number_expression: An angular expression that will give output a number. number : A pipe keyword that is used with pipe operator. digitInfo : It defines number format.

Now we will understand how to use digitInfo. The syntax for digitInfo is as follows.

{minIntegerDigits}.{minFractionDigits}-{maxFractionDigits}

Find the description.

minIntegerDigits : Minimum number of integer digits. Default is 1. 
minFractionDigits : Minimum number of fraction digits. Default is 0. 
maxFractionDigits : Maximum number of fraction digits. Default is 3.

Upvotes: 0

Ali Shawky
Ali Shawky

Reputation: 104

Use This Pipe

{{ number | number : '1.2-2'}}

Upvotes: 1

BrunoLM
BrunoLM

Reputation: 100331

tl;dr; Option 1: return a string, don't convert to number. Option 2: Use a number pipe.

toFixed returns a string.

You are converting the result of toFixed to a number

return +(this.getCost() * this.getQuantity()).toFixed(2);
       ↑

When you convert "1.20" to a number it will "remove" the extra 0 returning 1.2.

To show the result with 2 decimals you can return the result as a string so the 0 doesn't get cut off, or use a pipe.

You can use the number pipe

{{ 1.20 | number:'1.2-2' }}

Format: {minIntegerDigits}.{minFractionDigits}-{maxFractionDigits}

  • minIntegerDigits is the minimum number of integer digits to use. Defaults to 1.
  • minFractionDigits is the minimum number of digits after fraction. Defaults to 0.
  • maxFractionDigits is the maximum number of digits after fraction. Defaults to 3.

With the pipe you can keep your code returning a number and it will only change how the value is formatted when you show it on the screen.

Upvotes: 6

Kostas Asargiotakis
Kostas Asargiotakis

Reputation: 144

If your input is inside a form with name: inputForm e.g

HTML

    <form [formGroup]="inputForm">
      <input name="number" (keyup)="fixNumber()" pattern="^[0-9]+(\.[0-9]{1,2})?" step="0.01" `enter code here`formControlName="number" type="button" class="form-control" id="number">
</form>

TS

public fixNumber(){

      let value =this.inputForm.get('number').value;
      let prefix:string = value.toString().split('.')[0];
      let suffix:string = value.toString().split('.')[1];
      if(suffix.length > 2){
        let suffix_subed = suffix.substr(0,2);
        let new_value = prefix+'.'+suffix_subed;
        this.inputForm.get('number').setValue(new_value);
      }
}

You may get some log erros, but i think that's not big dead for that workaround

Upvotes: 1

Manit
Manit

Reputation: 1105

I don't know if I understood the problem correctly but what I understood is you somehow want to force the input to contain two digits after decimal. Here is a try: You need to convert the number to a float type and as you want it to be fixed to two decimal points use toFixed method.

Number.parseFloat(x).toFixed(2)
//Where x is the number which needs to be converted to a float type.

I hope this helps.

Upvotes: 4

Sathiyaraj
Sathiyaraj

Reputation: 343

In angular 2 have DecimalPipe this will helpful to your requirement.Please Use it. Sample:

Use format '3.2-5' : 

minIntegerDigits = 3 
minFractionDigits = 2 
maxFractionDigits = 5 

num = 12.324324

{{num1 | number:'3.2-5'}} 

012.63847 

Upvotes: 0

Related Questions