vConsole核心源码学习

2024-06-14 17:28
文章标签 源码 学习 核心 vconsole

本文主要是介绍vConsole核心源码学习,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文章目录

      • 概述
      • 核心类 `VConsole`
        • 1. 导入模块和定义常量
        • 2. 类的定义和构造函数
        • 3. 添加内置插件
        • 4. 初始化 Svelte 组件
        • 5. 自动运行
        • 6. 添加和移除插件
        • 7. 显示和隐藏面板
      • 总结


vConsole 核心类的实现,该工具由腾讯开发,用于在移动端进行调试。代码主要涉及 vConsole 的初始化、插件管理、事件触发和销毁等功能。以下是对代码的详细解析:

概述

  • vConsole 是一个用于移动端的调试工具。
  • 提供日志、网络、系统信息、元素查看和存储等调试功能。
  • 使用 Svelte 作为前端框架来构建调试面板。

核心类 VConsole

1. 导入模块和定义常量
import type { SvelteComponent } from 'svelte';
import type { VConsoleOptions } from './options.interface';
import * as tool from '../lib/tool';
import $ from '../lib/query';
import { default as CoreCompClass } from './core.svelte';
import type { IVConsoleTopbarOptions, IVConsolePluginEventName } from '../lib/plugin';
import { VConsolePlugin } from '../lib/plugin';
import { VConsoleLogPlugin } from '../log/log';
import { VConsoleDefaultPlugin } from '../log/default';
import { VConsoleSystemPlugin } from '../log/system';
import { VConsoleNetworkPlugin } from '../network/network';
import { VConsoleElementPlugin } from '../element/element';
import { VConsoleStoragePlugin } from '../storage/storage';
import { VConsoleLogExporter } from '../log/log.exporter';
import { VConsoleNetworkExporter } from '../network/network.exporter';const VCONSOLE_ID = '#__vconsole';
  • 导入必要的模块和类型。
  • 定义常量 VCONSOLE_ID,用于标识 vConsole 的 DOM 元素。
