js canvas实现写字动画效果


Posted in Javascript onNovember 30, 2018

本文实例为大家分享了js canvas实现写字动画效果展示的具体代码,供大家参考,具体内容如下

页面html:

<!DOCTYPE html>
<html>
<head lang="en">
 <meta charset="UTF-8">
 <title>学写一个字</title>
 <script src="jquery-2.1.3.min.js" type="text/javascript"></script>
 <link href="handwriting.css" rel="stylesheet" type="text/css"/>
 <meta name="viewport"
   content=" height = device-height,
     width = device-width,
     initial-scale = 1.0,
     minimum-scale = 1.0,
     maximum-scale = 1.0,
     user-scalable = no"/> //兼容移动端
 
</head>
<body>
 
 <canvas id="canvas">
  您的浏览器不支持canvas
 </canvas>//写字区域
 <div id="controller">
  <div id="black_btn" class="color_btn color_btn_selected"></div>
  <div id="blue_btn" class="color_btn"></div>
  <div id="green_btn" class="color_btn"></div>
  <div id="red_btn" class="color_btn"></div>
  <div id="orange_btn" class="color_btn"></div>
  <div id="yellow_btn" class="color_btn"></div>
 
  <div id="clear_btn" class="op_btn">清 除</div>
  <div class="clearfix"></div>
 </div>
 
 <script src = "handwriting.js"></script>
</body>
</html>

页面css:

#canvas{
 display:block;
 margin:0 auto;
}
#controller{
 margin:0 auto;
}
.op_btn{
 float: right;
 margin:10px 0 0 10px;
 border:2px solid #aaa;
 width:80px;
 height:40px;
 line-height:40px;
 font-size:20px;
 text-align:center;
 border-radius: 5px 5px;
 cursor:pointer;
 background-color: white;
 font-weight:bold;
 font-family: Microsoft Yahei, Arial;
}
.op_btn:hover{
 background-color:#def;
}
.clearfix{
 clear:both;
}
 
.color_btn{
 float: left;
 margin: 10px 10px 0 0;
 border:5px solid white;
 width:40px;
 height:40px;
 border-radius: 5px 5px;
 cursor:pointer;
}
.color_btn:hover{
 border: 5px solid violet;
}
.color_btn_selected{
 border: 5px solid blueviolet;
}
#black_btn{
 background-color: black;
}
#blue_btn{
 background-color: blue;
}
#green_btn{
 background-color: green;
}
#red_btn{
 background-color: red;
}
#orange_btn{
 background-color: orange;
}
#yellow_btn{
 background-color: yellow;
}

页面js:

var canvasWidth = Math.min( 800 , $(window).width() - 20 );//如果屏幕小于800px,则取值为屏幕大小宽度,便于移动端的展示,-20是为了使得米字格不紧贴于边缘
var canvasHeight = canvasWidth;
 
var strokeColor = "black";
var isMouseDown = false; //鼠标按下时候的状态
var lastLoc = {x:0,y:0}; //鼠标上一次结束时的位置
var lastTimestamp = 0; //上一次时间,与笔刷粗细有关
var lastLineWidth = -1; //笔刷粗细
 
var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
 
canvas.width = canvasWidth;
canvas.height = canvasHeight;
 
$("#controller").css("width",canvasWidth+"px");
drawGrid();//画米字格
 
$("#clear_btn").click(
 function(e){
  context.clearRect( 0 , 0 , canvasWidth, canvasHeight );
  drawGrid();
 }
)
$(".color_btn").click(
 function(e){
  $(".color_btn").removeClass("color_btn_selected");
  $(this).addClass("color_btn_selected");
  strokeColor = $(this).css("background-color");
 }
)
//适用于移动端触控
function beginStroke(point){
 
 isMouseDown = true
 //console.log("mouse down!");
 lastLoc = windowToCanvas(point.x, point.y); //上一次坐标位置
 lastTimestamp = new Date().getTime();
 
}
function endStroke(){
 isMouseDown = false;
}
function moveStroke(point){
 
 var curLoc = windowToCanvas( point.x , point.y );
 var curTimestamp = new Date().getTime();
 var s = calcDistance( curLoc , lastLoc );
 var t = curTimestamp - lastTimestamp;
 
 var lineWidth = calcLineWidth( t , s );
 
 //draw
 context.beginPath();
 context.moveTo( lastLoc.x , lastLoc.y );
 context.lineTo( curLoc.x , curLoc.y );
 
 context.strokeStyle = strokeColor;
 context.lineWidth = lineWidth;
 context.lineCap = "round";
 context.lineJoin = "round";
 context.stroke();
 
 lastLoc = curLoc;
 lastTimestamp = curTimestamp;
 lastLineWidth = lineWidth;
}
 
