Nokia X6 官方OVI无痛刷机 港版变国行 可更换颜色

买了个X6的换壳机, 16G, 蓝白色, 不过拿到手后发现界面依旧是粉红色的… 郁闷之际, 想通过刷机解决问题.

原来用过凤凰刷过6120c, 这次相应的应该也可以用凤凰来刷, 但是无意间看到一个通过修改手机CODE的方式来实现刷机的方法, 觉得甚妙, 于是写下来分享.

免责声明: 作者(Vilic)通过以下方法成功将固件从 “港版 白/粉红” 更新为 “国行 白/蓝”, 但是不保证此方法在其他人品条件下同样可用, 对于使用此方法造成的一切损失, 都与作者无关. 谢谢~

在刷机之前, 需要找到想要刷的版本的CODE, 你可能会用到这些:

0595776:诺基亚RM-559 国行3G 16GB的黑色/黑色
0595705:诺基亚RM-559 国行3G 16GB的白/粉红
0595778:诺基亚RM-559 国行3G 16GB的白色/黄色
0595196:诺基亚RM-559 国行3G 32GB的白/蓝
0595084:诺基亚RM-559 国行3G黑/红

如果上面没有你想刷的, 可以Google下X6 CODE. 请注意机型一定要一样. 输入*#0000#可以看到一个类似于RM-XXX的东西, 保证它和你要更改的CODE所对应的相同.

除了安装好的OVI套件, 我们还需要准备一个小软件, 叫NSS, 官方网站: http://www.b-phreaks.co.uk/, 到现在, NSS的下载地址为: http://www.b-phreaks.co.uk/index.php?main_page=page_2. 下载并完成安装.

  1. 退出NOKIA PC SUIT和OVI SUIT, 运行NSS.
  2. 使用USB数据线连接电脑和手机, 并且选择PC套件模式(其他模式未试).
  3. 单击NSS右上角的放大镜, 这时NSS会搜索设备.
  4. 完成搜索后, 在下方选择手机样式的图标(Phone Info).
  5. 在右边Production Data Edit处点Read, 来读取相应信息. (此步非必要)
  6. 将想要刷的固件对于的CODE填入Product Code文本框中, 并且勾选Enable.
  7. 点击Write写入新的CODE.
  8. 点击Read确认新的CODE已经写入成功.
  9. 关闭NSS.

现在, CODE就改好了, 下面需要做的就是打开OVI套件, 并且选择软件更新. OVI会自动检测可用的固件更新, 如果提示固件已经是最新版本, 则选择重新安装即可. 一般情况下, 数据不会丢的, 但是为了防止万一, 还是备份一下吧!

发现国行的简体中文和港版的简体中文字体上还是有区别的,  其他倒没发现什么(当然, 我换了颜色), 祝刷机成功!

Original link of this archive: http://vilic.info/blog/archives/550
本文的原始链接: http://vilic.info/blog/archives/550

JavaScript RegExp 正则表达式g模式的使用

说明下, 文章中的有些东西来自Franky大神的文章<浏览器中的 正则表达式陷阱>.

试考虑如下代码:

var re = /^\w$/g;
re.test(‘a’); //返回true
re.test(‘b’); //还是true吗?

猜猜返回值都是什么呢? 如果你已经阅读了Franky大神的那篇文章, 或者自己动手试了下, 就会发现, 一次是true, 一次是false. 原因在于正则表达式中的g, 使得搜索过程后, 如果匹配成功, 则记录上一次的位置, 如果匹配不成功, 则会归零. 所以, 如果在上面的语句中再加一条re.test(‘s’), 那么返回的将又会是我们期望的true了.

不过一般情况下, 我们自然会希望得到同样的结果, 这个时候可以在其中添加一条语句, 人工将位置归零, 防止这个 “错误” 的发生:

var re = /^\w$/g;
re.test(‘a’); //返回true
re.lastIndex = 0; //归零搜索的位置
re.test(‘b’); //返回true

或者我们可以更简单地直接将g去掉:

var re = /^\w$/;
re.test(‘a’); //返回true
re.test(‘b’); //返回true

于是, 利用g模式的这个性质, 可以这样使用. 考虑下面的代码:

var re = /\w/g; //注意, 我将分别表示开头的^和$去掉了
re.test(‘ab’);
re.test(‘ab’);

猜猜现在会返回什么呢? 答案是两个true. 用之前说到的东西也很好解释, 因为第一次记录了一个lastIndex, 但是在这个lastIndex的情况下, 同样能匹配成功第二个. 也就是说, 第一次匹配的是字符串中的a字母, 第二次则是b字母. 我在这里刻意地使用了两个相同的字符串, 因为我想告诉大家, 这才是g模式下, 正确的用法. 下面我们继续讨论这种机制存在的意义, 我也直接切入要害. 考虑下面的代码:

