所有题目地址:http://codestar.alloyteam.com/q2
本题内容:http://www.cnblogs.com/yedeying/p/3617593.html
腐蚀的画涉及到的图片有4张:
http://codestar.alloyteam.com/q2/puzzle/4/1.png
http://codestar.alloyteam.com/q2/puzzle/4/2.png
http://codestar.alloyteam.com/q2/puzzle/4/3.png
http://codestar.alloyteam.com/q2/puzzle/4/4.png
Step1——拿到图像数据
很少接触canvas,不过对获取canvas画布内像素数据的方法有印象,查了下,轻松解决。
- 创建画布元素canvas;
- 获取2D渲染上下文,相关方法:getContext('2d');
- 将图片绘制到画布里,相关方法:drawImage(imgElem, 0, 0, imgWidth, imgHeight);
- 获取画布里的ImageData对象,相关方法:getImageData(0, 0, canvas.width, canvas.height);
- 取出全部像素信息,第4步中返回对象里的data属性,一个类数组的对象,每个像素由rgba四个值组成,一个像素占4个元素;
Step2——像计算机一样阅读
这一步是个坑,只提示转成0跟1,但转换方式没说,可能性有很多,如果不是有高人提示,很少会想到二值化。
- 遍历上面提到的data属性,每4个元素取前3个,即rgb;
- 对rgb值判断,小于等于127为0,大于127为1;
- 逐个拼接以上得到的0和1;
Step3——变成ASCII字符
一开始还在想怎么把二进制转ASCII,原本以为得写个对象,用查表方式来处理,后来高人提示可以先转十进制再转,fromCharCode接受十进制参数不接二进制,我咋就没想到转二进制呢,该打。
- “二进制”字符串遍历,每8个一组,转十进制,相关方法:parseInt(str, 2),用二进制方式解析字符串,返回十进制数值;
- 第1步8个字符(0和1)已经变成一个十进制,同时使用String.fromCharCode()方法解析成ASCII字符;
- 全部转换完毕,判断字符串“AlloyImage”位置,相关方法:indexOf(str);
- 截取0到“A”的位置间的字符串,相关方法slice,substring;
Step4——转成base64数据
这一步已经很明显,图片url的base64表示方式,这表明结果将会是一张图片。一开始纠结着ASCII怎么转Base64,尝试了base64加密,出来的结果无法显示成图片,失望时想到jq的base64插件,下载后看了下readme,发现window.btoa的判断,一查才知道,强大的JavaScript已经有base64 to ascii的方法了(目前仅chrome、safari、firefox支持,http://help.dottoro.com/ljvfsbvr.php),果断直接使用,成功显示出图片。
- 创建img元素,createElement();
- 设置src值为'data:image/png;base64,' + btoa(str);
- 将img元素添加到document中,appendChild();
- 问题答案成功显示,4张图片,4个答案。
后记:做完这道题,又学到了很多东西,同时也巩固了一些快生疏的知识。
临睡前再扯一句:愿所有前端,拥抱新技术,珍爱生命,远离IE6789。