简体   繁体   English

在 mac 上使用 c++ 和 Xcode 打开带有 arduino 的串口

[英]Open a serial port with arduino using c++ with Xcode on mac

I've written a simple program in c++ which sends an angle value to an Arduino through a serial port;我用 C++ 编写了一个简单的程序,它通过串行端口向 Arduino 发送一个角度值; the Arduino than uses the value to control a servo motor. Arduino 然后使用该值来控制伺服电机。

This is c++ code这是 C++ 代码

#include <iostream>
#include <unistd.h>
#include <fstream>

using namespace std;

int main()
{
    unsigned int angle;
    fstream arduino;
    
    cout<<"check-1";

    arduino.open("/dev/tty.usbmodem3a21");

    cout<<"check-2";
    
    if(arduino)
    {
        do
        {
            cout<<"\n\ninsert a number between 0 and 179";
        
            cin>>angle;
            arduino<<angle;
            
        }while(angle <= 179);
        
        arduino.close();
    }
    else
    {
        cout<<"\n\nERROR!!\n\n";
    }
    
    
}

and this is arduino's:这是 arduino 的:

#include <Servo.h>

Servo servo;
const int pinServo = 2;
unsigned int angle;

void setup()
{
    Serial.begin(9600);
    servo.attach(pinServo);
    
    servo.write(0);
    
}

void loop()
{
    if(Serial.available()>0)
    {  
       angle = Serial.read();
       
       if(angle <= 179)
       {
         servo.write(angle);
       }
    }
}

The problem is that it stops at arduino.open(...) .问题是它停在arduino.open(...) Despite I checked that the selected port in the Arduino app in tools > serial port is correct, it doesn't even print out "check-1".尽管我在工具 > 串行端口中检查了 Arduino 应用程序中选择的端口是否正确,但它甚至没有打印出“check-1”。

To add more useful information, I tested opening the port with the iOS::binary parameter so the opening command becomes arduino.open("/dev/tty.usbmodem3a21",iOS::binary) ;为了添加更多有用的信息,我测试了使用iOS::binary参数打开端口,因此打开命令变为arduino.open("/dev/tty.usbmodem3a21",iOS::binary) as a result, this prints out "check-1", "check-2" and "ERROR!!".结果,这会打印出“check-1”、“check-2”和“ERROR!!”。 I get the same results if I type in a wrong serial port name.如果输入错误的串行端口名称,我会得到相同的结果。

Why is this happening and how do I fix this?为什么会发生这种情况,我该如何解决?

The arduino shows up as a serial device. arduino 显示为串行设备。 You should look at using the open() and close() function.您应该考虑使用open()close()函数。 I've done this on Linux but I'm pretty sure this works similarly on Mac.我已经在 Linux 上完成了这项工作,但我很确定这在 Mac 上的工作方式类似。 This is an example snippet of code.这是一个示例代码片段。 The first snippet opens and sets up the file descriptor.第一个片段打开并设置文件描述符。

int fd;                             // File descriptor
// Open port
fd = open("/dev/ttyACM0", O_RDWR | O_NOCTTY | O_NDELAY);
if (fd == -1){
    printf("Device cannot be opened.\n");
    exit(-1);                       // If the device is not open, return -1
}
struct termios options;

fcntl(fd, F_SETFL, FNDELAY);                    // Open the device in nonblocking mode

// Set parameters
tcgetattr(fd, &options);                        // Get the current options of the port
bzero(&options, sizeof(options));               // Clear all the options
speed_t         Speed;
switch (baudRate)                               // Set the speed (baudRate)
{
    case 110  :     Speed=B110; break;
    case 300  :     Speed=B300; break;
    case 600  :     Speed=B600; break;
    case 1200 :     Speed=B1200; break;
    case 2400 :     Speed=B2400; break;
    case 4800 :     Speed=B4800; break;
    case 9600 :     Speed=B9600; break;
    case 19200 :    Speed=B19200; break;
    case 38400 :    Speed=B38400; break;
    case 57600 :    Speed=B57600; break;
    case 115200 :   Speed=B115200; break;
    default : exit(-4);
}
cfsetispeed(&options, Speed);                   // Set the baud rate at 115200 bauds
cfsetospeed(&options, Speed);
options.c_cflag |= ( CLOCAL | CREAD |  CS8);    // Configure the device : 8 bits, no parity, no control
options.c_iflag |= ( IGNPAR | IGNBRK );
options.c_cc[VTIME]=0;                          // Timer unused
options.c_cc[VMIN]=0;                           // At least on character before satisfy reading
tcsetattr(fd, TCSANOW, &options);               // Activate the settings

This just closes it:这只是关闭它:

close(fd); 

To read from the actual file descriptor:从实际的文件描述符中读取:

ioctl(fd, FIONREAD, &t1);                           
if(t1 > 0) {
    // If the number of bytes read is equal to the number of bytes retrieved
    if(read(fd,pByte, t1) == t1) {  
        for(int i =0; i < t1; i++) {
            if(pByte[i] != '\r'){ // Just makes sure you're not scanning new lines
                // TODO: Do what you want with this character
            }
        }
    }
}

在用c++程序发送命令之前你应该做的第一件事是正确配置串口,你只需让串口闭环,你发送的所有东西都应该收到,如果你没有收到任何东西你有串口配置问题

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM