一个简单的中文字符转unicode的chrome插件

展开/收缩

插件安装地址(请用chrome打开): toUnicode.crx
12-7 更新增加了从unicode转字符,以及encode,decode等方便的功能

在通常的JS或CSS文件里,汉字等字符是以unicode的16进制形式存在的, 如果直接输入汉字,在英文或其他语种的系统上,容易造成乱码无法识别的状况,如果把所有汉字转成unicode形式就没有问题了,所以就想到做一个chrome小插件,随时查看汉字的unicode编码,
直接看下主转换代码:

/**
 * 中文转unicode字符工具
 */
function toUnicode(str, cssType) {
    var i = 0,
        l = str.length,
        result = [], //转换后的结果数组
        unicodePrefix, //unicode前缀 (example:\1234||\u1234)
        unicode16; //转换成16进制后的unicode

    //如果是css中使用格式为\1234之类
    unicodePrefix = (cssType && cssType.toLowerCase() === 'css') ? '\\' : '\\u';

    for (; i < l; i++) {
        //转为16进制的unicode, js及css里须转成16进制
        unicode16 = str.charCodeAt(i).toString(16);
        result.push( unicodePrefix + unicode16 );
    }

    return result.join(' ');
}

字符串的charCodeAt方法返回的是10进制的unicode,所以我们需要用toString(16)将其转为16进制的,才能在JS及CSS中使用,而CSS中跟JS不同的是少了个U。

再来看下页面上的调用 :

/**
 * excute
 */
var input = document.getElementById('input'),
    convert = document.getElementById('convert'),
    CSSResult = document.getElementById('resultCSSType'),
    JSResult = document.getElementById('resultJSType'),
    msg = document.getElementById('msg');

//事件处理
function convertStr(e) {
    var v = input.value;

    //管理事件
    switch (e.type) {
        case 'click':
            if (checkInput(v)) {
                renderResult(v);
            }
            break;

        case 'keydown':
            if (e.keyCode === 13 && checkInput(v)) {
                renderResult(v);
            }
            break;
    }

    //检测英文等字符排除
    function checkInput(str) {
        var charReg = /[^u0391-uFFE5]/g; //匹配英文等无需转换的字符

        if (charReg.test(str)) {
            msg.innerHTML = '输入字符格式有误,请输入中文等字符';
            input.select();
            input.focus();
            renderResult('');
            return false;
        } else {
            msg.innerHTML = '';
            return true;
        }

    }

    //渲染结果
    function renderResult(str) {
        JSResult.innerHTML = toUnicode(str);
        CSSResult.innerHTML = toUnicode(str, 'css');
    }

} 

//bind事件
convert.addEventListener('click', convertStr, false);
input.addEventListener('keydown', convertStr, false);
input.addEventListener('blur', convertStr, false);

正则/[\u0391-\uFFE5]/是用来匹配中文字符,包括标点,繁体什么的。

再来就是生成chrome插件,chrome插件制作很简单,只需在chrome的扩展程序里导入你的项目文件 ,通常就是html+css+js文件即可,然后就可打包生成crx文件,可以在chrome上安装的插件了,(PS:具体的插件制作GG搜索下就有了)

本来想发布至chrome的webstore里,结果发布竟然还要收费 ,所以还是作罢,直接贴一下插件安装地址吧,请用chrome打开 toUnicode.crx

关于递归在项目中的几种常用应用

展开/收缩

项目中常常会对开发返回的json数据进行遍历,然后更新页面,如果数据只是简单的一层结构,只需一个for循环即可搞定,但如果数据存在较深且不确定的层次,此时就需要使用递归配合循环来搞定,先看下模拟的数据格式:

//json数据
var json = {
    status: 'success',
    data: [
        {
            status: 0,
            title: '文件夹1',
            data: [
                {
                    status: 0,
                    title: '文件夹2',
                    data: [
                        {
                            status: 0,
                            title: '文件夹3',
                            data: [
                                {
                                    status: 0,
                                    title: '文件夹4',
                                    data: []
                                },
                                {
                                    status: 0,
                                    title: '文件夹4',
                                    data: []
                                }
                            ]
                        },
                        {
                            status: 0,
                            title: '文件夹3',
                            data: []
                        }
                    ]
                },
                {
                    status: 0,
                    title: '文件夹2',
                    data: []
                }
            ]
        },
        {
            status: 1,
            title: '文件1',
        }
    ]
};

对于上面这种深层次的数据结构,普通的循环是无法搞定的,此时可以提取重复处理的代码片段,然后使用递归 即可搞定,直接看代码:

