异步加载WordPress插件的Javascript和CSS

PS:此方法实现了异步加载成功,但是在第一次载入页面(js)的情况下,是显示不了效果的(至少我的插件是这样,各位童鞋可以试试),之后再刷新或者再浏览其他页面的话,会显示效果了-_-!!!,求解!!!同时大家可以参考这里,简洁的代码:Xhr异步按顺序加载script

因为博客里面有需要用到代码插件,之前的某些博文,几乎只集中在WordPress这个分类内。相信大家都知道,Wordpress的插件加载的话,是整个博客所有页面都会进行加载的,而且这个代码插件的Javascript代码竟然有10个之多,试想一下假如每个页面都进行加载的话,是多么的浪费资源和影响用户体验。只能改进啦,改进,翻资料,测试,终于最后算是成功了,耗费了一个下午的时间。下面通过我所用的插件和方法来说说思路。

一、插件Syntax Highlighter and Code Prettifier Plugin for WordPress

这款插件的代码作用标签为<pre>,使用方法类似<pre class=”brush:php”>,其中php的位置可以替换为其他你需要显示的代码名称,如c#、xml等。

二、判断标签<pre>

当然,假如博客里面有其他地方还用到<pre>标签的话,换需要更多的属性判断。

这里我采用document.getElementsByTagName方法:

if ( document.getElementsByTagName('pre').length > 0 ) {

}

用length来判断是否存在着标签,然后执行JS和CSS的加载行为。

三、同步加载Javascript

这个也是最难解决的问题,其实最难的问题,也就是夸浏览器,如万恶的IE。最后Google到了算是比较完美的方法,贡献。

function GetHttpRequest()

{

if ( window.XMLHttpRequest ) // Gecko

return new XMLHttpRequest() ;

else if ( window.ActiveXObject ) // IE

return new ActiveXObject("MsXml2.XmlHttp") ;

}

function AjaxPage(sId, url){

var oXmlHttp = GetHttpRequest() ;

oXmlHttp.onreadystatechange = function()

{

if ( oXmlHttp.readyState == 4 )

{

if ( oXmlHttp.status == 200 || oXmlHttp.status == 304 )

{

IncludeJS( sId, url, oXmlHttp.responseText );

}

else

{

alert( 'XML request error: ' + oXmlHttp.statusText + ' (' + oXmlHttp.status + ')' ) ;

}

}

}

oXmlHttp.open('GET', url, true);

oXmlHttp.send(null);

}

function IncludeJS(sId, fileUrl, source)

{

if ( ( source != null ) && ( !document.getElementById( sId ) ) ){

var oHead = document.getElementsByTagName('head');

var oScript = document.createElement( "script" );

oScript.language = "javascript";

oScript.type = "text/javascript";

oScript.id = sId;

oScript.defer = true;

oScript.text = source;

oHead[oHead.length-1].appendChild( oScript );

}

}

上面的代码,主要是用来同步多个JS文件的加载顺序,因为后面加载上来的JS文件可以会用到前面加载的文件的对象,必须前面的加载才能正常运行。而一般的异步加载JS文件加载顺序都是不同步的,也就是说,在声明加载了之后,会接着加载后面的文件,而不理会这个文件是否已经下载完成。

举个例子,A文件和B文件,B需要用到A的对象。A在B之前被声明要下载,然后A开始下载,然而Javascript继续运行,声明B,然后B下载,最后,B假如先于A下载完成,出现JS错误。

PS:已经写在HTMl里面的<script type=’text/javascript’ src=’……..’></script>是会被按照顺序执行的,加载完成后才再执行下面的一行,所以想想假如有10个JS文件要加载,那个等待时间,HLL地。

四、修改插件Javascript的加载方法

一般插件加载Javascript和CSS都会用到类似的钩子函数

add_action('wp_header','xxx_header');

add_action('wp_footer','xxx_footer');

而在这些函数(xxx_header、xxx_footer)里面,一般Javascript和CSS的声明都是直接输出的,所以需要在这里面进行修改。我们只需把要加载的JS和CSS文件的地址传递给处理的函数就可以了

以我的插件Syntax Highlighter and Code Prettifier Plugin for WordPress为例子

<?php

