Layui源码解读之define函数

news2024/11/24 14:49:39

一、layui.define 用法

layui.define([mods], callback)

通过layui.define该方法可在新的 JS 文件中定义一个 layui 模块。

  1. mods 是可选的,用于声明该模块所依赖的模块。
  2. callback 为模块加载完毕的回调函数,它返回一个 exports 参数,用于输出该模块的接口。

代码示例

layui.define(function(exports){
  //do something

  exports('demo', {
    msg: 'Hello Demo'
  });
});

跟 RequireJS 最大不同的地方在于接口输出,exports 是一个函数(exports(模块名,模块接口))。
当你声明了上述的一个模块后,你就可以在外部使用了,demo 就会注册到 layui 对象下,即可通过 var demo = layui.demo 去得到该模块接口。你也可以在定义一个模块的时候,声明该模块所需的依赖,如:

layui.define(['layer', 'laypage', 'mod1'], function(exports){ //此处 mod1 为你的任意扩展模块
  //do something

  exports('demo', {
    msg: 'Hello Demo'
  });
});

二、layui.define 源码

Layui.prototype.define = function(deps, factory) {
    var that = this; // 存储当前 this
    var type = typeof deps === 'function'; // deps 是否为函数

    // 定义回调函数
    var callback = function () {

        // setApp 用于把用户自定义导出的模块注册到实例对象 layui 上, 并标记模块已加载
        var setApp = function (app, exports) {
            layui[app] = exports; // layui 为实例对象, 在实例中添加自定义模块
            config.status[app] = true; // 在congfig中设置模块状态
        }

        /**
         * factory 工厂模式
         * app 用户自定义导处模块名
         * exports 用户自定义导处的数据
         */
        typeof factory === 'function' && factory(function(app, exports) {
            // 当前处于匿名函数内, 该匿名函数就是回调函数 exports

            setApp(app, exports);

            // 存储回调函数 (这里的匿名函数和 define 中 callback 一样), 用于后续如果重新执行模块
            config.callback[app] = function(){
                factory(setApp);
            }
        });
        return this;
    };

    // 第一个参数为函数时, 函数赋给 factory,并置为 []
    type && (
        factory = deps,
        deps = []
    );

    that.use(deps, callback, null, 'define');

    return that;
}

三、layui.define 关键代码分析

var type = typeof deps === ‘function’;

判断deps是否是函数。layui.define([mods], callback) 函数使用方法中 mods 是可选参数,第一个参数有可能是函数,例如

layui.define(function(exports){
  //do something

  exports('demo', {
    msg: 'Hello Demo'
  });
});

如果是函数 type 为 true,后续会执行函数交换赋值操作。

type && (
factory = deps,
deps = []
);

type 为 true 时, deps 变量中的内容赋值给factory,并且deps为空数组。

that.use(deps, callback, null, ‘define’);

调用use函数,官方文档中没有介绍第三、四参数的用法。use函数用法在layui.use博客中详细说明,这里不用多介绍

callback 回调函数

    // 定义回调函数
    var callback = function () {

        // setApp 用于把用户自定义导出的模块注册到实例对象 layui 上, 并标记模块已加载
        var setApp = function (app, exports) {
            layui[app] = exports; // layui 为实例对象, 在实例中添加自定义模块
            config.status[app] = true; // 在congfig中设置模块状态
        }

        /**
         * factory 工厂模式
         * app 用户自定义导处模块名
         * exports 用户自定义导处的数据
         */
        typeof factory === 'function' && factory(function(app, exports) {
            // 当前处于匿名函数内, 该匿名函数就是回调函数 exports

            setApp(app, exports);

            // 存储回调函数 (这里的匿名函数和 define 中 callback 一样), 用于后续如果重新执行模块
            config.callback[app] = function(){
                factory(setApp);
            }
        });
        return this;
    };

callback函数执行时,首先判断 factory 函数是否为函数,为函数时执行 factory 函数。
请添加图片描述

伪代码解释factory函数在实际代码中的位置

let factory = function(exports){
  //do something

  exports('demo', {
    msg: 'Hello Demo'
  });
};

layui.define(['layer', 'laypage', 'mod1'], factory);

exports函数在源码中为 factory 函数中的匿名函数参数。伪代码如下

