农民讲习所建立通用程序 笔记
请问前辈有没有收藏农民讲习所的裸奔GUI程序?麻烦提供一下,谢谢!
不是,你看文档,人家有提要共享GUI的东西,结果网上一直没找到。 貌似 没有共享完整?
这个套路不错,以前拿这个做了几个东西,不过现在一直用protothread +消息推送来做,占用空间更小
这是原来在C51bbs发表的: 有一台机电设备,有两个按键,控制设备的两个不同部分。 现要求: 每个按键按下,相应控制程序运行。但两个按键可以同时按下,就是说两个控制程序可能 需要同时运行。使用一个89C52,如何编写程序?(两个按键的动作可是随机的)
按键1有效:输出1HZ的方波,2S后停止。 按键2有效:一直输出1.2hz的方波,直到按键再次按
注:此程序不使用RTOS等操作系统。 相当放在两个CPU的程序放在一个里面
/*程序说明: 一)产生波形可以使用中断中计数来产生精确的波形。 本答案中为更能体现程序的多任务和资源复用问题,采用主程序循环产生。 二)请特别注意,题意是两个程序在并发运行,实际按本答案可以扩展到N个不同任务同 时运行,在此就不讨论。 (对大程序结构增加了很多其它的概念) 三)因为在论坛上直接贴出,所以程序放在一个文件中。 应该按Timer.c, Key.c, Const.h(存放常量定义),Task1, Task2, Answer.c存放 */ #include <REG52.h>
/Timer/ bit fTimer0_2ms; /T0中断产生的标志,准备传递给主循环/ bit fSYS_2ms; /系统T0中断产生的标志,12M,主循环使用/ bit fSYS_20ms; /每20MS产生一次的消息/
#define INT2MSCOUNT 10 /产生2MS所需要的时间次数/ unsigned char data mTimer_2msReg=INT2MSCOUNT; /产生2MS所需要的寄存器/ #define INT20MSCOUNT 10 /产生20MS所需要的时间次数,在 20MS基础上/ unsigned char data mTimer_20msReg=INT20MSCOUNT; /产生20MS所需要的寄存器,在20MS 基础上/
/KEY/ unsigned char data mKey1SwapTask; /按键任务寄存器/ unsigned char data mKey2SwapTask; /按键任务寄存器/ sbit iKey1=P1^0; /按键的输入口/ sbit iKey2=P1^1;
bit fKey1; /为简单化,没使用队列保存键值,使用标志/ bit fKey2; /为简单化,没使用队列保存键值,使用标志/
/Task1/ unsigned char data mTask1Id; /任务一的任务号/ unsigned char data mTask1_1HzReg; /1hz时间寄存器/ unsigned int data mTask1_2SReg; /2S时间寄存器/ sbit oTask1=P1^2; /输出方波口/
/Task2/ unsigned char data mTask2Id; /任务二的任务号/ unsigned char data mTask2_1p2HzReg; /1.2hz时间寄存器/ sbit oTask2=P1^3; /输出方波口/
/---------------------------------------------------------------------------/ /产生以1MS为基础的系统定时信号,T0作为基准定时器/
/************************************************* 定时器T0初始化0.2MS,12M *************************************************/ void Timer0_Init() { TMOD|=0x2; /8位定时器/
TL0=TH0=~(200)+1; /12M/
TR0=1; ET0=1; }
/************************************************* 定时器0的中断服务,产生fTimer0_2ms *************************************************/ void timer0(void) interrupt 1 /T0中断/ { mTimer_2msReg–; if(mTimer_2msReg==0){ mTimer_2msReg=INT2MSCOUNT; /产生1MS所需要的寄存器/ fTimer0_2ms=1; } }
答案2: [《农民_运动讲习所》所长] [248次] 03-5-15 14:25:56 /************************************************* 控制消息fSYS_2ms *************************************************/ void Timer0_MainLoop() { fSYS_2ms=0; fSYS_20ms=0;
if(fTimer0_2ms){ fTimer0_2ms=0; /接收中断过来的时间标志,转换为消息/ fSYS_2ms=1; /此消息在一周内有效,被外部程序复用/ /产生20MS的消息/ mTimer_20msReg–; if(mTimer_20msReg==0){ mTimer_20msReg=INT20MSCOUNT; /产生20MS所需要的寄存器,在20MS基础上/ fSYS_20ms=1; } } }
/---------------------------------------------------------------------------/ /按键扫描,包含两个扫描任务/ /********************************************** 每次系统时间进入一次,20ms.这里把20MS判断放进来,好看点 按键扫描循环 为简单化,没使用队列保存键值,使用标志 那些重复发出N键,在这个结构中非常容易加上 **********************************************/ void Key_MainLoop() { if(fSYS_20ms==0)return;
switch(mKey1SwapTask){ case 0:/***有按键按下吗?***/ if(iKey10){ mKey1SwapTask=1; } break; case 1: /键按下去抖延时/ mKey1SwapTask=2; /延时一个系统时间/ break; case 2: /键值判断/ if(iKey10){ fKey1=1; /按键有效/ mKey1SwapTask=3; /去按键去抖/ } else mKey1SwapTask=0; /抖动/ break; case 3: /***有松开吗?***/ if(iKey11){ mKey1SwapTask=4; } break; case 4: /键松开去抖延时/ mKey1SwapTask=5; /延时一个系统时间/ break; case 5: /键值判断/ if(iKey11){ mKey1SwapTask=0; /去按键检测开始/ } else mKey1SwapTask=3; /抖动/ break; }
switch(mKey2SwapTask){ case 0:/***有按键按下吗?***/ if(iKey20){ mKey2SwapTask=1; } break; case 1: /键按下去抖延时/ mKey2SwapTask=2; /延时一个系统时间/ break; case 2: /键值判断/ if(iKey20){ fKey2=1; /按键有效/ mKey2SwapTask=3; /去按键去抖/ } else mKey2SwapTask=0; /抖动/ break; case 3: /***有松开吗?***/ if(iKey21){ mKey2SwapTask=4; } break; case 4: /键松开去抖延时/ mKey2SwapTask=5; /延时一个系统时间/ break; case 5: /键值判断/ if(iKey21){ mKey2SwapTask=0; /去按键检测开始/ } else mKey2SwapTask=3; /抖动/ break; } }
/---------------------------------------------------------------------------/ /任务一/ /********************************************** 一个部分输出1HZ的方波,2S后停止。 **********************************************/ void Task1_MainLoop() { switch(mTask1Id){ case 0: if(fKey1){ fKey1=0; /接收该键值/ mTask1_1HzReg=500/2; /1hz时间寄存器,500ms,以2MS为单 位/ mTask1_2SReg=2000/2; /2S时间寄存器,500ms,以2MS为单 位/ oTask1=0; mTask1Id=1; } break; case 1: if(fSYS_2ms){ mTask1_1HzReg–; if(mTask1_1HzReg==0){ oTask1=~oTask1; mTask1_1HzReg=500/2; /1hz时间寄存器,500ms,以2MS为单 位/ }
mTask1_2SReg--; if(mTask1_2SReg==0){ oTask1=1; /*2S时间到*/ mTask1Id=0; } } break; }}
/---------------------------------------------------------------------------/ /任务二/ /********************************************** 一个一直输出1.2hz的方波,直到按键再次按 **********************************************/ void Task2_MainLoop() { switch(mTask2Id){ case 0: if(fKey2){ fKey2=0; /接收该键值/ mTask2_1p2HzReg=416/2; /1hz时间寄存器,832/2ms,以2MS为 单位/ oTask2=0; mTask2Id=1; } break; case 1: if(fKey2){ fKey2=0; oTask2=1; mTask2Id=0; } else { if(fSYS_2ms){ mTask2_1p2HzReg–; if(mTask2_1p2HzReg==0){ oTask2=~oTask1; mTask2_1p2HzReg=416/2; /1hz时间寄存器,832/2ms,以 2MS为单位/ } } } break; } }
/---------------------------------------------------------------------------/ /主程序/ void main(){ Timer0_Init(); EA=1;
while(1){ Timer0_MainLoop(); Key_MainLoop(); Task1_MainLoop(); Task2_MainLoop(); } }
youth、农民_运动讲习所、兽性大发的小白兔,都是当年C51BBS里的天才级人物啊,所以工作时有幸跟高手共事就很幸运了!!
N年前也经常上C51bbs,这几个人都是牛人,现在没去过了
讲习所是高手,hotpower是怪才。 如果讲习所能出书的话,我肯定会买,要学习他的思想。
8051时间触发嵌入式操作系统 大概这个名字,有系统的讲解
(稍后补充)