来看一下这个东西mousemat.html:
<html>
<head>
<link rel='stylesheet' type='text/css' href='mousemat.css' />
<script type='text/javascript'>
var cursor=null
window.onload=function(){
var mat=document.getElementById('mousemat');
mat.onmousemove=mouseObserver;
cursor=document.getElementById('cursor');
}
function mouseObserver(event){
var e=event || window.event;
writeStatus(e)
drawThumbnail(e)
}
function writeStatus(e){
window.status=e.clientX+","+e.clientY
}
function drawThumbnail(e){
cursor.style.left=((e.clientX/5)-2)+"px";
cursor.style.top=((e.clientY/5)-2)+"px";
}
</script>
</head>
<body>
<div class='mousemat' id='mousemat'></div>
<div class='thumbnail' id='thumbnail'>
<div class='cursor' id='cursor'></div>
</div>
</body>
</html>
并附上还有要用到的mousemat.css
.body{
background-color: white;
}
.mousemat{
background-color: #ffe0d0;
border: solid maroon 2px;
width: 500px;
height: 500px;
top: 24px;
left: 24px;
position: absolute;
}
.thumbnail{
background-color: cyan;
border: solid navy 1px;
width: 100px;
height: 100px;
top: 24px;
left: 528px;
position: absolute;
margin:0px;
padding: 0px;
}
.cursor{
background-color: navy;
width:3px;
height: 3px;
position: relative;
}
试试看,什么效果,然后再继续下面的吧
下面的会是同样的效果,只是代码复杂了,当然下面的代码是不完整的,只是核心部分。
首先简单介绍下需要模拟的东西,在W3C新的事件模型框架中,IE和Mozilla都实现了相应的版本,在基于Mozilla的浏览器和Safari中,使用addEventListener()来附加时间按回调,使用相应的removeEventListener()来删除,IE提供了类似的函数:attachEvent()和detachEvetn()。在传统的javascript时间模型中,我们无法为一个元素注册多个事件(任何事件),如何解决?
恩,是的,只有靠自己来实现观察者模式了。下面的代码来自《ajax in action》,加入了注释及相关说明。
注:对于观察者模式(Observer)是设计模式的一种,可以查看资料。
//命名空间,是的,只是一种形式
var jsEvent = new Array();
//构造函数
//其中的el在实际中表示的是页面的dom元素(可以是一个button元素,一个div元素等等等),eventType表示的是事件对象(如onclick等等等)
jsEvent.EventRouter = function(el,eventType){
//内部维护一个事件列表,这里的lsnrs很重要,里面存放当事件发生时我们需要的执行事件,是一个数组,所以允许我们把很多事件放进去
this.lsnrs = new Array();
this.el = el;
el.eventRouter = this; //给el元素(记住el是一个页面元素)添加属性eventRouter,这个属性是当前的EventRouter对象
//注册回调函数,恩,已经知道了前面的,现在可以翻译下下面这一句了
//类似于:el.onclick = jsEvent.EventRouter.callback;(后面只是一个当onclick事件发生时需要执行的事件函数而已,具体的callback是什么将在后面的代码中涉及)
el[eventType] = jsEvent.EventRouter.callback;
};
//添加事件,使用了原型,注意添加在了哪里,是的,在上面那个构造函数里,什么用呢?答案是将需要在eventType(如onclick事件)发生时执行的动作事件放到lsnrs数组中,这里只是放进去,并没有执行。对于里面的执行的函数,下面也会说明,现在只是理清过程
jsEvent.EventRouter.prototype.addListener = function(lsnr){
this.lsnrs.append(lsnr,true);
} ;
//移除事件,类似上面的增加事件
jsEvent.EventRouter.prototype.removeListener = function(lsnr){
this.lsnrs.remove(lsnr);
};
//通知所有事件,仍然看清楚这个属性函数加在了哪里,是的,还是在构造函数内,这个notify属性是真正执行、当事件发生时(如el元素被onclick)、需要执行的、被上面函数加在lsnrs数组中的、事件。这里用了奇怪的标点,只是为了不要产生误解
jsEvent.EventRouter.prototype.notify = function(e){
var lsnrs = this.lsnrs;
for(var i=0;i<lsnrs.length;i++){
var lsnr = lsnrs[i];
lsnr.call(this,e);
}
};
//回调函数调用notify,看到了么,callback属性出现了,每当事件发生,都将调用notify函数,这样需要被执行的时间将被不断执行
jsEvent.EventRouter.callback=function(event){
var e = event || window.event;
var router = this.eventRouter;
router.notify(e);
};
//下面的函数是用在addListener和removeListener中的,意思大家应该猜得出来了
//直接在内建类array中增加原型,所有array类的对象都可以使用,其中obj是事件,当事件发生时需要执行的事件,obj对象需要有一个实现,而这里没有,nodup函数只是用来判断,当true时有效
Array.prototype.append = function(obj,nodup){
if(nodup){
this[this.length]=obj; //为什么位置在this.length?恩,这里不明说了,自己动脑筋吧
}
};
//o表示当lsnrs数组中的一个元素,代表一个事件
Array.prototype.remove = function(o)
{
var i = this.indexOf(o);
if (i>-1)
{
this.splice(i,1); //这个函数的作用是:The splice() method is used to remove and add new elements to an array。splice(数组起始位置,删除元素个数,添加的新元素【0】,……,添加的新元素【n】),是的大概是这样的,这里的表示现在该清楚了吧
}
return (i>-1);
}
};
好了,如何使用上面的对象呢:
var mat=document.getElementById('mousemat');
cursor=document.getElementById('cursor');
var mouseRouter=new jsEvent.EventRouter(mat,"onmousemove");
mouseRouter.addListener(writeStatus); //这里面的事件嘛就需要自己写了
mouseRouter.addListener(drawThumbnail); //这里也一样
当然这里的只是些核心代码,如果需要运行,当然还要增加一些必要的东西。那么就到此为止吧,codd和他的朋友们头痛了~~~~~~
分享到:
相关推荐
在JavaScript中,事件模型实际上是一种观察者模式的实现。它允许开发者通过注册事件监听器的方式来响应不同的用户交互事件。这种方式的好处在于,它可以广泛地应用于异步编程中,取代了传统编程中传递回调函数的方式...
本书中详尽阐述了JavaScript中的经典设计模式,如单例模式、工厂模式、策略模式、观察者模式等。这些模式在JavaScript的应用开发中有着广泛的实际应用场景。例如,单例模式保证一个类仅有一个实例,并提供一个全局...
- **原型继承**:JavaScript支持基于原型的继承机制,这不同于传统的基于类的继承模型,因此在实现某些设计模式时会有不同的处理方式。 - **函数式编程**:JavaScript支持高阶函数等函数式编程特性,使得函数不仅...
常见的设计模式包括单例模式、工厂模式、原型模式、观察者模式、迭代器模式等。 JavaScript基础知识覆盖了语言的核心机制、语法结构、数据处理、函数操作、事件处理、DOM操作、异步编程和网络通信等各个方面。掌握...
尽管JavaScript的面向对象特性不同于其他语言,开发者依然可以使用如工厂模式、单例模式、观察者模式等常见的设计模式来组织代码。 了解JavaScript的这些面向对象特性对于编写高效、可维护的代码至关重要。同时,...
- **事件监听与观察者模式**:JavaScript应用的核心是用户交互,通过监听事件来响应用户的操作。 - **事件监听**:使用addEventListener等方法绑定事件处理器。 - **事件取消**:阻止事件的默认行为或阻止事件传播...
本书详细探讨了如何利用事件监听和观察者模式来增强应用程序的交互性。 - **监听事件**:注册事件监听器,以便在特定事件发生时执行相应的回调函数。 - **取消事件**:了解如何取消或阻止事件的默认行为,这对于...
JavaScript是一种广泛应用于Web开发的脚本语言,尤其在构建交互式和动态网页方面扮演着...在实际开发中,结合使用各种设计模式(如工厂模式、观察者模式、单例模式等)可以让JavaScript的面向对象编程更加灵活和强大。
模型通常实现观察者模式,以便在数据更改时通知相关的视图组件进行更新。 2. **视图(View)**:视图负责展示数据给用户,即用户界面的表示。它可以有多种形式,比如图表、列表等。视图并不直接与模型通信,而是...
面向对象设计模式在JavaScript中同样适用,如工厂模式、单例模式、观察者模式等,它们是解决特定问题的通用解决方案,有助于编写更清晰、更可扩展的代码。 以上就是JavaScript中面向对象程序设计的一些关键知识点,...
在“javascript代码大全”中,你可能还会发现关于jQuery库的使用、前端框架如React、Vue、Angular的应用示例,以及一些常见的JavaScript设计模式,如工厂模式、单例模式、观察者模式等。此外,可能还包括关于异步...
首先,传统的设计模式如工厂模式、单例模式、观察者模式等,仍然是现代软件开发的基础。它们为初学者提供了一个理解面向对象编程和软件架构的良好起点。这些模式在各种编程语言中被广泛采用,成为了许多框架和库的...
RxJava是一个强大的异步编程库,它将观察者模式和函数响应式编程结合在一起。RxBus使用`Observable`来发布事件,订阅者通过`subscribe()`方法订阅这些事件。RxBus的优势在于它可以提供更复杂的事件传播规则,如延迟...
而MobX则利用观察者模式,简化了状态的响应式更新。 总的来说,“强大,安全,多线程的Flux模式”是JavaScript开发中实现高效状态管理的一种策略,它通过单向数据流和明确的角色分工,确保了复杂应用的稳定性和可...
- **观察者模式**:理解观察者模式在Reactive Programming中的应用,以及如何通过`subscribe`方法来监听和响应事件。 - **错误处理**:学习如何在流中优雅地处理错误,如使用`catchError`操作符。 - **性能优化**:...
总结来说,Matreshka.js是一个强大且灵活的JavaScript框架,它通过事件驱动、数据绑定和观察者模式,为开发者提供了构建现代化Web应用的强大工具。无论是在小型项目还是大型企业级应用中,Matreshka.js都能以其高效...