function highlighter_footer() {

?>

<script type="text/javascript">

if ( document.getElementsByTagName('pre').length > 0 ) {

var jsS = new Array(

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shCore.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shBrushCss.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shBrushJScript.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shBrushPhp.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shBrushSql.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/shBrushXml.js",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/scripts/clipboard.js"

)

var styleS = new Array(

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/styles/shCore.css",

"http://wgmcn.com/wp-content/plugins/syntax-highlighter-and-code-prettifier/styles/shThemeDefault.css"

)

MiniSite.StyleLoader.load(styleS,function(){});

MiniSite.JsLoader.load(jsS,function(){});

}

</script>

<?php

}

add_action('wp_footer','highlighter_footer');

?>

然后,处理地址的函数

var	MiniSite=new Object();

MiniSite.Browser={

ie:/msie/.test(window.navigator.userAgent.toLowerCase()),

moz:/gecko/.test(window.navigator.userAgent.toLowerCase()),

opera:/opera/.test(window.navigator.userAgent.toLowerCase()),

safari:/safari/.test(window.navigator.userAgent.toLowerCase())

};

function loader(sUrl,	i, ltype)	{

var	sHead	=	document.getElementsByTagName('head');

var	_load	=	document.createElement(ltype);

if (i	== sUrl.length)

{

return;

}

if (ltype	== 'script')

{

AjaxPage(	"script_ajax_" + i,	sUrl[i]	);

return loader(sUrl,	i+1, ltype);/*递归求解*/

}

else if	(ltype ==	'stylesheet')

{

var	_load=document.createElement('link');

_load.href = sUrl[i];

_load.rel='stylesheet';

_load.type='text/css';

sHead[sHead.length-1].appendChild(_load);

return loader(sUrl,	i+1, ltype);/*递归求解*/

}

else {

alert('else');

return;

}

}

MiniSite.JsLoader={

load:function(sUrl,	fCallback){

loader(sUrl, 0,	'script');

fCallback();

}

};

MiniSite.StyleLoader = {

load:function(sUrl,	fCallback){

loader(sUrl, 0,	'stylesheet');

fCallback();

}

};

上面stylesheet的递归求解其实可以用到for循环来完成的,或者Javascript的加载也可以,没有试验过。在之前的版本中(不兼容IE)就是用for循环来进行异步加载的,并且可以判断各个类型浏览器的状态改变,后因同步问题改为递归形式,现在也懒得改动了。

将上面的Javascript代码全部复制进一个JS文件,命名为load_ajax.js,然后在Footer模板上加上。记得要加在<?php wp_footer(); ?>之前哦。

<script type='text/javascript' src='<?php bloginfo('template_directory'); ?>/js/load_ajax.js'></script>

然后,根据插件的输出,先判断是否存在<pre>标签,如果存在,则添加JS和CSS文件地址,使用load_ajax.js里面的函数加载JS和CSS;如果不存在,则不加载。这个load_ajax.js文件仅仅有2k大小,而且可以多个插件同时使用,并且可以用在广告和页面效果的实现上,实在是十分方便。(当然,插件还是要自己修改,这里有一点点麻烦,特别是插件升级的时候要注意备份)

如果童鞋们有更好的方法,希望告知,同时有任何疑问,可以在下面留言或者Email我,点页面最下面的Gmail图标。

Wordpress at 2010, August 18, 2:18 am, Tags: , , , ,
Trackback URL

6 Comments on "异步加载WordPress插件的Javascript和CSS"

  1. K
    Dianso
    August 23, 2010 at 04:57 Permalink

    我用这个插件都是直接在括号里填写代码名称就可以高亮了,这样省劲,比如

  2. K
    Dianso
    August 23, 2010 at 05:02 Permalink

    竟然屏蔽了代码,括号php括号your code here括号/php括号

    我都是这样用

  3. K
    K
    August 23, 2010 at 12:49 Permalink

    嗯嗯,需要写代码的确是这个插件好使哈,不过就是加载的js太多了。

  4. K
    krady
    October 18, 2010 at 18:14 Permalink

    可以使用autoloader.js,这个可以根据需要来加载特定的JS。可以去我的blog看,最近正好我写了一篇相关的

  5. K
    K
    October 21, 2010 at 22:57 Permalink

    謝謝,現在就圍觀去

  6. K
    wholesale
    December 7, 2010 at 08:34 Permalink

    谢谢分享,用jquery也可以啊

Hi Stranger, leave a comment:

ALLOWED XHTML TAGS:

<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Subscribe to Comments