对于Arduino,可以用
void(* resetFunc)(void) = 0;
......
resetFunc();
进行软复位。
但是,本人的UNO进行过这一操作后出现异常复位的现象。
laser.h如下:
#include "Arduino.h"
#include
#include
#define pi 3.14
#define ir1 16738455
#define ir2 16750695
#define ir3 16756815
#define ir4 16724175
#define ir5 16718055
#define ir6 16743045
#define ir7 16716015
#define ir8 16726215
#define ir9 16734885
#define ir0 16730805
#define irj 16732845
#define irx 16728765
#define longpress 4294967295
#define irok 16712445
#define left 16720605
#define right 16761405
#define down 16754775
#define up 16736925
using namespace std;
void laserSet(int,int,int);
void trans(float fa[], short int si[]);
void circle(short int x[], short int y[], float r);
void ellipse(short int x[], short int y[], float a, float b);
void heart(short x[], short y[], float a);
float serialIn(const char*);
void constout(short a[], short b[]);
void zoomout(short a[], short b[], float c);
void rotout(short a[], short b[], float c);
void rzout(short a[], short b[], float c, float d);
char irmode(int);
float irin(int,const char*);
short shape(const char* instream, int pin);
void t_ellipse(const char* instream, int pin, short x[], short y[]);
void t_circle(const char* instream, int pin, short x[], short y[]);
void t_heart(const char* instream, int pin, short x[], short y[]);
laser.cpp如下:
#include "laser.h"
void laserSet(int xpin,int ypin,int kpin) {
TCCR1B = TCCR1B & 0b11111000 | 1;//调整系统时钟
pinMode(xpin, OUTPUT);//x 连9
pinMode(ypin, OUTPUT);//y 连10
pinMode(kpin, OUTPUT); //laser on/off,连4
pinMode(13, OUTPUT);
digitalWrite(kpin, LOW);//关闭激光输出
digitalWrite(13, LOW);
Serial.begin(115200);
while (Serial.read() > 0);
}
void trans(float fa[], short int si[]) {//将浮点数据转为整形(0-255)
for (int i = 0; i < 90; i++)
si[i] = (short int)(fa[i]) + 128;
}
void circle(short int x[], short int y[], float r) {//生成圆坐标并转化,可自定义半径
float m[90], n[90];
for (int i = 0; i < 90; i++) {
m[i] = r * cos((2 * pi / 90) * i);
n[i] = r * sin((2 * pi / 90) * i);
}
trans(m, x);
trans(n, y);
delete []m;
delete []n;
}
void ellipse(short int x[], short int y[],float a, float b) {//生成椭圆坐标并转化,可自定义a、b
float m[90], n[90];
for (int i = 0; i < 90; i++) {
m[i] = a * cos(2 * (i * pi) / 90);
n[i] = b * sin(2 * (i * pi) / 90);
}
trans(m, x);
trans(n, y);
delete []m;
delete []n;
}
void heart(short x[], short y[], float a) {
float m[90], n[90];
for (unsigned short i = 0; i < 90; i++) {
m[i] = a * acos(sin(i*pi / 45))*cos(i*pi / 45);
n[i] = a * acos(sin(i*pi / 45))*sin(i*pi / 45);
}
trans(m, x);
trans(n, y);
delete[]m;
delete[]n;
}
float serialIn(const char* a) {
float b;
Serial.print(a);
while (Serial.available() == 0);
b = Serial.parseFloat();
Serial.println(b);
Serial.flush();
return b;
}
void constout(short a[], short b[]) {
for (int i = 0; i < 90; i++) {
analogWrite(9, a[i]);
analogWrite(10, b[i]);
}
}
void zoomout(short a[], short b[], float c) {
for (float t = c; t <= 1; t += 0.1) {
for (int i = 0; i < 90; i++) {
analogWrite(9, (int)((a[i] - 128)*t) + 128);
analogWrite(10, (int)((b[i] - 128)*t) + 128);
}
analogWrite(9, (int)((a[89] - 128)*t) + 128);
analogWrite(10, (int)((b[89] - 128)*t) + 128);
delay(10);
}
}
void rotout(short a[], short b[], float c) {
for (float t = 0; t <= 2 * pi / c; t++) {
for (int i = 0; i < 90; i++) {
analogWrite(9, (int)((a[i] - 128)*cos(t * c) + (b[i] - 128)*sin(t * c)) + 128);
analogWrite(10, (int)((b[i] - 128)*cos(t * c) - (a[i] - 128)*sin(t * c)) + 128);
}
}
}
void rzout(short a[], short b[], float c, float d) {
for (float t = c; t <= 1; t += 0.1) {
for (float p = 0; p <= 2 * pi / d; p++) {
for (int i = 0; i < 90; i++) {
analogWrite(9, (int)(((a[i] - 128)*t)*cos(p * d) + ((b[i] - 128)*t)*sin(p * d)) + 128);
analogWrite(10, (int)(((b[i] - 128)*t)*cos(p * d) - ((a[i] - 128)*t)*sin(p * d)) + 128);
}
}
}
}
char irmode(int pin) {//ir请连11
IRrecv irrecv(pin);
decode_results results;
irrecv.enableIRIn();
while (!irrecv.decode(&results));
if (irrecv.decode(&results)) {
if (results.value == ir1)
return '1';
if (results.value == ir2)
return '2';
if (results.value == ir3)
return '3';
if (results.value == ir4)
return '4';
if (results.value == ir5)
return '5';
if (results.value == ir6)
return '6';
if (results.value == ir7)
return '7';
if (results.value == ir8)
return '8';
if (results.value == ir9)
return '9';
if (results.value == ir0)
return '0';
if (results.value == irx)
return '.';
if (results.value == irok)
return '\0';
}
}
float irin(int pin,const char* item) {
Serial.print(item);
short i = 0;
char buf[10];
while (i < 9) {
buf[i] = irmode(pin);
if (buf[i] == '\0')
break;
i++;
}
return atof(buf);
}
short shape(const char* instream,int pin) {
Serial.println("请输入您的图形模式。(椭圆为1,圆为2,心形线为3)");
short temporary = 0;
if (strcmp(instream, "Serial") == 0) {
while (Serial.available() == 0);
temporary = Serial.parseInt();
}
if (strcmp(instream, "IR") == 0) {
char temp[2] = { '0','\0' };
temp[0] = irmode(pin);
temporary = atoi(temp);
}
Serial.print(temporary);
Serial.print("、");
if (temporary == 1)
Serial.println("椭圆");
if (temporary == 2)
Serial.println("圆");
if (temporary == 3)
Serial.println("心形线");
if (temporary == 1 || temporary == 2 || temporary == 3)
return temporary;
else
return (-1);
}
void t_ellipse(const char* instream, int pin,short x[], short y[]) {
Serial.println("OK!");
eerr_pos:float a, b = 0;
if (strcmp(instream, "Serial") == 0) {
a = serialIn("x轴半径 a=");
b = serialIn("y轴半径 b=");
}
if (strcmp(instream, "IR") == 0) {
a = irin(pin,"x轴半径 a=");
b = irin(pin,"y轴半径 b=");
}
if (a < 0 || b < 0 || a>128 || b>128) {
Serial.println("超出范围!");
goto eerr_pos;
}
ellipse(x, y, a, b);
}
void t_circle(const char* instream, int pin, short x[], short y[]) {
Serial.println("OK!");
cerr_pos:float r = 0;
if(strcmp(instream, "Serial") == 0)
r = serialIn("半径 r=");
if (strcmp(instream, "IR") == 0)
r = irin(pin, "半径 r=");
if (r < 0 || r>128) {
Serial.println("超出范围!");
goto cerr_pos;
}
circle(x, y, r);
}
void t_heart(const char* instream, int pin, short x[], short y[]) {
Serial.println("OK!");
herr_pos:float a = 0;
if (strcmp(instream, "Serial") == 0)
a = serialIn("比例系数(0-36) a=");
if (strcmp(instream, "IR") == 0)
a = irin(pin, "比例系数(0-36) a=");
if (a <= 0 || a > 36) {
Serial.println("超出范围!");
goto herr_pos;
}
heart(x, y, a);
}
.ino文件如下:
#include //自定义库文件
//先指定输入方式,使用串口请输入"Serial",使用ir请输入"IR"
//输出椭圆用serial的1或者ir的1
//输出圆用serial的2或者ir的2
//输出心形线用serial的3或者ir的3
short x[90], y[90];//x,y坐标组合
float beta = 1;//放大率beta
float omega = 0;//旋转角速度omega
const int irpin = 11;//可更改,ir初始连11
void(* resetFunc)(void) = 0;//虚拟复位
void setup() {
// put your setup code here, to run once:
laserSet(9, 10, 4);//可更改,x->9,y->10,key->4
Serial.println("==================================");
Serial.println("欢迎使用激光表演系统!");
Serial.println("激光输出状态:关闭。");
Serial.println("当板载LED(L,13)常亮时,需注意激光输出!");
String imodestr = "";//指示输入方式
char imode[10];
istream_pos: short buff = 0;//存图形
Serial.println("请指定输入方式。(Serial或IR)");
while (Serial.available() == 0);
imodestr = Serial.readString();
strcpy(imode, imodestr.c_str());
Serial.println(imodestr);
if (strcmp(imode, "Serial") != 0 && strcmp(imode, "IR") != 0) {
Serial.println("错误!");
goto istream_pos;
}
if (strcmp(imode, "IR") == 0)
Serial.println("小数点请用星号键输入。");
spos: buff = shape(imode, irpin);
if (buff == (-1)) {
Serial.println("指令错误!");
goto spos;
}
if (buff == 1) {
t_ellipse(imode, irpin, x, y);//异常复位点
while (Serial.read() > 0);
}
if (buff == 2) {
t_circle(imode, irpin, x, y);//异常复位点
while (Serial.read() > 0);
}
if (buff == 3) {
t_heart(imode, irpin, x, y);//异常复位点
while (Serial.read() > 0);
}
bpos: if (strcmp(imode, "Serial") == 0)
beta = serialIn("最小缩放倍率(<1) beta=");
if (strcmp(imode, "IR") == 0)
beta = irin(irpin, "最小缩放倍率(<1) beta=");
if (beta <= 0 || beta > 1) {
Serial.println("指令错误!");
goto bpos;
}
opos: if (strcmp(imode, "Serial") == 0)
omega = serialIn("旋转角速度(rad/ms) omega=");
if (strcmp(imode, "IR") == 0)
omega = irin(irpin, "旋转角速度(rad/ms) omega=");
if (omega < 0 || omega > 1) {
Serial.println("指令错误!");
goto opos;
}
Serial.print("若想要重新输入图形,");
Serial.print("按任意键并按回车或");
Serial.println("使用遥控器按任意键");
Serial.println("开启激光输出!注意安全!");
while (Serial.read() > 0);
digitalWrite(13, HIGH);
digitalWrite(4, HIGH);
}
void loop() {
// put your main code here, to run repeatedly:
bool key = false;
IRrecv irinstream(irpin);
decode_results res;
irinstream.enableIRIn();
if (Serial.available() != 0 || irinstream.decode(&res))
key = true;
if (!key) {
digitalWrite(13, HIGH);
if (beta == 1) {
if (omega == 0)
constout(x, y);
else
rotout(x, y, omega);
}
if (beta > 0 && beta < 1 && omega == 0)
zoomout(x, y, beta);
if (beta > 0 && beta < 1 && omega != 0)
rzout(x, y, beta, omega);
}
if (key) {
digitalWrite(4, LOW);
digitalWrite(13, LOW);
resetFunc();
}
digitalWrite(4, LOW);
digitalWrite(13, LOW);
}
请问是什么原因造成的?求各位大神指点!!