質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

89.09%

ionicで、FormGroupを使ったファイルアップロード機能でテンプレートエラー

受付中

回答 0

投稿

  • 評価
  • クリップ 0
  • VIEW 102

miichan

score 1

前提・実現したいこと

ionicで、ファイルアップロード機能を実装しています。
ionic serveコマンドでファイルアップロードのフォームテンプレートを表示しようとすると,
下記のエラーがでます。ご教授の程よろしくお願いいたします。

環境 
ionic info
Ionic:

Ionic CLI                     : 5.4.16 (C:\Users\info\AppData\Roaming\npm\node_modules\ionic)
Ionic Framework               : @ionic/angular 4.11.1
@angular-devkit/build-angular : 0.803.12
@angular-devkit/schematics    : 8.3.12
@angular/cli                  : 8.3.26
@ionic/angular-toolkit        : 2.0.0

Capacitor:

Capacitor CLI   : 2.0.0
@capacitor/core : 2.0.0

Cordova:

Cordova CLI       : 9.0.0 (cordova-lib@9.0.1)
Cordova Platforms : android 8.1.0
Cordova Plugins   : not available

Utility:

cordova-res : not installed
native-run  : 1.0.0

System:

NodeJS : v12.16.1 (C:\Program Files\nodejs\node.exe)
npm    : 6.13.4
OS     : Windows 10

JSフレームワークは、AngularJSを使っています。

発生している問題・エラーメッセージ

Chromeブラウザの開発コンソールのエラー

