【JS图形学基本】二维图形学的变更

二维图形学的变更

运用过前端的css3,canva,svg的小伙伴应当对平移,扭转,缩放,剪切这些结果变更应当很熟悉了,但应当大部分小伙伴应当不清楚个中的道理,在二维图形方面如果能闇练运用图形学的基础算法,连系canva,svg会有意想不到的欣喜。

盘算机图形学中的运用异常普遍的变更是一种称为仿射变更的特别变更,在仿射变更中的基础变更包含平移、扭转、缩放、剪切这几种。

平移

设某点向x方向挪动dx,y方向挪动dy ,[x,y]为变更前坐标,[X,Y]为变更后坐标。

 X = x+dx;  Y = y+dy;

以矩阵示意:
《【JS图形学基本】二维图形学的变更》

扭转

首先要明白扭转在二维中是绕着某一个点举行扭转,三维中是绕着某一个轴举行扭转。二维扭转中最简朴的场景是绕着坐标原点举行的扭转,以下图所示:

《【JS图形学基本】二维图形学的变更》

如图所示点v 绕 原点扭转θ角,获得点v’,假定 v点的坐标是(x, y) ,那末能够推导获得 v’点的坐标(x’, y’),设原点到v的间隔是r,原点到v点的向量与x轴的夹角是ϕ

x=rcosϕy=rsinϕ
 
x′=rcos(θ+ϕ)y′=rsin(θ+ϕ)

经由过程三角函数睁开获得

x′=rcosθcosϕ−rsinθsinϕ
 
y′=rsinθcosϕ+rcosθsinϕ

带入x和y表达式获得

x′=xcosθ−ysinθ
 
y′=xsinθ+ycosθ

写成矩阵的情势是:
《【JS图形学基本】二维图形学的变更》

只管图示中仅仅示意的是扭转一个锐角θ的情况,然则我们推导中运用的是三角函数的基础定义来盘算坐标的,因而当扭转的角度是恣意角度(比方大于180度,致使v’点进入到第四象限)结论仍然是建立的。

绕恣意点的二维扭转

《【JS图形学基本】二维图形学的变更》

《【JS图形学基本】二维图形学的变更》

缩放

简朴缩放

简朴缩放能够直接经由过程将缩放系数sx,sy与对应x,y坐标相乘:

x’=x*sx,y’=y*sy

基于一个固定点缩放

《【JS图形学基本】二维图形学的变更》

x’ = x * sx + sy(1-sx)
y’ = y * sy + yf(1-sy)

个中sx,sy属于缩放系数。0~1示意减少,>1示意放大

错切

图象错切变更在图象多少形变方面异常有效,罕见的错切变更分为X方向与Y方向的错切变更。对应的数学矩阵离别以下:
《【JS图形学基本】二维图形学的变更》
依据上述矩阵假定P(x1, y1)为错切变更之前的像素点,则错切变更今后对应的像素

P’(x2, y2)当X方向错切变更时:

x2 = x1 - y1 * tanθ
y2 = y1

当Y方向错切变更时:

x2 = x1
y2 = y1 - x1 * tanθ

实例

svg

canvas

只贴上扭转的demo,其他都能够模仿套用

扭转

橘色的点缭绕蓝色扭转
《【JS图形学基本】二维图形学的变更》

var canvas = document.getElementById("canvas");
    var context = canvas.getContext('2d');
    context.beginPath();
    context.fillStyle = "#3399ff";
    context.arc(100, 75, 5, 0, 2 * Math.PI);
    context.fill();

    //点a缭绕(100,75) 顺时针90度扭转
    var a = { x: 150, y: 75 }
    //套用上文公式
    //- 0.5 * Math.PI 由于canvas的0
    var x = 100 + (a.x - 100) * Math.cos(Math.PI / 2) - (a.y - 75) * Math.sin(Math.PI / 2);
    //y为简化后
    var y = 75 + (a.x - 100) * Math.sin(Math.PI / 2);
    context.beginPath();
    context.fillStyle = "#fe9901";
    context.arc(x, y, 5, 0, 2 * Math.PI);
    context.fill();

    //缭绕100,75 60度扭转
    var x = 100 + 50 * Math.cos(Math.PI / 3);
    var y = 75 + 50 * Math.sin(Math.PI / 3);
    context.beginPath();
    context.fillStyle = "#fe9901";
    context.arc(x, y, 5, 0, 2 * Math.PI);
    context.fill();
    原文作者:梵鹿
    原文地址: https://segmentfault.com/a/1190000014119613
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