var re = /\d+/g;
var str = ‘1## %$xx 34*&920 3’; //包含了数字的字符串

var arr = [];

while (re.test(str))
    arr.push(RegExp.lastMatch);
/*
    上面的代码我更愿意写成:
    var parts;
    while (parts = re.exec(str))
        arr.push(parts[0]);
    这样可以避免全局的RegExp对象造成的一些问题.
*/

alert(arr); //”1,34,920,3″

点到这里, 相信大家已经初步明白这种机制的用意了,它方便自定义的遍历 (当lastIndex已经达到字符串末尾时, 并不归零), 要知道, 在明白这点之前, 我一直用着replace来完成这一步. 现在, 大家可以用自己的循环来搞定了. 这种情况也提醒了我们, 要正确地使用g参数, 像前面那种正则中包含^或者$的加上g参数, 就是完全的画蛇添足, 这些是应当避免的.

当然, 以上也只是Vilic的个人认识, 欢迎大家指正!

Original link of this archive: http://vilic.info/blog/archives/531
本文的原始链接: http://vilic.info/blog/archives/531

Vlight 开发笔记 2010.8.19

Github https://github.com/vilic/vlight

昨天主要是添加了HTML代码高亮和CSS代码高亮, 并且自动识别HTML/CSS/JS. 同时也能高亮HTML中嵌套的CSS和JS. 有些判断并不是很严谨, 但是多数情况下是适用的. 下面分别是HTML/CSS/JS代码示例.