core.js:4002 ERROR Error: Uncaught (in promise): Error: Template parse errors:
Can't bind to 'formGroup' since it isn't a known property of 'form'. ("

<ion-content>
  <form class="ion-padding" (submit)="editProfileImage()" [ERROR ->][formGroup]="uploadForm">

    <ion-item lines="full" class="ion-padding-bottom">
"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@7:58
No provider for ControlContainer ("

<ion-content>
  [ERROR ->]<form class="ion-padding" (submit)="editProfileImage()" [formGroup]="uploadForm">

    <ion-item line"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@7:2
No provider for NgControl ("
    <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィール画像</ion-label>
      [ERROR ->]<ion-input type="file" formControlName="image" (change)="selectImageFile($event)"></ion-input>
    </"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@11:6
No provider for NgControl ("  <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィールカバー画像</ion-label>
      [ERROR ->]<ion-input type="file" formControlName="cover_image" (change)="selectCoverImageFile($event)"></ion-in"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@15:6
Error: Template parse errors:
Can't bind to 'formGroup' since it isn't a known property of 'form'. ("

<ion-content>
  <form class="ion-padding" (submit)="editProfileImage()" [ERROR ->][formGroup]="uploadForm">

    <ion-item lines="full" class="ion-padding-bottom">
"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@7:58
No provider for ControlContainer ("

<ion-content>
  [ERROR ->]<form class="ion-padding" (submit)="editProfileImage()" [formGroup]="uploadForm">

    <ion-item line"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@7:2
No provider for NgControl ("
    <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィール画像</ion-label>
      [ERROR ->]<ion-input type="file" formControlName="image" (change)="selectImageFile($event)"></ion-input>
    </"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@11:6
No provider for NgControl ("  <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィールカバー画像</ion-label>
      [ERROR ->]<ion-input type="file" formControlName="cover_image" (change)="selectCoverImageFile($event)"></ion-in"): ng:///EditProfileImagePageModule/EditProfileImagePage.html@15:6
    at syntaxError (compiler.js:2420)
    at TemplateParser.push../node_modules/@angular/compiler/fesm5/compiler.js.TemplateParser.parse (compiler.js:12208)
    at JitCompiler.push../node_modules/@angular/compiler/fesm5/compiler.js.JitCompiler._parseTemplate (compiler.js:27518)
    at JitCompiler.push../node_modules/@angular/compiler/fesm5/compiler.js.JitCompiler._compileTemplate (compiler.js:27505)
    at compiler.js:27448
    at Set.forEach (<anonymous>)
    at JitCompiler.push../node_modules/@angular/compiler/fesm5/compiler.js.JitCompiler._compileComponents (compiler.js:27448)
    at compiler.js:27358
    at Object.then (compiler.js:2411)
    at JitCompiler.push../node_modules/@angular/compiler/fesm5/compiler.js.JitCompiler._compileModuleAndComponents (compiler.js:27357)
    at resolvePromise (zone.js:836)
    at resolvePromise (zone.js:795)
    at zone.js:897
    at ZoneDelegate.invokeTask (zone.js:431)
    at Object.onInvokeTask (core.js:26246)
    at ZoneDelegate.invokeTask (zone.js:430)
    at Zone.runTask (zone.js:198)
    at drainMicroTaskQueue (zone.js:611)

該当のソースコード

<ion-header>
<ion-toolbar>
<ion-title>edit-profile-image</ion-title>
</ion-toolbar>
</ion-header>

<ion-content>
<form class="ion-padding" (submit)="editProfileImage()" [formGroup]="uploadForm">

<ion-item lines="full" class="ion-padding-bottom">
<ion-label>プロフィール画像</ion-label>
<ion-input type="file" formControlName="image" (change)="selectImageFile($event)"></ion-input>
</ion-item>
<ion-item lines="full" class="ion-padding-bottom">
<ion-label>プロフィールカバー画像</ion-label>
<ion-input type="file" formControlName="cover_image" (change)="selectCoverImageFile($event)"></ion-input>
</ion-item>

<ion-button expand="block" type="submit" >プロフィールイメージ投稿</ion-button>
</form>
</ion-content>

<ion-header>
  <ion-toolbar>
    <ion-title>edit-profile-image</ion-title>
  </ion-toolbar>
</ion-header>

<ion-content>
  <form class="ion-padding" (submit)="editProfileImage()" [formGroup]="uploadForm">

    <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィール画像</ion-label>
      <ion-input type="file" formControlName="image" (change)="selectImageFile($event)"></ion-input>
    </ion-item>
    <ion-item lines="full" class="ion-padding-bottom">
      <ion-label>プロフィールカバー画像</ion-label>
      <ion-input type="file" formControlName="cover_image" (change)="selectCoverImageFile($event)"></ion-input>
    </ion-item>

    <ion-button expand="block" type="submit" >プロフィールイメージ投稿</ion-button>
  </form>
</ion-content>


edit-profile-image.page.ts

import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, ReactiveFormsModule } from '@angular/forms'
import { HttpClient } from '@angular/common/http';

@Component({
  selector: 'app-edit-profile-image',
  templateUrl: './edit-profile-image.page.html',
  styleUrls: ['./edit-profile-image.page.scss'],
})
export class EditProfileImagePage implements OnInit {

  private formData: any;
  public uploadForm: FormGroup = this.formBuilder.group({ title: ''});;
  public image: any;
  public cover_image: any;

  constructor(private formBuilder: FormBuilder,  private http: HttpClient) {
    this.formData = new FormData();
    //this.uploadForm = this.formBuilder.group({ title: ''});
  }

  ngOnInit() {
  }

  async editImageProfile() {
    this.formData.append('image', this.uploadForm.get('image').value);
    this.formData.append('cover_image', this.uploadForm.get('cover_image').value);
    await this.http.post('http://13.115.2.76/api/movies', this.formData)
      .subscribe(
        data => console.log(data),
        error => console.log(error)
      );
  }

  selectImageFile(event: any) {
    if (event.target.files.length > 0) {
      const file = event.target.files[0];
      this.uploadForm.get('image').setValue(file);
    }
  }

  selectCoverImageFile(event: any) {
    if (event.target.files.length > 0) {
      const file = event.target.files[0];
      this.uploadForm.get('cover_image').setValue(file);
    }
  }

}

app.module.ts

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { RouteReuseStrategy } from '@angular/router';

import { IonicModule, IonicRouteStrategy } from '@ionic/angular';
import { SplashScreen } from '@ionic-native/splash-screen/ngx';
import { StatusBar } from '@ionic-native/status-bar/ngx';

import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { Camera } from '@ionic-native/camera/ngx';
import { IonicStorageModule } from '@ionic/storage';
import { HttpClientModule } from  '@angular/common/http';
import { FormsModule, ReactiveFormsModule } from '@angular/forms';
import { File } from '@ionic-native/file';
import { Facebook } from '@ionic-native/facebook/ngx';

@NgModule({
  declarations: [AppComponent],
  entryComponents: [],
  imports: [BrowserModule, IonicModule.forRoot(), AppRoutingModule,
    IonicStorageModule.forRoot(), HttpClientModule, ReactiveFormsModule, FormsModule
  ],
  providers: [
    StatusBar,
    SplashScreen,
    Camera,
    Facebook,
    { provide: RouteReuseStrategy, useClass: IonicRouteStrategy }
  ],
  bootstrap: [AppComponent]
})
export class AppModule {}
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

まだ回答がついていません

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 89.09%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる