整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:

程序员大神整理的好用工具

程序员大神整理的好用工具

术站点

  • Hacker News:非常棒的针对编程的链接聚合网站

  • Programming reddit:同上

  • MSDN:微软相关的官方技术集中地,主要是文档类

  • infoq:企业级应用,关注软件开发领域

  • OSChina:开源技术社区,开源方面做的不错哦

  • cnblogs,51cto,csdn:常见的技术社区,各有专长

  • stackoverflow:IT技术问答网站

  • GitHub:全球最大的源代码管理平台,很多知名开源项目都在上面,如Linux内核,

  • OpenStack等免费的it电子书:http://it-ebooks.info/

  • DevStore:开发者服务商店

不错的书籍

  • 人件

  • 人月神话

  • 代码大全2

  • 计算机程序设计艺术

  • 程序员的自我修养

  • 程序员修炼之道

  • 高效能程序员的修炼(成为一名杰出的程序员其实跟写代码没有太大关系)

  • 深入理解计算机系统

  • 软件随想录

  • 算法导论(麻省理工学院出版社)

  • 离线数学及其应用

  • 设计模式

  • 编程之美

  • 黑客与画家

  • 编程珠玑

  • C++ Prime

  • Effective C++

  • TCP/IP详解

  • Unix 编程艺术

  • 《精神分析引论》弗洛伊德

  • 搞定:无压力工作的艺术

平台工具(都是开源的好东东哦)

  • Redmine/Trac:项目管理平台

  • Jenkins/Jira(非开源):持续集成系统(Apache Continuum,这个是Apache下的CI系统,还没来得及研究)

  • Sonar:代码质量管理平台

  • git,svn:源代码版本控制系统

  • GitLib/Gitorious:构建自己的GitHub服务器

  • gitbook:https://www.gitbook.io/写书的好东西,当然用来写文档也很不错的

  • Travis-ci:开源项目持续集成必备,和GitHub相结合,https://travis-ci.org/

  • 开源测试工具、社区(Selenium、OpenQA.org)

  • Puppet:一个自动管理引擎,可以适用于Linux、Unix以及Windows平台。所谓配置管理系统,就是管理机器里面诸如文件、用户、进程、软件包这些资源。无论是管理1台,还是上万台机器Puppet都能轻松搞定。

  • Nagios:系统状态监控报警,还有个Icinga(完全兼容nagios所有的插件,工作原理,配置文件以及方法,几乎一模一样。配置简单,功能强大)

  • Ganglia:分布式监控系统

  • fleet:分布式init系统

爬虫相关(好玩的工具)

  • Phantomjs

  • berserkJS(基于Phantomjs的改进版本)

  • SlimerJS

  • CasperJS

  • selenium

Web 服务器性能/压力测试工具/负载均衡器

  • http_load: 程序非常小,解压后也不到100K

  • webbench: 是Linux下的一个网站压力测试工具,最多可以模拟3万个并发连接去测试网站的负载能力

  • ab: ab是apache自带的一款功能强大的测试工具

  • Siege: 一款开源的压力测试工具,可以根据配置对一个WEB站点进行多用户的并发访问,记录每个用户所有请求过程的相应时间,并在一定数量的并发访问下重复进行。

  • squid(前端缓存),nginx(负载),nodejs(没错它也可以,自己写点代码就能实现高性能的负载均衡器):常用的负载均衡器

  • Piwik:开源网站访问量统计系统

  • ClickHeat:开源的网站点击情况热力图

  • HAProxy:高性能TCP /HTTP负载均衡器

  • ElasticSearch:搜索引擎基于Lucene

  • Page Speed SDK和YSLOW

  • HAR Viewer: HAR分析工具

  • protractor:E2E(end to end)自动化测试工具

