FPGA Verilog实现基本的图像滤波处理仿真

描述

1、用matlab代码,准备好把图片转化成Vivado Simulator识别的格式,即每行一个数据:
img = imread('E:\matlab\Images\2016-09-05-211710.jpg');
if size(img,3)==3
   img = rgb2gray(img);
end
height = size(img, 1);
width = size(img, 2);
s = fopen('image2mem.txt','wb'); %opens the output file
cnt = 0;
for r=1:height
   for c=1:width
       cnt = cnt + 1;
       grey=img(r,c);
       greyb = dec2bin(grey,8);
       Outbyte =greyb(1:8);

       if (Outbyte(1:4) == '0000')fprintf(s,'0%X',bin2dec(Outbyte));
       else fprintf(s,'%X',bin2dec(Outbyte));   end
       if (mod(cnt,1) == 0)fprintf(s,'\r\n');   end
   end
end
figure,imshow(img);
fclose(s);

2、EdgeSobel的Verilog源代码:
`timescale 1ns / 1ps

module EdgeSobel
   (
   input clk,
   input [7:0] inData,
   input [11:0]x,
   input [11:0]y,
   output [7:0] outData
   );    
   parameter pixel_depth=8;
   parameter frame_width=640;
   parameter block_width=3;
   parameter block_height=3;

   parameter shiftRegSize=pixel_depth*((block_height-1)*frame_width+block_width);

   reg[shiftRegSize-1:0] shiftReg;
   wire [block_width*block_height*pixel_depth-1:0] Window;  

   initial begin shiftReg=10264'b0;end

   always@(posedge clk)if((x<640)&&(y<480))shiftReg<={shiftReg,inData};

   genvar i,j;
   generate
   for(i = 0; i < block_height; i = i + 1) begin : array
     for(j = 0; j < block_width; j = j + 1) begin : vector
        assign Window[pixel_depth*(i * block_width + j)+:pixel_depth] =shiftReg[pixel_depth*(i*frame_width+j)+:pixel_depth];
     end
   end
   endgenerate

   wire [7:0] average;
   assign average =
                   (Window[7:0]+Window[15:8]+Window[23:16]+
                    //Window[31:24]+Window[39:32]+Window[47:40]+
                    Window[31:24]+Window[39:32]+Window[47:40]+
                    Window[55:48]+Window[63:56]+Window[71:64])/9 ;

   wire signed [pixel_depth+1:0] Gx;
   wire signed [pixel_depth+1:0] Gy;
   wire [pixel_depth+1:0] Gxabs;
   wire [pixel_depth+1:0] Gyabs;
   wire [pixel_depth+1:0] G;

   assign Gx =   shiftReg[pixel_depth*(0*frame_width+2)+:pixel_depth]
              +2*shiftReg[pixel_depth*(1*frame_width+2)+:pixel_depth]
              +  shiftReg[pixel_depth*(2*frame_width+2)+:pixel_depth]
              -  shiftReg[pixel_depth*(0*frame_width+0)+:pixel_depth]
              -2*shiftReg[pixel_depth*(1*frame_width+0)+:pixel_depth]
              -  shiftReg[pixel_depth*(2*frame_width+0)+:pixel_depth];
   assign Gy =   shiftReg[pixel_depth*(2*frame_width+0)+:pixel_depth]
              +2*shiftReg[pixel_depth*(2*frame_width+1)+:pixel_depth]
              +  shiftReg[pixel_depth*(2*frame_width+2)+:pixel_depth]
              -  shiftReg[pixel_depth*(0*frame_width+0)+:pixel_depth]
              -2*shiftReg[pixel_depth*(0*frame_width+1)+:pixel_depth]
              -  shiftReg[pixel_depth*(0*frame_width+2)+:pixel_depth];              
   assign Gxabs = (Gx>0)?Gx-Gx);
   assign Gyabs = (Gy>0)?Gy-Gy);
   assign G = Gxabs+Gyabs;

   //assign outData = average;    //平滑
   assign outData = G[9:2];     //边缘检测
endmodule

3、仿真文件:tb_EdgeSobel.v
`timescale 1ns / 1ps

module tb_edgesobel;

   reg clk;
   reg [7:0]  inData;
   reg [19:0] cnt;
   reg [9:0] row;
   wire [7:0] outData;
   reg [7:0] image [307199:0];
   integer file_id;
   reg [4:0] frame_cnt;


   initial
   begin
       $readmemh("E:/matlab/Vivado/image2mem.txt", image);
       file_id = $fopen("E:/matlab/Vivado/mem2image.txt","w");
       clk = 0;
       cnt = 0;
       row = 0;
       frame_cnt = 0;
   end

   EdgeSobel u_2
   (
   .clk(clk),
   .x(1),
   .y(1),
   .inData(inData),
   .outData(outData)
   );

   always #1 clk = ~clk;

   always@(posedge clk)
   begin
       if(cnt == 307200)    
       begin
           cnt = 0;
           row = 0;
           frame_cnt = frame_cnt + 1;
       end    
       else
       inData = image[cnt];
       cnt = cnt+1;
       if(frame_cnt==1)
           begin
               $fwrite(file_id, "%d ", outData);
               if(((cnt % 640)==0) &&(cnt>0))
               begin
                   $fwrite(file_id,"\r\n");
                   row = row + 1;
               end;
           end
   end
endmodule

4、把输出的txt文件转化成图片Matlab程序:
A=importdata('E:\matlab\Vivado\mem2image.txt');
A=A./255;
imshow(A);

注意这里的A是double类型的,直接进行imshow会全白,要转化到0-1:A=A./255,或者把double类型转化为整形。

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分