`
jianguang_qq
  • 浏览: 91807 次
  • 性别: Icon_minigender_1
  • 来自: 深圳南山
社区版块
存档分类
最新评论

【JS优化系列】一个通用公告系统的实现

阅读更多

       之前一篇《【JS优化系列】从一个计时器的写法探讨js多种实现方式的优劣》的讨论让我学到不少东西,现在再来一篇,抛砖引玉。

 

       站点的很多页面经常需要发一些公告,而每次发公告都需要开发同学手工来操作是很麻烦的,而且经常不够实时。因此写了一个通用公告系统,希望能将这份工作交由产品同学来操作。这里只写了“小黄条”一种形式的公告,其他形式实现方法类似。实现了可以“定时自动关闭”,“所有页面每次打开都显示小黄条”,“仅在第一次打开的页面显示一次”,“用户手动关闭后不再显示”功能。以此基本能满足日常运营需求。

      先将代码和实现方式贴出,邀请大家一起探讨优化。

 

/**
 * 通用公告系统
 * 
 * @package    pub_notice.js
 * @author     jessezhang <jianguang.qq@gmail.com>
 * @date       2009-08-15
 * @version    1.0.0
 */

var LIB = LIB || {};
LIB .pubNotice = (function(){
	
	var $id = function(id){return document.getElementById(id);}
	var $ = LIB ;
	
	/**
	 * 小黄条
	 * 	 
	 * @access public
	 * @param {json} json 小黄条属性
	 */
	function yellowTips(json){
		this._id = json["id"];
		this._text = json["text"];
		this._showType = json["showType"];
		this._timeout = json["timeout"];
		this._domId = "QQVIP_pubNotice_yellowTips_" + json["id"];
		this._timer = null;
	}
	
	yellowTips.prototype = (function(){	
									 
		/**
		 * create一个小黄条
		 * 
		 * @access public
		 */	 				 
		function create(){	
			if(!_checkShowType.call(this))return ;
			//container标签为必须,诺没有container,则不显示小黄条						
			if(!$id("container"))return;
			
			var _nBox = document.createElement("div");
			_nBox.id = this._domId;
			_nBox.className = "bulletin";
			_nBox.innerHTML = "<button type=\"button\" class=\"bt_close_bulletin\" title=\"关闭\" onclick=\"javascript:document.getElementById('"+this._domId +"').style.display='none';QQVIP.cookie.set('" + this._domId + "', '2');\">X</button>" + this._text;
			document.body.insertBefore(_nBox,$id("container"));
			this._timeout && this.hide(this._timeout);
			$.cookie.set(this._domId,"1");//1:表示已经显示过该小黄条
		}
		
		/**
		 * 显示小黄条
		 * 
		 * @access public
		 */	 
		function show(){
			$id(this.domId).style.display = "";
		}
		
		/**
		 * 隐藏小黄条的接口
		 * 
		 * @access public
		 */		
		function hide() {
			var _this = this;
			if (this._timeout) {
				this._timer && clearTimeout(this._timer);
				this._timer = setTimeout(function(){_hide.call(_this);}, this._timeout);
			} else {
				_hide.call(_this);
			}
		}
		
		/**
		 * 内部实现隐藏小黄条
		 * 
		 * @access private
		 */	
		function _hide(){
			this._timer && clearTimeout(this._timer);
			$id(this._domId).style.display = "none";
		}	
		
		/**
		 * showType : 显示方式
		 * 1:所有页面每次打开都显示
		 * 2:只在第一次打开的页面显示一次
		 * 3:用户手动关闭后不显示
		 *
		 * cookieValue : cookie存储的状态
		 * 1:已经显示过
		 * 2:用户手动关闭
		 */	
		function _checkShowType(){
			if(this._showType == "1") return true;
			var cookieValue = $.cookie.get(this._domId);
			return (this._showType == "2" && cookieValue != "1" && cookieValue != "2") || (this._showType == "3" && cookieValue != "2");
		}
		
		return {
			create : create, 
			show : show, 
			hide : hide
		}		
	})()
	
	/**
	 * 浮出层,建设中...
	 * 
	 */
	function floatLayer(obj){}
	
	/**
	 * 弹出窗口,建设中...
	 * 
	 */
	function openWindow(obj){}
	
	/**
	 * 将设置的url转化成验证页面地址的正则表达式
	 * 
	 * @access private
	 * @param {istring} url 设置的url
	 * @return {RegExp} 验证页面地址的正则表达式
	 */
	 
	function _regURL(url){
		if (/^\^/.test(url)) {
			//以符号"^"开头的url都看成本身已经是正则表达式的形式了,不需要再处理
			return new RegExp(url);
		} else {
			//不是以符号"^"开头的url都需要处理成正则表达式的形式,
			//主要对符号"/"和index.html、index.htm、index.php进行处理,		
			//使得"http://vip.lib.com/index.html"、"http://vip.lib.com/"都可以被正确识别
			var RegStr = url.replace(/(^[\w-:\/\.]*).*/, function($0, $1){
				var ret = $1.replace(/\//g, "\/").replace(/\?/g, "\?");			
				var reg = new RegExp("(index.html|index.htm|index.php)$");
				if (reg.test($1)) {
					ret = ret.replace(reg, function(a,b){
						return 	"(("+b+")+|$|\\?|\\#)";						  
					});
				} else {
					ret = $1+"((index.html|index.htm|index.php)+|$|\\?|\\#)";
				}
				return ret;
			});
			return new RegExp(RegStr);
		}
	}
	
	/**
	 * 判断当前页面的url是否符合要求
	 * 
	 * @access public
	 * @param {istring} str 设置的验证url的字符串
	 */
	function checkUrl(str){
		var loaction = window.location;
		str = str.replace(/^\||\|$/g,"");
		var urls = str.split("|");
		for(var j=0; j<urls.length; j++){
			if(_regURL(urls[j]).test(loaction)){			
				return true;
			}
		}
		return false;
	}
		 
	return {
		yellowTips : yellowTips,
		floatLayer : floatLayer,
		openWindow : openWindow,
		checkUrl : checkUrl
	};
})();

 (function(){
	var yellowTips = [
		{id:1, url:'^http://vip.LIB .com/|', text:'<strong>LIB 宣:</strong><p>这是世界上最强大的紧急公告系统!</p>', showType:1, timeout:3*1000},
		{id:2, url:'http://vip.LIB .com/mall/mall.php|http://vip.LIB .com/freedom_act/act.html|http://vip.LIB .com/my_status/my_status_index.php', text:'<strong>LIB 专区问题</strong><p>LIB 专区问题</p>', showType:2, timeout:0*1000},
		{id:3, url:'http://vip.LIB .com/qq.html|http://vip.LIB .com/life.html|', text:'<strong>[LIB ]</strong><p>LIB 频道,生活公告ffff</p>', showType:3, timeout:0*1000}
	]
	for(var i=0; i<yellowTips.length; i++){
		if(LIB.pubNotice.checkUrl(yellowTips[i]["url"])){
			new LIB.pubNotice.yellowTips(yellowTips[i]).create();
		}
	}
})()

      目前的实现方式是,所有页面都在自身加载完成之后去加载这段代码。代码会通过页面的url来判断是否显示公告,以及显示哪几条公告。而设置的时候有两种方式,一种是输入特定页面的完全url,另一种是通过正则来匹配。在本实现中以传入的url是否以“^”符号其起始来判断是否当正则来处理(这种方式好坏大家可以一起探讨),如“^http://vip.lib.com/”表示发布到vip.lib.com域名下的所有页面,“http://vip.lib.com/”或者“http://vip.lib.com/index.html”表示仅仅发布到lib首页一个页面。

      这里的代码将由管理后台生成,若没有没有公告,则所有代码为空,以节省流量。

      在本例中应该有很多地方可以优化的,希望大家一起探讨优化。比如_regURL()这个函数的实现,我并没有做很多的考虑,肯定有很多可以优化的地方。还有实现方式上也有很多地方值得探讨,比如这样做所有页面都多了个请求,所有页面都会引入所有的公告内容,这样实现是否是最好的。代码是由管理后台生成的,那么产品同学输入内容的,在后台输出的时候是不是需要过滤处理那些特殊字符,等等。。。还有很多其他需要周全考虑的地方。

      希望大家一起来探讨,让代码达到最“优雅”。当然大家的探讨不仅仅是代码上,还可以是整个公告实现的方式上的。

 

 

 

 

【本人发帖抛砖引玉,希望能够引出更多的“玉”来,希望所写的每一段代码都能够得到一种最“优雅”的实现方式。以后本人会抛出更多的“砖”,希望能引来更多的“玉”,以供大家一起学习进步】

 

分享到:
评论

相关推荐

    通用网店系统源码webshop

    【通用网店系统源码WebShop】是一个用于构建在线商店的软件解决方案,它包含了实现电子商务功能所需的核心组件。这个源码提供了完整的购物系统框架,允许开发者根据业务需求进行定制和扩展,以满足各种类型的网店...

    SSM通用教师教学管理系统

    SSM通用教师教学管理系统是一个基于Java的Web应用,利用了Spring、SpringMVC和MyBatis这三大主流的Java EE开发框架,旨在为教育机构提供一个便捷、高效的在线教学管理平台。这个系统对于初学者来说,是理解SSM框架...

    基于SpringBoot的网上通用报名系统.docx

    2.1 Vue:Vue.js 是一个轻量级的前端JavaScript框架,用于构建用户界面,提供了丰富的组件化功能,使得页面交互更加简单直观。 2.2 Axios:Axios 是一个基于 promise 的 HTTP 库,常用于前端向后端发送请求,处理...

    通用OA系统,毕业设计

    在毕业设计中,开发一个通用的OA系统是一项具有挑战性的任务,它涵盖了多个IT领域的知识,如软件工程、数据库设计、Web开发、前端界面设计以及业务流程管理等。 首先,我们需要了解OA系统的基本架构。通常,OA系统...

    [信息办公]Asp.net通用OA系统_uds.zip

    【标题】"Asp.net通用OA系统"是一个基于.NET框架的办公自动化系统,它主要用于提升企业或组织的内部协作效率,实现信息化管理。这个系统利用Asp.net技术,结合数据库和Web服务,构建了一个功能丰富的在线办公平台。 ...

    信息办公Asp.net通用OA系统-uds.rar

    Asp.net通用OA系统_uds.rar是一个基于ASP.NET技术的通用办公自动化系统源码文件包,适用于作为毕业设计、课程设计的项目。该系统采用了B/S架构,前端使用HTML、CSS和JavaScript进行页面设计,后端使用C#语言进行业务...

    基于Web的通用BBS系统的建立与维护

    【基于Web的通用BBS系统的建立与维护】是关于构建和管理网络论坛系统的一个主题,主要探讨了如何利用Web技术创建一个功能齐全、用户友好的在线讨论平台。BBS(Bulletin Board System)即电子公告板,是互联网上的一...

    通用OA开源系统下载

    在“通用OA开源系统下载”这个主题中,我们关注的是一个可以免费获取并使用的OA系统。开源意味着其源代码是公开的,用户不仅可以自由地使用,还可以查看、修改和分发这些代码,这对于开发者来说具有极大的灵活性和可...

    通用企业网站系统.

    【通用企业网站系统】是一种基于ASP(Active Server Pages)技术构建的企业级网站解决方案。ASP是微软开发的一种服务器端脚本语言,它允许开发者在网页上动态生成内容,从而实现交互性和个性化服务。在这个系统中,...

    通用不间断滚动JS封装类

    通用不间断滚动JS封装类,即`MSClass (Class Of Marquee Scroll)`,是一种JavaScript技术,用于实现网页元素的持续滚动效果。在Web开发中,这种滚动效果常用于新闻标题、公告或者广告展示,以吸引用户的注意力。`...

    JSP源码——[信息办公]Asp.net通用OA系统_uds.zip

    【JSP源码详解——构建信息办公OA系统】 ...在【信息办公】Asp.net通用OA系统_uds...开发者可以通过阅读和分析源码,了解如何利用JSP实现一个功能完善的OA系统,同时也可以从中学习到企业级Web应用的设计原则和最佳实践。

    网页通用不间断滚动JS大全 简单实用

    "Class Of Marquee Scroll通用不间断滚动JS封装类"是一个专门设计的JS库,它提供了一种简便的方法来实现这种效果。 这个库的核心在于它的封装性。封装意味着开发者无需深入理解复杂的JS滚动逻辑,只需调用预定义的...

    新闻发布系统,非常好用的新闻发布系统

    6. **Utg.asp**:可能是一个未明确的组件,但根据命名,可能是“用户管理”或者“通用”功能的页面,负责用户注册、权限分配或通用的系统设置。 7. **link_js.asp**:可能与链接管理有关,特别是JavaScript实现的...

    通用BBS论坛原代码

    本资源包含的是一个通用的BBS论坛原代码,对于学习和理解BBS论坛的运作机制以及编程实践具有很高的价值。下面我们将深入探讨BBS论坛的核心概念和实现技术。 1. **BBS论坛架构** BBS论坛通常由前端用户界面和后端...

    layui企业网站后台管理通用模板

    layui的核心在于其模块化的结构,主要包括layui.all.js(全模块)和layui.css(全局样式)两个主要文件。框架提供表格、表单、按钮、提示、弹窗等多种组件,以及灵活的布局方式,支持响应式设计,适应各种设备屏幕。...

    中铁特货一个有特殊效果的系统源码

    标题中的“中铁特货一个有特殊效果的系统源码”暗示了这可能是一个专门为中铁特货公司定制的软件系统,其源代码包含了某些特定的功能或特效。这些特殊效果可能涉及用户体验优化、数据处理效率提升或者是为了满足物流...

Global site tag (gtag.js) - Google Analytics