标题:
Arduino简易小型PLC代码
[打印本页]
作者:
lamyauhoi
时间:
2022-11-28 12:45
标题:
Arduino简易小型PLC代码
简昜小型PLC只有16个指令,这几个是PLC基本功能,如需要其它功能可自行加上。
输入输出可自行更改位置点数。
内部继电器M,计数器,计时器,可增加所需要个数。
如果要在设备上运行。
需要在输入,输出,电源,每个部份要做好抗干扰功能。
连接人机介面HMI可成为小型控制系统。在小型设备使用很方便。
沒有实际在设备上測试,只在arduino LGT8F328 nulllab mini arduino nano板上测试过!
easy_mini_plc.ino
//在arduino LGT8F328 nulllab mini arduino nano板上测试过,
//这几个都是PLC基本功能,如需要其它功能可自行加上。
//------------------------------------------------------
#include "macrodef.h"
unsigned int T2ovfcount=10; //timers 100ms
//-------------------------------------------------------
void setup()
{
Serial.begin(115200);
//----------------------------------------
//更改自己的输入输出点
//-----------------------------------------
pinMode(A2, INPUT_PULLUP);
pinMode(A3, INPUT_PULLUP);
pinMode(4, INPUT_PULLUP);
pinMode(5, INPUT_PULLUP);
pinMode(6, INPUT_PULLUP);
//----------------------------------------
// fastioMode(6, OUTPUT);
pinMode(7, OUTPUT);
pinMode(8, OUTPUT);
pinMode(9, OUTPUT);
pinMode(13, OUTPUT);
//----------------------------------------
// T2 10ms Interrupt setup
//----------------------------------------
noInterrupts();
TCCR2A =
1 << WGM20;
TCCR2B =
1 << WGM22 |
1 << CS22 |
1 << CS21 |
1 << CS20;
TIMSK2 =
1 << TOIE2;
OCR2A = 78;
interrupts();
//--------------------------------
count0=0;
timer0=0;
count1=0;
timer1=0;
count2=0;
timer2=0;
count3=0;
timer3=0;
}
//-------------------------------
void loop()
{
//---------------------------------------------
// 其它程式
//---------------------------------------------
test_plc1();
//test_plc2();
//test_plc3();
//test_plc4();
//test_plc5();
//---------------------------------------------
PlcEnd();
//---------------------------------------------
//test output
Serial.print(stb);
Serial.print("\t");
Serial.print(count0);
Serial.print("\t");
Serial.print(timer30);
Serial.print("\t");
Serial.print(Y3);
Serial.print("\t");
Serial.print(T30);
Serial.println();
}
//---------------------------------------
// ISR Timer Routine 10ms Interrup
//---------------------------------------
ISR(TIMER2_OVF_vect){
T2ovfcount--;
isrtimer(30); //10ms 0.01s timer
isrtimer(31);
if(T2ovfcount<=0){
T2ovfcount=10;
isrtimer(0); //100ms 0.1s timer
isrtimer(1);
isrtimer(2);
isrtimer(3);
isrtimer(4);
}
}
//-------------------------------------
// PLC io input output
///更改自己的输入输出点
//-------------------------------------
void PlcEnd() {
digitalWrite(9,Y0);
digitalWrite(7,Y1);
digitalWrite(8,Y2);
digitalWrite(13,Y3);
X0=!digitalRead(A2);
X1=!digitalRead(A3);
X2=!digitalRead(4);
X3=!digitalRead(5);
X4=!digitalRead(6);
stb=0;
}
//--------------------------------
//X0,X1,其中一个接GND 生效
//test plc
//-------------------------------------------------------------------------------------
void test_plc1(){
LD(X0) // |----||----------|---|/|--------------------------( )-----|
OR(X1) // | LD X0 | ANI M1 OUT T3,2 | 0.2s
ANI(M1) // |----||----------| |
OUTT(3,2) // | OR X1 |
LD(T3) // |----||-------------------------------|-----------( )-----|
ATL(0,Y3) // | LD T2 | ATL Y3 |
OUT(M1) // | |-----------( )-----|
LD(Y3) // | OUT M1 |
OUTC(0,20) // |----||-------------------------------------------( )-----|
LD(C0) // | LD Y3 OUT C0,20 | 20
RSTC(0) // |----||-------------------------------------------( )-----|
// | LD C0 RST C0
}
//-------------------------------------------------------------------------------------------
void test_plc2(){
LD (X4) // |-------||-------|--------||-------||-------|------( )----|
LD (X0) // | LD X4 | LD X0 AND X1 | OUT Y3 |
AND(X1) // | |--------||-------||-------| |
LD (X2) // LD X2 AND X3
AND(X3)
ORB
ANB
OUT(Y3)
}
//-----------------------------------------------------------------------------------------
void test_plc3(){
LD (X0) // |------||------|------||------|--------------------( )-----|
OR (X2) // | LD X0 | AND X1 | OUT Y3
AND (X1) // |------||------| |
LD (X3) // | ORI X2 |
AND (X4) // |------||------||-------------|
ORB // | LD X3 AND X4
OUT(Y3)
}
//-------------------------------------------------------------------
void test_plc4(){
LD (X0)
SET(M0)
LD (M0)
OUT(Y3)
LD (X1)
RST(M0)
}
//------------------------------------------------------------------
void test_plc5(){
LD (X2)
ATL(0,Y3)
}
//------------------------------------------------------------------
复制代码
macrodef.h
//----------------------------------------------------------
//计时器 中斷 时间 -- isrtimer(0)---
//------------------------------------------------------------
#define isrtimer(x)\
if (startt##x){\
if(!T##x){\
if(!timer##x){\
T##x=1;\
}\
else{\
timer##x--;\
}\
}\
}
//-------------------------------------------------------
//计时器 OUT x=计时器号,k=计时器时间 ----OUTT(2,5)----
//-------------------------------------------------------
#define OUTT(x, k)\
stb=0;\
if (st0) {\
if(!T##x){\
if(!startt##x){\
startt##x=1;\
timer##x=k;\
}\
}\
}\
else {\
timer##x=0;\
startt##x=0;\
T##x=0;\
}
//-----------------------------------------------------------
//按一次键ON 又按一次键OFF ATL(a,d) a=ATL号 d=输出 --ATL(0,Y3)---
//-----------------------------------------------------------
#define ATL(a,d)\
if(st0){\
if (!atl##a){\
d =(st0^d);\
atl##a=1;\
}\
}\
else{\
atl##a=0;\
}
//---------------------------------------------------
//counter 计数器 x=计数器号 k=计数器数值----OUTC(0,20)---
//---------------------------------------------------------
#define OUTC(x,k)\
stb=0;\
if(C##x==0){\
if(st0){\
if(cset##x==0) { count##x=k; cset##x=1;}\
if(cst##x==0){\
cst##x=1;\
count##x--;\
if(count##x==0){\
C##x=1;\
}\
}\
}\
else{\
cst##x=0;\
}\
}
//---------------------------------------------------------
//reset 计数器 x=计数器号
//------------------------------------------------
#define RSTC(x)\
if(st0){\
C##x=0;\
cst##x=0;\
cset##x=0;\
count##x=0;\
}
//----------------------------------------------------------
//reset timer 计时器 ---RSTT(0)
//-------------------------------------------------------------
#define RSTT(d)\
if(st0){\
timer##x=0;\
startt##x=0;\
T##d=0;\
}
//-------------------------------------------------------
#define SET(d) if(st0){d=1;}
#define RST(d) if(st0){d=0;}
#define LD(d) stu[stb]=st0;stb++; st0=d;
#define LDI(d) stu[stb]=st0;stb++; st0 =!d;
#define OUT(d) d=st0;stb=0;
#define ANB stb--;st0=(st0 & stu[stb]);
#define AND(d) st0=(st0 & d);
#define ANI(d) st0=(st0 &!d);
#define ORB stb--;st0=(st0 | stu[stb]);
#define OR(d) st0=(st0 | d);
#define ORI(d) st0=(st0 |!d);
//------------------------------------------------
//內部状态使用
//-------------------------------------------------
bool stu[8]{};
unsigned int stb;
bool st0;
//------ATL------
bool atl0;
bool atl1;
bool atl2;
bool atl3;
bool atl4;
//-----------------------------------------
//PLC 输入
//----------------------------------------------
bool X0;
bool X1;
bool X2;
bool X3;
bool X4;
//---------------------------------------------
//PLC 输出
//----------------------------------------------
bool Y0;
bool Y1;
bool Y2;
bool Y3;
bool Y4;
//--------------------------
//PLC 內部继电器
//---------------------------
bool M0;
bool M1;
bool M2;
bool M3;
bool M4;
//----------------------------
//计时器状态使用
//------------------------------
unsigned int timer0;
bool startt0;
bool T0;
//------------------------
unsigned int timer1;
bool startt1;
bool T1;
//------------------------
unsigned int timer2;
bool startt2;
bool T2;
//------------------------
unsigned int timer3;
bool startt3;
bool T3;
//------------------------
unsigned int timer4;
bool startt4;
bool T4;
//------------------------
unsigned int timer30;
bool startt30;
bool T30;
//------------------------
unsigned int timer31;
bool startt31;
bool T31;
//----------------------------
//计数器状态使用
//------------------------------
unsigned int count0;
bool C0;
bool cset0;
bool cst0;
//--------------------------------
unsigned int count1;
bool C1;
bool cset1;
bool cst1;
//-------------------------------
unsigned int count2;
bool C2;
bool cset2;
bool cst2;
//-----------------------------------
unsigned int count3;
bool C3;
bool cset3;
bool cst3;
//----------------------------------------
unsigned int count4;
bool C4;
bool cset4;
bool cst4;
//---------------------------------------
unsigned int count30;
bool C30;
bool cset30;
bool cst30;
//-----------------------------------------
复制代码
作者:
gaoxinhang
时间:
2023-2-28 14:16
楼主厉害!👍👍👍请问这个怎么实现
作者:
smartphone
时间:
2023-3-2 20:10
这个厉害呀,应该会有实用性。
作者:
yctjs
时间:
2024-8-21 15:22
建议看看OpenPLC
作者:
zxy2266
时间:
2025-6-9 16:27
能做成通用arduino就完美了,这样可以不用328芯片了 古董芯片没有价值了,
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1