ng-bootstrap: ngb-datepicker 初始值 angular 反应形式组未设置

ng-bootstrap: ngb-datepicker initial value with angular reactive form group is not getting set

  1. 我正在使用 ngb-datepicker 如果没有初始值,它工作正常 设置了值或预定义值,但在尝试使用它时 formControlName[(ngModel)] 与现有的预定义 value 预定义或初始值未在 redenied 上设置 看法。将其想象为编辑表单或记录的场景 预填充值。其他带有文本和数字的 formControls 是 按预期工作。
  2. 我正在使用 NgbStruct 模型,但仍然无法正常工作。
  3. 我尝试并调试了将值分配给 patchValue 方法中的表单控件,格式为 NgbStruct 但在渲染视图中看不到
  4. 我尝试在堆栈中提供的示例中实现类似的场景 ng-bootstrap 的闪电战在那里工作得很好

Package.json 文件

       {
          "name": "angular",
          "version": "0.0.1-SNAPSHOT",
          "description": "Description for angular",
          "private": true,
          "license": "UNLICENSED",
          "cacheDirectories": [
            "node_modules"
          ],
          "dependencies": {
            "@angular/common": "10.0.0",
            "@angular/compiler": "10.0.0",
            "@angular/core": "10.0.0",
            "@angular/forms": "10.0.0",
            "@angular/localize": "10.0.0",
            "@angular/platform-browser": "10.0.0",
            "@angular/platform-browser-dynamic": "10.0.0",
            "@angular/router": "10.0.0",
            "@fortawesome/angular-fontawesome": "0.6.1",
            "@fortawesome/fontawesome-svg-core": "1.2.29",
            "@fortawesome/free-solid-svg-icons": "5.13.1",
            "@ng-bootstrap/ng-bootstrap": "^9.0.2",
            "@ngx-translate/core": "12.1.2",
            "@ngx-translate/http-loader": "5.0.0",
            "bootstrap": "4.5.0",
            "bootstrap-icons": "^1.4.0",
            "moment": "2.27.0",
            "ng-diff-match-patch": "^3.0.1",
            "ng-jhipster": "0.15.0",
            "ngx-cookie-service": "3.0.4",
            "ngx-infinite-scroll": "9.0.0",
            "ngx-webstorage": "5.0.0",
            "rxjs": "6.5.5",
            "swagger-ui-dist": "3.25.1",
            "tslib": "2.0.0",
            "zone.js": "0.10.3"
          },
          "devDependencies": {
            "@angular/cli": "10.0.0",
            "@angular/compiler-cli": "10.0.0",
            "@ngtools/webpack": "10.0.0",
            "@openapitools/openapi-generator-cli": "1.0.13-4.3.1",
            "@types/jest": "26.0.3",
            "@types/node": "13.13.4",
            "@typescript-eslint/eslint-plugin": "2.30.0",
            "@typescript-eslint/eslint-plugin-tslint": "2.30.0",
            "@typescript-eslint/parser": "2.30.0",
            "autoprefixer": "9.8.4",
            "browser-sync": "^2.26.1",
            "browser-sync-webpack-plugin": "2.2.2",
            "codelyzer": "5.2.2",
            "copy-webpack-plugin": "6.0.2",
            "css-loader": "3.6.0",
            "eslint": "6.8.0",
            "eslint-config-jhipster": "0.0.1",
            "eslint-config-prettier": "6.11.0",
            "eslint-loader": "4.0.2",
            "file-loader": "6.0.0",
            "friendly-errors-webpack-plugin": "1.7.0",
            "generator-jhipster": "6.10.5",
            "generator-jhipster-entity-audit": "3.3.0",
            "html-loader": "1.1.0",
            "html-webpack-plugin": "4.3.0",
            "husky": "4.2.5",
            "jest": "26.1.0",
            "jest-date-mock": "1.0.8",
            "jest-junit": "11.0.1",
            "jest-preset-angular": "8.2.1",
            "jest-sonar-reporter": "2.0.0",
            "lint-staged": "8.2.1",
            "mini-css-extract-plugin": "0.9.0",
            "moment-locales-webpack-plugin": "1.2.0",
            "optimize-css-assets-webpack-plugin": "5.0.3",
            "postcss-loader": "3.0.0",
            "prettier": "2.1.2",
            "rimraf": "3.0.2",
            "sass": "1.26.9",
            "sass-loader": "8.0.2",
            "simple-progress-webpack-plugin": "1.1.2",
            "style-loader": "1.2.1",
            "terser-webpack-plugin": "3.0.6",
            "thread-loader": "2.1.3",
            "to-string-loader": "1.1.6",
            "ts-loader": "7.0.5",
            "tslint": "6.1.2",
            "typescript": "3.9.5",
            "webpack": "4.43.0",
            "webpack-bundle-analyzer": "3.8.0",
            "webpack-cli": "3.3.12",
            "webpack-dev-server": "3.11.0",
            "webpack-merge": "4.2.2",
            "webpack-notifier": "1.8.0",
            "workbox-webpack-plugin": "5.1.3",
            "write-file-webpack-plugin": "4.5.1"
          },
          "engines": {
            "node": ">=12.16.1"
          }
        }

