繼昨天的研究,希望再接再厲把AD模入模出在模拟器上也實作出來,本以為挺簡單,其實AD相關功能,與GPIO不同,在模拟器中前者通過GpioPort實作,後者通過SpiDevice實作。幸好有Temperature(溫度采集)示例可以參考,否則一時真無法下手。不知道為什麼,很簡單的代碼他們總寫的很複雜,讓你很難看懂,幸好有以前的相關的經驗做底子,用了大半天的時間模入模出都搞定了。
下面就是模拟器中的AD輸入輸出的相關代碼。
public class SpiADComponent : SpiDevice
{
public Int16 AW0 = 0;
public Int16 QW0 = 0;
protected override byte[] Write(byte[] data)
{
//------------
try
{
QW0 = (Int16)((data[0] << 8) + data[1]);
}
catch { }
//------------
byte[] bytes = new byte[2];
bytes[0] = (byte)(AW0 >> 8);
bytes[1] = (byte)(AW0 & 0xff);
return bytes;
}
}
注:由于受西門子PLC200的影響比較大,是以把模拟量入和出,定義為AW0和QW0,并且用兩個位元組的整數表示,根據需要可以進行折算。
我們把昨天的GPIO代碼稍加改進,把AD部分測試代碼添加進去,代碼如下:
static SPI _spi;
public static void Main()
{
OutputPort[] output = new OutputPort[8];
InputPort[] input = new InputPort[8];
//葉帆模拟器GPIO的pin定義
Cpu.Pin[] pin_I = new Cpu.Pin[8] { (Cpu.Pin)10, (Cpu.Pin)11, (Cpu.Pin)12, (Cpu.Pin)13, (Cpu.Pin)14,(Cpu.Pin)15, (Cpu.Pin)16, (Cpu.Pin)17 };
Cpu.Pin[] pin_Q = new Cpu.Pin[8] { (Cpu.Pin)20, (Cpu.Pin)21, (Cpu.Pin)22, (Cpu.Pin)23, (Cpu.Pin)24, (Cpu.Pin)25, (Cpu.Pin)26, (Cpu.Pin)27 };
//SPI的pin定義
_spi=new SPI(new SPI.Configuration((Cpu.Pin)30, true, 0, 0, false, false, 4000, SPI.SPI_module.SPI1));
for (int i = 0; i < 8; i++)
{
input[i] = new InputPort(pin_I[i], false, Port.ResistorMode.PullDown);
output[i] = new OutputPort(pin_Q[i], false);
}
int intNum = 0;
while (true)
{
output[intNum].Write(!output[intNum].Read());
Debug.Print(input[0].Read().ToString() + " " + input[1].Read().ToString() + " " + input[2].Read().ToString() + " " + input[3].Read().ToString() + " " + input[4].Read().ToString()+ " " + input[5].Read().ToString() + " " + input[6].Read().ToString() + " " + input[7].Read().ToString());
Debug.Print(ReadWriteAD((Int16)intNum).ToString() + " " + intNum.ToString());
if (++intNum > 7) intNum = 0;
Thread.Sleep(1000);
}
}
public static Int16 ReadWriteAD(Int16 value)
{
byte[] bout = new byte[2];
byte[] bin = new byte[2];
bout[0] = (byte)(value >> 8);
bout[1] = (byte)(value & 0xff);
_spi.WriteRead(bout, bin);
Int16 aw0=(Int16)((bin[0] << 8) + bin[1]);
return aw0;
}
}
運作後的界面如下:

從上圖可以看出,模拟器已經和測試程式進行互動了,即可以設定AW0的值,也可以擷取QW0的值。
我又把模拟器改進了一下,可以支援多種IO模拟功能,目前已經完成了GPIO和AD,I2C應該也不難,但是Serial(序列槽)估計有問題,因為模拟器支援庫沒有相關函數。