详解angularjs的数组传参方式的简单实现


Posted in Javascript onJuly 28, 2017

初学 angularjs时,对 数组传参方式感到很好奇([‘a', ‘b', function(a,b){}]),它到底怎么实现的呢?后来由于工作很忙,对这个问题也就慢慢忘记了。

今天闲来无事,有想到了这个问题。最简单的方法就是查看他的源代码。无奈本人E文不好,不说看他的设计逻辑,仅看英文注释就够我头疼了。尝试闭门造车,最终竟然把车造出来了。

既然自己造的车,就要带上自己的名(取姓名拼音第一个字母),就叫他mqyJs把,下面是演示的调用方法:

var app2 = mqyJs.applicationCreate([{ name: '直接传入SCOPE' }, '$hello', '$world', function($scope, $hello, $world) {
  return $scope.name + ": " + $hello.name + $world.name;
}]);

核心部分如下:

//框架开设
var mqyJs = {
  //服务注册
  servicesList: {},
  servicesRegister: function(name, value) {
    this.servicesList[name] = value;
  },
  //应用创建
  applicationList: [],
  applicationCreate: function(_opts, _args) {
    if (!_args) {
      _args = _opts;
      _opts = {}
    }
    _opts.scope = _opts.scope || {
      name: 'SCOPE没有设置'
    };
    if (!(_args instanceof Array)) {
      _args = ['$scope', _args];
    }
    if (typeof _args[_args.length - 1] != 'function') {
      throw new Error('参数中没有指定运行函数');
    }
    _args.map((arg, index) => {
      if (typeof arg == 'string') {
        if (arg === '$scope') {
          _args[index] = _opts.scope;
        } else {
          if (!!arg && !(arg in this.servicesList)) {
            throw new Error('插件:' + arg + ' 还没有注册');
          }
          _args[index] = this.servicesList[arg];
        }
      }
    });
    return this.applicationList[this.applicationList.push({
      run: function(callback) {
        if (typeof callback != 'function') {
          callback = function(_opts) { return _opts; }
        }
        return callback(_args[_args.length - 1].apply(null, _args));
      }
    }) - 1];
  }
};
//框架结束

通过 servicesRegister,可以注册 服务,比如 angularjs 的 $http;

//插件开始
mqyJs.servicesRegister('$hello', {
  name: '你好'
});
mqyJs.servicesRegister('$world', {
  name: '世界'
});
mqyJs.servicesRegister('$china', {
  name: '中国'
});
//插件结束

最终,对所有注册的应用,自动执行

/**
 * 初始化完成后系统自动运行
 * 比如网页中 放到 window.onload
 */
mqyJs.applicationList.map(function(app, index) {
  console.log('自动调用 -> APP #' + index + ' -> ' + app.run());
});

尝试跑一下代码,能自动识别参数类型,完美执行。

不传入 $scope 时,程序会自动创建一个 $scope。

//演示代码 开始
var app = mqyJs.applicationCreate(['$scope', '$hello', '$china', function($scope, $hello, $china) {
  return $scope.name + ": " + $hello.name + $china.name;
}]);


var app2 = mqyJs.applicationCreate([{ name: '直接传入SCOPE' }, '$hello', '$world', function($scope, $hello, $world) {
  return $scope.name + ": " + $hello.name + $world.name;
}]);

 

var app3 = mqyJs.applicationCreate([{ name: 'world也直接传入' }, '$hello', { name: '地球' }, function($scope, $hello, $world) {
  return $scope.name + ": " + $hello.name + $world.name;
}]);


var app4 = mqyJs.applicationCreate(function($scope) {
  return $scope.name;
});

var opts = {
  scope: {
    name: '自定义SCOPE'
  }
};
var app5 = mqyJs.applicationCreate(opts, function($scope) {
  return $scope.name;
});

app4.run(function(result) {
  console.log('手动调用 -> RESULT -> ' + result);
});

//演示代码 结束

为了方便测试,再把代码重新写一遍,直接复制下面的代码到 浏览器控制台即可测试

//框架开设
var mqyJs = {
  //服务注册
  servicesList: {},
  servicesRegister: function(name, value) {
    this.servicesList[name] = value;
  },
  //应用创建
  applicationList: [],
  applicationCreate: function(_opts, _args) {
    if (!_args) {
      _args = _opts;
      _opts = {}
    }
    _opts.scope = _opts.scope || {
      name: 'SCOPE没有设置'
    };
    if (!(_args instanceof Array)) {
      _args = ['$scope', _args];
    }
    if (typeof _args[_args.length - 1] != 'function') {
      throw new Error('参数中没有指定运行函数');
    }
    _args.map((arg, index) => {
      if (typeof arg == 'string') {
        if (arg === '$scope') {
          _args[index] = _opts.scope;
        } else {
          if (!!arg && !(arg in this.servicesList)) {
            throw new Error('插件:' + arg + ' 还没有注册');
          }
          _args[index] = this.servicesList[arg];
        }
      }
    });
    return this.applicationList[this.applicationList.push({
      run: function(callback) {
        if (typeof callback != 'function') {
          callback = function(_opts) { return _opts; }
        }
        return callback(_args[_args.length - 1].apply(null, _args));
      }
    }) - 1];
  }
};
//框架结束
//插件开始
mqyJs.servicesRegister('$hello', {
  name: '你好'
});
mqyJs.servicesRegister('$world', {
  name: '世界'
});
mqyJs.servicesRegister('$china', {
  name: '中国'
});
 
