×

The Irrigator:人工智能驱动的灌溉机器人

消耗积分:2 | 格式:zip | 大小:0.60 MB | 2022-12-01

打马过草原

分享资料个

描述

The Irrigator:人工智能驱动的灌溉机器人

Irrigator是一种自主、可持续发展的智能机器人,可以照料室内和室外植物。本演示的重点是给植物浇水,但设计和实现可以扩展到执行其他任务,例如分配肥料和杀虫剂、检测土壤中的水位、检测生病的植物。

 

设计

广泛的设计目标:

自主- 它在没有(或最少的)人为交互的情况下完成工作。

可持续发展——它使用太阳能为电池充电,使用雨水为水箱注水,并且尽可能使用回收材料制成(例如,我使用回收木材、金属和螺丝制作底盘)。

智能- 它使用计算机视觉和机器学习来执行复杂的任务。

具体设计目标:

Nvidia Jetson Nano - 用作可以运行高级机器学习推理的中央控制单元。

Nvidia Isaac SDK - 用作机器人的编程平台。

机器人整体图及其主要模块如图1所示,实际实现如图2所示。

poYBAGOINEqAZ8kZAADQ33O3d7o289.png
图 1 - 灌溉器的主要模块
 
pYYBAGOINE-AJ2CTAAH2u6SyXSA231.png
图 2 - 灌溉器及其部分模块
 

 

 

硬件

下面(也在这里)是这个项目中使用的材料的详细清单(木头、螺丝、胶水、电线、胶带等除外)。价格以新加坡元为单位,链接仅供参考。对于我从当地五金店购买的某些组件,我找不到链接。但是,我在下面提供了详细信息和照片。

该项目的估计成本为 459 新元(约合 330 美元)。

 

我没有某些组件的网络参考,因为我是从我所在地区的五金店购买的。

poYBAGOINFWAUumxAAGyVGInVuY285.png
图 3 - 组件
 

在图 3 中,我展示了 (1) 一块 20W 太阳能电池板,(2) 一块 7Ah 可充电铅酸电池,(3) 2 个带齿轮箱的电机,(4) 2 个轮子,(5) 2 个电机支架,以及(6)太阳能电池板充电器一个。如果你打算建造这个机器人的复制品,你可以使用不同规格的组件,但你需要注意设计目标。例如,电机应能承载至少 10kg 的负载(主要是水箱)。电池可以具有更高的容量。我不建议使用容量低于 7Ah 的电池。太阳能电池板的功率应该足以给电池充电。

poYBAGOINFmAW_7FAAHCJBm0uZQ729.png
图 4 - 车轮
 
pYYBAGOINGyAABP9AAKoRDSDj10610.png
图 5 - 齿轮箱电机类型
 

图 4 和图 5 显示了带有齿轮箱的电机。这些是 12V、5000 转/分的电机,而齿轮箱将转速降低到 30 转,并使电机能够拉动超过 10 公斤。图 4 还显示了轮子。确保支撑轮(未连接到电机的)可以左右旋转。如果它们是固定的,您的机器人可能会由于高摩擦力而无法左转或右转。

控制单元

控制单元是机器人的“大脑”。图6是控制单元的原理图,图7是控制单元的接线图(我附上了Fritzing做的原理图),图8是实际实现。Irrigator的“大脑皮层”是一块Jetson Nano板,运行主控制回路和 AI 算法来检测植物和花盆。附加到它的是 Raspberry Pi Camera v2.1。

为了控制电机和读取所有传感器,我使用了两个Arduino Uno板。这些板代表灌溉器的“小脑”。Jetson Nano 和 Arduino Uno 之间的通信是通过SPI完成的我使用 Jetson 的J41 连接器的 SPI1 和 SPI2 引脚以及对应于其SPI 接口的 Arduino Uno 的引脚 10 (SS)、11 (MOSI)、12 (MISO)、13 (SCK)

在 Jetson 上启用 SPI ,您需要运行:

sudo /opt/nvidia/jetson-io/jetson-io.py

