Spaces:
Sleeping
Sleeping
const raf = require('licia/raf') | |
const LunaPerformanceMonitor = require('luna-performance-monitor').default | |
const now = require('licia/now') | |
module.exports = function (eruda) { | |
let { evalCss } = eruda.util | |
class Monitor extends eruda.Tool { | |
constructor() { | |
super() | |
this.name = 'monitor' | |
this.displayName = 'モニター' | |
this._style = evalCss( | |
require('./style.scss') + | |
require('luna-performance-monitor/luna-performance-monitor.css') | |
) | |
} | |
init($el, container) { | |
super.init($el, container) | |
// 各メトリクス表示用の要素を生成 | |
$el.html( | |
'<div class="eruda-fps"></div><div class="eruda-memory"></div><div class="eruda-dom-nodes"></div>' | |
) | |
this._initFps($el.find('.eruda-fps').get(0)) | |
if (performance.memory) { | |
this._initMemory($el.find('.eruda-memory').get(0)) | |
} | |
this._initDomNodes($el.find('.eruda-dom-nodes').get(0)) | |
eruda.get().config.on('change', this._onThemeChange) | |
} | |
show() { | |
super.show() | |
// 表示開始時にモニターを開始 | |
this._fpsMonitor.start() | |
if (this._memoryMonitor) { | |
this._memoryMonitor.start() | |
} | |
this._domNodesMonitor.start() | |
} | |
hide() { | |
super.hide() | |
// 非表示時にモニターを停止 | |
this._fpsMonitor.stop() | |
if (this._memoryMonitor) { | |
this._memoryMonitor.stop() | |
} | |
this._domNodesMonitor.stop() | |
} | |
destroy() { | |
// クリーンアップ処理 | |
eruda.get().config.off('change', this._onThemeChange) | |
this._fpsMonitor.destroy() | |
if (this._memoryMonitor) { | |
this._memoryMonitor.destroy() | |
} | |
super.destroy() | |
evalCss.remove(this._style) | |
} | |
_getColor() { | |
// 現在のテーマのアクセントカラーを取得 | |
return eruda.util.evalCss.getCurTheme().accent | |
} | |
_getTheme() { | |
// 現在のテーマがダークかライトかを判定 | |
return eruda.util.isDarkTheme() ? 'dark' : 'light' | |
} | |
_initFps(el) { | |
let frames = 0 | |
let prevTime = 0 | |
let fps = 0 | |
let fpsId | |
function updateFPS() { | |
frames++ | |
const time = now() | |
if (time > prevTime + 1000) { | |
fps = Math.round((frames * 1000) / (time - prevTime)) | |
prevTime = time | |
frames = 0 | |
} | |
fpsId = raf(updateFPS) | |
} | |
updateFPS() | |
// FPS モニター作成 | |
const fpsMonitor = new LunaPerformanceMonitor(el, { | |
title: 'FPS(フレームレート)', | |
color: this._getColor(), | |
smooth: false, | |
theme: this._getTheme(), | |
data: () => fps, | |
}) | |
fpsMonitor.on('destroy', () => raf.cancel.call(window, fpsId)) | |
this._fpsMonitor = fpsMonitor | |
} | |
_initMemory(el) { | |
// メモリ使用量モニター作成 | |
const memoryMonitor = new LunaPerformanceMonitor(el, { | |
title: '使用中の JS ヒープサイズ', | |
unit: 'MB', | |
color: this._getColor(), | |
smooth: false, | |
theme: this._getTheme(), | |
data() { | |
return (performance.memory.usedJSHeapSize / 1024 / 1024).toFixed(1) | |
}, | |
}) | |
this._memoryMonitor = memoryMonitor | |
} | |
_initDomNodes(el) { | |
// DOM ノード数モニター作成 | |
const domNodesMonitor = new LunaPerformanceMonitor(el, { | |
title: 'DOM ノード数', | |
color: this._getColor(), | |
smooth: false, | |
theme: this._getTheme(), | |
data() { | |
return document.body.getElementsByTagName('*').length | |
}, | |
}) | |
this._domNodesMonitor = domNodesMonitor | |
} | |
_onThemeChange = (name) => { | |
// テーマ変更時の色・テーマ再設定 | |
const fpsMonitor = this._fpsMonitor | |
const domNodesMonitor = this._domNodesMonitor | |
const memoryMonitor = this._memoryMonitor | |
if (name === 'theme') { | |
const theme = this._getTheme() | |
fpsMonitor.setOption({ | |
color: this._getColor(), | |
theme, | |
}) | |
domNodesMonitor.setOption({ | |
color: this._getColor(), | |
theme, | |
}) | |
if (memoryMonitor) { | |
memoryMonitor.setOption({ | |
color: this._getColor(), | |
theme, | |
}) | |
} | |
} | |
} | |
} | |
return new Monitor() | |
} | |