Web 前端相关

  • GRUNT: js task runner

  • Sea.js: js模块化

  • knockout.js:MVVM开发前台,绑定技术

  • Angular.js: 使用超动感HTML & JS开发WEB应用!

  • Highcharts.js,Flot:常用的Web图表插件

  • Raw:非常不错的一款高级数据可视化工具

  • Rickshaw:时序图标库,可用于构建实时图表

  • JavaScript InfoVis Toolkit:另一款Web数据可视化插件

  • Pdf.js,在html中展现pdf

  • ACE,CodeMirror:Html代码编辑器(ACE甚好啊)

  • NProcess:绚丽的加载进度条

  • impress.js:让你制作出令人眩目的内容展示效果(类似的还有reveal)

  • Threejs:3DWeb库

  • Hightopo:基于Html5的2D、3D可视化UI库

  • jQuery.dataTables.js:高度灵活的表格插件

  • Rapha?l:js,canvas绘图库,后来发现百度指数的图形就是用它绘出来的

  • director.js:js路由模块,前端路由,Nodejs后端路由等,适合构造单页应用

  • pace.js:页面加载进度条

  • bower:Web包管理器

  • jsnice:有趣的js反编译工具,猜压缩后的变量名 http://www.jsnice.org/

  • D3.js: 是一个基于JavaScript数据展示库(类似的还有P5.js)

  • Zepto.js:移动端替代jQuery的东东,当然也可以使用jquery-mobile.

UI框架:Foundation,Boostrap,Pure,EasyUI,Polymer

前端UI设计师必去的几个网站:Dribbble,awwwards,unmatchedstyle,UIMaker

Mozilla 开发者中心:https://developer.mozilla.org/en-US/

图标资源:IcoMoon(我的最爱),Themify Icons,FreePik,Glyphiconsart

  • Dialog:非常漂亮的对话框

  • AdminLTE:github上的一个开源项目,基于Boostrap3的后台管理页面框架

  • Respond.js:让不懂爱的IE6-8支持响应式设计

  • require.js: js模块加载库

  • select2:比chosen具有更多特性的选择框替代库

  • AngularUI:集成angular.js的UI库

  • normalize.css: 采用了现代化标准让各浏览器渲染出的html保持一致的库

  • CreateJS:Html5游戏引擎Less,Compass:简化CSS开发

  • emojify.js:用于自动识别网页上的Emoji文字并将其显示为图像

  • simditor:一个不错的开源的html编辑器,简洁高效

  • Sencha: 基于html5的移动端开发框架

  • SuperScrollorama+TweenMax+skrollr:打造超酷的视差滚动效果网页动画

  • jquery-smooth-scroll:同上,平滑滚动插件

  • Animate.css:实现了各种动画效果的css库

  • Emmet:前端工程师必备,ZenCode的前身

  • MagicDraw:Uml图工具

大数据处理/数据分析/分布式工具

  • Hadoop:分布式的文件系统,结合其MapReduce编程模型可以用来做海量数据的批处理(Hive,Pig,HBase啥的就不说了),值得介绍的是Cloudera的Hadoop分支CDH5,基于YARN MRv2集成了Spark可直接用于生产环境的Hadoop,对于企业快速构建数据仓库非常有用。

  • Ceph:Linux分布式文件系统(特点:无中心)

  • Storm:实时流数据处理,可以看下IBM的一篇介绍 (还有个Yahoo的S4,也是做流数据处理的)

  • Spark:大规模流式数据处理(可以应付企业中常见的三种数据处理场景:复杂的批量数据处理(batch data processing);基于历史数据的交互式查询(interactive query);基于实时数据流的数据处理(streaming data processing)),CSND有篇文章介绍的不错

  • Spark Streaming:基于Spark的实时计算框架

  • Tachyon:分布式内存文件系统

  • Mesos:计算框架一个集群管理器,提供了有效的、跨分布式应用或框架的资源隔离和共享Impala:新一代开源大数据分析引擎,提供Sql语义,比- Hive强在速度上

  • SNAPPY:快速的数据压缩系统,适用于Hadoop生态系统中

  • Kafka:高吞吐量的分布式消息队列系统

  • ActiveMQ:是Apache出品,最流行的,能力强劲的开源消息总线

  • MQTT:Message Queuing Telemetry Transport,消息队列遥测传输)是IBM开发的一个即时通讯协议,有可能成为物联网的重要组成部分

  • RabbitMQ:记得OpenStack就是用的这个东西吧

  • ZeroMQ:宣称是将分布式计算变得更简单,是个分布式消息队列,可以看下云风的一篇文章的介绍开源的日志收集系统:scribe、chukwa、kafka、flume。这有一篇对比文章

  • Zookeeper:可靠的分布式协调的开源项目

  • Databus:LinkedIn 实时低延迟数据抓取系统

数据源获取:Flume、Google Refine、Needlebase、ScraperWiki、BloomReach

序列化技术:JSON、BSON、Thrift、Avro、Google Protocol Buffers

NoSql:Apache Hadoop、Apache Casandra、MongoDB、Apache CouchDB、Redis、BigTable、HBase、Hypertable、Voldemort、Neo4j

