Angular 2服务在子组件中不作为单例运行(可能重复)

Angular 2服务在子组件中不作为单例运行(可能重复),angular,service,dependency-injection,angular2-services,angular2-directives,Angular,Service,Dependency Injection,Angular2 Services,Angular2 Directives,第二次更新 我的问题在于服务本身,将方法更改为箭头函数解决了问题 这可能是重复,但我已经对Angular DI做了详尽的研究,很明显,在根级别注入服务可以使它们作为同一个实例提供给应用程序中的所有组件 在我的AppComponent下面,我有三个子屏幕截图、确认和预览。我从Screenshot组件调用一个服务,并在该服务上保存一些数据,然后稍后尝试从Preview组件访问该数据,但似乎我正在访问该服务的一个新实例 应用程序模块 @NgModule({ declarations: [

第二次更新

我的问题在于服务本身,将方法更改为箭头函数解决了问题


这可能是重复,但我已经对Angular DI做了详尽的研究,很明显,在根级别注入服务可以使它们作为同一个实例提供给应用程序中的所有组件

在我的AppComponent下面,我有三个子屏幕截图、确认和预览。我从Screenshot组件调用一个服务,并在该服务上保存一些数据,然后稍后尝试从Preview组件访问该数据,但似乎我正在访问该服务的一个新实例

应用程序模块

@NgModule({
  declarations: [
    AppComponent,
    Screenshot,
    Confirm,
    Preview,
  ],
  entryComponents: [
    Preview
  ],
  imports: [
    CommonModule,
    BrowserModule
  ],
  providers: [
    MessageService,
    ScreenshotService
  ],
  bootstrap: [AppComponent]
})
export class AppModule { }
import { Injectable } from '@angular/core';

@Injectable()
export class ScreenshotService {
    public imageURL: string = '';
    public title: string  = '';
    public height: number = 0;
    public width: number = 0;

    constructor() {
    }
    convertToBlob(): Promise<any> {
        console.log(this); // returns all the initial values above when called from the Preview component the second time despite being previously assigned values when a different method was called from a different service
    }
    ...
}
应用程序组件

@Component({
    selector: 'app-root',
    templateUrl: './app.component.html',
    styleUrls: ['./app.component.css']
})

export class AppComponent implements OnInit, OnChanges, OnDestroy {
    @ViewChild(Preview) preview: Preview; 

    title: string;
    confirmed: boolean;
    constructor(
        private screenshotService: ScreenshotService,
        private messageService: MessageService,
    ) {
        this.title = 'Media Radar';
        this.confirmed = false;
    }

    onNotify(confirm): void {
        this.confirmed = confirm;
        if(this.confirmed) {
            this.preview.showPreview();
        }
    }
    ...
}
import { ScreenshotService } from './screenshot.service';
@Component({
    selector: 'preview',
    template: `<canvas #preview></canvas>`
})

export class Preview {
    @ViewChild('preview') preview: ElementRef;
    private canvas: HTMLCanvasElement;
    constructor(
        private screenshotService: ScreenshotService,
        private renderer: Renderer2
    ) {}

    showPreview() {
        console.log(this.screenshotService) // shows a new instance with no data
    ...
    }
}
app.component.html

<div class='popup'>
    <h3>{{ title }}</h3>
    <screenshot [hidden]="confirmed" (showConfirm)='onNotify($event)'></screenshot>
    <confirm [hidden]="!confirmed" (hideConfirm)='onNotify($event)'></confirm>
    <preview [hidden]="!confirmed"></preview>
</div>

{{title}}
预览组件

@Component({
    selector: 'app-root',
    templateUrl: './app.component.html',
    styleUrls: ['./app.component.css']
})

export class AppComponent implements OnInit, OnChanges, OnDestroy {
    @ViewChild(Preview) preview: Preview; 

    title: string;
    confirmed: boolean;
    constructor(
        private screenshotService: ScreenshotService,
        private messageService: MessageService,
    ) {
        this.title = 'Media Radar';
        this.confirmed = false;
    }

    onNotify(confirm): void {
        this.confirmed = confirm;
        if(this.confirmed) {
            this.preview.showPreview();
        }
    }
    ...
}
import { ScreenshotService } from './screenshot.service';
@Component({
    selector: 'preview',
    template: `<canvas #preview></canvas>`
})

export class Preview {
    @ViewChild('preview') preview: ElementRef;
    private canvas: HTMLCanvasElement;
    constructor(
        private screenshotService: ScreenshotService,
        private renderer: Renderer2
    ) {}

    showPreview() {
        console.log(this.screenshotService) // shows a new instance with no data
    ...
    }
}
从“/screenshot.service”导入{ScreenshotService};
@组成部分({
选择器:“预览”,
模板:``
})
导出类预览{
@ViewChild(“预览”)预览:ElementRef;
私有画布:HTMLCanvasElement;
建造师(
私人截屏服务:截屏服务,
私有渲染器:渲染器2
) {}
showPreview(){
console.log(this.screenshotService)//显示一个没有数据的新实例
...
}
}
为了避免代码太长,我将省略服务和其他子组件,它们首先调用服务,但如果需要可以发布

更新

屏幕截图。服务

@NgModule({
  declarations: [
    AppComponent,
    Screenshot,
    Confirm,
    Preview,
  ],
  entryComponents: [
    Preview
  ],
  imports: [
    CommonModule,
    BrowserModule
  ],
  providers: [
    MessageService,
    ScreenshotService
  ],
  bootstrap: [AppComponent]
})
export class AppModule { }
import { Injectable } from '@angular/core';

@Injectable()
export class ScreenshotService {
    public imageURL: string = '';
    public title: string  = '';
    public height: number = 0;
    public width: number = 0;

    constructor() {
    }
    convertToBlob(): Promise<any> {
        console.log(this); // returns all the initial values above when called from the Preview component the second time despite being previously assigned values when a different method was called from a different service
    }
    ...
}
从'@angular/core'导入{Injectable};
@可注射()
导出类截屏服务{
公共图像URL:string='';
公共标题:字符串=“”;
公共高度:数字=0;
公共宽度:数字=0;
构造函数(){
}
convertToBlob():承诺{
console.log(this);//在第二次从预览组件调用时返回上述所有初始值,尽管以前在从不同服务调用不同方法时分配了值
}
...
}

我的问题在于维修方法。我将它们改为箭头函数,解决了所有问题。

我的问题在于服务方法。我将它们改为箭头函数,它解决了所有问题。

您在服务中使用@Injectable()了吗?是的。我将添加一些服务以获得更多上下文。您可以构建一个plunker来演示您的问题吗?这里有一个示例显示跨组件工作的服务:查看APM Final文件夹中的message.service.ts文件。您在哪里注入了Auth和message服务?我没有看到main.ts、app.module或app.component。您在服务中使用了@Injectable()吗?是的。我将添加一些服务以获得更多上下文。您可以构建一个plunker来演示您的问题吗?这里有一个示例显示跨组件工作的服务:查看APM Final文件夹中的message.service.ts文件。您在哪里注入了Auth和message服务?我没有看到main.ts、app.module或app.component。