项目:基于百度API智能语音家居控制系统

 

目录

开发平台/开发环境:

        windows 10、Linux、arm cortex A9(Exynos 4412)、ubuntu20.04、zigebee通信、摄像头外设、cortex-M0;

项目模块:

        摄像头模块;qt界面及语音识别模块;qt客户端模块;服务器模块;

项目描述:

        qt客户端可以通过连接服务器后,通过语音识别,确定想要的功能,可以通过服务器显示摄像头内的视频内容,也可以通过服务器的串口通信去操控cortex M0的LED灯,风扇,蜂鸣器,服务器可以通过串口通信实时地获得cortex M0上的温度,湿度,光照信息,并发送给客户端,qt客户端还可以获取天气预报信息或者打开某一个应用。

具体代码:

        1.串口模块:

serial.h:

 serial.c:

 摄像头:

 camera.h:

 camera.c

 摄像头服务器:

camera_server.h:

camera_server.c:

服务器:

server.h

 server.c

主函数

main.c

下面是QT的模块:使用的模式是:QT widgets applicantion;使用的基类是:widget

 录音和设置语音文件:对应下面audio.c

audio.h

http请求百度api获取请求数据:

http.h

处理http请求数据并再次请求百度api再次返回的json:

speech.h

通过http协议获取天气 :

weather.h

 界面操作:

widget.h

audio.cpp

http.cpp

 main.cpp

speech.cpp

weather.cpp

widget.cpp

 ui界面:

 演示:


开发平台/开发环境:

        windows 10、Linux、arm cortex A9(Exynos 4412)、ubuntu20.04、zigebee通信、摄像头外设、cortex-M0;

arm cortex A9(Exynos 4412):内部使用裁剪后的Linux系统来搭建服务器。

ubuntu20.04:使用arm-linux-gcc工具编译成可以在arm架构芯片上执行的程序。

zigbee协调节点板块与A9板使用串口通信,ZigBee 模块主要实现的是数据的透传的工作,一个 ZigBee 节点接收服务器的消息无线转到ZigBee 的另外一个节点,另外一个节点把数据发送给终端设备,完成操作。同时也可以反过来,是终端设备的环境信息。我使用的CC2530 的单片机。它是一款完全兼容 8051 的内核,同时支持 IEEE 802.15.4协议的无线射频的单片机。这个项目主要是使用 ZigBee 提供的协议栈来进行开发。使用了其中的函数接口来完成项目需求的应用程序。


数据终端采集:
数据采集模块使用的是 ARM 系列的 Cortex-M0 芯片,在这个芯片的基础之上。分别外接了以下几个设备。有温湿度、光照、三轴传感器与 RFID 射频模块。还是风扇、LED、蜂鸣器、OLED 硬件。同时集成第 94 页了 RS485、CAN 总线。在这个项目中,使用到了温湿度、光照、三轴传感器获取当前的环境信息,发送到ZigBee 的节点。从 ZigBee 的节点接收命令通过风扇、LED、蜂鸣器来模拟家中的电器设备。在这个模块中使用了 ARM 开发的一些流程,如配置寄存器让硬件工作。一些总线设备的使用,如 SPI、I2C。还有中断的机制和定时器的使用,如本项目中启用了一个 32 位的定时器来做延时操作。

项目模块:

        摄像头模块;qt界面及语音识别模块;qt客户端模块;服务器模块;

项目描述:

        qt客户端可以通过连接服务器后,通过语音识别,确定想要的功能,可以通过服务器显示摄像头内的视频内容,也可以通过服务器的串口通信去操控cortex M0的LED灯,风扇,蜂鸣器,服务器可以通过串口通信实时地获得cortex M0上的温度,湿度,光照信息,并发送给客户端,qt客户端还可以获取天气预报信息或者打开某一个应用。

具体代码:

        1.串口模块:

serial.h:

#ifndef SERIAL_H
#define SERIAL_H

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
int serial_set(char *path);
int serial_write(int fd);
int serial_close(int fd);
int serial_ctrl(int fd,char *p);
int serial_getdata(int fd);

#endif

 serial.c:

#include 
#include 
#include 
#include 
#include 
#include 
#include 