app.module.ts

    import { NgModule } from '@angular/core';
    import { RouterModule } from '@angular/router';

    import { CommonModule } from '@angular/common';
    import { FormsModule, ReactiveFormsModule } from '@angular/forms';
    import { NgbModule } from '@ng-bootstrap/ng-bootstrap';
    import { NgJhipsterModule } from 'ng-jhipster';
    import { InfiniteScrollModule } from 'ngx-infinite-scroll';
    import { FontAwesomeModule } from '@fortawesome/angular-fontawesome';

    import * as moment from 'moment';
    import { NgbDateAdapter, NgbDatepickerConfig } from '@ng-bootstrap/ng-bootstrap';
    import { NgbDateMomentAdapter } from './datepicker-adapter';
    
    import { CeramicAccountingSoftwareSharedModule } from 'app/shared/shared.module';
    import { DemoComponent } from './demo-component.component';
    
    @NgModule({
      imports: [FormsModule, CommonModule, NgbModule, NgJhipsterModule, InfiniteScrollModule,  
                  `enter code here`FontAwesomeModule, ReactiveFormsModule],
      providers: [{ provide: NgbDateAdapter, useClass: NgbDateMomentAdapter }],
      declarations: [
        DemoComponent ,
      ],
    })
    export class AppModule {
      constructor(dpConfig: NgbDatepickerConfig) {
        dpConfig.minDate = { year: moment().year() - 100, month: 1, day: 1 };
      }
    }

demo.component.ts

    import { Component, OnInit } from '@angular/core';
    import { FormBuilder, Validators } from '@angular/forms';
    import { NgbDateAdapter, NgbDateStruct } from '@ng-bootstrap/ng-bootstrap';
            
    import { NgbDateMomentAdapter } from './datepicker-adapter';
    import * as moment from 'moment';
    import { Moment } from 'moment';
        
    @Component({
       selector: 'demo',
       templateUrl: './demo.component.html',
       providers: [{ provide: NgbDateAdapter, useClass: NgbDateMomentAdapter }],
    })
        
    export class PurchaseTransactionUpdateComponent implements OnInit {
        editForm = this.fb.group({
            date: ['', Validators.required],
        });
        constructor(
            private fb: FormBuilder,
            private dateAdaptor: NgbDateAdapter<Moment>
        ) {}
        ngOnInit(): void {
            this.editForm.patchValue({
                date: this.dateAdaptor.fromModel(moment('2021-03-20T18:30:00.000+0000')),
            });
        }
        save(): void{
            console.log("Form Value", this.editForm.value);
        }
    }

demo.component.html

    <form name="editForm" role="form" class="mt-4" (ngSubmit)="save()" 
        [formGroup]="editForm">
    <input class="form-control" placeholder="yyyy-mm-dd" type="text" name="dp"
        formControlName="date" ngbDatepicker #d="ngbDatepicker" />
        <div class="input-group-append">
                <button class="btn" (click)="d.toggle()" type="button">
                <i class="bi bi-calendar"></i>
            </button>
        </div>
        <button type="submit" id="save-entity" [disabled]="editForm.invalid || 
            isSaving" class="btn btn-dark">Save</button>
    </form>

日期选择器-adapter.ts

    import { Injectable } from '@angular/core';
    import { NgbDateAdapter, NgbDateStruct } from '@ng-bootstrap/ng-bootstrap';
    import { Moment } from 'moment';
    import * as moment from 'moment';
    
    @Injectable()
    export class NgbDateMomentAdapter extends NgbDateAdapter<Moment> {
      fromModel(date: Moment): NgbDateStruct {
        if (date && moment.isMoment(date) && date.isValid()) {
          return { year: date.year(), month: date.month() + 1, day: date.date() };
        }
        // ! can be removed after https://github.com/ng-bootstrap/ng-bootstrap/issues/1544 is resolved
        return null!;
      }
    
      toModel(date: NgbDateStruct): Moment {
        // ! after null can be removed after https://github.com/ng-bootstrap/ng-bootstrap/issues/1544 is resolved
        return date ? moment(date.year + '-' + date.month + '-' + date.day, 'YYYY-MM-DD') : null!;
      }
    }

实际上,由于 core.module.ts[=16 中提供的自定义 NgbDateAdapter,代码中没有问题。 =] 是在 app.module.ts 中导入的,它使用自定义方法中断了 NgbDateAdapter 的默认“fromModel”方法。实际上我没有意识到这是在我的项目中使用#JHIPSTER 时完成的,这是由 jhipster datePickerUtility

完成的

我通过从 app.module.ts

中删除 { provide: NgbDateAdapter, useClass: NgbDateNativeAdapter } 解决了我的问题

并在html

中使用打击代码
    <input class="form-control" (focus)="datepicker.open()"  
    formControlName="'datepicker'" ngbDatepicker #datepicker="ngbDatepicker">

并在 .ts 文件中使用 blow 代码

constructor(private ngbFormatter: NgbDateParserFormatter) { }

ngOnInit(): void {
   this.form.get('datepicker').patchValue(this.ngbFormatter.parse(this.date));
}