Angular 2 및 TypeScript 약속
저는 그것을 사용하려고 합니다.routerCanDeactivate
내 앱의 구성 요소에 대한 기능..
routerCanDeactivate() {
return confirm('Are you sure you want to leave this screen?');
}
이것에 대한 유일한 문제는 그것이 못생겼다는 것입니다.브라우저에서 생성된 확인 프롬프트만 사용합니다.부트스트랩 모달과 같은 사용자 지정 모달을 사용하고 싶습니다.부트스트랩 모달이 클릭한 버튼을 기준으로 참 또는 거짓 값을 반환합니다. 그routerCanDeactivate
나는 참/거짓 값 또는 참/거짓으로 해결되는 약속을 수락할 수 있습니다.
▁that▁다▁for▁code▁▁the니가 있는 구성 요소의 코드입니다.routerCanDeactivate
방법:
export class MyComponent implements CanDeactivate {
private promise: Promise<boolean>;
routerCanDeactivate() {
$('#modal').modal('show');
return this.promise;
}
handleRespone(res: boolean) {
if(res) {
this.promise.resolve(res);
} else {
this.promise.reject(res);
}
}
}
TypeScript 파일을 컴파일할 때 터미널에서 다음 오류가 발생합니다.
error TS2339: Property 'resolve' does not exist on type 'Promise<boolean>'.
error TS2339: Property 'reject' does not exist on type 'Promise<boolean>'.
구성 요소를 떠나려고 하면 모달이 시작되지만 구성 요소가 비활성화되고 약속이 해결될 때까지 기다리지 않습니다.
하기 위해 입니다.routerCanDeactivate
메서드가 약속이 확인될 때까지 기다립니다.없다는 오류가 발생하는 이유가 있습니까?'resolve'
의 Promise<boolean>
그 부분을 해결할 수 있다면, 앞으로 무엇을 반환해야 합니까?routerCanDeactivate
약속의 해결/해제를 기다리는 방법?
참고로, 여기에 Definite가 있습니다.약속 정의를 입력했습니다.거기에는 분명히 해결 및 거부 기능이 있습니다.
도와주셔서 고마워요.
갱신하다
다음은 Promise가 초기화되는 업데이트된 파일입니다.
private promise: Promise<boolean> = new Promise(
( resolve: (res: boolean)=> void, reject: (res: boolean)=> void) => {
const res: boolean = false;
resolve(res);
}
);
리고그고.handleResponse
함수:
handleResponse(res: boolean) {
console.log('res: ', res);
this.promise.then(res => {
console.log('res: ', res);
});
}
여전히 제대로 작동하지 않지만 모달이 나타나 응답을 기다립니다.Yes leave라고 하면 구성 요소에 남아 있습니다. 첫 또첫번째한.res
의 값은 정확합니다..then
에 .handleResponse
기능.
추가 업데이트
좀 더 읽어보니, 다음과 같습니다.promise
선언, 그것은 다음을 설정합니다.resolve
치가, 리고그promise
무슨 일이 있어도 그런 가치가 있습니다.그래서 나중에 내가 전화를 해도,.then
의 값은 바뀌지 .promise
그리고 나는 그것을 실현하고 구성요소를 바꿀 수 없습니다.그것을 만드는 방법이 있습니까?promise
기본값이 없으며 다음 값이 될 때까지 기다려야 합니다..then
메서드가 호출됩니까?
업데이트된 기능:
private promise: Promise<boolean> = new Promise((resolve, reject) => resolve(false) );
handleResponse(res: any) {
this.promise.then(val => {
val = res;
});
}
도와주셔서 다시 한번 감사드립니다.
마지막 업데이트
많은 제안들을 본 후에, 저는 그것을 만들기로 결심했습니다.Deferred
class.잘를 할 때. 꽤가있었만지할제, ▁class때는가제.deferred.reject(anyType)
다음의 콘솔에 오류가 표시됩니다.
EXCEPTION: Error: Uncaught (in promise): null
이와 같은 일이 제가 지나갈 때 일어납니다.null
,astring
는또.boolean
다음을 제공하려고 합니다.catch
에서 합니다.Deferred
수업이 안 됐어요
지연된 클래스
export class Deferred<T> {
promise: Promise<T>;
resolve: (value?: T | PromiseLike<T>) => void;
reject: (reason?: any) => void;
constructor() {
this.promise = new Promise<T>((resolve, reject) => {
this.resolve = resolve;
this.reject = reject;
});
}
}
부트스트랩 모달 api에 대해서는 잘 모르지만, 생성 시 어떻게든 근접 이벤트에 바인딩할 수 있는 방법이 있을 것으로 예상합니다.
export class MyComponent implements CanDeactivate {
routerCanDeactivate(): Promise<boolean> {
let $modal = $('#modal').modal();
return new Promise<boolean>((resolve, reject) => {
$modal.on("hidden.bs.modal", result => {
resolve(result.ok);
});
$modal.modal("show");
});
}
}
당신은 그것을 사용하려고 합니다.Promise
맘에 들다Deferred
.Deferred
학생들
class Deferred<T> {
promise: Promise<T>;
resolve: (value?: T | PromiseLike<T>) => void;
reject: (reason?: any) => void;
constructor() {
this.promise = new Promise<T>((resolve, reject) => {
this.resolve = resolve;
this.reject = reject;
});
}
}
export class MyComponent implements CanDeactivate {
private deferred = new Deferred<boolean>();
routerCanDeactivate(): Promise<boolean> {
$("#modal").modal("show");
return this.deferred.promise;
}
handleRespone(res: boolean): void {
if (res) {
this.deferred.resolve(res);
} else {
this.deferred.reject(res);
}
}
}
Promise에 'resolve' 속성이 없다는 오류가 발생한 이유가 있습니까?
가 네, 그고그 TSC의 수 입니다.es6-promise
베타.6에서 ng2 프로젝트의 이러한 문제와 기타 타이핑 문제를 방지하려면 다음을 명시적으로 포함해야 합니다.
///<reference path="node_modules/angular2/typings/browser.d.ts"/>
일반적으로 기본 부트스트랩 파일의 맨 위에서 수행됩니다.*
나머지 질문은 명확하지 않습니다(XY 문제일 가능성이 높습니다. 여기서 x는 위에서 설명한 타이핑 문제입니다).하지만, 당신이 다음과 같은 약속을 정의했다는 것을 이해하는 것이 맞다면,
private promise: Promise<boolean> = new Promise(
( resolve: (res: boolean)=> void, reject: (res: boolean)=> void) => {
const res: boolean = false;
resolve(res); // <=== how would this ever resolve to anything but false???
}
);
어떻게 이것이 거짓이 아닌 다른 것으로 해결될 것이라고 예상하십니까?
const res: boolean = false;
resolve(res); //always false
와 동등합니다.
resolve(false); //always false
*참고: 이는 (가능하면) 일시적인 것이며 이후 베타/릴리스 버전에서는 필요하지 않습니다.
사용자의 의견에 따라 업데이트:
handleResponse 기능이 실행되고 해당 응답을 기다리는 방법이 명확하지 않은 것 같습니다.
당신이 여기서 뭘 하려는 건지 아직 잘 모르겠지만, 일반적으로 당신이 원하는 건handleResponse
약속을하이행수다행합니다을음고수다▁return니.
private promise: Promise<boolean> = new Promise((resolve, reject) => {
handlePromise.then(resultOfHandleResult => {
//assuming you need to process this result somehow (otherwise this is redundant)
const res = doSomethingWith(resultOfHandleResult);
resolve(res);
})
});
handleResponse(res: any) {
this.promise.then(val => {
val = res;
});
}
또는 (멀리) 관측치를 사용하는 것이 더 좋습니다.
var promise = handleResult() //returns an observable
.map(resultOfHandleResult => doSomethingWith(resultOfHandleResult))
여기 저에게 효과가 있었던 기술이 있습니다.@iliacchool의 답변과 매우 유사하지만 jQuery 모달 대신 모달 구성 요소를 사용합니다.이것은 다소 더 "Angular 2" 접근법을 만듭니다.저는 그것이 당신의 질문과 여전히 관련이 있다고 믿습니다.
먼저, 모달에 대한 각도 구성요소를 작성합니다.
import {Component, Output, EventEmitter} from '@angular/core;
@Component({
selector: 'myModal',
template: `<div class="myModal" [hidden]="showModal">
<!-- your modal HTML here... -->
<button type="button" class="btn" (click)="clickedYes()">Yes</button>
<button type="button" class="btn" (click)="clickedNo()">No</button>
</div>
`
})
export class MyModal{
private hideModal: boolean = true;
@Output() buttonResultEmitter = new EventEmitter();
constructor(){}
openModal(){
this.hideModal = false;
}
closeModal(){
this.hideModal = true;
}
clickedYes(){
this.buttonResultEmitter.emit(true);
}
clickedNo(){
this.buttonResultEmitter.emit(false);
}
}
그런 다음 RouterCanDisactivate()가 있는 구성 요소에서 MyModal 인스턴스를 가져와 참조합니다.
import {MyModal} from './myModal';
@Component({
....
directives: [MyModal]
})
클래스 코드:
private myModal: MyModal;
myModal의 Emiter 이벤트에 가입된 약속을 반환하는 메서드를 만듭니다.
userClick(): Promise<boolean> {
var prom: new Promise<boolean>((resolve, reject) => {
this.myModal.buttonResultEmitter.subscribe(
(result) => {
if (result == true){
resolve(true);
} else {
reject(false);
}
});
});
return prom;
}
마지막으로 RouterCanDisactivate 후크에서 다음을 수행합니다.
routerCanDeactivate(next: ComponentInstruction, prev: ComponentInstruction) {
this.myModal.openModal();
return this.userClick().catch( function(){return false;} );
}
@drewmoore가 언급했듯이, Angular 2에서 관찰 가능한 것을 사용하는 것이 선호되지만, A) 그것은 당신의 질문이 아니었고, B) 라우터CanDetactivehook은 boolean | Promise로 해결되므로, 이 접근 방식이 더 자연스럽게 보였습니다.
모두가 관찰 가능한 것들에 대해 이야기하고 있기 때문에, 저는 @petryuno1의 답변을 보고 기반을 다질 것이라고 생각했습니다.
그의 것부터 시작해서,ModalComponent
:
import {Component, Output, ViewChild} from '@angular/core;
@Component({
selector: 'myModal',
template: `<div class="myModal" [hidden]="showModal">
<!-- your modal HTML here... -->
<button type="button" class="btn" (click)="clickedYes($event)">Yes</button>
<button type="button" class="btn" (click)="clickedNo($event)">No</button>
</div>
`
})
export class MyModal{
private hideModal: boolean = true;
private clickStream = new Subject<boolean>();
@Output() observable = this.clickStream.asObservable();
constructor(){}
openModal(){
this.hideModal = false;
}
closeModal(){
this.hideModal = true;
}
clickedYes(){
this.clickStream.next(true);
}
clickedNo(){
this.clickStream.next(false);
}
}
는 다으로는, 우리음에 .AppComponent
:
import { Component, ViewChild} from '@angular/core';
import {MyModal} from './myModal';
import {Subscription} from "rxjs";
@Component({
....
directives: [MyModal]
})
export class AppComponent {
@ViewChild(ConfirmModal) confirmModal: ConfirmModal;
constructor(){...};
public showModal(){
this.myModal.openModal();
this.subscription = this.myModal.observable.subscribe(x => {
console.log('observable called ' + x)
// unsubscribe is necessary such that the observable doesn't keep racking up listeners
this.subscription.unsubscribe();
});
}
}
관찰 가능한 것의 우아함은 이제 우리가 같은 일을 하기 위해 훨씬 더 적은 코드를 쓸 수 있다는 것입니다.
Angular2+ 월드에서는 s를 사용하여 즉시 실행할 수도 있습니다.
export class MyComponent {
private subject: Subject<boolean>;
routerCanDeactivate(): PromiseLike<boolean> {
$('#modal').modal('show');
return this.subject.toPromise();
}
handleRespone(res: boolean) {
this.subject.next(res);
}
}
언급URL : https://stackoverflow.com/questions/36609998/angular-2-and-typescript-promises
'programing' 카테고리의 다른 글
ggplot2 상자 그림에서 특이치 무시 (0) | 2023.06.07 |
---|---|
사용자별로 조건을 충족하는 초기 항목 필터링 (0) | 2023.06.07 |
소수점 다음에 숫자를 얻는 방법은? (0) | 2023.06.07 |
새 아스퍼.NetMVC5 프로젝트는 로그인 페이지에 대한 무한 루프를 생성합니다. (0) | 2023.06.07 |
파이썬 코드를 한 줄씩 프로파일링하려면 어떻게 해야 합니까? (0) | 2023.06.07 |