javaScript是不是面向对象语言?
以前在书上看到的比较好的一段描述,分享出来仅供参考,下面的例子是以大家熟知的person类,在这里对这个例子不做过多的阐述。
在传统的面向对象语言(java)中,我们一般会这样描述自己的做法:“我基于Person类创建了一个叫Bob的新对象。”,而在js这种基于原型的面向对象语言中,我们会这样描述:”我将现有的Person对象扩展成一个叫Bob的新对象。”
js压根没有类,该语言都是基于对象,其所依靠的是一套原型系统(prototype实际上也是一种对象)。这句话也与‘万物皆对象’呼应了哈。
结合之前项目中的代码细说一下(结合vue+es6--class)。
-
需求:一张人员卡片上有语音通话,视频监控,视频点呼(同微信视频)等功能,并且视频监控和视频电呼不能同时发起,语音通话和视频电话不能同时发起。
-
做法:抽象功能,一个功能创建一个类;再创建一个状态管理的类对所有功能类做一个状态冲突管理。比如,当处于语音通话中时发起视频电呼,提醒用户是否挂掉语音发起视频等操作。
创建功能类
//创建js文件work.js workManage.js(管理类)
import workManage from './workMange'
let manage = workManage.getInstance /*生成管理类单例*/
export default class work {
constructor(id,info){
this.id=id;
this.name=info.name;
this.type=info.type; /*monitor--视频监控;audio--语音通话;video--视频电呼*/
this.status='normal'; /*calling--通话中;normal--正常状态;callIn--呼入中;waiting--等待中;*/
//这里可能根据需求添加属性,比如通信号码等
manage.addWork(this);
}
//业务中断的时候需要重置实例属性
resetInstance(){
this.status='normal';
}
//发起业务,
callWork(){
this.status='waiting'
switch(this.type){
case "monitor":
//调用发起视频监控的api
breack;
case "audio":
//调用语音通话的api
break;
case "video"
//调用视频点呼的api
break;
}
}
//挂断业务
hangUp(){
//和发起业务类似
this.resetInstance();
}
//根据业务需求可继续添加需要的公共方法
}
创建状态管理类
export default class WorkManage {
constructor(){
/*创建一个map对象,存所有生成的功能类,做一个总的状态冲突管理*/
this.workMap=new Map();
}
//生成管理单例 保证全局只会有一个管理类
static getInstance(){
if(!WorkManage.manager){
WorkManage.manager=new WorkManage();
}
return WorkManage.manager;
}
//添加业务
addWork(work){
//key是为了日志方便分别才这么取得,全凭喜好
this.workMap.set(work.name+work.type,work);
};
//是否有语音业务冲突
getCallStatus(param){//参数是业务状态,比如传入calling,就是查看当前是否有通话中的业务
let data=null;
for(let [,value] of this.workMap){
if(value.status===param){
data=value
}
}
//返回null表示没有找到要查询的业务,反之返回查询业务
return data;
};
//当通信卡片关闭的时候删除缓存
deleteWork(id){
for(let [key,value] of this.workMap){
//销毁的组件处于通话中,挂断业务
if(value.id===id){
if(value.status==='calling'||value.status==='callIn'){
value.huangUp()
}
this.workMap.delete(key)
}
}
}
}
main.js 把管理类挂载全局vue上
import workManage from './../workMagage'
import Vue from './vue'
Vue.prototype.$workManage=workManage.getInstance();
组件中使用
mounted(){
this.audioWork=new work(manInfo);
this.monitorWork=new work(manInfo);
this.videoWork=new work(manInfo);
}
//组件销毁时应该把当前活动中的业务中断,并且删除缓存当前组件创建的类
beforeDestroy(){
this.$workManage.deleteWork(this.id);
}
methods:{
//发起语音
audioToOther(){
if(this.$workManage('calling')){
layer.msg('已经有一路语音通话')
reture;
}
this.audioWork.callWork();//外部调用,不需要知道关注api和发起功能业务的细节
}
//发起视频监控
monitorToOther(){
//做一些视频监控的限制条件和冲突,根据具体需求做判断;
//发起业务的冲突判断其实也可以写在work.js类中发起业务的方法里面
this.monitorWork.callWork();
}
}
- 因为业务问题,代码可能逻辑不是通,但是大致意思差不多达到了,具体的只需要根据需求增添