數字圖像處理----圖像旋轉

注:旋轉中心很重要 座標系爲像素,按照像素位置(第(m,n)作爲座標)bash

以座標原點爲中心旋轉的原理:

點p0繞座標原點逆時針方向旋轉θ角度獲得點p1. 函數

以任意圖形中心點爲座標原點旋轉原理:

從上圖可知以任意圖形中心點爲座標原點旋轉咱們須要三步:
(1)將座標系Ⅰ變成座標系Ⅱ
(2)在座標系Ⅱ中旋轉θ角
(3)將座標系Ⅱ變成座標系Ⅰ

(1)將座標系Ⅰ變成座標系Ⅱ
由Figure1獲得Figure2可知,變換矩陣爲:spa

(2)在座標系Ⅱ中旋轉θ角
見上面以座標原點爲中心旋轉的原理
(3)將座標系Ⅱ變成座標系Ⅰ

最近鄰插值matlab代碼

function [ A ] = myimrotate(B,degree,method)                                 %定義旋轉函數,degree爲要旋轉的角度
[r,c,d]=size(B);                                                      %獲取輸入圖像B的行r、列c和通道數d,爲了旋轉彩色圖像因此有必要獲得通道數d
nH=round(r*abs(cosd(degree))+c*abs(sind(degree)));                    %旋轉圖像後獲得的新高度,「round()函數四捨五入「
nW=round(c*abs(cosd(degree))+r*abs(sind(degree)));                    %旋轉圖像後獲得的新寬度
A=zeros(nH,nW,d);                                                     %定義生成目標圖像的行列以及通道數
M1=[1 0 0;
    0 -1 0;
    -0.5*nW 0.5*nH 1 ];                                  %座標系變換矩陣M1
M2=[cosd(degree) -sind(degree) 0;
    sind(degree) cosd(degree) 0;
    0 0 1];  %角度旋轉變換矩陣M2,我用的是順時針方向
M3=[1 0 0;
    0 -1 0;
    0.5*c 0.5*r 1];                                      %座標系變換矩陣M3
    for i=1:nW
        for j=1:nH
            temp=[i j 1]*M1*M2*M3;                                    %獲得旋轉後的矩陣temp
            y_r=temp(1,2);                                              %y取矩陣temp的第一行第二列,y對應j,爲高度
            x_r=temp(1,1);                                              %x取矩陣temp的第一行第一列,x對應i,爲寬度
            y=round(y_r);                                               %y四捨五入取整
            x=round(x_r);                                               %x四捨五入取整
           if(x>=1&&x<=c)&&(y>=1&&y<=r)                               %判斷的獲得的(x,y)點是否在原圖像上
                %最近鄰插值
               if strcmp(method,'near')
                  A(j,i,:)=B(y,x,:);                                     %將原圖像的像素點賦值給對應的旋轉後圖像上的點
               end                                                       %(」有人疑惑爲啥不是A(i,j,:)=B(x,y,:);由於i,x對應的是列,即寬,而j,y對應的是行,即高「),我這裏以x爲橫座標,y爲豎向縱座標
               %線性插值
               if strcmp(method,'linear')       
                  b = x_r-x;
                  a = y+1-y_r;
                  if(x>=1&&x+1<=c)&&(y>=1&&y+1<=r)
                      
                    
                      P1 = b*B(y, x) + (1-b)*B(y+1, x);
                      P2 = b*B(y, x+1) + (1-b)*B(y+1, x+1);
                      P = a*P1 + (1-a)*P2;
                  else
                      P=B(y,x,:);
                  end
                  A(j,i,:)=P;
               end  
               %三次插值
               if strcmp(method,'trib')    
                   x = floor(x_r);
                   y = floor(y_r);
                            
                   if(x>1&&x+2<=c)&&(y>1&&y+2<=r)     
                       b = x_r-x;
                       a = y_r-y;
                       A_A=[s(1+a) s(a) s(1-a) s(2-a)]; 
                       C=[s(1+b);s(b);s(1-b);s(2-b)]; 
                       B_B=[B(y-1,x-1) B(y-1,x) B(y-1,x+1) B(y-1,x+2)  
                          B(y,x-1)   B(y,x)  B(y,x+1)   B(y,x+2)  
                          B(y+1,x-1)   B(y+1,x) B(y+1,x+1) B(y+1,x+2)  
                          B(y+2,x-1) B(y+2,x) B(y+2,x+1) B(y+2,x+2)];
                      A(j,i,:) = (double(A_A)*double(B_B)*double(C));
%                    else
%                        if x<1
%                            x = x+1;
%                        end
%                        if y<1
%                            y = y+1;
%                        end
%                        A(j,i,:)=B(y,x,:);
                   end
               end
           end   
        end
    end
end
%計算S值
function [ re ] = s(x) 
    x = abs(x);
    if x<1 && x>=0
        re = 1-2*x^2 + x^3;
    end
    if x>=1 &&x<2
        re = 4 - 8*x +5*x^2-x^3;
    end
    if x>=2
        re = 0;
    end
end
複製代碼