var app = mqyJs.applicationCreate(['$scope', '$hello', '$china', function($scope, $hello, $china) {
  return $scope.name + ": " + $hello.name + $china.name;
}]);


var app2 = mqyJs.applicationCreate([{ name: '直接传入SCOPE' }, '$hello', '$world', function($scope, $hello, $world) {
  return $scope.name + ": " + $hello.name + $world.name;
}]);


var app3 = mqyJs.applicationCreate([{ name: 'world也直接传入' }, '$hello', { name: '地球' }, function($scope, $hello, $world) {
  return $scope.name + ": " + $hello.name + $world.name;
}]);


var app4 = mqyJs.applicationCreate(function($scope) {
  return $scope.name;
});

var opts = {
  scope: {
    name: '自定义SCOPE'
  }
};
var app5 = mqyJs.applicationCreate(opts, function($scope) {
  return $scope.name;
});

app4.run(function(result) {
  console.log('手动调用 -> RESULT -> ' + result);
});
 
//插件结束
mqyJs.applicationList.map(function(app, index) {
  console.log('自动调用 -> APP #' + index + ' -> ' + app.run());
});

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
jQuery EasyUI中对表格进行编辑的实现代码
Jun 10 Javascript
用Javascript实现Sleep暂停功能代码
Sep 03 Javascript
JS实现同时搜索百度和必应的方法
Jan 27 Javascript
jQuery实现的多级下拉菜单效果代码
Aug 24 Javascript
JavaScript的继承实现小结
May 07 Javascript
Vue单文件组件的如何使用方式介绍
Jul 28 Javascript
Vue项目组件化工程开发实践方案
Jan 09 Javascript
JavaScript数组及常见操作方法小结
Nov 13 Javascript
ES6扩展运算符和rest运算符用法实例分析
May 23 Javascript
关于angular浏览器兼容性问题的解决方案
Jul 26 Javascript
vue v-for 点击当前行,获取当前行数据及event当前事件对象的操作
Sep 10 Javascript
Vue项目中如何封装axios(统一管理http请求)
May 02 Vue.js
js 获取html5的data属性实现方法
Jul 28 #Javascript
jQuery获取table表中的td标签(实例讲解)
Jul 28 #jQuery
浅谈JS中的常用选择器及属性、方法的调用
Jul 28 #Javascript
js原生代码实现轮播图的实例讲解
Jul 28 #Javascript
js弹性势能动画之抛物线运动实例详解
Jul 27 #Javascript
js学习总结之dom2级事件基础知识详解
Jul 27 #Javascript
Angular指令之restict匹配模式的详解
Jul 27 #Javascript
You might like
Win2000+Apache+MySql+PHP4+PERL安装使用小结
2006/10/09 PHP
Trying to clone an uncloneable object of class Imagic的解决方法
2012/01/11 PHP
PHP使用feof()函数读文件的方法
2014/11/07 PHP
thinkPHP模板中函数的使用方法示例
2016/11/30 PHP
我也种棵OO树JXTree[js+css+xml]
2007/04/02 Javascript
for 循环性能比较 提高for循环的效率
2009/03/19 Javascript
巧用jquery解决下拉菜单被Div遮挡的相关问题
2014/02/13 Javascript
js校验表单后提交表单的三种方法总结
2014/02/28 Javascript
原生js实现addClass,removeClass,hasClass方法
2016/04/27 Javascript
jquery div模态窗口的简单实例
2016/05/28 Javascript
Javascript 引擎工作机制详解
2016/11/30 Javascript
用jQuery实现优酷首页轮播图
2017/01/09 Javascript
BootStrap表单宽度设置方法
2017/03/10 Javascript
详解react服务端渲染(同构)的方法
2017/09/21 Javascript
Vue header组件开发详解
2018/01/26 Javascript
详解vue项目接入微信JSSDK的坑
2018/12/14 Javascript
JavaScript数据结构与算法之二叉树插入节点、生成二叉树示例
2019/02/21 Javascript
浅谈laytpl 模板空值显示null的解决方法及简单的js表达式
2019/09/19 Javascript
JS轮播图的实现方法2
2020/08/25 Javascript
[02:52]DOTA2新手基础教程 米波
2014/01/21 DOTA
[03:57]《不朽》——2015DOTA2国际邀请赛—中国军团出征主题曲MV
2015/07/15 DOTA
Python装饰器的函数式编程详解
2015/02/27 Python
Python设计足球联赛赛程表程序的思路与简单实现示例
2016/06/28 Python
解决DataFrame排序sort的问题
2018/06/07 Python
Python OpenCV处理图像之图像直方图和反向投影
2018/07/10 Python
如何用Python来理一理红楼梦里的那些关系
2019/08/14 Python
Tensorflow Summary用法学习笔记
2020/01/10 Python
Python random库使用方法及异常处理方案
2020/03/02 Python
如何使用python写截屏小工具
2020/09/29 Python
英国领先的电动可调床制造商:Laybrook
2019/12/26 全球购物
品管员岗位职责
2013/11/10 职场文书
人力资源管理专业自荐书范文
2014/02/10 职场文书
解除劳动关系协议书2篇
2014/11/28 职场文书
违反工作规定检讨书范文
2014/12/14 职场文书
pandas提升计算效率的一些方法汇总
2021/05/30 Python
Win10防火墙白名单怎么设置?Win10添加防火墙白名单方法
2022/04/06 数码科技