而不是根据利用属性或样式放大缩小后的图片,

作者: 前端  发布:2019-11-29
<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
    <title>jQuery之家</title>
    <style type="text/css">
        *{margin:0;padding:0;}
        body{font-size: 14px;}
        canvas{
            display:none;
            background-color: #ffff91;
        }
        #square{
            width:80px;
            height: 80px;
            background-color: rgba(117,240,255,0.5);
            position:absolute;
            z-index: 999;
            cursor:crosshair;
            display:none;
        }
    </style>
    <script>
        onload=function(){
            var canvas=document.getElementById("canvas");//获取画布
            var ctx=canvas.getContext("2d");//获取画笔
            var img=document.getElementsByTagName("img")[0];//获取图片
            var square=document.getElementById("square");//获取选择框
            var squareData={};//存选择框信息
            var imgPosition=img.getBoundingClientRect();//获取图片的位置
            var p=img.naturalWidth/img.width;//原始图片与缩小后图片的比例
           // var even;
            //鼠标移入
            img.onmouseove=function(e){
                var even=e||event;//兼容火狐浏览器
                var x=even.clientX,
                    y=even.clientY;
                createSquare(x,y);
            };
            window.onmousemove=function(e){
                var even=e||event;
                var x=even.clientX;
                var y=even.clientY;
                //使选择框限制在图片内部
                if(x>=img.offsetLeft&&x<=img.offsetLeft+img.width&&y>=img.offsetTop&&y<=img.offsetTop+img.height){
                     createSquare(x,y);
                }else{
                    hideSquare();
                    hideCanvas();
                }
            };
            function createSquare(x,y){
                x=x-40<img.offsetLeft?img.offsetLeft:x-40;
                y=y-40<img.offsetTop?img.offsetTop:y-40;
                x=x+80<imgPosition.right?x:imgPosition.right-80;
                y=y+80<imgPosition.bottom?y:imgPosition.bottom-80;
                //将选择框左上角的位置存到squareData
                squareData.left=x;
                squareData.top=y;
                moveSquare(x,y);
            }
            function moveSquare(x,y){
                //设置选择框偏移位置
                square.style.left=x+"px";
                square.style.top=y+"px";
                showCanvas();
                showSquare();
                draw();
            }
            function showCanvas(){
                canvas.style.display="inline";
            }
            function hideCanvas(){
                canvas.style.display="none";
            }
            function showSquare(){
                square.style.display="inline";
            }
            function hideSquare(){
                square.style.display="none";
            }
            //将放大后的图片画到canvas中
            function draw(){
                console.log(squareData.left-imgPosition.left);
                ctx.drawImage(img,(squareData.left-imgPosition.left)*p,p*(squareData.top-imgPosition.top),p*80,p*80,0,0,canvas.width,canvas.height);
            }
        }
    </script>
</head>
<body>
<img src="img/N7ETzFO.jpg" alt="9159.com 1" width="300px">
<canvas id="canvas" width="300px" height="225px"></canvas>
<div id="square"></div>
</body>
</html>
 iOS一旦图片文件被加载就必须要进行解码,解码过程是一个相当复杂的任务,需要消耗非常长的时间。解码后的图片将同样使用相当大的内存。
 用于加载的CPU时间相对于解码来说根据图片格式而不同。对于PNG图片来说,加载会比JPEG更长,因为文件可能更大,但是解码会相对较快,而且Xcode会把PNG图片进行解码优化后引入工程。JPEG图片更小,加载更快,但是解压的步骤需要更长的时间,因为JPEG解压算法比基于zip的PNG算法更加复杂。
当加载图片的时候,iOS通常会延迟解压图片的时间,直到加载到内存之后。这就会在准别绘制图片的时候影响性能,因为需要在绘制之前需要解压(通常是消耗时间的问题所在)。
最简单的方法就是使用 UIImage 的 +imageNamed:方法避免延时加载。不像 +imageWithContentOfFile:(和其他别的 UIImage 加载方法),这个方法会在加载图片之后立刻解压。问题是 +imageNamed:只对从应用资源中的图片有效,所以对用户生成的图片内容或者是下载的图片就没法使用了。
另一种立刻加载图片的方法就是把他设置成图层内容,或者是 UIIMageView 的 image 属性。不幸的是,这又需要在主线程执行,所以不会对性能有所提升。
第三种方式就是绕过 UIKit,使用 ImageIO框架。
最后一种方式就是使用UIKit加载图片,但是立刻会知道 CGContext 中去。图片必须要在绘制之前解压,所以就强制了解压的及时性。这样的好处在于绘制图片可以在后台线程(例如加载本身)执行,而不会阻塞UI。

