#include <reg52.h>
#define uint unsigned int
#define uchar unsigned char
sbit LED0 = P1^0; // 定义LED0连接到P1口的第0位
sbit LED1 = P1^1; // 定义LED1连接到P1口的第1位
sbit LED2 = P1^2; // 以此类推...
sbit LED3 = P1^3;
sbit LED4 = P1^4;
sbit LED5 = P1^5;
sbit LED6 = P1^6;
sbit LED7 = P1^7;
void delay(uint ms) {
uint i, j;
for (i = ms; i > 0; i--)
for (j = 110; j > 0; j--);
}
// 左移流水灯
void left_shift() {
uchar i;
for (i = 0x01; i != 0x00; i <<= 1) {
P1 = ~i; // 将i的值取反后赋值给P1口,因为LED是共阳极接法,所以取反
delay(500); // 延时500ms
}
}
// 右移流水灯
void right_shift() {
uchar i;
for (i = 0x80; i != 0x00; i >>= 1) {
P1 = ~i; // 同上
delay(500); // 延时500ms
}
}
// 左右循环流水灯
void left_right_shift() {
uchar i, direction = 1; // direction用于控制方向,1表示左移,-1表示右移
while (1) {
for (i = 0x01; i != 0x00 && i != 0xFF; i <<= (direction == 1 ? 1 : -1)) {
if (i == 0x80 && direction == 1) { // 到达最右端时改变方向
direction = -1;
i >>= 1; // 因为上面已经左移了一位,所以要右移回来
} else if (i == 0x01 && direction == -1) { // 到达最左端时改变方向
direction = 1;
// i <<= 1; // 这里不需要左移,因为for循环会自动左移
}
P1 = ~i; // 同上
delay(500); // 延时500ms
}
// 当i等于0xFF时,表示已经遍历完所有LED,可以退出循环(但在这个例子中我们不让它退出)
// 为了简化代码,这里我们让i在到达0xFF后继续从0x01开始循环
// 如果不希望无限循环,可以在适当的位置加入退出条件
}
}
void main() {
while (1) {
// left_shift(); // 调用左移函数(只启用一个函数时取消注释)
// right_shift(); // 调用右移函数(只启用一个函数时取消注释)
left_right_shift(); // 调用左右循环流水灯函数
}
}