久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 2216|回復: 10
收起左側

關于顏色傳感器TCS230的測量RGB值的實驗

[復制鏈接]
ID:958627 發表于 2021-8-3 18:20 | 顯示全部樓層 |閱讀模式
大家好,我是學習單片機的新手,我在用TCS230和單片機STC8A8K64S4A12做測量RGB值的實驗,但不知為何,液晶屏只顯示RGB值皆為255,不會變化,所以想求助各位有沒有碰到過這種情況,怎么解決的?

程序在樓下

回復

使用道具 舉報

ID:280000 發表于 2021-8-4 08:58 | 顯示全部樓層
單片機和顏色傳感器通信協議編寫的有問題吧,沒有讀取到正確的數據
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 09:01 | 顯示全部樓層
湖南 發表于 2021-8-4 08:58
單片機和顏色傳感器通信協議編寫的有問題吧,沒有讀取到正確的數據

您好,您可以幫助我一下嗎,這是我的程序
#include <stc8a.h>
#include <LCD1602.h>
#define uchar unsigned char
#define uint  unsigned int

//=================顏色傳感模塊連接=====================
/*-----------------------------------------------------
       |EO-----GND
       |S0-----VCC | S2-----P1.0 | OUT-------P3.5
       |S1-----VCC | S3-----P1.1 |
  ---------------------------------------------------*/