实际落实思路:

  • 1.假使边框宽度为BorderW
  • 2.敞开的图样上下文的尺码就应有是原有图片的宽高分别增进两倍的BorderW,那样开启的指标是为着不让原始图片变形.
  • 3.在上下文上边增多三个圆形填充路径.地方从(0,0卡塔尔点起头,宽高和左右文尺寸相似大.设置颜色为要设置的边框颜色.
  • 4.后续在上下文上边加多二个圆形路线,这些渠道为裁剪路线.
    它的x,y分别从BorderW这一个点开头.宽度和中度分别和原本图片的宽高相仿大.将绘制的那个门路设为裁剪区域.
  • 5.把原本路线绘制到上下文在那之中.绘制的岗位和是裁剪区域的职务肖似,x,y分别从border初阶绘制.
  • 6.从上下文状态当中抽出图片.
  • 7.休憩上下文状态.

图表参照:

9159.com 2

3.gif

canvas.drawBitmap(Bitmap bitmap, Rect src,Rect dst, Paint paint)

9159.com,canvas 绘制图片是基于原有图片的尺寸举办绘图,并非借助使用属性或样式放大减少后的图样,所以要倍加原始图片与今后图片的比重。

有二种办法得以强制解压提前渲染图片:
1、将图纸的叁个像素绘制作而成二个像素大小的 CGContext。那样还是会解压整张图片,然而绘制本身并未成本任什么日期间。那样的益处在于加载的图纸并不会在特定的配备上为绘制做优化,所以能够在其它时刻点绘制出来。相仿iOS也就能够抛弃解压后的图纸来节省里部存款和储蓄器了。
2、将整张图片绘制到 CGContext 中,放任原始的图纸,而且用二个从上下文内容中新的图形来替代。那样比绘制单风度翩翩像素那样需求尤其复杂的思谋,然而因而发生的图纸将会为绘制做优化,何况由于原有压缩图片被扬弃了,iOS就不可以看到时刻抛弃任何解压后的来节本省部存款和储蓄器了。

加载要裁剪的图片

UIImage *image = [UIImage imageNamed:@"阿狸头像"];

  • 0.装置边框大小.
    CGFloat borderW = 10;
  • 1.拉开二个和原有图片相同大小的位图上下文.
UIGraphicsBeginImageContextWithOptions(size,NO,0);```
 -  2.绘制一个大圆,填充
``` UIBezierPath *path = [UIBezierPath bezierPathWithOvalInRect:CGRectMake(0, 0, size.width, size.height)];    
[[UIColor blueColor] set];
[path fill];```
 -   3.添加一个裁剪区域.
```path = [UIBezierPath bezierPathWithOvalInRect:CGRectMake(borderW, borderW, image.size.width, image.size.height)];
[path addClip];```
 -   4.把图片绘制到裁剪区域当中.
 ```[image drawAtPoint:CGPointMake(borderW, borderW)];```
 -   5.生成一张新图片.
```UIImage *clipImage = UIGraphicsGetImageFromCurrentImageContext();```
 -   6.关闭上下文.
 ```UIGraphicsEndImageContext();```

######抽取分类方法:

```根据传入的图片,生成一终带有边框的圆形图片.
borderW边框宽度
borderColor:边框颜色
image:要生成的原始图片.
+ (UIImage *)imageWithBorderW:(CGFloat)borderW borderColor:(UIColor *)color image:(UIImage *)image;

+ (UIImage *)imageWithBorderW:(CGFloat)borderW borderColor:(UIColor *)color image:(UIImage *)image;```
  - 1.开启一个和原始图片一样大小的位图上下文.
```CGSize size = CGSizeMake(image.size.width + 2 *borderW, image.size.height + 2 * borderW);
UIGraphicsBeginImageContextWithOptions(size,NO,0);```
  -  2.绘制一个大圆,填充
```UIBezierPath *path = [UIBezierPath bezierPathWithOvalInRect:CGRectMake(0, 0, size.width, size.height)];   
[[UIColor blueColor] set];
[path fill];```
  -  3.添加一个裁剪区域.
```path = [UIBezierPath bezierPathWithOvalInRect:CGRectMake(borderW, borderW, image.size.width, image.size.height)];
[path addClip];```
  -  4.把图片绘制到裁剪区域当中.
```[image drawAtPoint:CGPointMake(borderW, borderW)];```
  -  5.生成一张新图片.
```UIImage *clipImage = UIGraphicsGetImageFromCurrentImageContext();```
  -  6.关闭上下文.
```UIGraphicsEndImageContext();       return clipImage;```

1.Bitmap bitmap图片位图 (你所要绘制的图纸的固有位图)
2.Rect src 此矩形的left.top.right.bottom表示的是您需求怎么着裁剪原图片
譬如: 1.通通显示原始位图的样子(不包涵原始图片宽度是有个别和冲天是有些,那个是由上面包车型客车Rect dst决定的卡塔尔国
Rect src=new Rect(0,0,bitmap.getWidth(),bitmap.getHeight())
这个left=0;top=0;right=bitmap.getWidth(),bottom=bitmap.getHeight
本条right和bottom是本来位图的宽和高,代表的是裁剪整个原始位图(不表示绘制出来图片的深浅)
2.只体现原始位图的上半有个别
Rect src=new Rect(0,0,bitmap.getWidth()/2,bitmap.getHeight()/2)
就此说你想裁剪哪个部分直接增添或减小right和bottom的深浅就可以了
3.Rect dst 他的left和top代表将图纸绘制在View的哪位地点
而right和bottom代表的是将图纸的上升的幅度和可观展现多少

急需小心的是苹果极其推荐了永不选用那个诡计拉绕过科班图片解压逻辑(所以也是他俩筛选择暗中认可管理方式的缘由),然而即使你利用过多大图来营造利用,那借使想升官品质,就只可以和系统博艺了。

譬喻说你要绘制出原始位图的尺寸,就让right=bitmap.getWidth(卡塔尔(قطر‎和bottom=bitmap.getHeight(卡塔尔国;
压缩或加大的话就将right和bottom的值变大或变小就能够了

如果不适用 +imageNamed:,那么把整张图片绘制到 CGContext 恐怕是一流的办法了。固然你或然感觉多余的绘图相较其余解压技艺来说性能不是极高,可是新创造的图纸(在一定设备上做过的优化)只怕比原本图片绘制的越来越快。

相近,假诺想呈现图片到比原始尺寸小的器皿中,那么三次性在后台线程重新绘制到科学的尺寸会比每趟呈现的时候都做缩放会更使得。

本文由9159.com发布于前端,转载请注明出处:而不是根据利用属性或样式放大缩小后的图片,

关键词:

上一篇:没有了
下一篇:没有了