#c# #loops #button
Вопрос:
Я пытаюсь создать приложение, которое взаимодействует с arduino, и для перемещения сервопривода ему требуется вход от последовательного. Я кое-что сделал, но мне нужно продолжать нажимать кнопку, чтобы отправить переменную в последовательный, но мне нужно, чтобы она работала так же, как кнопка, поэтому, если я удерживаю ее нажатой, она продолжает отправлять переменные в последовательный.
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace test
{
public partial class Form1 : Form
{
private void Form1_Load(object sender, EventArgs e)
{
serialPort1.Open();
}
private void Form1_FormClosed(object sender, FormClosedEventArgs e)
{
serialPort1.Close();
}
public Form1()
{
InitializeComponent();
}
private void button3_MouseDown(object sender, MouseEventArgs e)
{
serialPort1.Write("z");
}
private void button4_MouseDown(object sender, MouseEventArgs e)
{
serialPort1.Write("c");
}
private void button1_MoseDown(object sender, MouseEventArgs e)
{
serialPort1.Write("a");
}
private void button2_MouseDown(object sender, MouseEventArgs e)
{
serialPort1.Write("d");
}
}
}
а вот и arduino
#include<Servo.h> // include server library
Servo ser;
Servo ser1;// create servo object to control a servo
int poser = 0; // initial position of server
int val; // initial value of input
void setup() {
Serial.begin(9600); // Serial comm begin at 9600bps
ser.attach(9);// server is connected at pin 9
}
void loop() {
if (Serial.available()) // if serial value is available
{
val = Serial.read();// then read the serial value
if (val == 'd') //if value input is equals to d
{
poser = 1; //than position of servo motor increases by 1 ( anti clockwise)
ser.write(poser);// the servo will move according to position
delay(10);//delay for the servo to get to the position
}
if (val == 'a') //if value input is equals to a
{
poser -= 1; //than position of servo motor decreases by 1 (clockwise)
ser.write(poser);// the servo will move according to position
delay(10);//delay for the servo to get to the position
}
if (val == 'c') //if value input is equals to d
{
poser = 10; //than position of servo motor increases by 1 ( anti clockwise)
ser.write(poser);// the servo will move according to position
delay(10);//delay for the servo to get to the position
}
if (val == 'z') //if value input is equals to a
{
poser -= 10; //than position of servo motor decreases by 1 (clockwise)
ser.write(poser);// the servo will move according to position
delay(10);//delay for the servo to get to the position
}
}
}
Комментарии:
1. Установите флажок, когда кнопка есть
down
, и снимите флажок, когда кнопка естьup
. Запустите задачу с помощью TPL, проверьте состояние флага и отправьте последовательное сообщение с заданным интервалом. Смотрите здесь: docs.microsoft.com/en-us/dotnet/standard/parallel-programming/…2. Вы также можете использовать таймер — в нем есть встроенный
Timer
класс,System.Threading
который запускает событие каждые X интервалов, где X может быть любым промежутком времени. Это, по сути, вызывает событие, когда прошло время.3. вам нужна кнопка повтора, этот элемент управления существует в WPF, но я не знаю, существует ли он в winforms или нет
Ответ №1:
Я бы предложил использовать задачу с маркером отмены. Из раздела Как: Отменить задачу и ее дочерние элементы
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace test
{
public partial class Form1 : Form
{
CancellationTokenSource taskATokenSource = new CancellationTokenSource();
private void button1_MoseDown(object sender, MouseEventArgs e)
{
Task.Run(TaskA(taskATokenSource.Token), taskATokenSource.Token);
}
private void button1_MoseUp(object sender, MouseEventArgs e)
{
taskATokenSource.Cancel();
}
private Action TaskA(CancellationToken ct)
{
//For example only
//Needs slowed down or some other way to prevent input buffer from overflowing.
while (!ct.IsCancellationRequested)
{
serialPort1.Write("a");
}
return null;
}