canvas.onmousedown = function(e){
 e.preventDefault();
 beginStroke( {x: e.clientX , y: e.clientY} );
};
canvas.onmouseup = function(e){
 e.preventDefault();
 endStroke();
};
canvas.onmouseout = function(e){
 e.preventDefault();
 endStroke();
};
canvas.onmousemove = function(e){
 e.preventDefault();
 if( isMouseDown ){
  moveStroke({x: e.clientX , y: e.clientY})
 }
};
 
canvas.addEventListener('touchstart',function(e){
 e.preventDefault();
 touch = e.touches[0];
 beginStroke( {x: touch.pageX , y: touch.pageY} )
});
canvas.addEventListener('touchmove',function(e){
 e.preventDefault();
 if( isMouseDown ){
  touch = e.touches[0];
  moveStroke({x: touch.pageX , y: touch.pageY});
 }
});
canvas.addEventListener('touchend',function(e){
 e.preventDefault();
 endStroke();
});
 
var maxLineWidth = 30;
var minLineWidth = 1;
var maxStrokeV = 10;
var minStrokeV = 0.1;
function calcLineWidth( t , s ){
 
 var v = s / t;
 
 var resultLineWidth;
 if( v <= minStrokeV )
  resultLineWidth = maxLineWidth;
 else if ( v >= maxStrokeV )
  resultLineWidth = minLineWidth;
 else{
  resultLineWidth = maxLineWidth - (v-minStrokeV)/(maxStrokeV-minStrokeV)*(maxLineWidth-minLineWidth);
 }
 
 if( lastLineWidth == -1 )
  return resultLineWidth;
 
 return resultLineWidth*1/3 + lastLineWidth*2/3;
}
 
function calcDistance( loc1 , loc2 ){
 
 return Math.sqrt( (loc1.x - loc2.x)*(loc1.x - loc2.x) + (loc1.y - loc2.y)*(loc1.y - loc2.y) );
}
 