#define N 36
int serial_set(char *path)
{
    struct termios options;
    /*
       struct termios {
       tcflag_t  c_iflag;//输入标志
       tcflag_t  c_oflag;//输出标志
       tcflag_t  c_lflag;// 本地标志
       tcflag_t  c_cc[NCCS];//控制字符
       };	
       */
    int fd = open(path,O_RDWR | O_NOCTTY | O_NDELAY);//打开串口
    if(-1 == fd)
    {
        perror("open error");
        return -1;
    }


    if(-1 == fcntl(fd,F_SETFL,0))
    {
        printf("fcntl error");
        return -1;
    }
    cfsetispeed(&options,B115200);
    cfsetospeed(&options,B115200);

    options.c_cflag |= CLOCAL;  
    //修改控制模式,使得能够从串口中读取输入数据  
    options.c_cflag |= CREAD;  
    options.c_oflag &= ~(ONLCR | OCRNL);
    options.c_iflag &= ~(BRKINT | ICRNL | INPCK | ISTRIP | IXON);
    options.c_iflag &= ~(ICRNL | INLCR);
    options.c_iflag &= ~(IXON | IXOFF | IXANY);

    //不使用流控制
    options.c_cflag &= ~CRTSCTS;
    options.c_cflag |= CS8;

    options.c_cflag &= ~CSTOPB;
    options.c_cflag &= ~PARENB;
    options.c_iflag &= ~INPCK;

    tcsetattr(fd, TCSANOW, &options); //TCSANOW更改立即发生
    return fd;
}
int serial_close(int fd) //关闭串口
{
    if (close(fd)) 
    {
        perror("serial close error");
        return -1;
    }
    return 0;
}
int serial_ctrl(int fd,char *p)
{  
    unsigned char envbuf[36]={0,0x08,0x24,0x00};
    if(strncmp(p,"light_on",8)==0)
    {
        //envbuf[]  = {0xdd,id,24,00,命令}
        //发送命令开灯
        envbuf[0]=0xdd;
        envbuf[4]=0x00;   //开灯命令
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
    }
    else if(strncmp(p,"light_off",9)==0)
    {
        //发送命令关灯
        envbuf[0]=0xdd;
        envbuf[4]=0x01; //关灯
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
    }
    else if(strncmp(p,"dshi_on",9)==0)
    {
        //发送命令打开蜂鸣器
        envbuf[0]=0xdd;
        envbuf[4]=0x02;  
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
    }
    else if(strncmp(p,"dshi_off",10)==0)
    {
        //发送命令关闭蜂鸣器
        envbuf[0]=0xdd;
        envbuf[4]=0x03;
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
    }
    else if(strncmp(p,"feng_on",7)==0)
    {
        printf("feng_on\n");
        //发送命令打开风扇
        envbuf[0]=0xdd;
        envbuf[4]=0x04;
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
    }
    else if(strncmp(p,"feng_off",8)==0)
    {
        //发送命令关闭风扇
        envbuf[0]=0xdd;
        envbuf[4]=0x08;
        if(write(fd,envbuf,36)<0)
        {
            perror("write");
            return -1;
        }
        printf("控制:%x %x %x %x %x\n",envbuf[0],envbuf[1],envbuf[2],envbuf[3],envbuf[4]);
    }

    //        memset(p, 0, 32); //清空buf
    return 0;
}

 摄像头:

 camera.h:

#ifndef _CAMERA_H
#define _CAMERA_H

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 

#define pwd "/dev/video0"
#define pwd2 "/dev/video1"
#define c_count 4

unsigned char *mmps[c_count];
unsigned long mmpsize[c_count];

int camera_init();
int camera_star(int fd);
//出队,采集数据
int dqbuf(int fd,int index);
//入队,归还数据
int qbuf(int fd,int index);
int camera_stop(int fd);

#endif

 camera.c

#include "camera.h"

int camera_init()
{
	int ret;
	//
	v4l2_std_id std;
	//
	struct v4l2_format fmt;
	//使用非阻塞方式打开摄像头设备
	int camera_fd = open(pwd,O_RDWR,0);
	if(camera_fd < 0)
	{
		camera_fd = open(pwd2,O_RDWR | O_NONBLOCK,0);
	} 
	if(camera_fd < 0)
	{
		printf("摄像头打开失败\n");
		return -1;
	} 
	printf("成功打开摄像头\n");
	
	//使用ioctl函数对设备的io通道进行管理
	//检查当前视频设备支持的标准,使用VIDIOC_QUERYSTD
/*	do{
		ret = ioctl(camera_fd,VIDIOC_QUERYSTD,&std); 
	}while(-1 == ret && errno == EAGAIN);
	switch (std)
	{
		case V4L2_STD_NTSC:
			printf("视频标准为NTSC\n");	
			break;	
		case V4L2_STD_PAL:
			printf("视频标准为PAL\n");
			break;
	}
	*/
	
	//设置视频捕获格式
	
	bzero(&fmt,sizeof(fmt));
	//摄像头的数据流类型,必须为V4L2_BUF_TYPE_VIDEO_CAPTURE
	fmt.type					= V4L2_BUF_TYPE_VIDEO_CAPTURE;
	fmt.fmt.pix.width			= 640; //必须为16的倍数
	fmt.fmt.pix.height		= 480; //必须为16的倍数
	//视频数据存储类型YUYV 或者 RGB
	fmt.fmt.pix.pixelformat	= V4L2_PIX_FMT_MJPEG;
	fmt.fmt.pix.field			= V4L2_FIELD_INTERLACED;
	
	if(-1 == ioctl(camera_fd,VIDIOC_S_FMT,&fmt))
	{
		printf("设置视频捕获格式失败\n");
		return -2;
	}
	
	//为视频捕获分配内存
	struct v4l2_requestbuffers req;
	bzero(&req,sizeof(req));
	req.count	= c_count;
	req.type		= V4L2_BUF_TYPE_VIDEO_CAPTURE;
	req.memory	= V4L2_MEMORY_MMAP;
	if(-1 == ioctl(camera_fd,VIDIOC_REQBUFS,&req))
	{
		printf("分配内存出错\n");
		return -3;
	}
	printf("分配内存成功\n");
	int i;
	struct v4l2_buffer buffer;
	for(i=0;i ioctl(camera_fd,VIDIOC_QUERYBUF,&buffer))
		{
			printf("取出映射地址出错\n");
			return -1;
		}
		//映射
		mmps[i] = mmap(NULL,buffer.length,PROT_READ|PROT_WRITE,MAP_SHARED,camera_fd,buffer.m.offset);
		mmpsize[i] = buffer.length;
		if((void *)-1 == mmps

你可能感兴趣的:(物联网,arm开发,qt,语音识别,http)