MapReduce相关:Hive、Pig、Cascading、Cascalog、mrjob、Caffeine、S4、MapR、Acunu、Flume、Kafka、Azkaban、Oozie、Greenplum

数据处理:R、Yahoo! Pipes、Mechanical Turk、Solr/ Lucene、ElasticSearch、Datameer、Bigsheets、TinkerpopNLP自然语言处理:Natural Language Toolkit、Apache OpenNLP、Boilerpipe、OpenCalais

机器学习:WEKA、Mahout、scikits.learn、SkyTree

可视化技术:GraphViz、Processing、Protovis、Google Fusion Tables、Tableau、Highcharts、EChats(百度的还不错)、Rapha?l.js

  • Kettle:开源的ETL工具

  • Pentaho:以工作流为核心的开源BI系统

  • Mondrian:开源的Rolap服务器

  • Oozie:开源hadoop的工作流调度引擎

开源的数据分析可视化工具:Weka、Orange、KNIME

Cobar:阿里巴巴的MySql分布式中间件

C & C++

Thrift:用来进行可扩展且跨语言的服务的开发(类似的还有个Avro,Google protobuf)。

libevent:是一个事件触发的网络库,适用于windows、linux、bsd等多种平台,内部使用select、epoll、kqueue等系统调用管理事件机制。(对了还有个libev呢)

Boost:不多说了,准C++标准库

Ptmalloc\Valgrind\Purify

NetworkServer架构:acceptor->dispatcher->worker(这个不算工具哦)

breakpad:崩溃转储和分析模块,很多crashreport会用到

UI界面相关:MFC、BCG和QT这类的就不说了,高端一点的还有Html和DirectUI技术:libcef(基于chrome内核的,想想使用html5开发页面,还真有点小激动呢)、HtmlLayout、Duilib、Bolt,非C++的,还有node-webkit也不错,集成了node和webkit内核。

游戏开发相关

MINA:使用Java开发手游和页游服务器(对了还有Netty,也很猛的,都是基于NIO的)

HP-Socket:见有有些页游服务器使用这个构建的

云风的技术博客:http://blog.codingnow.com/

OGRE:大名鼎鼎的3D图形渲染引擎

OpenVDB:梦工厂C++的特效库,开源的

cocos2d:跨平台2D游戏引擎

unity3d:跨平台3D游戏引擎,很火的哦

Nodejs:也有不少使用它来开发手游和也有服务器(网易的Pomelo就是哦)

日志聚合,分布式日志收集

Scribe:Facebook的(nodejs + scribe + inotify 同步日志)

logstash:强大的日志收集系统,可以基于logstash+kibana+elasticsearch+redis开发强大的日志分析平台

log.io: nodejs开发的实时日志收集系统

RTP,实时传输协议与音视频

RTP,RTCP,RTSP-> librtp,JRTPLIB(遵循了RFC1889标准)

环形缓冲区,实时数据传输用

SDL,ffmpeg,live555,Speex

Red5:用Java开发开源的Flash流媒体服务器。它支持:把音频(MP3)和视频(FLV)转换成播放流; 录制客户端播放流(只支持FLV);共享对象;现场直播流发布;远程调用。

Python

Eric,Eclipse+pydev,比较不错的Python IDE

PyWin:Win32 api编程包

numpy:科学计算包,主要用来处理大型矩阵计算等,此外还有SciPy,Matplotlib

GUI相关:PyQt,PyQwt

supervisor:进程监控工具

Java相关

常用的IDE:IntelliJ IDEA,Eclipse,Netbeans

Web开发相关:Tomcat、Resin、Jetty、WebLogic等,常用的组件Struts,Spring

HibernateNetty: 异步事件驱动网络应用编程框架,用于高并发网络编程比较好(NIO框架)

MINA:简单地开发高性能和高可靠性的网络应用程序(也是个NIO框架),不少手游服务端是用它开发的

jOOQ:java Orm框架Activiti:工作流引擎,类似的还有jBPM、Snaker

Perfuse:是一个用户界面包用来把有结构与无结构数据以具有交互性的可视化图形展示出来.

Gephi:复杂网络分析软件, 其主要用于各种网络和复杂系统,动态和分层图的交互可视化与探测开源工具

Nutch:知名的爬虫项目,hadoop就是从这个项目中发展出来的

web-harvest:Web数据提取工具