/**
 * 递归遍历数据
 */
function recursion(data) {
    var i = 0,
        len = data.length,
        j, item, current, flag;

    for (; i < len; i++) {
        item = data[i];

        for (j in item) {
            current = item[j];
            //是否数组判断
            flag = (Object.prototype.toString.call(current) === '[object Array]') ? true : false;

            if (flag) {
                recursion(current);
            } else {
                //这里执行对数据的相应操作
                console.log(current);
            }
        }
    }
}

//调用
recursion(json.data);

一个类似的应用是DOM节点的游走,可以遍历整个文档所有节点,包括子节点,看如下代码:

/**
 * 节点遍历
 */
function nodeWalk(node, fn) {
    var re = arguments.callee; //引用函数本身

    if (node.nodeType === 1) {
        //处理节点
        fn.call(node, node);
    }

    node = node.firstChild;

    while (node) {
        re(node, fn);
        node = node.nextSibling;
    }

}

//调用
nodeWalk(document.body, function(n){
    console.log(this.nodeName);
});

还有一种典型用例是,对于多行的input需要往后端ajax实时验证输入内容的时候,普通的for循环已不能解决问题,需要在ajax请求成功的回调函数里进行递归调用,直接看示例代码:

//初始化
var nodeList = $('#test input:text'),
    n = 0;

/**
 * 递归验证
 */
(function recursionCheck(node) {

    var v = node.value,
        nextNode = nodeList[++n];

    //ajax请求服务端验证
    $.ajax({
        'url': 'xxxxx.do',
        'data': 'xxxxxx',
        'dataType': 'json',
        'success': function(data){

            //验证成功,递归调用代码验证下一个node
            if (data.value === v) {

                //判断节点是否存在
                if (nextNode) {
                    recursionCheck(nextNode);
                } else {
                    alert('验证通过');
                }
            } 

            //验证不成功,结束执行,给出错误提示
            else {
                alert('数据验证不正确');
            }
        }
    });

})(nodeList[n]);

模拟AJAX无刷新的文件上传功能

展开/收缩

传统的文件上传功能一般是用form包一个input:file直接提交到后端进行处理,form须指定enctype=”multipart/form-data”,代码如下:

<form action="test.php" target="" method="post" enctype="multipart/form-data">
    <input type="file" name="file" id="file" />
    <input type="submit" id="J_submit"  value="submit" />
</form>

在ajax盛行的现时,提交form再刷新整个页面,显得用户体验不佳,然而ajax与后端通信 只能传送字符串,是无法传递实体文件的,所以用ajax是无法实现直接文件上传的,这里提供一个解决方案就是用一个实时创建的隐藏iframe来完成上传功能, 具体的原理是,在点击提交按钮时,动态的生成一个隐藏iframe加入到页面上,并且 将form 的 target指向该隐藏iframe,服务端就接收到上传的file文件,并进行相应的操作,然后将返回结果返回到隐藏的iframe里面,这时我们可以与后端开发约定返回结果的格式,可以是json格式,便于我们前端操作,然后前端部分就可以用iframe.contentWindow.document.body.innerHTML来获取后端返回的结果,进行相应的parseJSON处理,即可像处理ajax返回的json一样,处理数据。。。直接贴源代码了(ps:代码是基于jQuery库的):

/**
 * 模拟ajax无刷新文件上传
 */
var fileUpLoad = function(config) {

    var ifr = null,
        fm = null,
        defConfig = {
            submitBtn: $('#J_submit'), //提交按钮
            complete: function(response) {}, //上传成功后回调
            beforeUpLoad: function() {}, //点击提交未上传时回调
            afterUpLoad: function() {} //点击提交上传后回调
        };

    //静态变量
    var IFRAME_NAME = 'fileUpLoadIframe';

    //配置
    config = $.extend(defConfig, config);

    //绑定submit事件
    config.submitBtn.bind('click', function(e){
        e.preventDefault();

        //点击提交前触发事件, 函数返回false可阻止提交表单,用于file为空判断
        if (config.beforeUpLoad.call(this) === false) {
            return;
        }

        //生成一个隐藏iframe,并设置form的target为该iframe,模拟ajax效果
        ifr = $('<iframe name="'+ IFRAME_NAME +'" id="'+ IFRAME_NAME +'" style="display:none;"></iframe>');
        fm = this.form;

        ifr.appendTo($('body'));
        fm.target = IFRAME_NAME; //target目标设为ifr

        //上传完毕iframe onload事件
        ifr.load(function(){
            var response = this.contentWindow.document.body.innerHTML;

            config.complete.call(this, response);
            ifr.remove();
            ifr = null; //清除引用
        });

        fm.submit(); //提交表单

        //点击提交后触发事件
        config.afterUpLoad.call(this);

    });

};