HTML代码:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <!-- HTML Code -->
    <title>Vlight Demo</title>
    <style type="text/css">
        /* CSS Code */
        body { margin: 0px; line-height: 16px; font-size: 12px; font-family: Microsoft Yahei, Arial; }
        #test_div { height: 40px; }
        .test { background-color: #FFFFFF; }
    </style>
    <script src="vejis.js" type="text/javascript"></script>
    <script src="vlight.js" type="text/javascript"></script>
    <script type="text/javascript">
        /* JavaScript Code */
        vejis.use(vejis, true); //use vejis namespace
        _event.add(window, 'resize', resize); //add an event

        function resize() {
            var width = document.body.offsetWidth;
            alert(width);
        }
    </script>
</head>
<body>
    <h1>Vlight Demo</h1>
    <div id="test_div">
        <a href="http://www.vilic.info/" title="VILIC's Blog">VILIC's Blog</a>
        <img alt="" src="http://www.vilic.info/xxx.jpg" />
        <div></div>
    </div>
</body>
</html>

独立的CSS代码:

/* CSS Code */
body { margin: 0px; line-height: 16px; font-size: 12px; font-family: Microsoft Yahei, Arial; }
#test_div { height: 40px; }
.test { background-color: #FFFFFF; }

独立的JavaScript代码:

/* JavaScript Code */
vejis.use(vejis, true); //use vejis namespace
_event.add(window, 'resize', resize); //add an event

function resize() {
    var width = document.body.offsetWidth;
    alert(width);
}

var multilineStr = "abc\
def\
ghi";

Original link of this archive: http://vilic.info/blog/archives/527
本文的原始链接: http://vilic.info/blog/archives/527

Vlight & Vejis 开发笔记 2010.8.18

Github https://github.com/vilic/vlight

同志们可能已经发现了, 现在有代码高亮了.

这个属于心血来潮, 突然想到写一个, 然后就写了一个, 不过后来兼容IE6还是费了点事. 最后在样式上也动用了JS. 不过顺道, 也进一步完善了Vejis (Vlight需要Vejis). 代码不多, 去掉注释的话只有80+行. 所以直接贴出来, 也顺道测试下.

/*
Vlight JS Code Highlight (Style from Visual Studio 2010)

Version 0.3
Vejis JavaScript Library 0.0.0.5 is needed.

By Vilic Vane
http://www.vilic.info/

©2010 Groinup Studio
All rights reserved.

Redistribution and use in source and binary forms,
with or without modification, are permitted provided
that the following conditions are met:
Redistributions of source code must retain the above
copyright notice, this list of conditions and the
following disclaimer.
Redistributions in binary form must reproduce the
above copyright notice, this list of conditions and
the following disclaimer in the documentation and/or
other materials provided with the distribution.
Neither the name of the Groinup Studio nor the names
of its contributors may be used to endorse or promote
products derived from this software without specific
prior written permission.
*/

vejis.ready(function () {
    var className = 'vlight', //自定义类名
        maxLineCount = 20, //最多同时显示的行数
        lineHeight = 16, //行高
        scrollBarWidth = 24, //预计滚动条宽度
        cssText = //CSS内容
        'div.vlight { position: relative; margin: 5px 0px; border: solid 1px #FFF3D0; line-height: ' + lineHeight + 'px; color: #000000; font-size: 12px; font-family: Courier New, monospace; white-space: nowrap; overflow: hidden; }' +
        'div.vlight div.vlight_top { height: 5px; background-color: #FFE8A6; font-size: 0px; }' +
        'div.vlight div.vlight_left { position: absolute; width: 65px; left: 0px; text-align: right; color: #2B91AF; overflow: hidden; }' +
        'div.vlight div.vlight_left div { position: relative; width: 40px; left: 0px; padding-right: 5px; border-left: solid 16px #F0F0F0; border-right: solid 4px #6CE26C; }' +
        'div.vlight div.vlight_main { position: relative; margin-left: 65px; padding-left: 5px; overflow-x: scroll; overflow-y: auto; }' +
        'div.vlight span.vlight_comm { color: #008000; }' +
        'div.vlight span.vlight_re { color: #000000; }' +
        'div.vlight span.vlight_str { color: #800000; }' +
        'div.vlight span.vlight_key { color: #0000FF; }';

    cssText = cssText.replace(/vlight/g, className); //替换类名
    vejis.html.createStyleSheet(cssText); //创建样式

    var eles = vejis.html.getElementsByClassName(className); //获取元素
    var spanl = '<span>',
        spanr = '</span>';

    //处理每一个类名符合的元素
    vejis.foreach(eles, function (ele) {
        var div = document.createElement('div');
        div.className = className;
        div.innerHTML =
        '<div></div>' +
        '<div></div>';

        var top = div.childNodes[0],
            left = div.childNodes[1];

        var main = document.createElement('div');
        main.className = className + '_main';

        var oText;
        if (ele.tagName == 'TEXTAREA') oText = ele.value; //如果是textarea则直接取value
        else if (ele.tagName == 'PRE') oText = ele.innerText || ele.innerHTML;
        else oText = ele.innerHTML.replace(/\r?\n/g, '').replace(/<p( [^>]*)?>([\s\S]*?)<\/p>/gi, '$2\r\n\r\n').replace(/<div( [^>]*)?>([\s\S]*?)<\/div>/gi, '$2\r\n').replace(/<([a-z]+)( [^>]*)?>([\s\S]*?)<\/\1>/gi, '$3').replace(/<br[^>]*>/gi, '\r\n').replace(/&nbsp;/g, ' ').replace(/&lt;/g, '<').replace(/&gt;/g, '>').replace(/&amp;/g, '&');

        var result = convert(oText); //转换文本到高亮的HTML
        main.innerHTML = result.html;
        div.appendChild(main);

        //创建行号
        var lines = ''
        for (var i = 1; i <= result.count; i++)
            lines += i + '<br />';
        left.innerHTML = '<div>' + lines + '</div>';

        //将原来的元素替换成代码高亮区域
        ele.parentNode.replaceChild(div, ele);

        //设置高宽
        left.style.height = main.style.height = lineHeight * (result.count > maxLineCount ? maxLineCount : result.count) + scrollBarWidth + 'px';
        left.childNodes[0].style.height = result.count * lineHeight + scrollBarWidth + 'px';

        //绑定事件
        vejis._event.add(window, 'resize', resize);
        vejis._event.add(main, 'scroll', scroll);

        resize(); //初始化

        function resize() {
            try {
                main.style.width = top.offsetWidth - left.offsetWidth - 5 + 'px';
            } catch (e) { }
        }

        function scroll() {
            left.childNodes[0].style.marginTop = -main.scrollTop + 'px';
        }
    });

    function convert(text) {
        var names = ['comm', 're', 'str', 'key']; //类名的后缀

        //全局正则表达式
        var globalRE = /((\/\*[\s\S]*?\*\/|\/\/.*)|('('|.*?([^\\]'|\\\\'))|"("|.*?([^\\]"|\\\\")))|\/(\/|.*?([^\\]\/|\\\\\/))[gim]{0,3}|([^\w]|^)(break|delete|function|return|typeof|case|do|if|switch|var|catch|else|in|this|void|continue|false|instanceof|throw|while|debugger|finally|new|true|with|default|for|null|try)(?=[^\w]|$))/g;
       
        //拆分开的正则表达式
        var res = [
            /^(\/\*[\s\S]*?\*\/|\/\/.*)$/,
            /^\/(\/|.*?([^\\]\/|\\\\\/))[gim]{0,3}$/,
            /^'('|.*?([^\\]'|\\\\'))|"("|.*?([^\\]"|\\\\"))$/,
            /(break|delete|function|return|typeof|case|do|if|switch|var|catch|else|in|this|void|continue|false|instanceof|throw|while|debugger|finally|new|true|with|default|for|null|try)$/
        ];

        text = text.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;'); //符号处理

        //匹配
        text = text.replace(globalRE, function (s) {
            for (var i = 0; i < res.length; i++) {
                if (!res[i].test(s)) continue;
                var spanl2m = spanl + names[i] + spanm;

                s = s.replace(res[i], function (s) {
                    return spanl2m + s + spanr; //加标签
                });
                return s;
            }
        });

        var count = 1; //行数

        //字符处理
        text = text.replace(/\t/g, '    ').replace(/  /g, '&nbsp; ').replace(/  /g, ' &nbsp;').replace(/(\r?\n)+$/g, '').replace(/\r?\n/g, function () { count++; return '<br />'; });

        return { html: text, count: count };
    }
});