let exports = function(app, exports) {
    // 当前处于匿名函数内, 该匿名函数就是回调函数 exports

    setApp(app, exports);

    // 存储回调函数 (这里的匿名函数和 define 中 callback 一样), 用于后续如果重新执行模块
    config.callback[app] = function(){
        factory(setApp);
    }
};

factory(exports);

exports函数中执行模块注册和存储回调函数,其中setApp函数通过 layui[app] = exports 语句把导出的内容挂在到全局中,并且使用 config.status[app] = true 语句表示该模块已经被加载。最后会向config中callback中注册函数,可用于以后某种场景调用。执行的内容或者结果和factory函数一样。

config 初始对象如下(在代码运行中还有向config中加入新属性的可能)

var config = {
    modules: {}, // 记录模块物理路径
    status: {}, // 记录模块加载状态
    timeout: 10, // 符合规范的模块请求最长等待秒数
    event: {} // 记录模块自定义事件
}

如有问题,欢迎指出

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/588221.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

鸿蒙App开发选择Java还是JavaScript?

众所周知, Java和 JavaScript是两种编程语言,这两种语言在不同的环境中都有许多用途。在鸿蒙 App开发中, Java和 JavaScript是两种常见的编程语言,它们都具有广泛的应用,并且都有其独特的优势。下面我们将就这两种编程…

LiveGBS国标GB/T28181国标平台功能-电子地图移动位置订阅mobileposition地图定位GPS轨迹坐标位置获取redis获取位置

LiveGBS国标GB/T28181国标平台功能-电子地图移动位置订阅mobileposition地图定位GPS轨迹坐标位置获取redis获取位置 1、位置订阅1.1、国标设备编辑1.2、选择设备开启位置订阅1.3、全局开启位置订阅1.4、通过目录订阅获取位置(少数情况) 2、经纬度信息查询2.1、访问接口获取2.1.…

详解iPaaS与RPA的区别及各自的应用场景

随着企业数字化转型的加速,业务系统集成和自动化流程成为关键议题。本文旨在探讨iPaaS(Integration Platform as a Service)与RPA(Robotic Process Automation)在业务系统集成方面的区别,它们各自的用途和适…

python数据分析案例——零售商店电子销售订单分析

一、项目背景 通过"扫描"零售商店电子销售点个别产品的条形码而获得的消费品销售的详细数据。 这些数据提供了有关所售商品的数量、特征和价值以及价格的详细信息。 二、数据来源 https://www.kaggle.com/marian447/retail-store-sales-transactions 三、提出问…

windows11@OpenWith@选择文件打开方式导致卡死@windows11任务栏显示秒

文章目录 OpenWith选择文件打开方式导致卡死解决方案 windows11任务栏显示秒显示秒的注册表设置取消显示秒: OpenWith选择文件打开方式导致卡死 关键在于一个名为openwith的进程出现问题该进程有时会卡死,并且无法关闭,这个bug存在很久了,具体参考:Windows11 - Microsoft Comm…

MySQL 多行函数

文章目录 多行函数1. 求 country 表中,所有国家人口的平均值,其 SQL 语句实现如下:2. 求 country 表中,所有国家人口的总数,其 SQL 语句实现如下:3. 求 country 表中,人口最多和最少国家的人口数…

KD7742耐压接地泄漏绝缘四合一并行测试仪

一、产品简介 KD7742耐压接地泄漏绝缘四合一并行测试仪具有交/直流耐压、绝缘电阻等项目的测试分析功能,能显示电压、电流和电阻的波形图以及趋势图,以便更直观的监测分析绝缘性能和绝缘崩溃时的各项指标,适用于高要求的测试分析场合。 产品具…

Pig项目新加权限类型生成Token并且解决验证问题

前言 这个教程可能不是最好的,也许是最直白的,你只需要找到对应的地方跟着博主一起去修改就能操作成功,今天用添加 mini 的授权模式的例子说一下这个 mini 模式是自己自定义的,你想叫什么都行 最近可烦死了快被折磨死人,在昨天睡了一觉,今天就解决问题了…睡一觉就能解决问题,那…

教你一步步使用实现TensorFlow 进行对象检测

在本文中,我们将学习如何使用 TensorFlow Hub 预训练模型执行对象检测。TensorFlow Hub 是一个库和平台,旨在共享、发现和重用预训练的机器学习模型。TensorFlow Hub 的主要目标是简化重用现有模型的过程,从而促进协作、减少冗余工作并加速机器学习的研发。用户可以搜索社区…

