js+jquery实现图片裁剪功能


Posted in Javascript onJanuary 02, 2015

现在我们在使用各大网站的个人中心时,都有个上传个人头像的功能。用户在上传了个人照片之后,可能不符合网站的要求,于是要求用户对照片进行裁剪,最终根据用户裁剪的尺寸生成头像。这个功能真是太棒了,原来不懂js的时候,感觉很神奇,太神奇了。心想哪天要是自己也能搞明白这里面的技术,那该多牛呀~大家是不是也有何我一样的想法呀~哈哈~~

下面我们就来用javascript来实现这个功能吧。

<!DOCTYPE html>

<html xmlns="http://www.w3.org/1999/xhtml">

<head>

<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

<title>clip</title>

<style type="text/css">

*{ padding:0; margin:0;}

ul{ list-style-type:none; overflow:hidden; zoom:1; width:1000px; margin:30px auto; }

li{ float:left; width:500px;}

#container{width:480px; height:480px; margin:0 auto; border:1px solid #999; position:relative;background:url(http://images.cnblogs.com/cnblogs_com/wtcsy/192373/r_xx.jpg);}

#container .block{height:100px; width:100px; border:1px solid #000000; position:absolute; left:50px; top:50px; background:#fff;filter:alpha(opacity=30);opacity:0.3; cursor:move;}

#container .tips{ position:absolute; padding:5px; border:1px solid #ccc;background:#fff;filter:alpha(opacity=60);opacity:0.6; display:none; font-size:12px; color:#333; ;}

.tips span{ display:inline-block;zoom:1; width:28px;}

