鼠标操作图形旋转

xiaoxiao2021-02-28  29

算法思路: 寻找图形的中心点或者给定一个点,将影响图形形状的关键点绕着这个点旋转,然后根据旋转后的新值重绘图形。这里旋转的角度,即为鼠标移动开始点与定点的向量,和移动结束点与定点的向量之间的夹角。

用到的数学公式:

部分函数实现:

////////////////////////////////////////////////////////////////////////// struct POINTF { float x; float y; POINTF::POINTF(){} POINTF::POINTF(float a,float b):x(a),y(b){} }; //判断向量顺时针旋转还是逆时针旋转(两向量起点相同) //向量a,旋转前的向量 //向量b,旋转后的向量 //返回值1-顺时针 0-平行 -1-逆时针 int vecCross(const POINTF& a,const POINTF& b) { float fValue = a.x*b.y - b.x*a.y; if (fValue > 1e-6)//正 { return 1; } else if(fValue < -1e-6)//负 { return -1; } else//零 { return 0; } } //点pta绕ptCenter点旋转 int vecCross(const POINTF& ptCenter,const POINTF& pta,const POINTF& ptScreen) { POINTF a = POINTF(pta.x-ptCenter.x,pta.y-ptCenter.y); POINTF b = POINTF(ptScreen.x-ptCenter.x,ptScreen.y-ptCenter.y); int axb = vecCross(a,b); return axb; } //计算向量旋转角度cos值 //点pta绕ptCenter点旋转 float rotCosAngle(const POINTF& ptCenter,const POINTF& pta,const POINTF& ptScreen) { POINTF a = POINTF(pta.x-ptCenter.x,pta.y-ptCenter.y); POINTF b = POINTF(ptScreen.x-ptCenter.x,ptScreen.y-ptCenter.y); POINTF c = POINTF(ptScreen.x-pta.x,ptScreen.y-pta.y); float A = sqrtf(a.x*a.x+a.y*a.y); float B = sqrtf(b.x*b.x+b.y*b.y); float C = sqrtf(c.x*c.x+c.y*c.y); float CosC = (A*A+B*B-C*C)/(2*A*B);//cosC = (a^2+b^2-c^2)/2ab 此处没有考虑除数为0的情况 return CosC; } //计算一个点绕另一个点旋转,得到的点 POINTF getRotationPoint(const POINTF& ptCenter,const POINTF& pta,const int& axb,const float& costheta) { POINTF pt(0.0,0.0); POINTF a = POINTF(pta.x-ptCenter.x,pta.y-ptCenter.y); //POINTF b = POINTF(ptScreen.x-ptCenter.x,ptScreen.y-ptCenter.y); //int axb = vecCross(a,b); //float costheta = rotCosAngle(ptCenter,pta,ptScreen); float sintheta = sqrtf(1-costheta*costheta);//计算sin值,sinA^2+cosA^2 = 1 POINTF ptTemp; switch(axb) { case 0: pt = pta; break; case -1://逆时针 ptTemp = POINTF(a.x*costheta+a.y*sintheta+ptCenter.x,-a.x*sintheta+a.y*costheta+ptCenter.y); pt = ptTemp; break; case 1://顺时针 ptTemp = POINTF(a.x*costheta-a.y*sintheta+ptCenter.x,a.x*sintheta+a.y*costheta+ptCenter.y); pt = ptTemp; break; } return pt; }
转载请注明原文地址: https://www.6miu.com/read-1699983.html

最新回复(0)