【数据结构与算法分析inC-MarkAllen】2-算法分析

文章目录 第二章——算法分析2.1 算法评价的量化理论2.1.1 函数渐进增长四种渐进增长定义运算法则两个函数相对增长率判断 2.1.2 算法分析的计算机模型2.1.3 要分析的目标最坏情况 2.1.4 一般法则for循环嵌套for循环顺序语句分支语句二分函数调用 2.2 计算方法2.2.1 循环主体中…

Android应用的加固与逆向

文章目录 前言名词释义加固手段逆向dex文件resources.arscReact Native TODO文档链接工具参考加固工具逆向工具 前言 加固与逆向是安卓攻防的两个方面。搞安卓研发时间长了就不可避免走到这一步。既要研究别人的实现,又要保护好自己的东西。个人认为,逆…

糖尿病首创新药的中国梦

《多肽链》原创出品 作者|慕白 在中国上市一款first-in-class(FIC)全球首创新药,有多难?先来看一组数据对比。 按照美国FDA的药品评价和研究中心(CDER)报告数据,2022年有37款新药…

chatgpt赋能python:介绍Python中二次函数的基本知识

介绍Python中二次函数的基本知识 在Python中,二次函数是一个重要的概念,它是由一个二次项、一次项和一个常数项构成的一个代数式。二次函数在数学和物理学中都有广泛的应用,了解二次函数的基本知识对于学习和理解这些领域都是非常重要的。在…

uni-app实现 app 小程序 手机端H5扫码功能

首先 扫码这个功能小程序和App都是有现成的方法 但是H5是不行的 我们可以看这样一段代码 <template><view><!-- #ifdef MP-WEIXIN --><button click"scan">扫描</button><view v-if"result">{{result}}</view>…

长尾词挖掘,挖掘百度相关词和下拉词的操作步骤

什么是下拉词 在搜索引擎的搜索框输入一个关键词的时候&#xff0c;搜索框会推荐一些与这个关键词有关联的长尾关键词&#xff0c;如“汉服”。 什么是相关词 在搜索引擎的搜索框输入一个关键词的时候&#xff0c;一般会推荐与这个关键词相关的长尾关键词。如“汉服”。 挖…

【SpringBoot系列】SpringBoot中 @Configuration 和 @Component 的区别及原理分析

示例 //Component Configuration public class AppConfig {Beanpublic Foo foo() {System.out.println("foo() invoked...");Foo foo new Foo();System.out.println("foo() 方法的 foo hashcode: " foo.hashCode());return foo;}Beanpublic Eoo eoo() {…

华为OD机试真题B卷 Java 实现【等差数列】,附详细解题思路

一、题目描述 等差数列 2&#xff0c;5&#xff0c;8&#xff0c;11&#xff0c;14。。。。 从 2 开始的 3 为公差的等差数列。 输出求等差数列前n项和。 数据范围&#xff1a; 1≤n≤1000 。 二、输入描述 输入一个正整数n。 三、输出描述 输出一个相加后的整数。 四…

Dell电脑出现ac power adapter电压异常的解决办法

最近这段时间不知怎么的&#xff0c;dell笔记本电脑一开机就出现下面错误&#xff1a; The AC Power Adapter Wattage Cannot be Determined. 无法确定此交流电源的功率信息。 The Battery Maynot Charge. 电池将可能无法充电。 The System Will Adjust the Performance to Ma…

springboot+java农产品网上购物商城系统005

基于springboot技术的购物商城系统是属于JavaWeb项目&#xff0c;采用的开发框架为springboot框架&#xff0c;也就是Spring mvc、Spring、MyBatis这三个框架&#xff0c;页面设计用的是jsp技术作为动态页面文件设计&#xff0c;jsp文件里可以对实现html等界面布局的代码&#…

MySQL CAST 函数与 CONVERT 函数

文章目录 CAST 函数与 CONVERT 函数1. 数字和小数点组成的字符串转换为整型2. 非数值字符串转换为整型3. 把整型转换为二进制4. 数字和小数点组成的字符串转换为浮点型 CAST 函数与 CONVERT 函数 前面我们介绍的两个函数用于字符串和日期类型之间进行相互转换&#xff0c;有时我…