Basic - 基础代码

在开始所有的Prototype学习之旅之前,我们首先对Prototype中最常用的一些公用函数做一些研究,这些JavaScript函数将贯穿整个Prototype框架,熟练使用它们不仅有助于我们学习Prototype框架,同时也为我们自己编写JavaScript应用提供了独特的思路。

Source View - 源码解析

var Prototype = {     // 定义一个Prototype对象,封装了一些简单的静态函数和变量
Version: '1.5.0_rc1',     // 定义当前Prototype框架的版本号
ScriptFragment: '(?:
)((\n|\r|.)*?)(?:<\/script>)',   // 返回一个正则表达式,判断是否为Script块
emptyFunction: function() {},    // 返回一个空的函数, 该函数什么都不做, 在编写一些复杂流程中会使用此功能
K: function(x) {return x}     // 返回参数本身, 在编写一些复杂流程中会使用此功能
}
/*****************************************************************************************************************/
function $() {   // 一个根据id读取对象的快捷函数, 根据id返回所对应的对象
var results = [], element;
for (var i = 0; i < arguments.length; i++) { // 可以接受多个参数, 返回由每个id所对应的对象构成的数组
element = arguments[i];
if (typeof element == 'string')    // 可以接受非string参数,直接返回对象本身
element = document.getElementById(element);  // 通过DOM操作读取对象
results.push(Element.extend(element)); // 参见Element.extend的解析, 为返回的对象添加了一些额外特性,并压入到结果数组中
}
return results.reduce(); // 根据参数的个数返回对象或者对象数组
}
/*****************************************************************************************************************/
var Abstract = new Object();  // 定义了一个全局的对象, 可以理解为一个命名空间, 成为一个抽象基类
/*****************************************************************************************************************/
var Try = {
these: function() {  // 一个静态的函数, 接受多个函数作为参数, 依次执行并返回第一个成功执行的函数的结果
var returnValue;
for (var i = 0; i < arguments.length; i++) {
var lambda = arguments[i];   // 每个参数都是一个将被执行的函数
try {
returnValue = lambda();    // 执行函数并记录返回值
break;                     // 第一次成功执行后, 即退出
} catch (e) {}   // 捕获每个函数执行过程中的异常
}
return returnValue;
}
}
/*****************************************************************************************************************/
var PeriodicalExecuter = Class.create();  // 定义一个定时器, 重复执行某一函数
PeriodicalExecuter.prototype = {
initialize: function(callback, frequency) {  // 构造函数, 定义需要重复执行的函数和执行周期
this.callback = callback;      // 需要重复执行的函数
this.frequency = frequency;    // 重复执行的周期, 单位是秒
this.currentlyExecuting = false;   // 是否当前执行标志
this.registerCallback();    // 调用重复执行的函数
},
registerCallback: function() { // 调用window.setInterval函数完成重复执行, 返回一个标志留作被stop函数调用, 以停止定时器
// 第一个参数巧妙地使用了bind方法, 将this作为bind的参数, 这样onTimeEvent方法内部可以通过this获取当前对象的引用
this.timer = setInterval(this.onTimerEvent.bind(this), this.frequency * 1000);
},
stop: function() {
if (!this.timer) return;   // 通过setInterval函数的返回值来判断是否当前执行
clearInterval(this.timer);   // 当前执行时, 调用clearInterval方法来中止当前的执行
this.timer = null;    // 将当前执行的标志设置为null
},
onTimerEvent: function() {
if (!this.currentlyExecuting) {  // 判断是否当前执行, 否则跳过, 相当于一个同步信号量
try {
this.currentlyExecuting = true;  // 设置是否当前执行的标志
this.callback(this);   // 调用callback完成真正的函数执行
} finally {
this.currentlyExecuting = false;  // 无论是否成功执行, 最终设置当前执行标志为false
}
}
}
}

Field & Function Reference - 属性方法一览

Prototype ( 静态 )
Method / Property Kind Arguments Description
Version 静态属性  / 表示Prototype框架的版本号
ScriptFragment 静态属性  / 表示script代码段的正则表达式
emptyFunction 静态方法  / 返回一个什么都不做的空函数
K 静态方法 任意对象 返回传入的参数
$() ( 静态 )
Method / Property Kind Arguments Description
$() 静态方法 string或者任意对象, 参数数量不限 根据参数的类型和数量返回DOM操作的结果, 传入的参数为string时,返回document.getElementById所读取的对象; 传入的参数为非string类型的对象时, 直接返回参数本身; 当参数个数是1个时, 直接返回上述操作所得的结果; 当参数个数大于1个时, 将每个参数操作的结果组成一个对象数组返回
Abstract ( 静态 )
Method / Property Kind Arguments Description
Abstract  / 一个全局的对象, 可以理解为一个命名空间, 成为一个抽象基类
Try ( 静态 )
Method / Property Kind Arguments Description
these 静态方法 多个有待依次执行的函数 返回第一个成功执行的函数的执行结果
PeriodicalExecuter ( 实例 )
Method / Property Kind Arguments Description
callback 属性  / 构造函数实例化时初始化的属性, 定义定时器重复执行时真正需要调用的函数
frequency 属性(Number)  / 构造函数实例化时初始化的属性, 定义定时器重复执行的时间间隔
currentlyExecuting 属性(Boolean)  / 在整个定时器执行过程中表示是否当前执行的标志, 可以作为执行过程中的同步信号量
timer 属性  / 一个内部变量, 在registerCallback方法调用window.setInterval时记录该函数的返回值, 用以给stop方法使用
registerCallback 方法  / 在构造函数初始化完成时调用执行, 也可以直接调用该函数启动定时器, 在函数内部通过调用window.setInterval方法完成定时器功能
stop 方法 this.timer, 即重复执行时调用setInterval的返回值 用于暂停定时器, 通过实例变量调用完成
onTimerEvent 方法  / 一个内部方法, 真正调用callback完成函数执行

Analysis & Usage - 分析与使用

Extension - 扩展

$()为我们提供了一个快捷的方式,通过id来读取一个对象,从而避免了我们在编写JavaScript代码时的重复而又冗长的代码段。然而,在某些情况下,我们需要通过对象的name属性来读取对象,并对对象进行一定的操作,此时,$()方法就显得有些力不从心了。因而在这里,我针对这种需求,并模仿$()方法,实现了一个通过name来读取对象的函数。


事实上,getElementsByName()已经帮我们解决了大多数的问题。由于name在HTML的document中可以不唯一,因而我们需要对此进行简单的处理,当name唯一时,直接返回单一对象;当name不唯一时,返回一个数组(这已经与getElementsByName()本身的含义不同了,当然这仅仅是为了方便编程而已)。



------君临天下,舍我其谁------