如何从 angular 服务订阅 window.resize?

How to Subscribe window.resize from an angular Service?

我试过了,

窗口服务

import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';

interface WindowSize {
  width?: number;
  height?: number;
}

@Injectable({
  providedIn: 'root'
})
export class WindowService {
  webWindow = window;
  windowHeight: number;
  windowWidth: number;
  windowSize: number;
  constructor() {

    this.getWindowSize = this.getWindowSize.bind(this);

  }


  getWindowSize(): Observable<any> {
    return this.webWindow.addEventListener('resize', ()=> {
      this.windowSize = {
        width: window.innerWidth,
        height: window.innerHeight
      };
      return this.windowSize;
    });
  }
}

我尝试订阅 getWindowSize 方法的组件

  ngOnInit() {
    this.loadUser();
    this.windowSize = this.windowService.getWindowSize().subscribe(data=> {
      console.log(data)
      this.windowSize = data;
    }); 
  }

我遇到的错误是

AppComponent.ngfactory.js? [sm]:1 ERROR TypeError: Cannot read property 'subscribe' of undefined at FeedlistComponent.ngOnInit

addEventListener 不是 return 可观察的。您可以使用 fromEvent(window, 'resize')HerefromEvent 的文档。

这是一个不会在服务器端环境中引发任何错误并且不会泄漏订阅的服务:

import {DOCUMENT} from '@angular/common';
import {Inject, Injectable} from '@angular/core';
import {fromEvent, NEVER, Observable} from 'rxjs';

// @dynamic
@Injectable({
    providedIn: 'root',
})
export class ResizeService extends Observable<Event> {
    private readonly resize$: Observable<Event>;

    constructor(
        @Inject(DOCUMENT) {defaultView}: Document,
    ) {
        super(subscriber => this.resize$.subscribe(subscriber));

        this.resize$ = defaultView ? fromEvent(defaultView, 'resize') : NEVER;
    }
}

注意:注释// @dynamic很重要,否则AOT构建会失败,Document类型的构造函数参数。

注意:您也可以考虑限制这些事件。

用法:

export class MyComponent {
    constructor(@Inject(ResizeService) resize$: Observable<Event>) {
        resize$.subscribe(console.log);
    }
}