POM工具:Maven+ArtifactoryNetflix

Curator:Netflix公司开源的一个Zookeeper client library,用于简化Zookeeper客户端编程

Akka:一款基于actor模型实现的 并发处理框架

EclEmma:覆盖测试工具

.net相关

Xilium.CefGlue:基于CEF框架的.NET封装,基于.NET开发Chrome内核浏览器

CefSharp:同上,有一款WebKit的封装,C#和Js交互会更简单

netz:免费的 .NET 可执行文件压缩工具

SmartAssembly:变态的.net代码优化混淆工具

NETDeob0:.net反混淆工具,真是魔高一尺道高一丈啊(还有个de4dot,在GitHub上,都是开源的)

ILMerge:将所有引用的DLL和exe文件打成一个exe文件

ILSpy:开源.net程序反编译工具

Javascript.NET:很不错的js执行引擎,对v8做了封装

NPOI: Excel操作

DotRAS:远程访问服务的模块

WinHtmlEditor: Winform下的html编辑器

SmartThreadPool:使用C#实现的,带高级特性的线程池

Snoop: WPF Spy Utility

Autofac: 轻量级IoC框架

HtmlAgilityPack:Html解析利器

Quartz.NET:Job调度

HttpLib:@CodePlex,简化http请求

SuperSocket:简化Socket操作,基于他的还有个SuperWebSocket,可以开发独立的WebSocket服务器了

DocX:未安装Office的情况下操作Word文件

Dapper:轻量级的ORM类,性能不错

HubbleDotNet:支持接入数据库的全文搜索系统

fastJSON:@CodeProject,高性能的json序列化类

ZXing.NET:@CodePlex,QR,条形码相关

Nancy:轻量级Http服务器,做个小型的Web应用可以摆脱IIS喽(Nancy.Viewengines.Razor,可以加入Razor引擎)

AntiXSS:微软的XSS防御库Microsoft Web Protection

LibraryJint:JavaScript解释器

CS-Script:将C#代码文件作为脚本执行

Jexus:Linux下 高性能、易用、免费的ASP.NET服务器

Clay:将dynamic发挥的更加灵活,像写js一样写C#

DynamicJSON:不必定义数据模型获取json数据