.rRightDown,.rLeftDown,.rLeftUp,.rRightUp,.rRight,.rLeft,.rUp,.rDown{

position:absolute;background:#f00;width:6px;height:6px;z-index:5;font-size:0;}

.rLeftDown,.rRightUp{cursor:ne-resize;}

.rRightDown,.rLeftUp{cursor:nw-resize;}

.rRight,.rLeft{cursor:e-resize;}

.rUp,.rDown{cursor:n-resize;}

.rRightDown{ bottom:-3px; right:-3px;}

.rLeftDown{ bottom:-3px; left:-3px;}

.rRightUp{ top:-3px; right:-3px;}

.rLeftUp{ top:-3px; left:-3px;}

.rRight{ right:-3px; top:50%}

.rLeft{ left:-3px; top:50%}

.rUp{ top:-3px; left:50%}

.rDown{ bottom:-3px; left:50%}

#imgC{ border:1px solid #CCC; width:0; height:0; margin:0 auto;background:url(http://images.cnblogs.com/cnblogs_com/wtcsy/192373/r_xx.jpg);}

.code {

    background: none repeat scroll 0 0 #E3F4F9;

    border: 1px solid #BAE2F0;

    font: 12px "Courier New",Courier,monospace;

    margin: 30px auto;

    padding: 10px 10px 40px;

 width:980px;

}

.code p{ height:24px; line-height:24px;}

.code span{ display:inline-block;zoom:1; margin-right:5px; width:85px; font-weight:bold; color:#00F}

</style>

</head>

<body>

<div class="code">

 <div class="how">使用方法</div>

    <p>$("#container").clip({

  imgC : $("#imgC"),

        blockClass : "block",

        tipsClass  : "tips"        

 });</p>

    <p><span>imgC :</span> 表示裁剪图片的容器,也就是右边的图</p>

    <p><span>blockClass :</span> block的样式名  也就是页面上的可以拖动的滑块的样式 因为怕和别的页面上的样式重名  默认是block</p>

    <p><span>tipsClass  :</span> tips的样式名   也就是页面上显示left width height top的那个span的样式名 默认是tips</p>

</div>

<ul>

 <li>

     <div id="container"></div>

    </li>

    <li>

     <div id="imgC"></div>

    </li>

</ul>

<script type="text/javascript" src="http://common.cnblogs.com/script/jquery.js"></script>

<script type="text/javascript">

(function(){

 var dBody = document.body,

  dDoc = document.documentElement,

  ie   = $.browser.msie;

 ie&&($.browser.version=="6.0")

  &&document.execCommand("BackgroundImageCache", false, true); 

 var  clip =  function(options){

  this.init.call(this,options); 

 }

 clip.prototype = {

  options :{

   moveCallBack : function(){},

   blockClass : "block",

   tipsClass  : "tips"

  },

  init : function(options){   

   $.extend(this,this.options,options||{});

   if(!this.container || !this.imgC){

    return;

   }

   this.container = $(this.container);

   var self = this;

   this.block = $('<div class="'+this.blockClass+'">\

     <div action="rightDown" class="rRightDown"></div>\

     <div action="leftDown" class="rLeftDown"></div>\

     <div action="rightUp" class="rRightUp"></div>\

     <div action="leftUp" class="rLeftUp"></div>\

     <div action="right" class="rRight"></div>\

     <div action="left" class="rLeft"></div>\

     <div action="up" class="rUp"></div>\

     <div action="down" class="rDown" ></div>\

       </div>')

   .bind("mousedown.r",function(e){self.start(e)})

   .appendTo(this.container[0]);

   this.tips = $('<span class="'+this.tipsClass+'" />').appendTo(this.container[0]);

   this.setImg();

  },

  setImg : function(){

   var block = this.block;

   var left  = block.css("left"),

    top   = block.css("top"),

    height = block.height(),

    width  = block.width();

   this.imgC.css({

    height: height,

    width : width,

    "background-position" : "-"+left+" -"+top

   });

   this.tips.html("left:<span>"+parseInt(left) + "</span>top:<span>" + +parseInt(top) + "</span>width:<span>"+width+ "</span>height:<span>"+height+"</span>");

  },

  start : function(e){      

   var $elem     = $(e.target),

    block     = this.block,

    self      = this,

    move      = false,

    container = this.container,

    action    = $elem.attr("action");

   //这个 每次都要计算 基本dom结构的改变 浏览器的缩放 都会让里面的值发生改变 

   this.offset = $.extend({height:container.height(),width:container.width()},container.offset());

   this.blockOriginal = {height:block.height(),width:block.width(),left:parseInt(block.css("left")),top:parseInt(block.css("top"))};

   if(action){

    this.fun = this[action];    

   }else{

    this.x = e.clientX - this.offset.left - this.blockOriginal.left ;

    this.y = e.clientY - this.offset.top - this.blockOriginal.top;

    move = true;

   }   

   ie

    &&this.block[0].setCapture();

   this.tips.show();

   $(document)

    .bind("mousemove.r",function(e){self.move(e,move)})

    .bind("mouseup.r",function(){self.end()});   

  },

  end  : function(){

   $(document)

    .unbind("mousemove.r")

    .unbind("mouseup.r");

   ie 

    &&this.block[0].releaseCapture();

   this.tips.hide(); 

  },

  move : function(e,isMove){

   window.getSelection 

    ? window.getSelection().removeAllRanges() 

    : document.selection.empty();

    

   var block = this.block; 

   if(isMove){

    var left = Math.max(0,e.clientX - this.offset.left - this.x);

    left = Math.min(left,this.offset.width - this.blockOriginal.width);

    var top = Math.max(0,e.clientY - this.offset.top - this.y);

    top = Math.min(top,this.offset.height - this.blockOriginal.height);

    block.css({left:left,top:top});    

   }else{

    var offset = this.fun(e);

    block.css(offset);

   }

   

   this.setImg();

   this.moveCallBack();

  },

  down : function(e){

   var blockOriginal = this.blockOriginal, 

    sTop = Math.max(dBody.scrollTop,dDoc.scrollTop), //出现垂直方向滚动条时候 要计算这个  

    offset = this.offset;

    

   if(e.clientY-offset.top>=blockOriginal.top-sTop){

    var height = Math.min(offset.height - blockOriginal.top,e.clientY-offset.top-blockOriginal.top+sTop),

     top = blockOriginal.top;

   }else{

    var height = Math.min(offset.top+blockOriginal.top-e.clientY-sTop,blockOriginal.top),

     top = Math.max(e.clientY - offset.top+sTop,0);

   }

   return {height:height, top:top};

  },

  up : function(e){

   var blockOriginal = this.blockOriginal,

    sTop = Math.max(dBody.scrollTop,dDoc.scrollTop),

    offset = this.offset;

   if(e.clientY-offset.top-blockOriginal.height<=blockOriginal.top-sTop){

    var top = Math.max(e.clientY-offset.top+sTop,0),

     maxHeight = blockOriginal.top + blockOriginal.height,

     height = Math.min(maxHeight,blockOriginal.top + blockOriginal.height -(e.clientY-offset.top)-sTop);     

   }else{

    var height = Math.min(e.clientY-offset.top-blockOriginal.top-blockOriginal.height+sTop,offset.height-blockOriginal.top-blockOriginal.height),

     top = blockOriginal.top+blockOriginal.height;  

   }

   return {height:height, top:top};

  },

  left : function(e){

   var blockOriginal = this.blockOriginal,

    offset = this.offset;

    

   if(e.clientX - offset.left - blockOriginal.width - blockOriginal.left<=0){

    var left  = Math.max(e.clientX - offset.left,0),

     width = Math.min(blockOriginal.left + blockOriginal.width,blockOriginal.left + blockOriginal.width -(e.clientX-offset.left));

   }else{

    var width = Math.min(e.clientX-offset.left-blockOriginal.left-blockOriginal.width,offset.width-blockOriginal.left-blockOriginal.width),

     left  = blockOriginal.left + blockOriginal.width;

   }

   return {left : left,  width : width};

  },

  right : function(e){

   var blockOriginal = this.blockOriginal,

    offset = this.offset;

   if(e.clientX-offset.left>=blockOriginal.left){

    var width = Math.min(offset.width - blockOriginal.left,e.clientX - offset.left - blockOriginal.left),

     left  = blockOriginal.left;

   }else{

    var width = Math.min(offset.left + blockOriginal.left - e.clientX,blockOriginal.left),

     left  = Math.max(e.clientX - offset.left,0);

   }

   return {left : left,  width : width};

  },

  rightDown : function(e){

   return $.extend(this.right(e),this.down(e));  

  },

  leftDown : function(e){

   return $.extend(this.left(e),this.down(e));

  },

  rightUp : function(e){

   return $.extend(this.right(e),this.up(e));

  },

  leftUp : function(e){

   return $.extend(this.left(e),this.up(e));

  },

  getValue : function(){

   var block = this.block;

   return {

    left   : parseInt(block.css("left")),

    top    : parseInt(block.css("top")),

    width  : block.width(),

    height : block.height()

   }

  }

 }

 $.fn.clip = function(options){

  options.container = this;

  return new clip(options);

 }

})();

 xx = $("#container").clip({

  imgC : $("#imgC")

 })

</script>

</body>

</html>

是不是很炫酷啊,小伙伴们,学学本示例的思路吧。

Javascript 相关文章推荐
JavaScript DOM 学习第五章 表单简介
Feb 19 Javascript
jQuery在IE下使用未闭合的xml代码创建元素时的Bug介绍
Jan 10 Javascript
浅析jQuery中常用的元素查找方法总结
Jul 04 Javascript
当前页禁止复制粘贴截屏代码小集
Jul 24 Javascript
用jquery等比例控制图片宽高的具体实现
Jan 28 Javascript
js+css实现文字散开重组动画特效代码分享
Aug 21 Javascript
两种js监听滚轮事件的实现方法
May 13 Javascript
从零开始学习Node.js系列教程之SQLite3和MongoDB用法分析
Apr 13 Javascript
JS实现的数组去除重复数据算法小结
Nov 17 Javascript
vue 通过下拉框组件学习vue中的父子通讯
Dec 19 Javascript
ES6 Promise对象概念及用法实例详解
Oct 15 Javascript
vue移动端模态框(可传参)的实现
Nov 20 Javascript
javascript 构造函数方式定义对象
Jan 02 #Javascript
深入探寻javascript定时器
Jan 02 #Javascript
JavaScript中的Truthy和Falsy介绍
Jan 01 #Javascript
JavaScript中的null和undefined区别介绍
Jan 01 #Javascript
JavaScript中的全局对象介绍
Jan 01 #Javascript
原生javascript获取元素样式
Dec 31 #Javascript
JavaScript分析、压缩工具JavaScript Analyser
Dec 31 #Javascript
You might like
PHP下一个非常全面获取图象信息的函数
2008/11/20 PHP
数组与类使用PHP的可变变量名需要的注意的问题
2013/06/20 PHP
ThinkPHP中URL路径访问与模块控制器之间的关系
2014/08/23 PHP
PHP7匿名类的用法示例
2019/04/05 PHP
Yii Framework框架使用PHPExcel组件的方法示例
2019/07/24 PHP
js获取控件位置以及不同浏览器中的差别介绍
2013/08/08 Javascript
javascript获取元素离文档各边距离的方法
2015/02/13 Javascript
简介JavaScript中toUpperCase()方法的使用
2015/06/06 Javascript
JS实现仿苹果底部任务栏菜单效果代码
2015/08/28 Javascript
JavaScript中的闭包
2016/02/24 Javascript
Bootstrap基本插件学习笔记之折叠(22)
2016/12/08 Javascript
node中Express 动态设置端口的方法
2017/08/04 Javascript
webpack打包js文件及部署的实现方法
2017/12/18 Javascript
vue单页面打包文件大?首次加载慢?nginx带你飞,从7.5M到1.3M蜕变过程(推荐)
2018/01/16 Javascript
彻底弄懂 JavaScript 执行机制
2018/10/23 Javascript
微信小程序自定义导航栏实例代码
2019/04/05 Javascript
vue中axios实现数据交互与跨域问题
2019/05/12 Javascript
ES6 Promise对象的含义和基本用法分析
2019/06/14 Javascript
js getBoundingClientRect使用方法详解
2019/07/17 Javascript
JavaScript在web自动化测试中的作用示例详解
2019/08/25 Javascript
vue data恢复初始化数据的实现方法
2019/10/31 Javascript
Vue中使用wangeditor富文本编辑的问题
2021/02/07 Vue.js
Flask框架配置与调试操作示例
2018/07/23 Python
django 将model转换为字典的方法示例
2018/10/16 Python
python实现自动获取IP并发送到邮箱
2018/12/26 Python
详解Django+uwsgi+Nginx上线最佳实战
2019/03/14 Python
Python 实现键盘鼠标按键模拟
2020/11/18 Python
Michael Kors澳大利亚官网:世界知名的奢侈饰品和成衣设计师
2020/02/13 全球购物
工厂门卫岗位职责
2013/11/25 职场文书
派出所所长先进事迹
2014/05/19 职场文书
生活小常识广播稿
2014/09/16 职场文书
2014年工会工作总结
2014/11/12 职场文书
简爱电影观后感
2015/06/10 职场文书
校运会加油稿大全
2015/07/22 职场文书
高一军训口号
2015/12/25 职场文书
php 原生分页
2021/04/01 PHP