完成此步骤后,您可以使用/dev/spidev0.0/dev/spidev1.0与两个 Arduino 板进行通信。我使用 Linux 源代码中的SPI 测试程序作为我在 Jetson Nano 上的驱动程序的起点(请参阅Github上的更多详细信息)。

poYBAGOINHCAGOz8AACmCWpj8M4109.png
图 6 - 控制单元图
 
pYYBAGOINHiAQ0Z0AAvalVNfaqk457.png
图 7 - 控制单元示意图
 
poYBAGOINHyAOv5HAAN4hIRB9G4381.png
图 8 - 控制单元实现
 

控制单元读取以下传感器:

  • 用于对象识别的Raspberry Pi 相机模块v2.1。
  • 两个声纳 ( HC04 ) 分别放置在距地面约 5 厘米和约 50 厘米处(见图 2)。您可能想要添加更多的接近传感器以获得更高的精度。
  • 两个编码器分别检测左右两个车轮的运动。目前,我使用 IR 接近传感器实现这些编码器,但它们不是很准确。
  • 水箱水位传感器(YwRobot Water Level )。
  • 【选配】四个电流传感器,测量不同模块的用电量。这些是ADS712基于霍尔效应的线性电流传感器。

控制单元命令:

  • 使用L298 H 桥的电机。
  • 打开/关闭水泵和灯的继电器 ( SRD-05VDC-SL-C )。这些继电器需要一个额外的晶体管 ( BD137 ),因为 Arduino GPIO 电流可能不足以流过继电器的线圈。

为了分配和测量这些模块使用的能量,我创建了一个自定义配电单元。请注意,某些组件使用 12V:

  • 马达
  • 泵(需要 ~ 3A 电流)

一些组件使用 5V:

  • Jetson Nano(需要 ~3A)
  • 阿杜诺
  • 所有的传感器

软件

Irrigator的代码托管在 Github 上。您可以在README.md中找到有关设置的更多详细信息

该代码有两个主要层,(1) 机器人控制和 (2) 使用 AI 进行植物检测。对于第一层,您需要使用 Arduino IDE 和 USB-B 电缆对 Arduino 板进行编程。两块板的代码在src/arduino文件夹中。

接下来,您需要在 Jetson Nano 上运行驱动程序。控制单元的主循环用C代码表示如下:

while (run_flag) {
    go_forward();
    if (dist1 < 100 || dist2 < 100) {
        stop();
        usleep(250000);
        on_light();
        int ret = run_ai();
        if ((ret >> 8) == 1) {
            printf("Plant detected!\n");
            go_forward();
            sleep(2);
            stop();
            usleep(250000);
            on_pump();
            sleep(5);
            off_pump();
            usleep(250000);
            go_backwards();
            sleep(2);
            stop();
            usleep(250000);
        }
        off_light();
        usleep(250000);
        go_left_90();
    }
    sleep(1);
}

上面的代码告诉机器人只要声纳没有检测到障碍物(1m 以内)就向前移动。如果检测到某些障碍物,机器人将执行以下任务:

  • 停止
  • 在灯上
  • 拍张照片
  • 运行物体检测
  • 如果检测到植物或花盆,则向前移动一点,在水面上,等待几秒钟,离开水面,向后移动
  • 关灯
  • 向左转以避开障碍物

请注意,需要一些延迟(usleep() )以避免 Arduino 上的 SPI 消息丢失。

控制器可以通过两种方式实现。首先,编写 C 或 Python 程序来控制机器人的经典整体方式。这是在irrigator_spi.c中实现的要运行它,请在 Jetson 上执行这些 shell 命令:

$ cd git/irrigator/src/jetson/driver
$ make
$ ./irrigator_spi

第二种方式,模块化且灵活,是使用 Nvidia 的Isaac SDK对于这个版本的 Irrigator,我在 Github 上的src/jetson/isaac文件夹中的两个小代码 Driver 和 Detector 中实现了我的代码。Driver 处理机器人的硬件和运动,而 Detector 处理 AI 部分。他们使用 Isaac Messaging API 进行通信。

