SAP 电商云 Spartacus UI 的响应式 UI 实现细节
在文件 projects\storefrontlib\layout\config\default-layout.config.ts 里,定義了各個屏幕尺寸所對應的 breakpoint:
export const defaultLayoutConfig: LayoutConfig = {breakpoints: {xs: 576,sm: 768,md: 992,lg: 1200,xl: {min: 1200,},}, };注意這個 breakpoint 和編程語言里的斷點沒有關系。
breakpoint.service.ts 的 getBreakpoint 方法,提供了根據當前屏幕寬度返回最合適的 breakpoint:
以這個 id 為 trigger 的按鈕為例,它是完全 css 驅動的:
這個按鈕的 css:
btn btn-action btn-block dialog-trigger
該按鈕在 lg 這個 breakpoint 情況下,會被設置為 display:none:
而 Spartacus 應用代碼怎么知道當前的屏幕尺寸對應的 break point 呢?
答案是我們自己實現的 breakpoint.service.ts.
首先定義枚舉類型 BREAKPOINT:
export enum BREAKPOINT {xs = 'xs',sm = 'sm',md = 'md',lg = 'lg',xl = 'xl', }然后根據當前代碼的運行環境進行計算:
breakpoint$: Observable<BREAKPOINT> = isPlatformBrowser(this.platform)? this.winRef.resize$.pipe(map((event) => this.getBreakpoint((<Window>event.target).innerWidth)),distinctUntilChanged()): of(this.fallbackBreakpoint);constructor(protected winRef: WindowRef,protected layoutConfig: LayoutConfig,@Inject(PLATFORM_ID) protected platform: any) {}如果當前運行在瀏覽器環境下,isPlatformBrowser(this.platform) 返回 true,那么進入三元表達式前面的分支,調用 this.getBreakpoint 根據當前屏幕的 innerWidth,獲取對應的 breakpoint.
同時,一旦有 resize 事件發生,會自動重新計算新的 breakpoint. 每次 resize 事件發生時,產生的 event 對象 event.target 指向 Window 對象,該對象的 innerWidth 即是新的屏幕寬度。
如何捕捉屏幕的 resize 事件?
get resize$(): Observable<any> {if (!this.nativeWindow) {return of(null);} else {return fromEvent(this.nativeWindow, 'resize').pipe(debounceTime(300),startWith({ target: this.nativeWindow }),distinctUntilChanged());}}這里我們使用了 rxJs 的 fromEvent 和 debounce, 將 window 對象產生的 resize 事件,做了一個 300 毫秒的限流,意思是當 resize 事件觸發后,如果300毫秒之內并沒有新的 resize 事件發生時,再把這個 resize 事件,交給 Observable 執行鏈的下游處理,即重新獲取 breakpoint.
如果當前代碼在服務器端 Node.js 環境中運行,進入三元表達式問號后面的分支:of(this.fallbackBreakpoint);
返回最小屏幕尺寸對應的 breakpoint,這也體現了 mobile first 的設計思路。
更多Jerry的原創文章,盡在:“汪子熙”:
總結
以上是生活随笔為你收集整理的SAP 电商云 Spartacus UI 的响应式 UI 实现细节的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 冰墩墩盲盒在哪可以买到 冰墩墩盲盒多少钱
- 下一篇: 勿忘我怎么修改记忆-记忆修改方法讲解