sbit    tcs230_s2=P1^0;//TCS230 S2接單片機P1.0
sbit    tcs230_s3=P1^1;//TCS230 S3接單片機P1.1
sbit    tcs230_en=P3^0; //TCS230 EN(E0)接GND
//**************函數聲明***************************************
void    DisplayOneChar(uchar X,uchar Y,uchar ASCII);//在第X+1行的第Y+1位置顯示一個字符
void    baipingheng();//白平衡子程序
void    celiang();//實際顏色程序
void    LCD1602_Init(void);
void    LCD1602_Display_Str(uchar* str);
void    Delay_ms(unsigned int ms);
uint    ryz,gyz,byz;//分別定義紅色因子 綠色因子 藍色因子
uint    rb,gb,bb;//RGB值
uchar   tab1[]={'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
//***********************主程序******************************
main()   
{   
   TMOD=0x51;//設定T0以工作方式1定時10毫秒
   LCD1602_Init();//LCD初始
   baipingheng();//上電時先白平衡一次
   while(1)
   {
       celiang();//顏色測試
       DisplayOneChar(0, 0,'R');//以十進制顯示RGB中紅色的分值
       DisplayOneChar(0, 1, rb/100+0x30); //顯示百位數據
       DisplayOneChar(0, 2, rb/10%10+0x30);//顯示十位數據
       DisplayOneChar(0, 3, rb%10+0x30);//顯示個位數據
                   DisplayOneChar(0, 5,'G');//以十進制顯示RGB中綠色的分值
       DisplayOneChar(0, 6, gb/100+0x30); //顯示百位數據
       DisplayOneChar(0, 7, gb/10%10+0x30);
       DisplayOneChar(0, 8, gb%10+0x30);
       DisplayOneChar(0, 10,'B');//以十進制顯示RGB中藍色的分值
       DisplayOneChar(0, 11, bb/100+0x30);
       DisplayOneChar(0, 12, bb/10%10+0x30);
       DisplayOneChar(0, 13, bb%10+0x30);
       //*****在LCD1602的第二行以16進制顯示RGB*******************
       DisplayOneChar(1, 1, tab1[rb/16]);
       DisplayOneChar(1, 2, tab1[rb%16]);
       DisplayOneChar(1, 3, 'H');
       DisplayOneChar(1, 6, tab1[gb/16]);
       DisplayOneChar(1, 7, tab1[rb%16]);
       DisplayOneChar(1, 8, 'H');
       DisplayOneChar(1, 11,tab1[bb/16]);
       DisplayOneChar(1, 12,tab1[bb%16]);
       DisplayOneChar(1, 13,'H');
       Delay_ms(1000);//每隔2.5秒測試一次顏色
   }
}
//******************************************************
//白平衡子程序
void   celiang()
{
        TMOD=0x51;//設定T0以工作方式1定時10毫秒
     //*********求R值************************************
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=0;
     tcs230_s3=0;//選擇紅色濾光器
     tcs230_en=0;
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     rb=(unsigned long)(TH1*256+TL1)*255/ryz;
     if(rb>255)rb=255;//判斷RGB值是否合法
     //***********求B值**************************************
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=0;
     tcs230_s3=1;//選擇藍色濾光器
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     bb=(unsigned long)(TH1*256+TL1)*255/byz;
     if(bb>255)bb=255;//判斷RGB值是否合法     
     //***********求G值**************************************   
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=1;
     tcs230_s3=1;//選擇綠色濾光器
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     tcs230_en=1;
     gb=(unsigned long)(TH1*256+TL1)*255/gyz;
     if(gb>255)gb=255;//判斷RGB值是否合法  
}
//******************************************************
//白平衡子程序
void    baipingheng()
{
        TMOD=0x51;//設定T0以工作方式1定時10毫秒
     //**************求取紅色因子***********************
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=0;
     tcs230_s3=0;//選擇紅色濾光器
     tcs230_en=0;
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     ryz=TH1*256+TL1;//其實這里的比例因子應該為255/(TH1*256+TL1)
     //**************求取藍色因子***********************
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=0;
     tcs230_s3=1;//選擇藍色濾光器
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     byz=TH1*256+TL1;//其實這里的比例因子應該為255/(TH1*256+TL1)
     //**************求綠紅色因子***********************
     TH0=(65536-10000)/256;
           TL0=(65536-10000)%256;
     TH1=0;
     TL1=0;
     tcs230_s2=1;
     tcs230_s3=1;//選擇綠色濾光器
     TR0=1;//10毫秒開始計時
     TR1=1;//開始計數
     while(TF0==0);//等待定時器溢出
     TF0=0;//清楚定時器0溢出標志
     TR0=0;//關閉定時0
     TR1=0;
     tcs230_en=1;
     gyz=TH1*256+TL1;//其實這里的比例因子應該為255/(TH1*256+TL1)
}
/***********************************************
函數名稱:LCD1602_Init
功    能:LCD1602初始化
入口參數:無
返 回 值:無       
備    注:詳見數據手冊定義。
************************************************/
void LCD1602_Init(void)  
{
        //將P04 P05 P06 P07設置為準雙向口
        P0_Mode_IO_PU(PIN_4|PIN_5|PIN_6|PIN_7);  
        //將P41 P43 P44設置為準雙向口
        P4_Mode_IO_PU(PIN_1|PIN_3|PIN_4);
       
  Delay_ms(15);                              //上電延時15ms
        LCD1602_SetFourMode();        //設置為四線模式
  Delay_ms(5);
  LCD1602_WriteCMD(0x28); //寫顯示指令(不檢測忙信號)
  Delay_ms(5);
  LCD1602_WriteCMD(0x28); //寫顯示指令(不檢測忙信號)
  LCD1602_CheckBusy();
  LCD1602_WriteCMD(0x28); //寫顯示指令
  LCD1602_CheckBusy();
  LCD1602_WriteCMD(0x08); //顯示關閉
  LCD1602_CheckBusy();
  LCD1602_WriteCMD(0x01); //清屏
  LCD1602_CheckBusy();
  LCD1602_WriteCMD(0x06); //顯示光標移動設置
  LCD1602_CheckBusy();
  LCD1602_WriteCMD(0x0c); //顯示開及光標設置  
}

/***********************************************
函數名稱:LCD1602_Display_Str
功    能:lcd1602顯示字符函數
入口參數:str指針地址
返 回 值:無       
備    注:無
************************************************/
void LCD1602_Display_Str(uchar* str)
{
        while(*str!='\0')               //未到字符串末尾
  {
                LCD1602_CheckBusy();   //檢測忙信號
    LCD1602_WriteDAT(*str);//寫入數據
          str++;
  }
}

/*======================================================================
功 能:     在1602 指定位置顯示一個字符:第一行位置0~15,第二行16~31
說 明:     第 X 行,第 y 列  注意:字符串不能長于16個字符
======================================================================*/
void DisplayOneChar( uchar X, uchar Y, uchar ASCII)
{
  X &= 0x1;
  Y &= 0xF; //限制Y不能大于15,X不能大于1
  if (X) Y |= 0x40; //當要顯示第二行時地址碼+0x40;
  Y |= 0x80; // 算出指令碼
  LCM_WriteCMD(Y,0); //這里不檢測忙信號,發送地址碼
  LCD1602_Display_Str(&ASCII);
}

/***********************************************
函數名稱:Delay_ms
功    能:STC8系列單片機1ms延時程序
入口參數:ms:延時的毫秒數
返 回 值:無       
備    注:示波器實測:1.01ms,內部時鐘:24MHz           
************************************************/
void Delay_ms(unsigned int ms)
{
  unsigned int i;
  while( (ms--) != 0)
  {
    for(i = 0; i < 1850; i++);
  }            
}
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 09:02 | 顯示全部樓層
湖南 發表于 2021-8-4 08:58
單片機和顏色傳感器通信協議編寫的有問題吧,沒有讀取到正確的數據

這是LCD1602的程序
#include "LCD1602.h"
//包含該函數可以使用_nop_()函數
#include <intrins.h>

#define  Busy  0x80
/***********************************************
函數名稱:LCD1602_Delay1us
功    能:STC 1T單片機1us延時程序
入口參數:us:延時的微秒數
返 回 值:無       
備    注:外部時鐘24MHz
************************************************/
void LCD1602_Delay1us(unsigned int us)
{
  while( us--)
  {
    _nop_();
  }            
}

/*************************************
* 函 數 名: LCD1602_WriteHalfByte
* 函數功能: 向lcd1602寫入半個字節數據
* 入口參數: dat:數據
* 返    回: 無
* 備    注:寫入的數據為高四位有效,低四位無效
**************************************/
void LCD1602_WriteHalfByte(unsigned char dat)
{
        LCD1602_D7=dat&0x80;        //取數據的第7位       
        LCD1602_D6=dat&0x40;        //取數據的第6位
        LCD1602_D5=dat&0x20;        //取數據的第5位       
        LCD1602_D4=dat&0x10;        //取數據的第4位
}
/*************************************
* 函 數 名: LCD1602_ReadHalfByte
* 函數功能: 從lcd1602半個讀取字節數據
* 入口參數: dat:數據
* 返    回: 無
* 備    注:讀出的數據為高四位有效,低四位無效
**************************************/
unsigned char LCD1602_ReadHalfByte(void)
{
        unsigned char LCD1602_Dat=0;
        //輸入先置高
        LCD1602_D7=1;
        LCD1602_D6=1;
        LCD1602_D5=1;
        LCD1602_D4=1;

        if(LCD1602_D7==1)
        {
                LCD1602_Dat |=0x80;
        }
        if(LCD1602_D6==1)
        {
                LCD1602_Dat |=0x40;
        }
        if(LCD1602_D5==1)
        {
                LCD1602_Dat |=0x20;
        }
        if(LCD1602_D4==1)
        {
                LCD1602_Dat |=0x10;
        }

        return LCD1602_Dat;
}

void LCM_WriteCMD(unsigned char cmd,BusyC)
{
        unsigned char H_Data,L_Data;
       
   if(BusyC)
                LCD1602_CheckBusy();
         
        H_Data=cmd&0xf0;                          //取高四位
        L_Data=(cmd&0x0f)<<4;          //取低四位

  EN_Clr();
  RS_Clr();
  RW_Clr();

  LCD1602_Delay1us(10);                          
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入高四位
  LCD1602_WriteHalfByte(H_Data);
  LCD1602_Delay1us(10);
  EN_Clr();

        LCD1602_Delay1us(10);
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入低四位
  LCD1602_WriteHalfByte(L_Data);
  LCD1602_Delay1us(10);
  EN_Clr();
}
/*************************************
* 函 數 名: LCD1602_WriteCMD
* 函數功能: 向lcd1602寫指令
* 入口參數: cmd:指令
* 返    回: 無
* 備    注:無
**************************************/
void LCD1602_WriteCMD(unsigned char cmd)
{
        unsigned char H_Data,L_Data;

        H_Data=cmd&0xf0;                          //取高四位
        L_Data=(cmd&0x0f)<<4;          //取低四位

  EN_Clr();
  RS_Clr();
  RW_Clr();

  LCD1602_Delay1us(10);                          
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入高四位
  LCD1602_WriteHalfByte(H_Data);
  LCD1602_Delay1us(10);
  EN_Clr();

        LCD1602_Delay1us(10);
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入低四位
  LCD1602_WriteHalfByte(L_Data);
  LCD1602_Delay1us(10);
  EN_Clr();
}
/***********************************************
函數名稱:LCD1602_WriteDAT
功    能:向lcd1602寫數據
入口參數:dat:數據
返 回 值:無       
備    注:無
************************************************/
void LCD1602_WriteDAT(unsigned char dat)
{
        unsigned char H_Data,L_Data;

        H_Data=dat&0xf0;                  //取高四位
        L_Data=(dat&0x0f)<<4; //取低四位

        EN_Clr();
  RS_Set();
  RW_Clr();

  LCD1602_Delay1us(10);
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入高四位
  LCD1602_WriteHalfByte(H_Data);
  LCD1602_Delay1us(10);
  EN_Clr();

        LCD1602_Delay1us(10);
  EN_Set();
  LCD1602_Delay1us(10);                          //寫入低四位
  LCD1602_WriteHalfByte(L_Data);
  LCD1602_Delay1us(10);
  EN_Clr();
}
/***********************************************
函數名稱:LCD1602_CheckBusy
功    能:檢測lcd1602忙信號
入口參數:無
返 回 值:無       
備    注:無
************************************************/
void LCD1602_CheckBusy(void)
{
        unsigned char H_Data,L_Data;
       
  while(1)
  {   
    EN_Clr();                  
    RS_Clr();
    RW_Set();

    LCD1602_Delay1us(10);
    EN_Set();
    LCD1602_Delay1us(10);
    H_Data=LCD1602_ReadHalfByte();    //讀取忙通道數據高四位
    LCD1602_Delay1us(10);
    EN_Clr();
               
                LCD1602_Delay1us(10);
    EN_Set();
    LCD1602_Delay1us(10);
    L_Data=LCD1602_ReadHalfByte();    //讀取忙通道數據低四位
    LCD1602_Delay1us(10);
    EN_Clr();

    if((H_Data&0x80)!=0x80)                                          //判斷忙信號
    {   
      break;
    }
  }
}
/***********************************************
函數名稱:LCD1602_SetFourMode
功    能:設置lcd1602為四線模式。
入口參數:無
返 回 值:無       
備    注:無
************************************************/
void LCD1602_SetFourMode(void)
{
        EN_Clr();
  RS_Clr();
  RW_Clr();

  LCD1602_Delay1us(10);
  EN_Set();
  LCD1602_Delay1us(10);
  LCD1602_WriteHalfByte(0x20);//寫入控制字節,四位模式
  LCD1602_Delay1us(10);
  EN_Clr();
}
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 09:03 | 顯示全部樓層
湖南 發表于 2021-8-4 08:58
單片機和顏色傳感器通信協議編寫的有問題吧,沒有讀取到正確的數據

謝謝您了
回復

使用道具 舉報

ID:844772 發表于 2021-8-4 09:03 | 顯示全部樓層
我只在arduino用過,沒出啥特別問題,只是離遠的時候測的不準。
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 09:17 | 顯示全部樓層
現在我已經有程序了,并且編譯過并沒有任何錯誤,所以想讓各位幫我看一下是有哪里不妥當嗎
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 09:18 | 顯示全部樓層
這里是我的程序
回復

使用道具 舉報

ID:844772 發表于 2021-8-4 15:44 | 顯示全部樓層
bb=(unsigned long)(TH1*256+TL1)*255/byz; 這句有點問題,數據類型也不對,建議你先不用白平衡,改為bb=TH1*256+TL1,距離近點用不著白平衡。等差不多了,你再調白平衡。
回復

使用道具 舉報

ID:958627 發表于 2021-8-4 15:58 | 顯示全部樓層
glinfei 發表于 2021-8-4 15:44
bb=(unsigned long)(TH1*256+TL1)*255/byz; 這句有點問題,數據類型也不對,建議你先不用白平衡,改為bb=TH ...

你好,我嘗試改變了,但是依舊顯示的全部是255
回復

使用道具 舉報

ID:844772 發表于 2021-8-4 17:22 | 顯示全部樓層
安逸啊 發表于 2021-8-4 15:58
你好,我嘗試改變了,但是依舊顯示的全部是255

抱歉,我沒說清楚,既然沒做白平衡,它的范圍是0-65535,你看是不是在這個范圍,這決定你模塊是否有效,
我主要認為你在強制類轉換上有問題,簡單辦法是改比例因子算法: 1。是改這句 ryz=65535/(TH1*256+TL1);//其實這里的比例因子應該為255/(TH1*256+TL1)  2。是改bb=(TH1*256+TL1)/byz;
當然三個顏色都要改啊。
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

手機版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 久草成人 | 亚洲午夜视频 | 日韩成人精品在线 | 亚洲视频二 | 超碰超碰 | 91精品国产91久久综合桃花 | 中文字幕男人的天堂 | 亚洲国产偷 | 国产草草视频 | 国产精品99久久久久久www | 国产成人精品一区二区三区网站观看 | 一区在线观看视频 | 黄色片免费看视频 | 九九热精品在线视频 | 成人午夜激情 | 久久亚洲欧美日韩精品专区 | 国产日韩一区二区三区 | 日本不卡在线视频 | 91日韩在线 | 国产视频线观看永久免费 | 亚洲瑟瑟 | 毛片一区二区 | 91精品国产综合久久久动漫日韩 | 亚洲成年在线 | 伊人网一区 | 国产一区二区在线视频 | 国产精品久久久久一区二区三区 | 婷婷综合色 | 久久久久久国产精品免费免费男同 | 韩国主播午夜大尺度福利 | 青青草原精品99久久精品66 | 久久亚洲精品国产精品紫薇 | 亚洲一区二区三区四区五区午夜 | 国产一区h | 国产乱码精品一区二区三区忘忧草 | 在线黄av | 91视频国产区 | 成人国产精品免费观看 | 欧美激情综合 | 成人小视频在线观看 | 日韩视频三区 |