该软件的第二层包括使用 AI 对象检测的植物和盆栽检测。由于代码在 Jetson Nano 上运行,我首先考虑使用jetson-inference存储库中的教程。但是,我使用 TensorFlow Lite (TFLite) 模型获得了最佳结果。特别是,我正在使用coco_ssd_mobilenet_v1_1.0_quant_2018_06_29inception_resnet_v2_2018_04_27有关更多 TFLite 模型,请参阅TFLite 托管模型我从每个模型中获取前 3 个检测结果并搜索plant of pot关键字(参见run-all-models.sh). 目前,检测(包括拍照)需要 10-11 秒。光是拍照就需要 4 秒。

未来的工作

我计划在不久的将来进行这些优化:

  • 只在晚上开灯(使用光检测传感器或模型来检测太阳升起)
  • 根据图像中检测到的罐/计划的位置将软管枪(或机器人)居中
  • 如果检测到多个盆/植物,使用一系列灌溉步骤使机器人居中并为每株植物浇水
  • 使用 cron 作业在晚上开始灌溉,在早上为电池充电

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

评论(0)
发评论

下载排行榜

全部0条评论

快来发表一下你的评论吧 !

'+ '

'+ '

'+ ''+ '
'+ ''+ ''+ '
'+ ''+ '' ); $.get('/article/vipdownload/aid/'+webid,function(data){ if(data.code ==5){ $(pop_this).attr('href',"/login/index.html"); return false } if(data.code == 2){ //跳转到VIP升级页面 window.location.href="//m.obk20.com/vip/index?aid=" + webid return false } //是会员 if (data.code > 0) { $('body').append(htmlSetNormalDownload); var getWidth=$("#poplayer").width(); $("#poplayer").css("margin-left","-"+getWidth/2+"px"); $('#tips').html(data.msg) $('.download_confirm').click(function(){ $('#dialog').remove(); }) } else { var down_url = $('#vipdownload').attr('data-url'); isBindAnalysisForm(pop_this, down_url, 1) } }); }); //是否开通VIP $.get('/article/vipdownload/aid/'+webid,function(data){ if(data.code == 2 || data.code ==5){ //跳转到VIP升级页面 $('#vipdownload>span').text("开通VIP 免费下载") return false }else{ // 待续费 if(data.code == 3) { vipExpiredInfo.ifVipExpired = true vipExpiredInfo.vipExpiredDate = data.data.endoftime } $('#vipdownload .icon-vip-tips').remove() $('#vipdownload>span').text("VIP免积分下载") } }); }).on("click",".download_cancel",function(){ $('#dialog').remove(); }) var setWeixinShare={};//定义默认的微信分享信息,页面如果要自定义分享,直接更改此变量即可 if(window.navigator.userAgent.toLowerCase().match(/MicroMessenger/i) == 'micromessenger'){ var d={ title:'The Irrigator:人工智能驱动的灌溉机器人',//标题 desc:$('[name=description]').attr("content"), //描述 imgUrl:'https://'+location.host+'/static/images/ele-logo.png',// 分享图标,默认是logo link:'',//链接 type:'',// 分享类型,music、video或link,不填默认为link dataUrl:'',//如果type是music或video,则要提供数据链接,默认为空 success:'', // 用户确认分享后执行的回调函数 cancel:''// 用户取消分享后执行的回调函数 } setWeixinShare=$.extend(d,setWeixinShare); $.ajax({ url:"//www.obk20.com/app/wechat/index.php?s=Home/ShareConfig/index", data:"share_url="+encodeURIComponent(location.href)+"&format=jsonp&domain=m", type:'get', dataType:'jsonp', success:function(res){ if(res.status!="successed"){ return false; } $.getScript('https://res.wx.qq.com/open/js/jweixin-1.0.0.js',function(result,status){ if(status!="success"){ return false; } var getWxCfg=res.data; wx.config({ //debug: true, // 开启调试模式,调用的所有api的返回值会在客户端alert出来,若要查看传入的参数,可以在pc端打开,参数信息会通过log打出,仅在pc端时才会打印。 appId:getWxCfg.appId, // 必填,公众号的唯一标识 timestamp:getWxCfg.timestamp, // 必填,生成签名的时间戳 nonceStr:getWxCfg.nonceStr, // 必填,生成签名的随机串 signature:getWxCfg.signature,// 必填,签名,见附录1 jsApiList:['onMenuShareTimeline','onMenuShareAppMessage','onMenuShareQQ','onMenuShareWeibo','onMenuShareQZone'] // 必填,需要使用的JS接口列表,所有JS接口列表见附录2 }); wx.ready(function(){ //获取“分享到朋友圈”按钮点击状态及自定义分享内容接口 wx.onMenuShareTimeline({ title: setWeixinShare.title, // 分享标题 link: setWeixinShare.link, // 分享链接 imgUrl: setWeixinShare.imgUrl, // 分享图标 success: function () { setWeixinShare.success; // 用户确认分享后执行的回调函数 }, cancel: function () { setWeixinShare.cancel; // 用户取消分享后执行的回调函数 } }); //获取“分享给朋友”按钮点击状态及自定义分享内容接口 wx.onMenuShareAppMessage({ title: setWeixinShare.title, // 分享标题 desc: setWeixinShare.desc, // 分享描述 link: setWeixinShare.link, // 分享链接 imgUrl: setWeixinShare.imgUrl, // 分享图标 type: setWeixinShare.type, // 分享类型,music、video或link,不填默认为link dataUrl: setWeixinShare.dataUrl, // 如果type是music或video,则要提供数据链接,默认为空 success: function () { setWeixinShare.success; // 用户确认分享后执行的回调函数 }, cancel: function () { setWeixinShare.cancel; // 用户取消分享后执行的回调函数 } }); //获取“分享到QQ”按钮点击状态及自定义分享内容接口 wx.onMenuShareQQ({ title: setWeixinShare.title, // 分享标题 desc: setWeixinShare.desc, // 分享描述 link: setWeixinShare.link, // 分享链接 imgUrl: setWeixinShare.imgUrl, // 分享图标 success: function () { setWeixinShare.success; // 用户确认分享后执行的回调函数 }, cancel: function () { setWeixinShare.cancel; // 用户取消分享后执行的回调函数 } }); //获取“分享到腾讯微博”按钮点击状态及自定义分享内容接口 wx.onMenuShareWeibo({ title: setWeixinShare.title, // 分享标题 desc: setWeixinShare.desc, // 分享描述 link: setWeixinShare.link, // 分享链接 imgUrl: setWeixinShare.imgUrl, // 分享图标 success: function () { setWeixinShare.success; // 用户确认分享后执行的回调函数 }, cancel: function () { setWeixinShare.cancel; // 用户取消分享后执行的回调函数 } }); //获取“分享到QQ空间”按钮点击状态及自定义分享内容接口 wx.onMenuShareQZone({ title: setWeixinShare.title, // 分享标题 desc: setWeixinShare.desc, // 分享描述 link: setWeixinShare.link, // 分享链接 imgUrl: setWeixinShare.imgUrl, // 分享图标 success: function () { setWeixinShare.success; // 用户确认分享后执行的回调函数 }, cancel: function () { setWeixinShare.cancel; // 用户取消分享后执行的回调函数 } }); }); }); } }); } function openX_ad(posterid, htmlid, width, height) { if ($(htmlid).length > 0) { var randomnumber = Math.random(); var now_url = encodeURIComponent(window.location.href); var ga = document.createElement('iframe'); ga.src = 'https://www1.elecfans.com/www/delivery/myafr.php?target=_blank&cb=' + randomnumber + '&zoneid=' + posterid+'&prefer='+now_url; ga.width = width; ga.height = height; ga.frameBorder = 0; ga.scrolling = 'no'; var s = $(htmlid).append(ga); } } openX_ad(828, '#berry-300', 300, 250);