Почему моя угловая страница не обновляется при использовании EventEmitter? - PullRequest
0 голосов
/ 15 октября 2018

Мой угловой SPA не обновляется, когда EventEmitter генерирует событие.

Вот мой EventEmitter в дочернем компоненте:

import { Component, OnInit, Output, EventEmitter } from '@angular/core';
import { Todo } from '../todo';

@Component({
  selector: 'app-add-todo',
  templateUrl: './add-todo.component.html',
  styleUrls: ['./add-todo.component.css']
})
export class AddTodoComponent implements OnInit {
  newTodo: Todo = new Todo();

  @Output() addTodoEvent: EventEmitter<Todo> = new EventEmitter();

  constructor() { }

  addTodo() {
    this.addTodoEvent.emit(this.newTodo);
    console.log('event emitted');
    this.newTodo = new Todo();
    console.log('new todo created');
  }

  ngOnInit() {
  }

}

Вот шаблон, который его использует:

<div class="container">
  <app-add-todo (addTodoEvent)='onAddTodo($event)'></app-add-todo>
   // other template stuff
</div>

Вот объявление onAddTodo:

  onAddTodo(todo: Todo) {
    console.log('onAddTodo called');
    this.todoDataService.addTodo(todo);
  }

По сути, приложение работает, но мне нужно нажать F5, чтобы обновить страницу после внесения любых изменений.

Следует отметить, что это работало, когда я использовал массив в качестве источника данных, но когда я перешел на json-server и Observables, страница перестала обновляться.

IЯ рад предоставить любую дополнительную информацию, которая может потребоваться.

ОБНОВЛЕНИЕ:

Вот addTodo:

  addTodo(todo: Todo): void {
    this.aHttpService.post<Todo>(`http://localhost:3000/todos`, todo).subscribe(
      val => {
        console.log('POST call successful value returned in body', val);
      },
      response => {
        console.log('POST call in error', response);
      },
      () => {
        console.log('The POST observable is now completed.');
      }
    );
  }

Полный код для перечисления задач:следует:

import { Component, OnInit } from '@angular/core';
import { Todo } from '../todo';
import { TodoDataService } from '../todo-data.service';
import { Observable } from 'rxjs/Observable';

@Component({
  selector: 'app-todo-list',
  templateUrl: './todo-list.component.html',
  styleUrls: ['./todo-list.component.css']
})
export class TodoListComponent implements OnInit {
  constructor(private todoDataService: TodoDataService) {}

  completetodos: Observable<Array<Todo>>;
  incompletetodos: Observable<Array<Todo>>;

  onAddTodo(todo: Todo) {
    console.log('onAddTodo called');
    this.todoDataService.addTodo(todo);
  }

  toggleTodoComplete(todo) {
    this.todoDataService.toggleTodoComplete(todo);
  }

  removeTodo(todo) {
    this.todoDataService.deleteTodoById(todo.id);
  }

  editTodo(todo: Todo) {
    todo.editMode = true;
  }

  updateTodo(todo: Todo, editInput) {
    todo.title = editInput.value;
    todo.editMode = false;
    this.todoDataService.updateTodoById(todo.id, todo);
  }

  allTasks(): Observable<Array<Todo>> {
    return this.todoDataService.getAllTodos();
  }

  completedTodos(): Observable<Array<Todo>> {
    return this.todoDataService.completedTodos();
  }

  incompletedToDos(): Observable<Array<Todo>> {
    return this.todoDataService.incompletedTodos();
  }

  ngOnInit() {
    this.completetodos = this.completedTodos();
    this.incompletetodos = this.incompletedToDos();
  }
}

Ответы [ 2 ]

0 голосов
/ 15 октября 2018

Как только вы закончите с успешным сохранением задачи, вы должны обновить наблюдаемые

 onAddTodo(todo: Todo) {
this.todoDataService.addTodo(todo).subscribe(
      val => {
         // here you have to update the observables //incompletetodos.next(newTodo)
      },
      response => {
        console.log('POST call in error', response);
      },
      () => {
        console.log('The POST observable is now completed.');
      }
    );
}

Также вам не нужно подписываться здесь

 addTodo(todo: Todo): void {
    return this.aHttpService.post<Todo>(`http://localhost:3000/todos`, todo);
  }

Я думаю,push не будет работать для наблюдаемых, вы можете обратиться по ссылке ниже, чтобы добавить новый элемент в массив наблюдаемых неполных данных

Как добавить элементы в Observable

Если вместо Observable вы будете использовать BehaviorSubject (другой тип наблюдаемых), вы можете легко добавить новый элемент.Что-то вроде ниже

incompletetodos: BehaviorSubject<Array<Todo>> = BehaviorSubject.empty<Array<Todo>>();

// вы можете нажать новый элемент, как показано ниже

 incompletetodos.next(newTodo)
0 голосов
/ 15 октября 2018

Ваш сервис должен возвращать наблюдаемое следующим образом:

 addTodo(todo: Todo): void {
    return this.aHttpService.post<Todo>(`http://localhost:3000/todos`, todo);
 }

И использовать его в таком компоненте:

 onAddTodo(todo: Todo) {
    this.todoDataService.addTodo(todo).subscribe(val => {
       this.incompletetodos.push(val);
    });;
 }

(я свернул код)


Ссылка: https://angular.io/tutorial/toh-pt6#add-a-new-hero

src / app / heroes / heroes.component.ts (добавить)

add(name: string): void {
  name = name.trim();
  if (!name) { return; }
  this.heroService.addHero({ name } as Hero)
    .subscribe(hero => {
      this.heroes.push(hero);
    });
}

src / app / hero.service.ts (addHero)

/** POST: add a new hero to the server */
addHero (hero: Hero): Observable<Hero> {
  return this.http.post<Hero>(this.heroesUrl, hero, httpOptions).pipe(
    tap((hero: Hero) => this.log(`added hero w/ id=${hero.id}`)),
    catchError(this.handleError<Hero>('addHero'))
  );
}

Почему моя угловая страница не обновляется при использовании EventEmitter?

Возможно, вы так думаете, мы используем Angular для создания одностраничного приложения, которое не вызывает полного обновления страницы, мы просто обновляем часть веб-сайта.

По сути,приложение работает, но мне нужно нажать F5, чтобы обновить страницу после внесения каких-либо изменений.

Потому что всякий раз, когда вы нажимаете F5, ваше Angular-приложение хорошо инициализируется, что вызывает этот хук жизненного цикла:

ngOnInit() {
    this.completetodos = this.completedTodos();
    this.incompletetodos = this.incompletedToDos();
}

Следовательно, ваше приложение отображает обновленные данные базы данных.

Следует отметить, чтораньше это работало, когда я использовал массив в качестве источника данных, но когда я перешел на json-сервер и Observables, страница перестала обновлять .

На самом деле, когда вы используете массив в качестве источника данных, наше приложение вообще не обновляется.Это то, что называется привязка данных , данные, которые мы видим в пользовательском интерфейсе, привязаны к данным, которые приложение Angular хранит (на стороне клиента, в памяти клиента).

При обмене даннымис сервером, когда мы вносим некоторые изменения в базу данных сервера, мы должны обновить данные нашего клиента на основе ответа от сервера.Вот как мы поступим в этом случае в вашем приложении Todo.

...