找回密码
 马上注册

QQ登录

只需一步,快速开始

查看: 12314|回复: 7

最直的三百厘米——开环控制的小车

[复制链接]
发表于 2017-7-25 22:09:23 | 显示全部楼层 |阅读模式
本帖最后由 hello怪 于 2017-7-25 22:24 编辑
* t$ q) w- Y) W$ L0 A
' L+ e' L: S( g* ~
(视频里面最终轮子与黑线的距离,都不超过6mm,最小距离只有2mm。虽然也有运气成分在里面,不过就结果来讲已经很令人满意了^_^)
优酷视频网址:
http://v.youku.com/v_show/id_XMjkxOTU1MjEyNA==.html
0 H" q( S6 R% }9 N
首先说说车子的设计思路,希望也能对大家有用。我想到的影响车子走直线的因素有以下几个方面:
& j" V$ b5 g7 s$ N/ ~
场地
! G3 d6 Q  A3 Z9 d. X8 q  水平度和光滑度
在家里当然瓷砖的效果是最好的
5 P2 m* V$ V0 P! h9 m: i- a# e  线的直度
虽然规则里说起点终点之间不能有黑线,但是因为没用光感,完全是开环控制,所以也无所谓了。这里就直接用了瓷砖上的黑线来说明车子走的直不直
5 u. u* Y6 j3 H+ b1 n8 P# C: T& B3 x4 ?
车子结构; w4 e. J4 J6 g, g5 y# @
  轮子间距
* G3 p! U5 \; [     轮子间距越大越好,稍微想一下便知" |( f! I/ O! D: n" }
  轮子大小- @, ]2 Q. h- k( r/ L, U7 R
     轮子直径越小越好,而且轮皮要尽量薄(我这里用的是nxt自带的轮子)
0 L9 p/ d; x3 n+ T' C  随动轮的设计
9 s8 q8 T  [& J/ [; U# s% T  V     随动轮转动时对车子的影响应该尽量小。这里我自己想出了一个设计方案(当然我觉得别人也用过),让车子几乎不受随动轮的影响
* P, [  q% V. p$ s  重心位置7 k6 u# {$ E1 a" Z; L7 U
     重心应该稍稍靠近主动轮以增大主动轮的抓地能力。但是太靠近的话就会降低车子的稳定性,并且升级空间较小
( M4 C& [& [/ v. O* H$ G' T& w4 b; F$ J  结构稳定性
不用说,肯定是越结实越好。但是不能造成重量过大9 p1 p& o& |" M% J3 L" T
  轮子个数
有三种方案:平衡车(独轮或双轮),三轮车,四轮或以上。虽然很想做平衡车,但是无奈暂时不会用陀螺仪。四轮的话转角不好把控,而且结构复杂,所以就用了最简单的三轮车。(另外,我个人认为不能拐弯的车子就不能叫车子~叫火车或者轨道炮比较合适。。。)4 _+ W) l3 A  t0 b0 I
  驱动方式
这里我选择了直接由马达驱动轮子,不经过任何齿轮传动,一种简单准确的方式驱动
; a/ {6 X: y4 r, G% r/ K1 Q/ ~* _  t; V1 Y) s2 |9 J* F- [
控制程序4 k6 b9 e& }$ p: c0 c# ]! J0 w
  运动过程控制4 i. P! N2 K/ N' u0 {4 q
     好的程序应该使轮子不打滑,车子运行平稳。由此采取平滑运动的控制方法,让车子开始时(近似)匀加速,直到速度足够(160度每秒)。在开始时,加速度甚至更小,可以参考我的程序(加速度增加->加速度不变->加速度为零)* v+ v$ q9 u- H* C. W+ W
% A; j7 t/ m8 V* X# h( x
调试与运行& |: e4 |4 E- S  A8 U, g; f
  轮子转速调整(车轮大小的设定)2 ~; `8 |3 ^+ \8 ]1 X) W
      这个就没什么办法,只能硬着头皮调了。调整轮子的大小设置,实际上就是调马达转速,没有什么更有效的解决办法/ r9 x  ?3 K, J
  起始位置车子正方向和直线间的夹角4 `$ p/ \: q& F! Y4 U8 E
      一个非常重要的因素,可谓差之毫厘谬以千里。所以尽可能减小两者的方向差。顺带一提,开环控制的小车,如果最终结果差距在一厘米只内,就已经没有什么可比性了。一厘米之内运气成分占比很大,因为0.01rad(0.5度以内)的夹角足以造成差距一厘米的偏差。这就是开环控制的特点
4 d/ V4 \* e1 H* L

, j* l% h, w+ D+ K" p) ]! W
4 s1 p, R$ m' o* C* r5 I/ k
然后上源代码:
  1. ) v) \8 c- P/ g0 F/ D0 J
  2. importlejos.robotics.navigation.DifferentialPilot;+ l5 w. ^4 \" ^- o. w9 d4 q
  3. import lejos.util.Delay;
      c) z1 C+ |* [2 H1 f
  4. 3 w% a" y6 [" @1 y5 w- {- ?* V; m6 A
  5. /**
    * z, h- f! ~$ t
  6. *Robot that stops if the buttons are presses before it completes its travel.  {3 s# B1 _  T+ L& C$ ]( i, g
  7. */
    9 g6 P% d) ~# a
  8. 4 w1 X* |( d* o) |

  9. 1 y" R) }  v5 I1 Y( [/ Z
  10. public class Straight {6 N  }: _* K0 _
  11.   DifferentialPilotpilot;: H: k6 d; h) Y
  12.   doubleleftD = 4.3, rightD = 4.3;
    3 m; s! h2 i& `+ C* \

  13. . I) L* m3 W  ^% p  I3 r$ Y
  14.   publicvoid adjust() {
    0 a. {5 m' }0 d' N; z/ J6 y+ v
  15.            //wait for release& d' [4 p$ G+ B! m# V: l
  16.            while(Button.readButtons() > 0)
    ' T  Y9 j2 K, G7 d
  17.                    ;3 v  q3 S  t1 U) y, I  _
  18.            while(Button.readButtons() == 0) {2 \: A( l! M  ~+ ^/ h
  19.                    //input size by adjusting the wheels
    0 P/ \+ u2 }$ P
  20.                    rightD= (double) (Motor.A.getTachoCount()) / 2160 + 4.3;
    7 b( r& f6 P& q- v* V: [
  21.                    leftD= (double) (Motor.B.getTachoCount()) / 2160 + 4.3148;// 调试所得值
    1 h- Z4 c9 Q; K7 q9 c% Y
  22. * e, F# c# N2 M
  23.                    //display the size input5 x! r+ q+ w! E5 w/ o
  24.                    LCD.drawString("L:"+ String.valueOf(leftD), 0, 0);
      [9 v, e9 r: }2 w! U( f
  25.                    LCD.drawString("R:"+ String.valueOf(rightD), 0, 1);" @! K1 T* ^/ ^; I( s$ M
  26.                    Delay.msDelay(100);
    ; J/ D* Y3 U! q$ L
  27.                    LCD.clear();
    $ j4 o) j: U6 Q* a4 u
  28.            }8 s) U+ s/ A# V1 n. ?) {2 V
  29. ; P; _( ?6 Z3 K; H
  30.   }
      S6 H- T+ l/ p2 ~( e

  31. 6 C; n) O7 F3 d9 C9 \% O, W
  32.   publicvoid go() {. K6 I% g0 T% q# ~  Y) J- I8 H7 }6 H
  33.            //准备起步3 k3 \* l5 t4 J" W# O
  34.            //wait for release
    9 }3 r( h; l: B0 c$ v" M: k
  35.            while(Button.readButtons() > 0)
    # p6 v7 _5 L! `( K; V
  36.                    ;% P( H) w, ^1 l  \7 Y4 ~3 l
  37.            System.out.println("pressto go");2 n& g& Y- W8 z$ c
  38. 3 X8 |3 E6 d0 Z  [
  39.            Button.waitForAnyPress();4 ~+ m, }3 i7 f- O7 F
  40.            LCD.clear();
    - {8 ?+ N) Z% U2 l3 \

  41. + c  b9 z4 }, f9 M. ?4 b$ \
  42.            //初始化
    $ {' n4 y+ g$ n( o1 h0 U
  43.            pilot= new DifferentialPilot(rightD, leftD, 13.5, Motor.A, Motor.B, true);. k2 U0 b- e- I' ?- b
  44.            pilot.reset();6 x: L4 E2 G1 ]. F# F1 K

  45. . ]! @% e" Z! Q8 z
  46.            Delay.msDelay(3000);
    7 ]8 N3 g$ _' j! x3 s  s9 h0 h: L: r
  47. % P4 e6 o! Y) U# e  |6 y
  48.            doublespeed = 10;
    # O* Z/ G1 ~: N
  49.            doubledistance = 0;
    ! {+ G; X. Z4 `) H8 o" y8 n

  50. 3 U! R2 ~' I/ ^; H* k" X
  51.            //起步加速
    ) c  K( u' B# y6 F/ S" g
  52.            pilot.travel(300,true);$ E% H  A/ A  P3 A' B  \
  53. - n& s6 o2 q/ t9 @! F% C! P& f% \
  54.            while(distance < 20) {
    7 b; G* F7 I. v2 g  }* E
  55.                    distance= pilot.getMovement().getDistanceTraveled();) e: J3 x1 ~' a  M/ h3 {
  56.                    speed= distance * 5 + 10;
    1 s; u. @1 s7 ~0 J1 ^. Q
  57.                    pilot.setRotateSpeed(speed);3 k. J; Q6 Y! {
  58.                    Delay.msDelay(100);& P) N' Q2 G; f
  59.            }' I! `9 g# V3 T7 ?3 S& j) h, N
  60.            for(int i = 0; i < 10; i++) {
    # k( O% Y7 E% R! m4 E% r8 b. r! a2 l
  61.                    speed+= 5;
    . u7 K; V( r( V# U0 a
  62.                    pilot.setRotateSpeed(speed);, {$ t* |0 N3 z7 G
  63.                    Delay.msDelay(200);. i- T/ J1 T' p" C6 _+ M& ]
  64.            }
    , H5 y2 x4 y* H( C# w: O6 ^

  65. 1 W) y+ r) a5 h, \; n
  66.            //TODO 减速
    3 m7 Q& [1 X, C0 p6 {) x
  67. * f/ l* @( \4 \+ j  c
  68.            //停止机能
    - w8 P9 D7 [- P4 Z; F0 c
  69.            while(pilot.isMoving()) {
    3 O5 v% z% @/ [0 q" }
  70.                    if(Button.readButtons() > 0)
    - z( h6 @9 m1 _8 G1 ?& s
  71.                            pilot.stop();* Q6 Z8 W/ e4 }& W) q3 `. f: E
  72.            }- C9 I2 _! t3 b, r6 B
  73. ; [5 i8 O3 _/ _' G; N
  74.            System.out.println("" + pilot.getMovement().getDistanceTraveled());
    - P0 P) h# [2 y
  75.            System.out.println(-Motor.A.getTachoCount());$ u) P/ c$ \9 I1 n
  76.            System.out.println(-Motor.B.getTachoCount());8 A7 L( z7 Q- ~; t- x; H: `
  77.            Button.waitForAnyPress();* R' f# x  S& p5 ]$ c- Q
  78.   }/ s- s; g0 [4 ~  d" q/ `
  79. ( i5 h. m8 m* Q
  80.   publicstatic void main(String[] args) {
    9 y" w% j  q$ P  d- z
  81.            Straighttraveler = new Straight();
    ! G+ }& g" R% f
  82. 9 w& ]8 j- @' q6 w. j: u/ k6 K
  83.            traveler.adjust();  h# Q/ z% y1 A  u# ]
  84.            traveler.go();
    ( E, U4 m9 W+ @" h0 n
  85.   }
    ' P7 X+ h' a# Y
  86. }
复制代码
; N2 {# r- Q, L) H# C( x1 ~. r- o
IMG_20170720_111026()().jpg
IMG_20170720_114534()().jpg

轮子外缘与标尺间的距离:半个乐高单位

轮子外缘与标尺间的距离:半个乐高单位
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
 楼主| 发表于 2017-7-25 22:10:06 | 显示全部楼层
二楼自占备用,欢迎发表评论
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2017-7-26 01:34:48 | 显示全部楼层
这个源代码是什么语言呀
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2017-7-26 07:22:29 | 显示全部楼层
本帖最后由 clx 于 2017-7-26 07:26 编辑
7 ^$ S9 j2 d4 j2 [" {( Z! T7 [. o/ K6 X- q
这一行行代码,C?,暂还不懂,反正看到写代码的都敬仰,这种程序是不是比G(乐高是不是叫G语言)的严谨,用代码程序的机器人都能很好的实现复杂功能
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2017-7-26 10:08:44 | 显示全部楼层
clx 发表于 2017-7-26 07:22
* I* L5 {  K) k; O. O! p7 J/ ^这一行行代码,C?,暂还不懂,反正看到写代码的都敬仰,这种程序是不是比G(乐高是不是叫G语言)的严谨, ...
; }! H) z' S$ W2 }
我用的是lejos,一种基于Java的nxt专用语言。论严谨的话,程序结构的严谨和语言选择是无关的,但是不同的语言确实各有专长。比如这个lejos,他的函数库就比G大若干倍,有很多别人写过的东西可以直接拿来用。虽然G很适合给小朋友和初学者普及(本来就是针对于此),但是图形编程界面本身不适合大项目的编写,如果想要深入玩乐高的话转向代码是必然的
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2017-7-26 10:23:44 | 显示全部楼层
学习了,在乐高深入了解方向还不太明确,转代码确实必不可少
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2017-7-29 16:34:41 | 显示全部楼层
车子结构很好,赞
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

发表于 2019-8-16 14:40:13 | 显示全部楼层
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 马上注册

本版积分规则

手机版|中文乐高 ( 桂ICP备13001575号-7 )

GMT+8, 2026-6-14 16:01 , Processed in 0.386472 second(s), 19 queries .

Powered by Discuz! X3.5

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表