2. 类的定义和构造函数
export class VConsole {public version: string = __VERSION__;public isInited: boolean = false;public option: VConsoleOptions = {};protected compInstance: SvelteComponent;protected pluginList: { [id: string]: VConsolePlugin } = {}; // plugin instance// Export plugin methodspublic log: VConsoleLogExporter;public system: VConsoleLogExporter;public network: VConsoleNetworkExporter;// Export static classespublic static VConsolePlugin: typeof VConsolePlugin;public static VConsoleLogPlugin: typeof VConsoleLogPlugin;public static VConsoleDefaultPlugin: typeof VConsoleDefaultPlugin;public static VConsoleSystemPlugin: typeof VConsoleSystemPlugin;public static VConsoleNetworkPlugin: typeof VConsoleNetworkPlugin;public static VConsoleElementPlugin: typeof VConsoleElementPlugin;public static VConsoleStoragePlugin: typeof VConsoleStoragePlugin;constructor(opt?: VConsoleOptions) {if (!!VConsole.instance && VConsole.instance instanceof VConsole) {console.debug('[vConsole] vConsole is already exists.');return VConsole.instance;}VConsole.instance = this;this.isInited = false;this.option = {defaultPlugins: ['system', 'network', 'element', 'storage'],log: {},network: {},storage: {},};// merge optionsif (tool.isObject(opt)) {for (let key in opt) {this.option[key] = opt[key];}}// check deprecated optionsif (typeof this.option.maxLogNumber !== 'undefined') {this.option.log.maxLogNumber = this.option.maxLogNumber;console.debug('[vConsole] Deprecated option: `maxLogNumber`, use `log.maxLogNumber` instead.');}if (typeof this.option.onClearLog !== 'undefined') {console.debug('[vConsole] Deprecated option: `onClearLog`.');}if (typeof this.option.maxNetworkNumber !== 'undefined') {this.option.network.maxNetworkNumber = this.option.maxNetworkNumber;console.debug('[vConsole] Deprecated option: `maxNetworkNumber`, use `network.maxNetworkNumber` instead.');}// add built-in pluginsthis._addBuiltInPlugins();// try to initconst _onload = () => {if (this.isInited) {return;}this._initComponent();this._autoRun();};if (document !== undefined) {if (document.readyState === 'loading') {$.bind(<any>window, 'DOMContentLoaded', _onload);} else {_onload();}} else {// if document does not exist, wait for itlet _timer;const _pollingDocument = () => {if (!!document && document.readyState == 'complete') {_timer && clearTimeout(_timer);_onload();} else {_timer = setTimeout(_pollingDocument, 1);}};_timer = setTimeout(_pollingDocument, 1);}}
  • 定义 VConsole 类,并在构造函数中进行初始化。
  • 检查是否已有实例存在,如果有则返回现有实例。
  • 初始化选项并合并用户传入的选项。
  • 检查并处理已弃用的选项。
  • 添加内置插件。
  • 尝试初始化组件,等待文档加载完成后进行初始化。
3. 添加内置插件
/*** Add built-in plugins.*/
private _addBuiltInPlugins() {// add default log pluginthis.addPlugin(new VConsoleDefaultPlugin('default', 'Log'));// add other built-in plugins according to user's configconst list = this.option.defaultPlugins;const plugins = {'system': { proto: VConsoleSystemPlugin, name: 'System' },};if (__TARGET__ === 'web') {plugins['network'] = { proto: VConsoleNetworkPlugin, name: 'Network' };plugins['element'] = { proto: VConsoleElementPlugin, name: 'Element' };plugins['storage'] = { proto: VConsoleStoragePlugin, name: 'Storage' };}if (!!list && tool.isArray(list)) {for (let i = 0; i < list.length; i++) {const pluginConf = plugins[list[i]];if (!!pluginConf) {this.addPlugin(new pluginConf.proto(list[i], pluginConf.name));} else {console.debug('[vConsole] Unrecognized default plugin ID:', list[i]);}}}
}
  • 根据用户配置添加内置插件。
  • 支持日志、系统、网络、元素查看和存储等插件。
4. 初始化 Svelte 组件
/*** Init svelte component.*/
private _initComponent() {if (! $.one(VCONSOLE_ID)) {const switchX = <any>tool.getStorage('switch_x') * 1;const switchY = <any>tool.getStorage('switch_y') * 1;let target: HTMLElement;if (typeof this.option.target === 'string') {target = document.querySelector(this.option.target);} else if (this.option.target instanceof HTMLElement) {target = this.option.target;}if (! (target instanceof HTMLElement)) {target = document.documentElement;}this.compInstance = new CoreCompClass({target,props: {switchButtonPosition: {x: switchX,y: switchY,},},});// bind eventsthis.compInstance.$on('show', (e) => {if (e.detail.show) {this.show();} else {this.hide();}});this.compInstance.$on('changePanel', (e) => {const pluginId = e.detail.pluginId;this.showPlugin(pluginId);});}// set options into componentthis._updateComponentByOptions();
}
  • 初始化 Svelte 组件并绑定事件。
  • 设置开关按钮的位置并绑定显示和切换面板事件。
5. 自动运行
/*** Auto run after initialization.* @private*/
private _autoRun() {this.isInited = true;// init pluginsfor (let id in this.pluginList) {this._initPlugin(this.pluginList[id]);}// show first pluginthis._showFirstPluginWhenEmpty();this.triggerEvent('ready');
}
  • 初始化所有插件。
  • 如果没有激活的插件,显示第一个插件。
  • 触发 ready 事件。
6. 添加和移除插件
/*** Add a new plugin.*/
public addPlugin(plugin: VConsolePlugin) {// ignore this plugin if it has already been installedif (this.pluginList[plugin.id] !== undefined) {console.debug('[vConsole] Plugin `' + plugin.id + '` has already been added.');return false;}this.pluginList[plugin.id] = plugin;// init plugin only if vConsole is readyif (this.isInited) {this._initPlugin(plugin);// if it's the only plugin, show it by defaultthis._showFirstPluginWhenEmpty();}return true;
}/*** Remove a plugin.*/
public removePlugin(pluginID: string) {pluginID = (pluginID + '').toLowerCase();const plugin = this.pluginList[pluginID];// skipif is has not been installedif (plugin === undefined) {console.debug('[vConsole] Plugin `' + pluginID + '` does not exist.');return false;}// trigger `remove` event before uninstallplugin.trigger('remove');try {delete this.pluginList[pluginID];delete this.compInstance.pluginList[pluginID];} catch (e) {this.pluginList[pluginID] = undefined;this.compInstance.pluginList[pluginID] = undefined;}this.compInstance.pluginList = this.compInstance.pluginList;// show the first plugin by defaultif (this.compInstance.activedPluginId == pluginID) {this.compInstance.activedPluginId = '';this._showFirstPluginWhenEmpty();}return true;
}
  • addPlugin 方法用于添加新插件,初始化插件并在需要时显示第一个插件。
  • removePlugin 方法用于移除插件,并在需要时显示第一个插件。
7. 显示和隐藏面板
/*** Show console panel.*/
public show() {if (!this.isInited) {return;}this.compInstance.show = true;this._triggerPluginsEvent('showConsole');
}/*** Hide console panel.*/
public hide() {if (!this.isInited) {return;}this.compInstance.show = false;this._triggerPluginsEvent('hideConsole');
}/*** Show switch button*/
public showSwitch() {if (!this.isInited) {return;}this.compInstance.showSwitchButton = true;
}/*** Hide switch button.*/
public hideSwitch() {if (!this.isInited) {return;}this.compInstance.showSwitchButton = false;
}/*** Show a plugin panel.*/
public showPlugin(pluginId: string) {if (!this.isInited) {return;}if (!this.pluginList[pluginId]) {console.debug('[vConsole] Plugin `' + pluginId + '` does not exist.');}// trigger plugin eventthis.compInstance.activedPluginId && this._triggerPluginEvent(this.compInstance.activedPluginId, 'hide');this.compInstance.activedPluginId = pluginId;this._triggerPluginEvent(this.compInstance.activedPluginId, 'show');
}
  • showhide 方法用于显示和隐藏调试面板。
  • showSwitchhideSwitch 方法用于显示和隐藏开关按钮。
  • showPlugin 方法用于显示指定插件的面板。

总结

vConsole 是一个功能强大的移动端调试工具,通过插件机制提供了日志、网络、系统信息、元素查看和存储等功能。核心类 VConsole 负责初始化、插件管理、事件触发和销毁等操作,使用 Svelte 组件来构建调试面板,并提供了一系列方法来管理插件和显示调试信息。

这篇关于vConsole核心源码学习的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1061044

相关文章

HarmonyOS学习(七)——UI(五)常用布局总结

自适应布局 1.1、线性布局(LinearLayout) 通过线性容器Row和Column实现线性布局。Column容器内的子组件按照垂直方向排列,Row组件中的子组件按照水平方向排列。 属性说明space通过space参数设置主轴上子组件的间距,达到各子组件在排列上的等间距效果alignItems设置子组件在交叉轴上的对齐方式,且在各类尺寸屏幕上表现一致,其中交叉轴为垂直时,取值为Vert

Ilya-AI分享的他在OpenAI学习到的15个提示工程技巧

Ilya(不是本人,claude AI)在社交媒体上分享了他在OpenAI学习到的15个Prompt撰写技巧。 以下是详细的内容: 提示精确化:在编写提示时,力求表达清晰准确。清楚地阐述任务需求和概念定义至关重要。例:不用"分析文本",而用"判断这段话的情感倾向:积极、消极还是中性"。 快速迭代:善于快速连续调整提示。熟练的提示工程师能够灵活地进行多轮优化。例:从"总结文章"到"用

【前端学习】AntV G6-08 深入图形与图形分组、自定义节点、节点动画(下)

【课程链接】 AntV G6:深入图形与图形分组、自定义节点、节点动画(下)_哔哩哔哩_bilibili 本章十吾老师讲解了一个复杂的自定义节点中,应该怎样去计算和绘制图形,如何给一个图形制作不间断的动画,以及在鼠标事件之后产生动画。(有点难,需要好好理解) <!DOCTYPE html><html><head><meta charset="UTF-8"><title>06

学习hash总结

2014/1/29/   最近刚开始学hash,名字很陌生,但是hash的思想却很熟悉,以前早就做过此类的题,但是不知道这就是hash思想而已,说白了hash就是一个映射,往往灵活利用数组的下标来实现算法,hash的作用:1、判重;2、统计次数;

Andrej Karpathy最新采访:认知核心模型10亿参数就够了,AI会打破教育不公的僵局

夕小瑶科技说 原创  作者 | 海野 AI圈子的红人,AI大神Andrej Karpathy,曾是OpenAI联合创始人之一,特斯拉AI总监。上一次的动态是官宣创办一家名为 Eureka Labs 的人工智能+教育公司 ,宣布将长期致力于AI原生教育。 近日,Andrej Karpathy接受了No Priors(投资博客)的采访,与硅谷知名投资人 Sara Guo 和 Elad G

JAVA智听未来一站式有声阅读平台听书系统小程序源码

智听未来,一站式有声阅读平台听书系统 🌟&nbsp;开篇:遇见未来,从“智听”开始 在这个快节奏的时代,你是否渴望在忙碌的间隙,找到一片属于自己的宁静角落?是否梦想着能随时随地,沉浸在知识的海洋,或是故事的奇幻世界里?今天,就让我带你一起探索“智听未来”——这一站式有声阅读平台听书系统,它正悄悄改变着我们的阅读方式,让未来触手可及! 📚&nbsp;第一站:海量资源,应有尽有 走进“智听

零基础学习Redis(10) -- zset类型命令使用

zset是有序集合,内部除了存储元素外,还会存储一个score,存储在zset中的元素会按照score的大小升序排列,不同元素的score可以重复,score相同的元素会按照元素的字典序排列。 1. zset常用命令 1.1 zadd  zadd key [NX | XX] [GT | LT]   [CH] [INCR] score member [score member ...]

【机器学习】高斯过程的基本概念和应用领域以及在python中的实例

引言 高斯过程(Gaussian Process,简称GP)是一种概率模型,用于描述一组随机变量的联合概率分布,其中任何一个有限维度的子集都具有高斯分布 文章目录 引言一、高斯过程1.1 基本定义1.1.1 随机过程1.1.2 高斯分布 1.2 高斯过程的特性1.2.1 联合高斯性1.2.2 均值函数1.2.3 协方差函数(或核函数) 1.3 核函数1.4 高斯过程回归(Gauss

【学习笔记】 陈强-机器学习-Python-Ch15 人工神经网络(1)sklearn

系列文章目录 监督学习:参数方法 【学习笔记】 陈强-机器学习-Python-Ch4 线性回归 【学习笔记】 陈强-机器学习-Python-Ch5 逻辑回归 【课后题练习】 陈强-机器学习-Python-Ch5 逻辑回归(SAheart.csv) 【学习笔记】 陈强-机器学习-Python-Ch6 多项逻辑回归 【学习笔记 及 课后题练习】 陈强-机器学习-Python-Ch7 判别分析 【学

Java ArrayList扩容机制 (源码解读)

结论:初始长度为10,若所需长度小于1.5倍原长度,则按照1.5倍扩容。若不够用则按照所需长度扩容。 一. 明确类内部重要变量含义         1:数组默认长度         2:这是一个共享的空数组实例,用于明确创建长度为0时的ArrayList ,比如通过 new ArrayList<>(0),ArrayList 内部的数组 elementData 会指向这个 EMPTY_EL