function windowToCanvas( x , y ){
 var bbox = canvas.getBoundingClientRect();
 return {x:Math.round(x-bbox.left) , y:Math.round(y-bbox.top)}
}
function drawGrid(){
 
 context.save();
 
 context.strokeStyle = "rgb(230,11,9)";
 
 context.beginPath();
 context.moveTo( 3 , 3 );
 context.lineTo( canvasWidth - 3 , 3 );
 context.lineTo( canvasWidth - 3 , canvasHeight - 3 );
 context.lineTo( 3 , canvasHeight - 3 );
 context.closePath();
 context.lineWidth = 6;
 context.stroke();
 
 context.beginPath();
 context.moveTo(0,0);
 context.lineTo(canvasWidth,canvasHeight);
 
 context.moveTo(canvasWidth,0);
 context.lineTo(0,canvasHeight);
 
 context.moveTo(canvasWidth/2,0);
 context.lineTo(canvasWidth/2,canvasHeight);
 
 context.moveTo(0,canvasHeight/2);
 context.lineTo(canvasWidth,canvasHeight/2);
 
 context.lineWidth = 1;
 context.stroke();
 
 context.restore();
}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
TinyMCE 新增本地图片上传功能
Nov 05 Javascript
javascript基础知识大集锦(二) 推荐收藏
Jan 13 Javascript
javascript数字格式化通用类 accounting.js使用
Aug 24 Javascript
一个css与js结合的下拉菜单支持主流浏览器
Oct 08 Javascript
jQuery中设置form表单中action值的实现方法
May 25 Javascript
浅谈jquery.form.js的ajaxSubmit和ajaxForm的使用
Sep 09 Javascript
javascript判断firebug是否开启的方法
Nov 23 Javascript
浅谈让你的代码更简短,更整洁,更易读的ES6小技巧
Oct 25 Javascript
vue+axios实现post文件下载
Sep 25 Javascript
vue 实现cli3.0中使用proxy进行代理转发
Oct 30 Javascript
Vue通过配置WebSocket并实现群聊功能
Dec 31 Javascript
微信小程序scroll-view的滚动条设置实现
Mar 02 Javascript
webpack打包多页面的方法
Nov 30 #Javascript
Element Table的row-class-name无效与动态高亮显示选中行背景色
Nov 30 #Javascript
VUE2.0+ElementUI2.0表格el-table实现表头扩展el-tooltip
Nov 30 #Javascript
VUE2.0+ElementUI2.0表格el-table循环动态列渲染的写法详解
Nov 30 #Javascript
js字符串倒序的实例代码
Nov 30 #Javascript
实例讲解JavaScript截取字符串
Nov 30 #Javascript
支付宝小程序自定义弹窗dialog插件的实现代码
Nov 30 #Javascript
You might like
PHP高级对象构建 工厂模式的使用
2012/02/05 PHP
用PHP代码给图片加水印
2015/07/01 PHP
PHP+原生态ajax实现的省市联动功能详解
2017/08/15 PHP
php基于环形链表解决约瑟夫环问题示例
2017/11/07 PHP
PHP重置数组为连续数字索引的几种方式总结
2018/03/12 PHP
JavaScript在IE中“意外地调用了方法或属性访问”
2008/11/19 Javascript
window.onload和$(function(){})的区别介绍
2013/10/30 Javascript
JS关键字球状旋转效果的实例代码
2013/11/29 Javascript
javascript在网页中实现读取剪贴板粘贴截图功能
2014/06/07 Javascript
jQuery级联操作绑定事件实例
2014/09/02 Javascript
nodejs开发微博实例
2015/03/25 NodeJs
Javascript中arguments用法实例分析
2015/06/13 Javascript
jQuery实现对象转为url参数的方法
2017/01/11 Javascript
微信小程序 定位到当前城市实现实例代码
2017/02/23 Javascript
JS中使用正则表达式g模式和非g模式的区别
2017/04/01 Javascript
用 js 的 selection range 操作选择区域内容和图片
2017/04/18 Javascript
[48:53]2014 DOTA2华西杯精英邀请赛 5 25 LGD VS VG第一场
2014/05/26 DOTA
Python实现二维数组按照某行或列排序的方法【numpy lexsort】
2017/09/22 Python
简单了解Django ContentType内置组件
2019/07/23 Python
python装饰器练习题及答案
2019/11/01 Python
python实现局域网内实时通信代码
2019/12/22 Python
使用Keras中的ImageDataGenerator进行批次读图方式
2020/06/17 Python
Silk’n激光脱毛器官网:silkn.com
2016/10/06 全球购物
加利福尼亚州威尼斯的女性奢侈品设计师服装和概念店:Mona Moore
2018/09/13 全球购物
美国在线打印网站:Overnight Prints
2018/10/11 全球购物
销售总监岗位职责
2014/01/04 职场文书
婚前协议书
2014/04/15 职场文书
《花瓣飘香》教学反思
2014/04/15 职场文书
安全责任协议书
2014/04/21 职场文书
2014中考励志标语
2014/06/05 职场文书
职业道德模范事迹材料
2014/08/24 职场文书
试用期自我评价怎么写
2015/03/10 职场文书
新郎父母婚礼致辞
2015/07/27 职场文书
商业计划书之服装
2019/09/09 职场文书
微信小程序实现拍照和相册选取图片
2021/05/09 Javascript
pytorch 中autograd.grad()函数的用法说明
2021/05/12 Python