0

I`m using primeNg input controls (p-spinner, p-calendar). Unfortunately the [(ngModel)]=”value” binding does not fire when I select the paste option from the context menu by mouse. Even if I click out of the control the lost focus does not take into account. The ctrl+v keyboard operation is fine but the mouse/context menu option would be the more important. Please help. My current version: "primeng": "^4.1.3",

McLac
  • 2,713
  • 3
  • 15
  • 19

1 Answers1

1

calendar input field looks like:

<input #inputfield 
       type="text" 
       [attr.id]="inputId" 
       [attr.name]="name" 
       [attr.required]="required" 
       [value]="inputFieldValue" 
       (focus)="onInputFocus($event)" 
       (keydown)="onInputKeydown($event)" 
       (click)="datepickerClick=true" 
       (blur)="onInputBlur($event)"
       [readonly]="readonlyInput" 
       (input)="onUserInput($event)" 
       [ngStyle]="inputStyle" 
       [class]="inputStyleClass" 
       [placeholder]="placeholder||''" 
       [disabled]="disabled" 
       [attr.tabindex]="tabindex"
       [ngClass]="'ui-inputtext ui-widget ui-state-default ui-corner-all'">

when you copy from contextual menu (keydown)="onInputKeydown($event)" is triggered:

onInputKeydown(event) {
  this.isKeydown = true;
  if(event.keyCode === 9) {
    this.overlayVisible = false;
  }
}

and then (input)="onUserInput($event)"

onUserInput(event) {
  // IE 11 Workaround for input placeholder : https://github.com/primefaces/primeng/issues/2026
  if(!this.isKeydown) {
    return;
  }
  this.isKeydown = false;

  let val = event.target.value;   
  try {
    let value = this.parseValueFromString(val);
    this.updateModel(value);
    this.updateUI();
  } 
  catch(err) {
    //invalid date
    this.updateModel(null);
  }

  this.filled = val != null && val.length;
  this.onInput.emit(event);
}

it looks like IE 11 Workaround causes additional problems with none-keyboard interactions (like paste via right click). So, as work around set this.isKeydown = true; on input paste event.

  1. Import Calendar and ViewChild:

    import { Component, NgModule, ViewChild } from '@angular/core';
    import { CalendarModule, Calendar } from 'primeng/primeng';
    
  2. get p calendar reference: HTML:

    <p-calendar #calendarRef [(ngModel)]="value"></p-calendar>
    

    TS file:

    @ViewChild('calendarRef') calendarRef: Calendar;
    
  3. register paste listener in ngAfterViewInit hook:

    ngAfterViewInit() {
      this.calendarRef.inputfieldViewChild.nativeElement.onpaste = (e) {
        this.calendarRef.isKeydown = true;
      }
    }
    

it should work now,

plunker: https://plnkr.co/edit/SSI4XDxGtu1O59DJZfd4?p=preview

UPDATE FOR SPINNER

  1. add spinner reference as @ViewChild
  2. register onpaste listener on spinner reference

    export class App implements OnAfterViewInit {
      @ViewChild('calendarRef') calendarRef: Calendar;
      @ViewChild('spinnerRef') spinnerRef: Spinner;
    
      value: Date;
    
      ngAfterViewInit() {
        this.calendarRef.inputfieldViewChild.nativeElement.onpaste = (e) {
          this.calendarRef.isKeydown = true;
        }
    
        this.spinnerRef.el.nativeElement.onpaste = (event) {
          setTimeout(_ => {
            this.spinnerRef.onInput(event, event.target.value);
          });
        }
      }
    }
    

    PLUNKER also updated

Reference to onInput() function: https://github.com/primefaces/primeng/blob/master/src/app/components/spinner/spinner.ts#L201

Andriy
  • 14,781
  • 4
  • 46
  • 50