页面调用是:

fileUpLoad({
    submitBtn: $('#J_submit'),
    complete: function(response){ //上传成功后处理回调
        var d = $.parseJSON(response);

        alert('返回成功')
        console.log(d);
    },
    beforeUpLoad: function() {
        alert('上传前');
    },
    afterUpLoad: function() {
        alert('上传后');
    }
});

而对于需要实时显示上传进度条的应用,则可以考虑form提交后用ajax实时轮询的方式向后端取文件上传的进度,来进行前端页面进度渲染,另一种方式则是基于flash上传,这里就不详细展开了。。

正则表达式的技巧总结

展开/收缩

正则表达式在现在web的应用当中,如表单验证,url解析等,应用非常方便,比起普通的字符串解析性能上也高出不少。
这里就做一些关于正则表达式通用技巧的个人小总结,正则的入门可以参考以下网址内容
http://www.regexlab.com/zh/regref.htm
http://w3school.com.cn/js/jsref_obj_regexp.asp

1. 一些常用的元字符.
\w : 查找单词字符,包含字母数字及下划线,相当于[A-Za-z0-9_];
\d : 查找数字,相当于[0-9]
\s : 查找空白字符
\n : 查找换行符
. : 点号代表除换行符及行结束符外所有字符

2. 验证完整字符串,这在表单验证中常用到,例子如下:

var str = '18636200607';
var str2 = '10010';
var reg = /^\d{11}$/;
console.log(reg.test(str)); // return true;
console.log(reg.test(str2)); // return false;

这里的头尾的^$即是限定匹配的必须是整个字符串,而不是其中一部分,这对于表单验证里验证完整的合法输入很有用。
[继续阅读全文...]

浮动元素的水平居中

展开/收缩

对于页面上的块级元素,只须定宽及设置margin:0 auto;即可在水平上居中,但对于浮动的元素水平居中是无效的,一个典型的应用就是页面的分页效果了,看如下图:

这种分页效果,在以往可能会采取设置inline-block,然后父容器设置text-align:center方式来实现内容居中,像如下代码:

提示:你可以先修改部分代码再运行。

[继续阅读全文...]

HTML5的本地存储 LocalStorage

展开/收缩

localStorage顾名思义,就是本地存储的意思,在以前很长一段时间,要想在客户端存储一些配置及登录信息等数据都只能通过COOKIE或flash的方式,如今html5来临,也带来了更强大的本地存储,最多可存储大小5M的字符串,足可以满足大部分的web应用,比cookie的4K要大出不少,还有一个sessionStorage,功能基本与localStorage相同,看名字便知与sesstion一样,关闭浏览器即失效。

以前有用过cookie的都了解cookie的存储读取方式都不太优雅,需要自己封装set get方法,而localStorage则方便许多,localStorage 是作為window的一个属性存在的,拥有setItem,getItem,removeItem,clear等方法,相当方便。

浏览器的支持除了IE7及以下不支持外,其他标准浏览器都完全支持(ie及FF需在web服务器里运行),支持情况如下图:

如下代码即可判断浏览器是否支持

if(window.localStorage){
    alert("浏览支持localStorage")
}else{
   alert("浏览暂不支持localStorage")
}

[继续阅读全文...]

页面性能优化之内容加载优化

展开/收缩

图片按需加载
现在大部分门户或电子商务网站的产品列表页,都比较长,且图片较多,如果全部加载,通常会耗费较多时间,而且有数据表明长时间的等待页面响应会流失大部分的用户,
所以此时我们就可以考虑只加载第一屏的内容,第一屏内容以外的图片按需加载,用户滚动到该屏时再加载(包括tab切换也可以考虑未显示的区域图片不加载),这样用户在不进行任何操作时,加载页面会很快.
看下面的简单demo:

提示:你可以先修改部分代码再运行。

点运行可查看结果,这里测试代码略显粗糙,其实可以利用JQuery好好的用插件形式封装一下,比如可以判断img是否有src属性,没有再执行赋值操作,避免重要赋值,以及setTimeout的使用可以避免滚动过程中大量scroll事件引起性能损耗.

[继续阅读全文...]

>>
后台管理 工具库 RSS 微博 简历