我還是參照相關資料寫出程序,但是不適用于STC89C51單片機,需要構造外圍電路,有大神能告訴我怎樣構造外圍電路來調方波振幅嗎
0.png (48.98 KB, 下載次數: 81)
下載附件
2017-7-15 17:09 上傳
單片機源程序如下:
- //三角波發生程序
- #include"reg51.h"
- #include <intrins.h>
- #define I2CDelay() {_nop_();_nop_();_nop_();_nop_();}
- sbit I2C_SCL = P3^7;
- sbit I2C_SDA = P3^6;
- sbit p_out=P1^0;
- unsigned char code triwave[]={0,16,32,48,64,80,96,112,
- 128,144,160,176,192,208,
- 224,240,255,240,224,208,
- 192,176,160,144,128,112,
- 96,80,64,48,32,16,};//三角波波表,選取32點
-
- unsigned char *pwave;//波表指針
- unsigned char T1RH = 1;
- unsigned char T1RL = 1;
- void I2CStart() //產生總線起始信號
- {
- I2C_SDA = 1; //首先確保SDA、SCL都是高電平
- I2C_SCL = 1;
- I2CDelay();
- I2C_SDA = 0; //先拉低SDA
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL
- }
- void I2CStop() //產生總線停止信號
- {
- I2C_SCL = 0; //首先確保SDA、SCL都是低電平
- I2C_SDA = 0;
- I2CDelay();
- I2C_SCL = 1; //先拉高SCL
- I2CDelay();
- I2C_SDA = 1; //再拉高SDA
- I2CDelay();
- }
- bit I2CWrite(unsigned char dat) //I2C總線寫操作,待寫入字節dat,返回值為應答狀態
- {
- bit ack; //用于暫存應答位的值
- unsigned char mask; //用于探測字節內某一位值的掩碼變量
- for (mask=0x80; mask!=0; mask>>=1) //從高位到低位依次進行
- {
- if ((mask&dat) == 0) //該位的值輸出到SDA上
- I2C_SDA = 0;
- else
- I2C_SDA = 1;
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL,完成一個位周期
- }
- I2C_SDA = 1; //8位數據發送完后,主機釋放SDA,以檢測從機應答
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- ack = I2C_SDA; //讀取此時的SDA值,即為從機的應答值
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL完成應答位,并保持住總線
- return (~ack); //應答值取反以符合通常的邏輯:0=不存在或忙或寫入失敗,1=存在且空閑或寫入成功
- }
- unsigned char I2CReadNAK() //I2C總線讀操作,并發送非應答信號,返回值為讀到的字節
- {
- unsigned char mask;
- unsigned char dat;
- I2C_SDA = 1; //首先確保主機釋放SDA
- for (mask=0x80; mask!=0; mask>>=1) //從高位到低位依次進行
- {
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- if(I2C_SDA == 0) //讀取SDA的值
- dat &= ~mask; //為0時,dat中對應位清零
- else
- dat |= mask; //為1時,dat中對應位置1
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL,以使從機發送出下一位
- }
- I2C_SDA = 1; //8位數據發送完后,拉高SDA,發送非應答信號
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL完成非應答位,并保持住總線
- return dat;
- }
- unsigned char I2CReadACK() //I2C總線讀操作,并發送應答信號,返回值為讀到的字節
- {
- unsigned char mask;
- unsigned char dat;
- I2C_SDA = 1; //首先確保主機釋放SDA
- for (mask=0x80; mask!=0; mask>>=1) //從高位到低位依次進行
- {
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- if(I2C_SDA == 0) //讀取SDA的值
- dat &= ~mask; //為0時,dat中對應位清零
- else
- dat |= mask; //為1時,dat中對應位置1
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL,以使從機發送出下一位
- }
- I2C_SDA = 0; //8位數據發送完后,拉低SDA,發送應答信號
- I2CDelay();
- I2C_SCL = 1; //拉高SCL
- I2CDelay();
- I2C_SCL = 0; //再拉低SCL完成應答位,并保持住總線
- return dat;
- }
- //設置DAC的初始值,val是初始值
- void DA(unsigned char val)
- {
- I2CStart();
- if(!I2CWrite(0x48<<1))//尋址PCF8591,如未應答,停止操作并返回
- {
- I2CStop();
- return;
- }
- I2CWrite(0x40);
- I2CWrite(val);
- I2CStop();
- }
- //輸出波形頻率
- void setwavefreq(unsigned char freq)
- {
- unsigned long temp;
- temp=(12/12)/(freq*32);//定時器的計數頻率,是波形頻率的32倍
- temp=65536-temp;//定時器重載
- temp=temp+33;//修斷中斷響應延時造成的誤差
- T1RH=(unsigned char)(temp>>8);
- T1RL=(unsigned char)temp;
- TMOD&=0x0F;
- TMOD|=0x10;
- TH1=T1RH;
- TL1=T1RL;
- ET1=1;
- PT1=1;
- TR1=1;
- }
- //中斷T1服務函數
- void timer1() interrupt 3
- {
- static unsigned int i=0;
- ……………………
- …………限于本文篇幅 余下代碼請從51黑下載附件…………
復制代碼
所有資料51hei提供下載:
三角波.rar
(30.75 KB, 下載次數: 37)
2017-7-15 16:12 上傳
點擊文件名下載附件
|