Vejis主要改进是在事件处理上(没有完全测试过, 所以可能还有大量bug), 琐碎的就不说了, 上代码:

var _event = this._event = new function () {
    var objects = [];
    var holders = [];

    this.add = _(Object, String, Function, function (obj, name, callback) {
        name = name.toLowerCase();

        var index = array.indexOf(objects, obj),
            subHolder;

        if (index < 0) {
            index = objects.length;
            objects.push(obj);
            var holder = {};
            holders.push(holder);
            createListener(holder);
        }
        else {
            var holder = holders[index];
            subHolder = holder[name];
            if (subHolder) {
                if (array.exists(subHolder, callback)) return false;
                subHolder.push(callback);
            }
            else createListener(holder);
        }

        return true;

        function createListener(holder) {
            var subHolder = holder[name] = [callback];
            subHolder.handler = handler;
            if (obj.addEventListener) obj.addEventListener(name, handler, false);
            else if (obj.attachEvent) obj.attachEvent('on' + name, handler);
        }

        function handler(ev) {
            var e = window.event || ev;
            onEvent(e, obj, name);
        }
    });

    this.remove = _(Object, String, Function, function (obj, name, callback) {
        name = name.toLowerCase();
        var index = array.indexOf(objects, obj);
        if (index < 0) return false;
        else {
            var holder = holders[index],
                subHolder;
            if (holder && (subHolder = holder[name])) {
                var idx = array.indexOf(subHolder, callback);
                if (idx < 0) return false;
                else {
                    array.removeByIndex(subHolder, idx);
                    if (!subHolder.length) {
                        var handler = subHolder.handler;
                        if (obj.removeEventListener) obj.removeEventListener(name, handler);
                        else if (obj.detachEvent) obj.detachEvent('on' + name, handler);
                        delete holder[name];
                        if (object.isEmpty(holder)) {
                            array.remove(holders, index);
                            array.remove(objects, index);
                        }
                    }
                    return true;
                }
            }
            return false;
        }
    });

    function onEvent(e, obj, name) {
        var index = array.indexOf(objects, obj);
        var callbacks = holders[index][name];

        foreach(callbacks, function (callback) {
            callback(e);
        });
    }
} ();

Original link of this archive: http://vilic.info/blog/archives/519
本文的原始链接: http://vilic.info/blog/archives/519

Vejis 开发笔记 2010.8.17

Version: 0.0.0.4

昨天做的东西比较多, 有大致有cookie的操作, 简单的get和post, json.

cookie的操作目前有1个集合, 5种方法共8次重载. (vejis的重载是我的大爱啊!) 简单操作的例子.

vejis.use(vejis, true); //使用vejis命名空间.

cookies.set(‘name’, ‘Vilic’); //添加名称为name的cookie, 值为’Vilic’.
cookies.set([‘age’, ‘sex’], [’17’, ‘male’]); //批量添加.

alert(cookies[‘name’]);

cookies.del(‘name’); //删除名称为name的cookie.

alert(cookies[‘name’]);

然后是xmlhttp, 做得比较简单, 够我用就好了:

vejis.use(vejis, true);

var data = new xmlhttp.Data();
data.title = ‘This is a test!’;
data.content = ‘Hello, I\’m Vilic!’;

var callback = _(Boolean, String, Number, function (done, text, status) {
    alert(‘Done:\n’ + done + ‘\nText:\n’ + text + ‘\nStatus:\n’ + status);
});

var xhr = xmlhttp.post(‘sample.ashx’, data, callback);

最后是json, 这个我只做了post带callback的, 因为一般不会用get来传递json.

vejis.use(vejis, true);

var callback = _(Boolean, Object, Number, function (done, value, status) {
    alert(JSON.stringify(value));
});

var obj = { name: ‘Vilic’, age: 18, hobbies: [‘Physics’, ‘JavaScript’, ‘Drawing’] };

json.post(‘sample.ashx’, ‘json’, obj, callback);

现在文件已经有500多行了, 虽然与一些专业的框架还相距甚远. 呵呵, 比不得. 顺便昨天七夕, 我跟代码从早到晚都在一起…

Original link of this archive: http://vilic.info/blog/archives/509
本文的原始链接: http://vilic.info/blog/archives/509