Antlr:开源的语法分析器(归到C#不太合适,其他语言也可以去用)

SharpPcap:C#版的WinPcap调用端,牛逼的网络包分析库(自带PacketNotNet用于包协议分析)

Roslyn:C#,VB编译器

ImageResizer: 服务端自由控制图片大小,真乃神器也,对手机端传小图,PC端传大图,CMS用它很方便

UI相关:DevExpress, Fluent(Office 07风格), mui(Modern UI for WPF)

NetSparkle:应用自动更新组件

ConfuserEx: 开源.net混淆工具

ServiceStack: 开源高性能Web服务框架,可用于构建高性能的REST服务Expression

Evaluator:Eval for C#,处理字符串表达式

http://nugetmusthaves.com/

常用工具

  • Fiddler:非常好用的Web前端调试工具,当然是针对底层http协议的,一般情况使用Chrome等自带的调试工具也足够了,特殊情况还得用它去处理

  • wireshark:知名的网络数据包分析工具

  • PowerCmd:替代Windows Cmd的利器

  • RegexBuddy:强大的正则表达式测试工具

  • Soure Insight:源代码阅读神器

  • SublimeText:程序员最爱的编辑器

  • Database.NET:一个通用的关系型数据库客户端,基于.NET 4.0开发的,做简单的处理还是蛮方便的

  • Navicat Premium:支持MySql、PostgreSQL、Oracle、Sqlite和SQL Server的客户端,通用性上不如Database.NET,但性能方面比Database.NET好很多,自带备份功能也用于数据库定时备份。

  • Synergy : 局域网内一套键盘鼠标控制多台电脑

  • DameWare:远程协助工具集(我在公司主要控制大屏幕用)

  • Radmin: 远程控制工具,用了一段时间的

  • DameWare,还要破解,对Win7支持的不好,还是发现这个好用

  • Listary:能极大幅度提高你 Windows 文件浏览与搜索速度效率的「超级神器」

  • Clover:给资源管理器加上多标签

  • WinLaunch:模拟Mac OS的Launch工具

  • Fritzing:绘制电路图

  • LICEcap:gif教程制作git,

  • svn:版本控制系统Enigma Virtual Box(将exe,dll等封装成一个可执行程序)

  • Open DBDiff(针对SqlServer)数据库同步

  • SymmetricDS:数据库同步

  • BIEE,Infomatica,SPSS,weka,R语言:数据分析

  • CodeSmith,LightSwitch:代码生成

  • Pandoc:Markdown转换工具,出书用的。以前玩过docbook,不过现在还是Markdown盛行啊。

  • Window Magnet[Mac]:增强Mac窗口管理功能,想Win7一样具有窗口拖放到屏幕边缘自动调整的功能

  • log explorer:查看SqlServer日志dependency

  • walker:查询Windows应用程序dll依赖项

  • Shairport4w:将iPhone,iPad,iPod上的音频通过AirPlay协议传输到PC上

  • ngrok:内网穿透工具Axure:快速原型制作工具,还有个在线作图的工具国内的一个创业团队做的,用着很不错 http://www.processon.com

  • tinyproxy:(Linux)小型的代理服务器支持http和https协议EaseUS Partition

  • Master:超级简单的分区调整工具,速度还是蛮快的,C盘不够用了就用它从D盘划点空间吧,不用重装系统这么折腾哦。

  • CheatEngine:玩游戏修改内存值必备神器(记得我在玩轩辕剑6的时候就用的它,超级方便呢)

  • ApkIDE:Android反编译神器翻、墙工具(自|由|门、天行浏览器)

最后推荐下我的Android学习群:110359956,不管你是小白还是大牛,小编我都挺欢迎,不定期分享干货,包括我自己整理的一份2017最新的Android学习资料和零基础入门教程,送给大家,欢迎初学和进阶中的小伙伴。还有最新opengl,opencv,VR,AR技术防止两年至三年之后的一批大筛选。

还有MVP最新教程实训班,欢迎大家加入

近刷脸支付很火,老板们当然要追赶时代潮流,于是就有了刷脸支付这个项目。前端实现关键的技术是摄像头录像拍照人脸比对,本文来探讨一下如何在html5环境中如何实现刷脸支付以及开发过程中遇到的问题。

1.摄像头

1.1 input获取摄像头

html5中获取手机上的图片,有两种方式,使用input,如下可以打开摄像头拍照:

<input type="file" capture="camera" accept="image/*"/>

另外如果想打开相册,可以这样:

<input type="file" accept="img/*">

但是这两种方式都会有兼容性问题,用过的同学可能都知道。

1.2 getUserMedia获取摄像头

getUserMedia是html5一个新的api,官方一点的定义是:

MediaDevices.getUserMedia() 会提示用户给予使用媒体输入的许可,媒体输入会产生一个MediaStream,里面包含了请求的媒体类型的轨道。此流可以包含一个视频轨道(来自硬件或者虚拟视频源,比如相机、视频采集设备和屏幕共享服务等等)、一个音频轨道(同样来自硬件或虚拟音频源,比如麦克风、A/D转换器等等),也可能是其它轨道类型。

简单一点说就是可以获取到用户摄像头。

同上面input一样,这种方式也有兼容性问题,不过可以使用其他方式解决,这里可以参考MediaDevices.getUserMedia(),文档中有介绍"在旧的浏览器中使用新的API"。我这里在网上也找了一些参考,总结出一个相对全面的getUserMedia版本,代码如下:

// 访问用户媒体设备
getUserMedia(constrains, success, error) {
    if (navigator.mediaDevices.getUserMedia) {
        //最新标准API
        navigator.mediaDevices.getUserMedia(constrains).then(success).catch(error);
    } else if (navigator.webkitGetUserMedia) {
        //webkit内核浏览器
        navigator.webkitGetUserMedia(constrains).then(success).catch(error);
    } else if (navigator.mozGetUserMedia) {
        //Firefox浏览器
        navagator.mozGetUserMedia(constrains).then(success).catch(error);
    } else if (navigator.getUserMedia) {
        //旧版API
        navigator.getUserMedia(constrains).then(success).catch(error);
    } else {
        this.scanTip="你的浏览器不支持访问用户媒体设备"
    }
}

1.3 播放视屏

获取设备方法有两个回调函数,一个是成功,一个是失败。成功了就开始播放视频,播放视屏其实就是给video设置一个url,并调用play方法,这里设置url要考虑不同浏览器兼容性,代码如下:

success(stream) {
    this.streamIns=stream
    // 设置播放地址,webkit内核浏览器
    this.URL=window.URL || window.webkitURL
    if ("srcObject" in this.$refs.refVideo) {
        this.$refs.refVideo.srcObject=stream
    } else {
        this.$refs.refVideo.src=this.URL.createObjectURL(stream)
    }
    this.$refs.refVideo.onloadedmetadata=e=> {
        // 播放视频
        this.$refs.refVideo.play()
        this.initTracker()
    }
},
error(e) {
    this.scanTip="访问用户媒体失败" + e.name + "," + e.message
}

注意:

  1. 播放视屏方法最好写在onloadmetadata回调函数中,否则可能会报错。
  2. 播放视频的时候出于安全性考虑,必须在本地环境中测试,也就是http://localhost/xxxx中测试,或者带有https://xxxxx环境中测试,不然的话或有跨域问题。
  3. 下面用到的initTracker()方法也好放在这个onloadedmetadata回调函数里,不然也会报错。

2. 捕捉人脸

2.1 使用tracking.js捕捉人脸

视屏在video中播放成功之后就开始识别人脸了,这里使用到一个第三方的功能tracking.js,是国外的大神写的JavaScript图像识别插件。关键代码如下:

// 人脸捕捉
initTracker() {
    this.context=this.$refs.refCanvas.getContext("2d")    // 画布
    this.tracker=new tracking.ObjectTracker(['face'])     // tracker实例
    this.tracker.setStepSize(1.7)                           // 设置步长
    this.tracker.on('track', this.handleTracked)            // 绑定监听方法
    try {
        tracking.track('#video', this.tracker)      // 开始追踪
    } catch (e) {
        this.scanTip="访问用户媒体失败,请重试"
    }
}

捕获到人脸之后,可以在页面上用一个小方框标注出来,这样有点交互效果。

// 追踪事件
handleTracked(e) {
    if (e.data.length===0) {
        this.scanTip='未检测到人脸'
    } else {
        if (!this.tipFlag) {
            this.scanTip='检测成功,正在拍照,请保持不动2秒'
        }
        // 1秒后拍照,仅拍一次
        if (!this.flag) {
            this.scanTip='拍照中...'
            this.flag=true
            this.removePhotoID=setTimeout(()=> {
                this.tackPhoto()
                this.tipFlag=true
            }, 2000)
        }
        e.data.forEach(this.plot)
    }
}

在页面中画一些方框,标识出人脸:

<div class="rect" v-for="item in profile"
             :style="{ width: item.width + 'px', height: item.height + 'px', left: item.left + 'px', top: item.top + 'px'}"></div>
// 绘制跟踪框
plot({x, y, width: w, height: h}) {
    // 创建框对象
    this.profile.push({ width: w, height: h, left: x, top: y })
}

2.2 拍照

拍照,就是使用video作为图片源,在canvas中保存一张图片下来,注意这里使用toDataURL方法的时候可以设置第二个参数quality,从0到1,0表示图片比较粗糙,但是文件比较小,1表示品质最好。

// 拍照
tackPhoto() {
    this.context.drawImage(this.$refs.refVideo, 0, 0, this.screenSize.width, this.screenSize.height)
    // 保存为base64格式
    this.imgUrl=this.saveAsPNG(this.$refs.refCanvas)
    // this.compare(imgUrl)
    this.close()
},
// Base64转文件
getBlobBydataURI(dataURI, type) {
    var binary=window.atob(dataURI.split(',')[1]);
    var array=[];
    for(var i=0; i < binary.length; i++) {
        array.push(binary.charCodeAt(i));
    }
    return new Blob([new Uint8Array(array)], {
        type: type
    });
},
// 保存为png,base64格式图片
saveAsPNG(c) {
    return c.toDataURL('image/png', 0.3)
}

拍照完成之后就可以把文件发送给后端,让后端进行对比验证,这里后端使用的是阿里云的接口。

3. 最后效果

3.1 参考代码demo

最后,demo我已经放在github上了,感兴趣可以打开看一下。

效果如下:

3.2 在项目中落地

最后放在项目中,无非就是最后一个步骤,去调用接口比对,根据比对结果成功是成功还是失败,决定是人脸支付还是继续使用原来的密码支付,效果如下:

ps:这里人脸比对失败了,是因为我带着口罩,就不呲牙露脸了。

作者:Tyler Ning 出处:http://www.cnblogs.com/tylerdonet/ 本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,如有问题,可以通过以下邮箱地址344805262@qq.com 联系我,非常感谢。

TML5为了更好地处理今天的互联网应用,添加了很多新元素及功能,比如: 图形的绘制,多媒体内容,更好的页面结构,更好的形式处理,和几个api拖放元素,定位,包括网页应用程序缓存,存储,网络工作者等。

HTML5的<canvas>标签可以定义图形,比如图表和其他图像。该标签是基于 JavaScript 的绘图 API。

如想完成这样一个任务,画一个包含时间轴的世界历史年表,如下图所示:

要完成上述任务,便可以使用HTML5+CSS+JS,代码如下:

<!DOCTYPE html>

<html><title>historyTidePrev</title>

<style type="text/css">

.left{/*total 974,竖线起始位置:436px*/

width:350px;

float:left;

padding-left:56px;

padding-right:30px;

}

.right{/*竖线起始位置:436px*/

width:500px;

float:left;

padding-left:38px;

}

p{

line-height:16px;

margin:0;

padding:0;

text-indent:-2em;

}

</style>

<script>

function scrol...(){

var scl=document.body.scrollHeight/2+30*14;

window.scrollBy(0,scl);

}

</script>

<canvas id="myCanvas2" width="974" height="29418" style="border:0px solid #d3d3d3;">

Your browser does not support the HTML5 canvas tag.

</canvas>

<script>

var c=document.getElementById("myCanvas2");

var ctx=c.getContext("2d");

var canvasW=974;

var dingJiange=18; //顶端间隔 竖线起始位置(Y轴)

var diJiange=0; //底部间隔 竖线起始位置(Y轴)

var jianGe=dingJiange+diJiange;

var Xcor=436; //竖线X坐标的起始位置;

//因最小的字体需要12它,所以下面的定位需要达到12;

var nianPX=14; //一年间隔使用的像素;

var nianYprev=2100; //公元前有多少年开始

var nianYnex=0;//公元前后多少年结束

var nianYprevPx=nianYprev*nianPX; //公元前有多少年及像素;

var nianYnexPx=nianYnex*nianPX; //公元后有多少年及像素;

var Ycor=nianYprevPx+nianYnexPx; //竖线Y坐标的终点位置(长度);

var nianL=8; //年线段的长度;

var nianL10=20; //10年线段的长度;

var nianL100=30; //100年线段的长度;

var fontsi=nianPX*3;//字体大小

var fontsi10=nianPX*4;

var fontsi100=nianPX*5;

//长竖线

ctx.beginPath();

ctx.moveTo(Xcor,dingJiange);

ctx.lineTo(Xcor,Ycor+diJiange);

ctx.stroke();

//年横线

for(i=dingJiange;i<=Ycor+diJiange;i+=nianPX){

ctx.beginPath();

ctx.moveTo(Xcor,i);

ctx.lineTo(Xcor-nianL,i);

ctx.strokeStyle="rgba(0, 0, 0, 0.4)";

ctx.stroke();

}

//5年横线

for(i=dingJiange;i<=Ycor+jianGe;i+=nianPX*5){

ctx.beginPath();

ctx.moveTo(Xcor,i);

ctx.lineTo(Xcor-nianL*1.5,i);

ctx.strokeStyle="rgba(0, 0, 0, 0.6)";

ctx.stroke();

}

//10年横线和文本

for(i=dingJiange;i<=Ycor+jianGe;i+=nianPX*10){

ctx.beginPath();

ctx.moveTo(Xcor,i);

ctx.lineTo(Xcor-nianL*2,i);

ctx.strokeStyle="rgba(0, 0, 0, 0.8)";

ctx.stroke();

ctx.textAlign="right";

var varmid=(i-dingJiange)/nianPX;

if(varmid%100!=0){

ctx.font="12px 宋体"; //30px 可以写在里面

// Create gradient

var gradient=ctx.createLinearGradient(0,0,c.width,0);

gradient.addColorStop("0","magenta");

gradient.addColorStop("0.5","blue");

gradient.addColorStop("1.0","red");

// Fill with gradient

ctx.fillStyle=gradient;

ctx.fillText((i-dingJiange)/nianPX-nianYprev,Xcor-nianL*2,i+6);

}

}

//100年横线和文本

for(i=dingJiange;i<=Ycor+jianGe;i+=nianPX*100){

ctx.beginPath();

ctx.moveTo(Xcor,i);

ctx.lineTo(Xcor-nianL*3,i);

ctx.strokeStyle="rgba(0, 0, 0, 0.9)";

ctx.stroke();

ctx.textAlign="right";

ctx.font="18px 宋体"; //30px 可以写在里面

// Create gradient

var gradient=ctx.createLinearGradient(0,0,c.width,0);

gradient.addColorStop("0","magenta");

gradient.addColorStop("0.5","blue");

gradient.addColorStop("1.0","red");

// Fill with gradient

ctx.strokeStyle=gradient;

ctx.strokeText((i-dingJiange)/nianPX-nianYprev,Xcor-nianL*3,i+8);

}

function txtL(year0,txt){

var xc=Xcor-nianL-65; //左边的线条从右边开始到左边结束的位置;

var xc2=10;//左边文本从左边开始的位置;

var yp;

if(year0>=0){

yp=dingJiange+nianYprevPx+year0*nianPX;

txt="" + year0 + "年," + txt;

}else{

yp=dingJiange+nianYprevPx+year0*nianPX;

yearp=year0*(-1);

txt="前" + yearp + "年," + txt;

}

ctx.fillStyle="#00f";

ctx.beginPath();

ctx.moveTo(Xcor-60,yp);

ctx.lineTo(xc+xc2-25,yp);

ctx.stroke();

ctx.font="12px Verdana";

ctx.fillStyle="#000";

ctx.textAlign="left";

//xc的位置是xc=Xcor+nianL100=974-436-30=508,可以容纳46个12px的字符(44*12=535);

var txtN;//右边屏幕可容纳字符串个数;

var txtW=12*1;//手工算出是0.945;txtW是一个字符串的宽度;

txtN=Math.floor(xc/txtW);

if(txt.length>txtN){

var fortime=Math.ceil(txt.length/txtN);//需要循环的次数;

ctx.fillText(txt.substring(0,txtN),xc2,yp);

for(i=0;i<fortime;i++){

yp=yp+14;

txt=txt.substring(txtN);

var txt2=" "+txt.substring(0,txtN);

ctx.fillText(txt2,xc2,yp);

}

}else{

ctx.fillText(txt,xc2,yp);

}

}

function txtR(year0,txt){

var xc=Xcor+nianL100;

var yp;

if(year0>=0){

yp=dingJiange+nianYprevPx+year0*nianPX;

txt="" + year0 + "年," + txt;

}else{

yp=dingJiange+nianYprevPx+year0*nianPX;

yearp=year0*(-1);

txt="前" + yearp + "年," + txt;

}

ctx.fillStyle="#00f";

ctx.beginPath();

ctx.moveTo(Xcor+3,yp);

ctx.lineTo(xc,yp);

ctx.stroke();

ctx.font="12px Verdana";

ctx.fillStyle="#000";

ctx.textAlign="left";

//xc的位置是xc=Xcor+nianL100=974-436-30=508,可以容纳46个12px的字符(44*12=535);

var txtN;//右边屏幕可容纳字符串个数;

var txtW=12*1;//手工算出是0.945;txtW是一个字符串的宽度;

txtN=Math.floor((canvasW-xc)/txtW);

if(txt.length>txtN){

var fortime=Math.ceil(txt.length/txtN);//需要循环的次数;

ctx.fillText(txt.substring(0,txtN-4),xc,yp);

for(i=0;i<fortime;i++){

yp=yp+14;

txt=txt.substring(txtN-4);

var txt2=" "+txt.substring(0,txtN-4);

ctx.fillText(txt2,xc,yp);

}

}else{

ctx.fillText(txt,xc,yp);

}

}

txtR(-580,"毕达哥拉斯(约-580~-500年)古希腊数学家、哲学家创立毕达哥拉斯学派,提出毕达哥拉斯定理、数和谐说和灵魂轮回说。");

txtR(-563,"释迦牟尼约-563~前483年佛教创始人建立了完整的佛教教义学说。");

txtL(-551,"孔子-551.9.28--479.4.11,春秋时期鲁国人.");

txtR(-552,"孙武齐国乐安人,汉族.公元前527年,年仅25岁的孙武完成旷世圣书——《孙子兵法》。");

txtR(-427,"公元前427~前348/347)年古希腊哲学家柏拉图创立“学园派”,建立以“理念论”为核心的客观唯心主义哲学体系。");

txtR(-384,"前4世纪,希腊亚里士多德(公元前384年-公元前322年)对数学、动物学等进行综合研究。");

txtR(-0,"");

txtR(-0,"");

</script>

</body>

</html>