基于STM32車牌識別程序
完整源碼下載:
程序.zip
(7.41 MB, 下載次數: 729)
2016-12-14 22:06 上傳
點擊文件名下載附件
主程序預覽:
- #include "stm32f10x.h"
- #include "stm32f10x_it.h"
- #include "led.h"
- #include "key.h"
- #include "usart.h"
- #include "delay.h"
- #include "lcd.h"
- #include "ov7670.h"
- #include "string.h"
- TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
- u8 cur_status;
- u8 LED_flag;
- u32 a;
- u32 b;
- u16 AA,BB;
- u16 color;
- u16 color_save;//保存一個像素的值
- u8 R,G,B;//顏色分量
- u8 TableChangePoint_240[240];//跳變點240個
- u8 Max_ChangePoint_240,Min_ChangePoint_240,Max_bChangePoint,Min_bChangePoint;//跳變點縱軸始、末坐標,跳變點橫軸始、末坐標
- u8 a_Continue,b_Continue;//記錄縱、橫軸突變點的連續性
- u8 flag_aMax;//末值更新標志
- u8 Max_aChangePoint_reset,Min_aChangePoint_reset;//修正后的上下限
- u16 Length_card,Width_card;//車牌的長和寬
- u8 Max_aChangePoint_reset_1,Min_aChangePoint_reset_1;//保存上次的數據
- u8 flag_MaxMinCompare;//Max_aChangePoint_reset_1和Max_aChangePoint_reset的標志
- u8 TableChangePoint_320[320];//縱向跳變點320個
- float V,S,H;//定義HSV值
- u16 Min_blue;
- u16 Max_blue;//定義車牌藍色區域的橫向最大值和最小值
- u16 k1,kk1,k2,kk2,k3,kk3,k4,kk4,k5,kk5,k6,kk6,k7,kk7,k8,kk8;//八個字符邊界
- extern u8 Table[6300];//所有字符集 (10+26)*150 = 5400 字節
- extern u8 talble_0[150];//字符3,測試用
- extern u8 table_yu[32];//渝字
- extern u8 table_min[32];//閩字
- extern u8 table_lu[32];//魯字
- extern u8 table_zhe[32];//浙字
- extern u8 table_shan[32];//陜字
- extern u8 table_cuan[32];//川字
- u8 R_a,G_a,B_a;//閾值
- u8 table_picture[150];//定義保存圖片的數組
- u8 table_char[36]={0,1,2,3,4,5,6,7,8,9,'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z',};
- u8 table_card[5][8]={ //保存5個車牌的二維數組
- {0,0,0,0,0,0,0,0}, //最后一位保存時間
- {0,0,0,0,0,0,0,0},
- {0,0,0,0,0,0,0,0},
- {0,0,0,0,0,0,0,0},
- {0,0,0,0,0,0,0,0},
- };
- u8 tim3_num;//TIM3分鐘計時
- u8 table_cardMeasure[7];//測量的車牌結果
- void Show_Card(u8 i);//顯示第幾組車牌
- void Show_Title();//顯示標題
- void MYRCC_DeInit(void)//復位并配置向量表
- {
- NVIC_InitTypeDef NVIC_InitStructure;
- RCC->APB1RSTR = 0x00000000;//復位結束
- RCC->APB2RSTR = 0x00000000;
-
- RCC->AHBENR = 0x00000014; //睡眠模式閃存和SRAM時鐘使能.其他關閉.
- RCC->APB2ENR = 0x00000000; //外設時鐘關閉.
- RCC->APB1ENR = 0x00000000;
- RCC->CR |= 0x00000001; //使能內部高速時鐘HSION
- RCC->CFGR &= 0xF8FF0000; //復位SW[1:0],HPRE[3:0],PPRE1[2:0],PPRE2[2:0],ADCPRE[1:0],MCO[2:0]
- RCC->CR &= 0xFEF6FFFF; //復位HSEON,CSSON,PLLON
- RCC->CR &= 0xFFFBFFFF; //復位HSEBYP
- RCC->CFGR &= 0xFF80FFFF; //復位PLLSRC, PLLXTPRE, PLLMUL[3:0] and USBPRE
- RCC->CIR = 0x00000000; //關閉所有中斷
- /* Enable the TIM3 global Interrupt */
- NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn; //TIM3中斷
- NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; //先占優先級0級
- NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //從優先級3級
- NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能
- NVIC_Init(&NVIC_InitStructure); //根據NVIC_InitStruct中指定的參數初始化外設NVIC寄存器
- }
- void Stm32_Clock_Init(u8 PLL)//系統時鐘初始化函數 pll:選擇的倍頻數,從2開始,最大值為16
- {
- unsigned char temp=0;
- MYRCC_DeInit(); //復位并配置向量表
- RCC->CR|=0x00010000; //外部高速時鐘使能HSEON
- while(!(RCC->CR>>17));//等待外部時鐘就緒
- RCC->CFGR=0X00000400; //APB1=DIV2;APB2=DIV1;AHB=DIV1;
- PLL-=2;//抵消2個單位
- RCC->CFGR|=PLL<<18; //設置PLL值 2~16
- RCC->CFGR|=1<<16; //PLLSRC ON
- FLASH->ACR|=0x32; //FLASH 2個延時周期
- RCC->CR|=0x01000000; //PLLON
- while(!(RCC->CR>>25));//等待PLL鎖定
- RCC->CFGR|=0x00000002;//PLL作為系統時鐘
- while(temp!=0x02) //等待PLL作為系統時鐘設置成功
- {
- temp=RCC->CFGR>>2;
- temp&=0x03;
- }
- }
- void LED()//LED指示燈-提示
- {
- GPIO_WriteBit(LED1_GPIO_PORT, LED1_GPIO_PIN,LED_flag>>7);
- LED_flag=~LED_flag;
- }
- void Data_LCD_Display()//常規顯示
- {
- LCD_SetWindows(0,0,320,240);//設置顯示窗口
- GPIO_WriteBit(LCD_RS_PORT, LCD_RS_PIN,1);//標志:數據寫入
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 0);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 1);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==0);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 0);
-
- FIFO_Reset_Read_Addr();
- // LED();
-
- for (a=0;a<240;a++)
- {
- for(b=0;b<320;b++)
- {
- GPIOC->BRR =1<<4;
- AA=GPIOA->IDR;
- GPIOC->BSRR =1<<4;
-
- GPIOC->BRR =1<<4;
- BB=GPIOA->IDR&0x00ff;
- GPIOC->BSRR =1<<4;
-
- color=(AA<<8)|BB;
-
- LCD_DATA_PORT->ODR = color;
- GPIOC->BRR =1<<11;
- GPIOC->BSRR =1<<11;
- }
- }
- }
- void RGB_HSV(u16 num)//RGB565轉HSV
- {
- float max,min;
- u8 r,g,b;
- r=(num>>11)*255/31;g=((num>>5)&0x3f)*255/63;b=(num&0x1f)*255/31;
-
- max=r;min=r;
- if(g>=max)max=g;
- if(b>=max)max=b;
- if(g<=min)min=g;
- if(b<=min)min=b;
-
- V=100*max/255;//轉換為百分比
- S=100*(max-min)/max;//擴大100倍顯示
- if(max==r) H=(g-b)/(max-min)*60;
- if(max==g) H=120+(b-r)/(max-min)*60;
- if(max==b) H=240+(r-g)/(max-min)*60;
- if(H<0) H=H+360;
- }
- void Data_LCD_ColorDisplay()//單色像素顯示、測量
- {
- LCD_SetWindows(0,0,320,240);//設置顯示窗口
- GPIO_WriteBit(LCD_RS_PORT, LCD_RS_PIN,1);//標志:數據寫入
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 0);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 1);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==0);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 0);
-
- FIFO_Reset_Read_Addr();
- // LED();
-
- for (a=0;a<240;a++)
- {
- for(b=0;b<320;b++)
- {
- GPIOC->BRR =1<<4;
- AA=GPIOA->IDR;
- GPIOC->BSRR =1<<4;
-
- GPIOC->BRR =1<<4;
- BB=GPIOA->IDR&0x00ff;
- GPIOC->BSRR =1<<4;
-
- color=(AA<<8)|BB;
-
- // if(a==100&&b==100)
- // {
- // R=color>>11;
- // G=(color>>5)&0x3f;
- // B=color&0x1f;
- //
- // color_save=color;
- // }
- // //像素點測試,位置指示
- // if(a==99&&b==100)
- // {
- // color=0xf800;
- // }
- // if(a==101&&b==100)
- // {
- // color=0xf800;
- // }
- // if(a==100&&b==99)
- // {
- // color=0xf800;
- // }
- // if(a==100&&b==101)
- // {
- // color=0xf800;
- // }
- if(a==100&&b==250)
- {
- R=color>>11;
- G=(color>>5)&0x3f;
- B=color&0x1f;
-
- color_save=color;
- }
- //像素點測試,位置指示
- if(a==100&&b==249)
- {
- color=0xf800;
- }
- if(a==100&&b==251)
- {
- color=0xf800;
- }
- if(a==99&&b==250)
- {
- color=0xf800;
- }
- if(a==101&&b==250)
- {
- color=0xf800;
- }
- LCD_DATA_PORT->ODR = color;
- GPIOC->BRR =1<<11;
- GPIOC->BSRR =1<<11;
- }
- }
- RGB_HSV(color_save);//RGB565轉HSV
- LCD_ShowChar(30,200,'H',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(30,220,H,3);//X坐標,Y坐標,數字,幾位數
- LCD_ShowChar(60,200,'S',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(60,220,S,3);//X坐標,Y坐標,數字,幾位數
- LCD_ShowChar(90,200,'V',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(90,220,V,3);//X坐標,Y坐標,數字,幾位數
- //顯示測定的像素
- LCD_ShowChar(160,200,'R',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(160,220,R,2);//X坐標,Y坐標,數字,幾位數
- LCD_ShowChar(190,200,'G',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(190,220,G,2);//X坐標,Y坐標,數字,幾位數
- LCD_ShowChar(220,200,'B',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(220,220,B,2);//X坐標,Y坐標,數字,幾位數
- for(a=0;a<30;a++)//劃線
- {
- for(b=0;b<30;b++)//劃線
- {
- LCD_DrawPoint(a+300,b+200,(R<<11)|(G<<5)|B);
- }
- }
- }
- void Picture_String()//圖片->數組table_picture 有個BUG,先放著吧
- {
- u16 a,b,num1;
- for(a=0;a<150;a++)//歸零
- {
- table_picture[a]=0x00;
- }
- for(a=0;a<50;a++)//50排
- {
- for(b=0;b<24;b++)//24行
- {
- num1=LCD_ReadPoint(b+296,a+191);
- if(num1==0xffff)
- {
- table_picture[b/8+a*3]|=(1<<(7-b%8));
- }
- }
- }
- }
- void String_Picture_All()//總數組->圖片
- {
- u16 a,b,e,i,num1;
- for(a=0;a<42;a++)//36
- {
- for(e=0;e<50;e++)//50排
- {
- for(i=0;i<24;i++)//24行
- {
- if(Table[150*a+i/8+e*3]&(1<<(7-i%8)))
- {
- num1=0xffff;
- }
- else
- {
- num1=0x0000;
- }
- LCD_DrawPoint(i+296,e+191,num1);//畫點
- }
- }
- delay_ms(500);
- }
- }
- u8 MoShiShiBie_All(u8 begin,u8 end)//字符匹配,模式識別,選擇性匹配begin-end
- {
- u16 Compare_num,num_save;
- u8 a,b,e,a_save,st1,st2,s1,s2;
- int num1;
- for(a=begin;a<end;a++) //36
- {
- num1=0;
- for(b=0;b<150;b++)
- {
- st1=table_picture[b];
- st2=Table[150*a+b];
- for(e=0;e<8;e++)
- {
- s1=st1&(1<<e);
- s2=st2&(1<<e);
- if(s1==s2) num1++;
- if(s1!=s2) num1--;
- }
- }
- if(num_save<num1)
- {
- num_save=num1;
- a_save=a;
- }
- LCD_ShowNum(50,220,a,2);//顯示匹配的字符是"a" <調試用>
- LCD_ShowNum(70,220,num1,4);//顯示匹配的正確像素數
- LCD_ShowNum(120,220,num_save,4);//匹配的最大值顯示
- }
- return a_save;
- }
- void String_Picture()//數組->圖片
- {
- u16 a,b,e,num1;
-
- for(a=0;a<50;a++)//50排
- {
- for(b=0;b<24;b++)//24行
- {
- if(talble_0[b/8+a*3]&(1<<(7-b%8)))
- {
- num1=0xffff;
- }
- else
- {
- num1=0x0000;
- }
- LCD_DrawPoint(b+296,a+191,num1);//畫點
- }
- }
- }
- void WordShow(u8 num,u16 x,u16 y)//顯示漢字16*16
- {
- u16 a,b,e,num1;
- u8 table1[32];
- if(num==1)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_yu[a];
- }
- }
- if(num==2)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_min[a];
- }
- }
- if(num==3)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_lu[a];
- }
- }
- if(num==4)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_zhe[a];
- }
- }
- if(num==5)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_shan[a];
- }
- }
- if(num==6)
- {
- for(a=0;a<32;a++)
- {
- table1[a]=table_cuan[a];
- }
- }
- for(a=0;a<16;a++)
- {
- for(b=0;b<16;b++)
- {
- if(table1[b/8+a*2]&(1<<(7-b%8)))
- {
- num1=0xffff;
- }
- else
- {
- num1=0x0000;
- }
- LCD_DrawPoint(b+x,a+y,num1);//畫點
- }
- }
- }
- u8 ZhiFuFenGe()//字符分割,返回分割的字符個數,用于判斷合法性
- {
- u16 a,b;
- u8 i;//統計分割的字符個數,不為9說明分割有誤
- i=0;//必須置0一下,不然會有錯
- for(b=Max_blue;b>Min_blue;b--)
- {
- if(TableChangePoint_320[b]==0)//間隙分割
- {
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)//劃線--調試用
- {
- LCD_DrawPoint(b,a+1,0x001f);
- }
- i++;b--;
- while(TableChangePoint_320[b]==0)
- {
- b--;
- if(b<=Min_blue) break;
- }
- }
- }
- i--;
- LCD_ShowNum(30,220,i,2);//顯示分割的字符個數+1,8是正常值
- return i;
- }
- void GuiYi(u16 k,u16 kk)//歸一化 25*50
- {
- u16 a,b,e;
- u16 num;//保存讀取像素
- u8 Mo,Yu;//取整和取模
- u8 num1,num2,num3;
- u8 Mo_1;//
- u8 Min_240,Max_240;//框緊字符后的上下限
-
- if((k-kk)<25)
- {
- //框緊字符
- Min_240=Min_ChangePoint_240+1;
- Max_240=Max_ChangePoint_240-1;
- while(Min_240++)//框緊后,得到: Min_240
- {
- for(b=kk+1;b<k;b++)//kk1→k1
- {
- num=LCD_ReadPoint(b,Min_240);
- if(num) break;
- }
- if(num) break;
- }
- while(Max_240--)//框緊后,得到: Max_240
- {
- for(b=kk+1;b<k;b++)//kk1→k1
- {
- num=LCD_ReadPoint(b,Max_240);
- if(num) break;
- }
- if(num) break;
- }
- Min_240-=1;
- Max_240+=2;
- LCD_DrawPoint(kk,Min_240,0xffff);//
- LCD_DrawPoint( k,Max_240,0xffff);//
- //顯示復制的圖片
- num3=0;
- for(a=Min_240+1;a<Max_240;a++)
- {
- num2=0;
- for(b=kk+1;b<k;b++)//kk1→k1 +1
- {
- num=LCD_ReadPoint(b,a);
- LCD_DrawPoint(271-(k-kk-1)+num2,191+num3,num);//復制像素值
- num2++;
- }
- num3++;
- }
- num3=0;
- Mo=(24-(k-kk-1))/(k-kk-1);//取模
- Yu=(24-(k-kk-1))%(k-kk-1);//取余
- if(Yu!=0)
- {
- Mo_1=24/Yu;//平均Mo_1個像素,插有一個像素,機7+1
- }
- // LCD_ShowNum(30,20,Mo,3);//顯示模 <調試用>
- // LCD_ShowNum(70,20,Yu,3);//顯示余
- // LCD_ShowNum(100,20,(k1-kk1),3);//顯示差值
- for(a=Min_240+1;a<Max_240;a++)//寬放大為25像素 =??
- {//↓
- num2=0;
- Yu=(24-(k-kk-1))%(k-kk-1);//取余
-
- for(b=kk+1;b<k;b++)//kk1→k1 +1
- {
- num=LCD_ReadPoint(b,a);
- LCD_DrawPoint(271+num2,191+num3,num);
- num2++;
- Mo=(24-(k-kk-1))/(k-kk-1);//取模
- while(Mo)
- {
- LCD_DrawPoint(271+num2,191+num3,num);
- Mo--;
- num2++;
- }
- if(Yu!=0)//橫軸拉長
- {
- if(((num2+1)%Mo_1==0) && (num2!=1))//改插入的地方7+1
- {
- LCD_DrawPoint(271+num2,191+num3,num);
- Yu--;
- num2++;
- }
- }
- }
- num3++;
- }
- LCD_DrawPoint(271,191,0x07E0);//標記點,4個頂角
- LCD_DrawPoint(271,240,0x07E0);
- LCD_DrawPoint(295,191,0x07E0);
- LCD_DrawPoint(295,240,0x07E0);
- //縱軸拉長
- if((Max_240-Min_240)<50)
- {
- Mo=(50-(Max_240-Min_240+1))/(Max_240-Min_240+1);//取模
- Yu=(50-(Max_240-Min_240+1))%(Max_240-Min_240+1);//取余
- Mo_1=50/Yu;
-
- // LCD_ShowNum(30,170,Mo,3);// <調試用>
- // LCD_ShowNum(70,170,Yu,3);//
- // LCD_ShowNum(100,170,Max_ChangePoint_240-Min_ChangePoint_240,3);//
- num2=0;
- for(a=0;a<(Max_240-Min_240);a++)//復制圖像,考慮范圍是否需要進行修正?
- {//↓
- for(b=271;b<=295;b++)//271開始復制,295才結束
- {
- num=LCD_ReadPoint(b,a+191);
- LCD_DrawPoint(b+25,191+num2,num);//復制像素值
- }
- num2++;
- while(Mo)
- {
- for(b=271;b<=295;b++)//271開始復制,295才結束
- {
- num=LCD_ReadPoint(b,a+191);
- LCD_DrawPoint(b+25,191+num2+a,num);//復制像素值
- }
- Mo--;
- num2++;
- }
- if(Yu!=0)
- {
- if((((num2+1) % Mo_1)==0)&& (num2!=1))
- {
- for(b=271;b<=295;b++)//271開始復制,295才結束
- {
- num=LCD_ReadPoint(b,a+191);
- LCD_DrawPoint(b+25,191+num2,num);//復制像素值
- }
- Yu--;
- num2++;
- }
- }
- }
- }
- LCD_DrawPoint(320,191,0xf800);//標記點,1個頂角
- }
- }
- void ZhiFuShiBie()//字符識別
- {
- u16 a,b,e;
- u16 i,u;
- u8 Result;//識別結果
- for(b=Max_blue-1;b>Min_blue;b--)//由右至左識別,獲取各個字符的k,kK值
- {
- while(TableChangePoint_320[b]==0) b--;//取第1個字符
- k1=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk1=b;
- if((k1-kk1)<4)//省略低于三個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k1=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk1=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第2個字符
- k2=b+1;
- while(TableChangePoint_320[b]>0) b--;
- kk2=b;
- if((k2-kk2)<4)//省略低于3個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k2=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk2=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第3個字符
- k3=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk3=b;
- if((k3-kk3)<4)//省略低于3個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k3=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk3=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第4個字符
- k4=b+1;
- while(TableChangePoint_320[b]>0) b--;
- kk4=b;
- if((k4-kk4)<4)//省略低于3個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k4=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk4=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第5個字符
- k5=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk5=b;
- if((k5-kk5)<4)//省略低于3個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k5=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk5=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第6個字符
- k6=b+1;
- while(TableChangePoint_320[b]>0) b--;
- kk6=b;
- while(TableChangePoint_320[b]==0) b--;//取第7個字符
- k7=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk7=b;
- if((k7-kk7)<4)//省略低于3個像素的位置
- {
- while(TableChangePoint_320[b]==0) b--;//
- k7=b+1;//+1
- while(TableChangePoint_320[b]>0) b--;
- kk7=b;
- }
- while(TableChangePoint_320[b]==0) b--;//取第8個字符
- k8=b+1;
- while(TableChangePoint_320[b]>0)
- {
- if(b<=Min_blue)
- {
- break;
- }
- b--;
- }
- kk8=b;
- b=Min_blue;//以防萬一,還滿足for循環條件
- }
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)//劃線
- {
- LCD_DrawPoint(k1,a+1,0x001f);
- LCD_DrawPoint(kk1,a+1,0x001f);
- LCD_DrawPoint(k2,a+1,0x001f);
- LCD_DrawPoint(kk2,a+1,0x001f);
- LCD_DrawPoint(k3,a+1,0x001f);
- LCD_DrawPoint(kk3,a+1,0x001f);
- LCD_DrawPoint(k4,a+1,0x001f);
- LCD_DrawPoint(kk4,a+1,0x001f);
- LCD_DrawPoint(k5,a+1,0x001f);
- LCD_DrawPoint(kk5,a+1,0x001f);
- LCD_DrawPoint(k6,a+1,0x001f);
- LCD_DrawPoint(kk6,a+1,0x001f);
- LCD_DrawPoint(k7,a+1,0x001f);
- LCD_DrawPoint(kk7,a+1,0x001f);
- LCD_DrawPoint(k8,a+1,0x001f);
- LCD_DrawPoint(kk8,a+1,0x001f);
- }
- //歸一化處理:大小為25*50
-
- //第1個字符:
- GuiYi(k1,kk1);//歸一化 24*24
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(0,36);//字符匹配,模式識別,返回a,0<= a <36
- if(Result<10)
- {
- LCD_ShowNum(240,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(240,220,table_char[Result],0);
- }
- table_cardMeasure[6]=Result;//保存識別的車牌結果
-
- //第2個字符:
- GuiYi(k2,kk2);//歸一化 25*50
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(0,36);//字符匹配,模式識別
- if(Result<10)
- {
- LCD_ShowNum(230,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(230,220,table_char[Result],0);
- }
- table_cardMeasure[5]=Result;//保存識別的車牌結果
-
- GuiYi(k3,kk3);//歸一化 25*50
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(0,36);//字符匹配,模式識別
- if(Result<10)
- {
- LCD_ShowNum(220,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(220,220,table_char[Result],0);
- }
- table_cardMeasure[4]=Result;//保存識別的車牌結果
-
- GuiYi(k4,kk4);//歸一化 25*50
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(0,36);//字符匹配,模式識別
- if(Result<10)
- {
- LCD_ShowNum(210,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(210,220,table_char[Result],0);
- }
- table_cardMeasure[3]=Result;//保存識別的車牌結果
-
- GuiYi(k5,kk5);//歸一化 25*50
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(0,36);//字符匹配,模式識別
- if(Result<10)
- {
- LCD_ShowNum(200,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(200,220,table_char[Result],0);
- }
- table_cardMeasure[2]=Result;//保存識別的車牌結果
- LCD_ShowChar(190,220,'.',0);
- GuiYi(k7,kk7);//歸一化 25*50
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(10,36);//字符匹配,模式識別,只匹配字母
- if(Result<10)
- {
- LCD_ShowNum(180,220,table_char[Result],1);
- }
- else
- {
- LCD_ShowChar(180,220,table_char[Result],0);
- }
- table_cardMeasure[1]=Result;//保存識別的車牌結果
-
- GuiYi(k8,kk8);//歸一化 25*50 最后一個漢字,不做識別
- Picture_String();//圖片->數組
- Result=MoShiShiBie_All(36,42);//字符匹配,匹配漢字
- WordShow(Result-35,160,220);//顯示漢字
- table_cardMeasure[0]=Result-35;//保存識別的車牌結果
- //識別結束
- // while(1);
- //先匹配已保存的車牌號
- for(u=0;u<5;u++)
- {
- for(i=0;i<7;i++)
- {
- if(table_card[u][i]!=table_cardMeasure[i]) i=8;//退出for循環
-
- }
- if(i==7)//匹配成功
- {
- LCD_Fill(0x00);//黑屏
- Show_Title();//顯示標題
- Show_Card(u);//顯示第幾組車牌
- delay_ms(15000);
- u=5;
- }
- }
- if(i==9)//無匹配車牌,則保存車牌
- {
- i=0;
- while(1)
- {
- if(GPIO_ReadInputDataBit(KEY1_PORT,KEY1_PIN)==0) break;
- LCD_ShowNum(30,220,i/100,2);
- if(i==300) //保存數據
- {
- for(u=0;u<5;u++)
- {
- if(table_card[u][0]==0)
- {
- for(i=0;i<7;i++)
- {
- table_card[u][i]=table_cardMeasure[i];
- }
- u=5;//退出循環
- }
- }
- LCD_Fill(0x00);//黑屏
- Show_Title();//顯示標題
- Show_Card(0);//顯示第幾組車牌
- Show_Card(1);
- Show_Card(2);
- Show_Card(3);
- Show_Card(4);
- delay_ms(10000);
- break;
- }
- delay_ms(1);
- i++;
- }
- }
-
- }
- void Copy_Card()//復制車牌Max_aChangePoint_reset_1,Min_blue
- {
- u16 a,b,num;
- for(a=Min_aChangePoint_reset;a<=Max_aChangePoint_reset;a++)
- {
- for(b=Min_blue;b<Max_blue;b++)
- {
- num=LCD_ReadPoint(b,a);//讀取像素值
- LCD_DrawPoint(b,50+a,num);
- }
-
- }
- }
- void ChangePoint_Show_240()//240方向跳變點顯示
- {
- for(a=0;a<240;a++)//建立參考線10、20、30
- {
- LCD_DrawPoint(10,a,0x63<<5);//10
- LCD_DrawPoint(20,a,0x63<<5);//20
- LCD_DrawPoint(30,a,0x63<<5);//30
- }
-
- for(a=0;a<240;a++)//顯示對應的橫向跳變點
- {
- LCD_DrawPoint(TableChangePoint_240[a],a,0xf800);//跳變點顯示,紅色標記
- if(TableChangePoint_240[a]>=15) //跳變點個數(閾值)設定 閾值調節3-(1)
- {
- for(b=35;b<40;b++) //顯示達到閾值標準的點
- {
- LCD_DrawPoint(b,a,0x63<<5);//Green
- }
- }
- }
- }
- void ChangePoint_Analysis_240()//240跳變點分析
- {
- Min_ChangePoint_240=240;Max_ChangePoint_240=0;
-
- for(a=0;a<240;a++)//240掃描 ,獲取上下限值 :Min_ChangePoint_240,Max_ChangePoint_240
- {
- while(TableChangePoint_240[a]<=15) //閾值調節3-(2)
- {
- a++;
- }
- Min_ChangePoint_240=a;
- while(TableChangePoint_240[a]>15) //閾值調節3-(3)
- {
- a++;
- }
- Max_ChangePoint_240=a;
- if(Max_ChangePoint_240-Min_ChangePoint_240>=15) a=240;//連續性閾值 //閾值調節2-(1)
- }
- Min_ChangePoint_240=Min_ChangePoint_240-3;//向上微調3像素
- Max_ChangePoint_240=Max_ChangePoint_240+2;//向下微調2像素
- for(a=30;a<280;a++)//顯示上界限
- {
- LCD_DrawPoint(a,Max_ChangePoint_240,0x001f);
- }
- for(a=30;a<280;a++)//顯示下界限
- {
- LCD_DrawPoint(a,Min_ChangePoint_240,0x001f);
- }
- for(a=30;a<280;a++)//顯示50,參考50像素位置處,車牌位置不要超過這根線,免得不能字符的歸一化處理
- {
- LCD_DrawPoint(a,Min_ChangePoint_240+50,0xf800);
- }
- flag_MaxMinCompare=1;
- if(Min_ChangePoint_240>Max_ChangePoint_240)//判斷合法性1:最小值>最大值
- {
- flag_MaxMinCompare=0;
- }
- if(Min_ChangePoint_240==240||Max_ChangePoint_240==0)//判斷合法性2:值沒有重新賦值
- {
- flag_MaxMinCompare=0;
- }
- if(Max_ChangePoint_240-Min_ChangePoint_240<15) //判斷合法性3: //閾值調節2-(2)
- {
- flag_MaxMinCompare=0;
- }
- }
- void ChangePoint_Analysis_Blue()//320藍色區域分析,采用讀取像素,得結果Min_blue,Max_blue
- {
- u16 a,b,num_color;
- u16 min_320,max_320;//各行的最小、最大值
-
- Min_blue=0;Max_blue=320;
- min_320=320;max_320=0;
-
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)
- {
- for(b=30;b<290;b++)//不用到320 for(b=30;b<320;b++)
- {
- num_color=LCD_ReadPoint(b,a);//讀取像素,代碼優化速度有待提升 ?掃描方法也可優化,以提升速度
- RGB_HSV(num_color);//RGB565轉HSV
- if( 250>H && H>190 && 60>S && S>15 && 100>V && V>45)//HSV 閾值
- {
- if(b<min_320)//獲得橫軸的Min和Max值,即藍色車牌的左右邊界
- {
- min_320=b;
- }
- if(b>max_320)
- {
- max_320=b;
- }
- }
- }
- }
- Min_blue=min_320;//獲取各行的最大值//修正一點
- Max_blue=max_320-5;//獲取各行的最小值//修正一點
-
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)//顯示左界限
- {
- LCD_DrawPoint(Min_blue,a,0xf8);//LCD_DrawPoint(Min_blue,a,0xf800);
- }
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)//顯示右界限
- {
- LCD_DrawPoint(Max_blue,a,0xf800);
- }
- // delay_ms(6000);
- }
- void Card_101Show()//車牌區域二值化顯示
- {
- u16 a,b,num_color;
- u8 R1,G1,B1;
- u8 Mid_ChangePoint_240;
- u8 max_R,max_G,max_B,min_R,min_G,min_B;
- u8 mid_R,mid_G,mid_B;
-
- max_R=0;max_G=0;max_B=0;
- min_R=30;min_G=60;min_B=30;
-
- Mid_ChangePoint_240=(Min_ChangePoint_240+Max_ChangePoint_240)/2;
- for(b=Min_blue;b<Max_blue;b++)
- {
- num_color=LCD_ReadPoint(b,Mid_ChangePoint_240);//讀取像素,代碼優化速度有待提升 ?掃描方法也可優化,以提升速度
- R1=num_color>>11;
- G1=(num_color>>5)&0x3F;
- B1=num_color&0x1F;
- if( (R1>10) && (G1>25) && (B1>15) && (R1<=30) && (G1<=60) && (B1<=30) )//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- if(max_R<R1) max_R=R1;//獲得最大值和最小值
- if(max_G<G1) max_G=G1;
- if(max_B<B1) max_B=B1;
-
- if(min_R>R1) min_R=R1;
- if(min_G>G1) min_G=G1;
- if(min_B>B1) min_B=B1;
- }
- }
- mid_R=(max_R+min_R)/2;
- mid_G=(max_G+min_G)/2;
- mid_B=(max_B+ min_B)/2;
- // LCD_ShowNum(30,200,max_R,2);//X坐標,Y坐標,數字,幾位數 <調試用>
- // LCD_ShowNum(70,200,max_G,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(100,200,max_B,2);//X坐標,Y坐標,數字,幾位數
- //
- // LCD_ShowNum(30,220,min_R,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(70,220,min_G,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(100,220,min_B,2);//X坐標,Y坐標,數字,幾位數
-
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)
- {
- for(b=Min_blue;b<Max_blue;b++)
- {
- num_color=LCD_ReadPoint(b,a);//讀取像素,代碼優化速度有待提升 ?掃描方法也可優化,以提升速度
- R1=num_color>>11;
- G1=(num_color>>5)&0x3F;
- B1=num_color&0x1F;
- if((R1>=mid_R) && (G1>=mid_G) && (B1>=mid_B))//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- LCD_DrawPoint(b,a,0xffff);
- }
- else
- {
- LCD_DrawPoint(b,a,0x0000);
- }
- }
- }
- delay_ms(20000);
- }
- void ChangePoint_Show_320()//320方向跳變點顯示
- {
- for(a=0;a<320;a++)//顯示對應的橫向跳變點
- {
- if(TableChangePoint_320[a]==0)
- {
- LCD_DrawPoint(a,0,0x001F);//跳變點顯示,紅色標記
- }
- else
- {
- LCD_DrawPoint(a,TableChangePoint_320[a],0xf800);//跳變點顯示,紅色標記
- }
-
- }
- }
- void ChangePoint_Analysis_320()//藍色區域中,320跳變點分析,獲得TableChangePoint_320[b]結果
- { //(先二值化,再判斷白點個數,=0則是分割線)
- u16 a,b,num_color;
- u8 R1,G1,B1;
- u8 Mid_ChangePoint_240;
- u8 max_R,max_G,max_B,min_R,min_G,min_B;
- u8 mid_R,mid_G,mid_B;
-
- max_R=0;max_G=0;max_B=0;
- min_R=30;min_G=60;min_B=30;
-
- Mid_ChangePoint_240=(Min_ChangePoint_240+Max_ChangePoint_240)/2;
- for(b=Min_blue;b<Max_blue;b++)
- {
- num_color=LCD_ReadPoint(b,Mid_ChangePoint_240);//讀取像素,代碼優化速度有待提升 ?掃描方法也可優化,以提升速度
- R1=num_color>>11;
- G1=(num_color>>5)&0x3F;
- B1=num_color&0x1F;
- if( (R1>10) && (G1>25) && (B1>15) && (R1<=30) && (G1<=60) && (B1<=30) )//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- if(max_R<R1) max_R=R1;//獲得最大值和最小值
- if(max_G<G1) max_G=G1;
- if(max_B<B1) max_B=B1;
-
- if(min_R>R1) min_R=R1;
- if(min_G>G1) min_G=G1;
- if(min_B>B1) min_B=B1;
- }
- }
- mid_R=(max_R+min_R)/2;
- mid_G=(max_G+min_G)/2;
- mid_B=(max_B+ min_B)/2;
- // LCD_ShowNum(30,200,max_R,2);//X坐標,Y坐標,數字,幾位數 <調試用>
- // LCD_ShowNum(70,200,max_G,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(100,200,max_B,2);//X坐標,Y坐標,數字,幾位數
- //
- // LCD_ShowNum(30,220,min_R,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(70,220,min_G,2);//X坐標,Y坐標,數字,幾位數
- // LCD_ShowNum(100,220,min_B,2);//X坐標,Y坐標,數字,幾位數
- for(b=0;b<320;b++)//各行跳變點計數,數組清零
- {
- TableChangePoint_320[b]=0;
- }
- for(a=Min_ChangePoint_240;a<Max_ChangePoint_240;a++)
- {
- for(b=Min_blue+1;b<Max_blue;b++)
- {
- num_color=LCD_ReadPoint(b,a);//讀取像素,代碼優化速度有待提升 ?掃描方法也可優化,以提升速度
- R1=num_color>>11;
- G1=(num_color>>5)&0x3F;
- B1=num_color&0x1F;
- if((R1>=mid_R) && (G1>=mid_G) && (B1>=mid_B))//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- LCD_DrawPoint(b,a,0xffff);
- TableChangePoint_320[b]++;//白色,跳變點+1
- }
- else
- {
- LCD_DrawPoint(b,a,0x0000);
- }
- }
- }
- }
- void Data_LCD_ColorChange()//攝像頭掃描
- {
- u8 i;
- for(a=0;a<240;a++)//各行跳變點計數,數組清零
- {
- TableChangePoint_240[a]=0;
- }
- Min_blue=320;//初始化記錄藍色車牌區域的值
- Max_blue=0;
-
- LCD_SetWindows(0,0,320,240);//設置顯示窗口
- GPIO_WriteBit(LCD_RS_PORT, LCD_RS_PIN,1);//標志:數據寫入
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 0);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 1);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==0);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 0);
-
- FIFO_Reset_Read_Addr();
- // LED();
-
- for (a=0;a<240;a++)
- {
- for(b=0;b<320;b++)
- {
- GPIOC->BRR =1<<4;
- AA=GPIOA->IDR;
- GPIOC->BSRR =1<<4;
-
- GPIOC->BRR =1<<4;
- BB=GPIOA->IDR&0x00ff;
- GPIOC->BSRR =1<<4;
-
- color=(AA<<8)|BB;
- R=color>>11;
- G=(color>>5)&0x3f;
- B=color&0x1f;
-
- if((R>R_a) && (G>=G_a) && (B>=B_a))//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- color=0xffff;
- }
- else
- {
- color=0x0000;
- }
-
- if(color!=color_save)//跳變點
- {
- TableChangePoint_240[a]++; //該行跳變點計數+1
- }
- color_save=color;//保存像素值,供下一次判斷和比較
-
- color=(AA<<8)|BB;//還原色彩
-
- LCD_DATA_PORT->ODR = color;
- GPIOC->BRR =1<<11;
- GPIOC->BSRR =1<<11;
- }
- }
-
- ChangePoint_Show_240();//240方向跳變點顯示
- ChangePoint_Analysis_240(); //跳變點分析
- //返回flag_MaxMinCompare,Min_ChangePoint_240,Max_ChangePoint_240
- if(flag_MaxMinCompare==1)//跳變點篩選成功
- {
- ChangePoint_Analysis_Blue();//320藍色區域分析,采用讀取像素,得結果Min_blue,Max_blue
- if(Min_blue>Max_blue) flag_MaxMinCompare=0;//進行合理性判斷1
- if((Min_blue>290)||(Max_blue>290)) flag_MaxMinCompare=0;//進行合理性判斷2
- }
- if(flag_MaxMinCompare==1)//跳變點篩選成功
- {
- // ChangePoint_Analysis_Blue();//320藍色區域分析,采用讀取像素,得結果Min_blue,Max_blue
- // Card_101Show();//車牌區域二值化顯示
- ChangePoint_Analysis_320();//藍色區域中,320跳變點分析,獲得:TableChangePoint_320[b]結果
- ChangePoint_Show_320();//320方向跳變點顯示
- i=ZhiFuFenGe();
-
- if(i==8)//字符分割,返回分割的字符個數,用于判斷合法性
- {
- ZhiFuShiBie();//字符識別
- }
- else
- {
- LCD_Fill(0x6666);//黑屏,顯示Measure Faill
- LCD_ShowChar(8*1,200,'M',0);
- LCD_ShowChar(8*2,200,'e',0);
- LCD_ShowChar(8*3,200,'a',0);
- LCD_ShowChar(8*4,200,'s',0);
- LCD_ShowChar(8*5,200,'u',0);
- LCD_ShowChar(8*6,200,'r',0);
- LCD_ShowChar(8*7,200,'e',0);
-
- LCD_ShowChar(8*9,200,'F',0);
- LCD_ShowChar(8*10,200,'a',0);
- LCD_ShowChar(8*11,200,'i',0);
- LCD_ShowChar(8*12,200,'l',0);
- LCD_ShowChar(8*13,200,'l',0);
- delay_ms(800);
- }
- }
- }
- void Data_LCD_ColorChange_Test()//攝像頭掃描測試
- {
- for(a=0;a<240;a++)//各行跳變點計數,數組清零
- {
- TableChangePoint_240[a]=0;
- }
- Min_blue=320;//初始化記錄藍色車牌區域的值
- Max_blue=0;
-
- LCD_SetWindows(0,0,320,240);//設置顯示窗口
- GPIO_WriteBit(LCD_RS_PORT, LCD_RS_PIN,1);//標志:數據寫入
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 0);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 1);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==0);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 0);
-
- FIFO_Reset_Read_Addr();
- // LED();
-
- for (a=0;a<240;a++)
- {
- for(b=0;b<320;b++)
- {
- GPIOC->BRR =1<<4;
- AA=GPIOA->IDR;
- GPIOC->BSRR =1<<4;
-
- GPIOC->BRR =1<<4;
- BB=GPIOA->IDR&0x00ff;
- GPIOC->BSRR =1<<4;
-
- color=(AA<<8)|BB;
- R=color>>11;
- G=(color>>5)&0x3f;
- B=color&0x1f;
-
- if((R>R_a) && (G>=G_a) && (B>=B_a))//二值化,高閾值:25.55.25,較合適閾值(21,47,21)
- {
- color=0xffff;
- }
- else
- {
- color=0x0000;
- }
-
- if(color!=color_save)//跳變點
- {
- TableChangePoint_240[a]++; //該行跳變點計數+1
- }
- color_save=color;//保存像素值,供下一次判斷和比較
-
- color=(AA<<8)|BB;//還原色彩
-
- LCD_DATA_PORT->ODR = color;
- GPIOC->BRR =1<<11;
- GPIOC->BSRR =1<<11;
- }
- }
- ChangePoint_Show_240();//240方向跳變點顯示
- ChangePoint_Analysis_240(); //跳變點分析
- }
- void Data_LCD_ColorPut()//顏色處理
- {
- LCD_SetWindows(0,0,320,240);//設置顯示窗口
- GPIO_WriteBit(LCD_RS_PORT, LCD_RS_PIN,1);//標志:數據寫入
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 0);
- GPIO_WriteBit(FIFO_WRST_PORT, FIFO_WRST_PIN, 1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 1);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==0);
- while(GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_0)==1);
- GPIO_WriteBit(FIFO_WR_PORT, FIFO_WR_PIN, 0);
-
- FIFO_Reset_Read_Addr();
- // LED();
-
- for (a=0;a<240;a++)
- {
- for(b=0;b<320;b++)
- {
- GPIOC->BRR =1<<4;
- AA=GPIOA->IDR;
- GPIOC->BSRR =1<<4;
-
- GPIOC->BRR =1<<4;
- BB=GPIOA->IDR&0x00ff;
- GPIOC->BSRR =1<<4;
-
- color=(AA<<8)|BB;
-
- R=color>>11;
- G=(color>>5)&0x3f;
- B=color&0x1f;
-
- // if(R<25&&G<50&&B<25)
- // {
- // color=0xf800;
- // }
- if(R<29&&G<59&&B<29)
- {
- color=0x0000;
- }
- LCD_DATA_PORT->ODR = color;
- GPIOC->BRR =1<<11;
- GPIOC->BSRR =1<<11;
- }
- }
- }
- void PC0_in()//PC0引腳為輸入
- {
- GPIO_InitTypeDef gpio_init_struct;//結構體
- gpio_init_struct.GPIO_Mode = GPIO_Mode_IPU;//輸入上拉
- gpio_init_struct.GPIO_Speed = GPIO_Speed_50MHz;
- gpio_init_struct.GPIO_Pin = GPIO_Pin_0;
- GPIO_Init(GPIOC, &gpio_init_struct);
- }
- void Show_Card(u8 i)//顯示第幾組車牌
- {
- u16 t0;
- //顯示漢字
- if(table_card[i][0]!=0)
- {
- WordShow(table_card[i][0],9,i*16+50);//
- }
-
- if(table_card[i][1]<10)
- {
- LCD_ShowNum(25,i*16+50,table_char[table_card[i][1]],1);
- }
- else
- {
- LCD_ShowChar(25,i*16+50,table_char[table_card[i][1]],0);
- }
- LCD_ShowChar(33,i*16+50,'.',0); //點
- if(table_card[i][2]<10)
- {
- LCD_ShowNum(41,i*16+50,table_char[table_card[i][2]],1);
- }
- else
- {
- LCD_ShowChar(41,i*16+50,table_char[table_card[i][2]],0);
- }
- if(table_card[i][3]<10)
- {
- LCD_ShowNum(49,i*16+50,table_char[table_card[i][3]],1);
- }
- else
- {
- LCD_ShowChar(49,i*16+50,table_char[table_card[i][3]],0);
- }
- if(table_card[i][4]<10)
- {
- LCD_ShowNum(57,i*16+50,table_char[table_card[i][4]],1);
- }
- else
- {
- LCD_ShowChar(57,i*16+50,table_char[table_card[i][4]],0);
- }
- if(table_card[i][5]<10)
- {
- LCD_ShowNum(65,i*16+50,table_char[table_card[i][5]],1);
- }
- else
- {
- LCD_ShowChar(65,i*16+50,table_char[table_card[i][5]],0);
- }
- if(table_card[i][6]<10)
- {
- LCD_ShowNum(73,i*16+50,table_char[table_card[i][6]],1);
- }
- else
- {
- LCD_ShowChar(73,i*16+50,table_char[table_card[i][6]],0);
- }
- t0=table_card[i][7];
- LCD_ShowNum(100,i*16+50,t0,6);//顯示時間
- if(t0<60)
- {
- LCD_ShowNumPoint(168,i*16+50,t0*8);
- }
- else
- {
- LCD_ShowNumPoint(168,i*16+50,t0/60*500+t0%60*8);
- }
-
- }
- //定時器3中斷服務程序
- void TIM3_IRQHandler(void)
- {
- if(TIM3->SR&0X0001)//溢出中斷
- {
- LED();
- if(tim3_num==60)
- {
- if(table_card[0][0]!=0)//第1組計時
- {
- table_card[0][7]++;
- }
- if(table_card[1][0]!=0)//第2組計時
- {
- table_card[1][7]++;
- }
- if(table_card[2][0]!=0)//第3組計時
- {
- table_card[2][7]++;
- }
- if(table_card[3][0]!=0)//第4組計時
- {
- table_card[3][7]++;
- }
- if(table_card[4][0]!=0)//第5組計時
- {
- table_card[4][7]++;
- }
- tim3_num=0;
- }
- }
- tim3_num++;
- TIM3->SR&=~(1<<0);//清除中斷標志位
- }
- void TIM3_Configuration(void)
- {
- /* TIM3 clock enable */
- RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);
- /* ---------------------------------------------------------------
- TIM3CLK 即PCLK1=36MHz
- TIM3CLK = 36 MHz, Prescaler = 7200, TIM3 counter clock = 5K,即改變一次為5K,周期就為10K
- --------------------------------------------------------------- */
- /* Time base configuration */
- TIM_TimeBaseStructure.TIM_Period = 10000; //設置在下一個更新事件裝入活動的自動重裝載寄存器周期的值 計數到10000為1000ms
- TIM_TimeBaseStructure.TIM_Prescaler =(12800-1); //設置用來作為TIMx時鐘頻率除數的預分頻值 10Khz的計數頻率
- TIM_TimeBaseStructure.TIM_ClockDivision = 0; //設置時鐘分割:TDTS = Tck_tim
- TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上計數模式
- TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); //根據TIM_TimeBaseInitStruct中指定的參數初始化TIMx的時間基數單位
-
- /* Enables the Update event for TIM3 */
- //TIM_UpdateDisableConfig(TIM3,ENABLE); //使能 TIM3 更新事件
-
- /* TIM IT enable */
- TIM_ITConfig( //使能或者失能指定的TIM中斷
- TIM3, //TIM2
- TIM_IT_Update | //TIM 中斷源
- TIM_IT_Trigger, //TIM 觸發中斷源
- ENABLE //使能
- );
-
- /* TIM3 enable counter */
- TIM_Cmd(TIM3, ENABLE); //使能TIMx外設
- }
- void Show_Title()//顯示標題
- {
- LCD_ShowChar(35+8*0,10,'N',0);
- LCD_ShowChar(35+8*1,10,'u',0);
- LCD_ShowChar(35+8*2,10,'m',0);
- LCD_ShowChar(35+8*3,10,'b',0);
- LCD_ShowChar(35+8*4,10,'e',0);
- LCD_ShowChar(35+8*5,10,'r',0);
-
- LCD_ShowChar(35+8*9,10,'T',0);
- LCD_ShowChar(35+8*10,10,'i',0);
- LCD_ShowChar(35+8*11,10,'m',0);
- LCD_ShowChar(35+8*12,10,'e',0);
-
- LCD_ShowChar(35+8*17,10,'P',0);
- LCD_ShowChar(35+8*18,10,'r',0);
- LCD_ShowChar(35+8*19,10,'i',0);
- LCD_ShowChar(35+8*20,10,'c',0);
- LCD_ShowChar(35+8*21,10,'e',0);
- }
- void main(void)
- {
- unsigned int num;
- u16 i;
- Stm32_Clock_Init(16);//初始化時鐘
- Led_init(); //初始化 LED
- Lcd_Gpio_Init();
- LCD_Init();
-
- Key_init(); //初始化 KEY1
- PC0_in();//PC0引腳為輸入
-
- OV7670_Gpio_Init();//OV7670引腳初始化,放在串口初始化前面
- GPIO_WriteBit(FIFO_OE_PORT, FIFO_OE_PIN, 0);
- USART1_init();//初始化串口
- // PC0_in();//PC0引腳為輸入
- TIM3_Configuration();//10Khz的計數頻率,計數到5000為500ms
- LCD_Fill(0x6666);
-
- // while(1)//
- // {
- // LCD_ShowNumPoint(0,0,12345);
- // }
- while(!Sensor_init());
-
- LCD_Fill(0xF800);
- delayms(100);
- num=2;
-
- R_a=24;
- G_a=53;
- B_a=24;
- while(1)
- {
- if(num<=1)
- {
- Data_LCD_ColorChange();//車牌測定
- }
- if(num>1)
- {
- Data_LCD_ColorChange_Test();//攝像頭掃描測試
- LCD_ShowNum(30,220,21-num,2);//
- while(GPIO_ReadInputDataBit(KEY1_PORT,KEY1_PIN)==0)
- {
- LCD_Fill(0x00);//黑屏
- Show_Title();//顯示標題
- Show_Card(0);//顯示第幾組車牌
- Show_Card(1);
- Show_Card(2);
- Show_Card(3);
- Show_Card(4);
- delay_ms(5000);
- }
- }
- if(num==20)
- {
- num=0;
- }
- num++;
- }
- while(1)
- {
- MoShiShiBie();//字符匹配,模式識別
- }
- while(1)//圖片瀏覽
- {
- String_Picture_All();//總數組->圖片
- }
- while(1)
- {
- String_Picture();//數組->圖片
- delayms(5000);
- Picture_String();//圖片->數組table_picture
- delayms(5000);
- LCD_Fill(0xF800);
- delayms(5000);
- String_Picture9();//數組->圖片
- delayms(5000);
- }
- while(1)//測量像素
- {
- Data_LCD_ColorDisplay();//單色像素顯示、測量
- }
- while(1)
- {
- RGB_HSV(0x4f32);//RGB轉HSV
- }
- while(1)
- {
- LCD_ShowChar(10,200,'X',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(30,200,123456,6);//X坐標,Y坐標,數字,幾位數
- LCD_ShowChar(10,220,'Y',0);//X坐標,Y坐標,字符,填充模式
- LCD_ShowNum(30,220,789012,6);//X坐標,Y坐標,數字,幾位數
- }
- while(1)//測量像素
- {
- WordShow(1,160,220);//顯示渝字
- delayms(1000);
- WordShow(2,160,220);//顯示渝字
- delayms(1000);
- WordShow(3,160,220);//顯示渝字
- delayms(1000);
- WordShow(4,160,220);//顯示渝字
- delayms(1000);
- WordShow(5,160,220);//顯示渝字
- delayms(1000);
- WordShow(6,160,220);//顯示渝字
- delayms(1000);
- }
- }
復制代碼
|