找回密码
 马上注册

QQ登录

只需一步,快速开始

查看: 10932|回复: 7

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

[复制链接]
发表于 2017-7-25 22:09:23 | 显示全部楼层 |阅读模式
本帖最后由 hello怪 于 2017-7-25 22:24 编辑
+ R4 P% e/ {1 ?5 p! V  ?! U& ~; G: |; q. w7 w- k
(视频里面最终轮子与黑线的距离,都不超过6mm,最小距离只有2mm。虽然也有运气成分在里面,不过就结果来讲已经很令人满意了^_^)
优酷视频网址:
http://v.youku.com/v_show/id_XMjkxOTU1MjEyNA==.html
' _& C$ K  ?1 T' r0 a0 N" |
首先说说车子的设计思路,希望也能对大家有用。我想到的影响车子走直线的因素有以下几个方面:

, g+ [5 Q% O" ?: e, I+ ^
场地
( F7 K. v& f* L. t' B# o% o7 A  水平度和光滑度
在家里当然瓷砖的效果是最好的# K4 {  B$ X7 ^1 Q7 P/ r) C. E
  线的直度
虽然规则里说起点终点之间不能有黑线,但是因为没用光感,完全是开环控制,所以也无所谓了。这里就直接用了瓷砖上的黑线来说明车子走的直不直7 a9 {4 s7 ]. Q" y" @) N

' R. }/ i! Y) i* Q' Z9 f1 K5 [车子结构
9 m6 {6 }! {: C  S! X  轮子间距
; P9 S1 O( [! v! i+ x: v. c1 V$ T     轮子间距越大越好,稍微想一下便知
; F9 B8 [3 F5 l1 v* [! l* R+ B- @  轮子大小; M4 v" F' }6 V) }' N
     轮子直径越小越好,而且轮皮要尽量薄(我这里用的是nxt自带的轮子)
) y1 E% l( L/ L8 y0 }* u# _5 B  随动轮的设计
- {' A3 x, i& f9 M     随动轮转动时对车子的影响应该尽量小。这里我自己想出了一个设计方案(当然我觉得别人也用过),让车子几乎不受随动轮的影响
+ U2 `6 o! x) t4 ~! F  重心位置
6 r! z" B4 T  X0 `' a/ M     重心应该稍稍靠近主动轮以增大主动轮的抓地能力。但是太靠近的话就会降低车子的稳定性,并且升级空间较小) Q1 E5 U; \& g- r! r* @8 d
  结构稳定性
不用说,肯定是越结实越好。但是不能造成重量过大/ L7 X, r  E: _1 d8 [
  轮子个数
有三种方案:平衡车(独轮或双轮),三轮车,四轮或以上。虽然很想做平衡车,但是无奈暂时不会用陀螺仪。四轮的话转角不好把控,而且结构复杂,所以就用了最简单的三轮车。(另外,我个人认为不能拐弯的车子就不能叫车子~叫火车或者轨道炮比较合适。。。)0 Q* y5 v* y( v" f" c& |
  驱动方式
这里我选择了直接由马达驱动轮子,不经过任何齿轮传动,一种简单准确的方式驱动3 J7 n4 v, ]. Z( u" L: I

! ]+ K- A! `% g  P2 o控制程序( b0 a* [. d2 E- @2 A$ h: F6 Z# x
  运动过程控制
" n0 J" q: n! O- v2 ]2 I" c2 |     好的程序应该使轮子不打滑,车子运行平稳。由此采取平滑运动的控制方法,让车子开始时(近似)匀加速,直到速度足够(160度每秒)。在开始时,加速度甚至更小,可以参考我的程序(加速度增加->加速度不变->加速度为零)9 _" [2 \5 _; C- Z: e

1 O7 Z( w! B9 j/ @调试与运行
9 o! w+ {9 |( s9 N" m4 }: n  轮子转速调整(车轮大小的设定)' [% G) ^  R; ~- D/ ~5 b
      这个就没什么办法,只能硬着头皮调了。调整轮子的大小设置,实际上就是调马达转速,没有什么更有效的解决办法
1 x. Z; R- R. R6 ?% D) V  起始位置车子正方向和直线间的夹角
! v2 e) T* z& L/ o) \, d5 M      一个非常重要的因素,可谓差之毫厘谬以千里。所以尽可能减小两者的方向差。顺带一提,开环控制的小车,如果最终结果差距在一厘米只内,就已经没有什么可比性了。一厘米之内运气成分占比很大,因为0.01rad(0.5度以内)的夹角足以造成差距一厘米的偏差。这就是开环控制的特点
( w; f8 X+ e4 U% y
0 a% R. X+ M: _2 d
$ |& s" X  w* c# Z- N& ~
然后上源代码:

  1.   S# V, p' Z2 c& @- v2 _; D$ i
  2. importlejos.robotics.navigation.DifferentialPilot;  k, X( P8 s( z! ~# N. L( H0 D# ~
  3. import lejos.util.Delay;7 l7 g# ?6 u; V
  4. ' i9 ^4 z  i! S7 g5 V1 d/ Y* e" F
  5. /**
    % A( {9 \; X; t% l' k
  6. *Robot that stops if the buttons are presses before it completes its travel.4 S. I$ L: }6 l( s; x/ e
  7. */" L5 g5 z! _% i8 s/ ^
  8. 2 d  n% z3 R$ ^/ s* J& n, k- e

  9. % m" y0 M/ p! I9 d) A7 Y: K) \
  10. public class Straight {
    5 h) g( f. M% }& I' U4 n. s
  11.   DifferentialPilotpilot;5 Q2 M6 l$ D  p3 S
  12.   doubleleftD = 4.3, rightD = 4.3;0 o: T* B5 B1 [% w

  13. 8 \2 `4 ~: |5 O0 l( G
  14.   publicvoid adjust() {
    . X1 E8 X% a& c- w' U2 ]2 Z
  15.            //wait for release
    : e- D  j3 k# ~; k8 {- T
  16.            while(Button.readButtons() > 0)3 q# L, d8 |! X* g% r; h2 b
  17.                    ;" I9 W# X* D- \4 i! n
  18.            while(Button.readButtons() == 0) {$ F, n2 ]7 n5 A
  19.                    //input size by adjusting the wheels& Z( d$ O# Z! c
  20.                    rightD= (double) (Motor.A.getTachoCount()) / 2160 + 4.3;
    9 I/ c% U# J+ F0 H
  21.                    leftD= (double) (Motor.B.getTachoCount()) / 2160 + 4.3148;// 调试所得值
    - `! i' r& Q1 M

  22. ! q  T( h, }; j/ q# L! s. r) W
  23.                    //display the size input; |) Z! ?# ~! ^# I" P% p
  24.                    LCD.drawString("L:"+ String.valueOf(leftD), 0, 0);
    - ]+ c  r1 q  o9 j1 m; p
  25.                    LCD.drawString("R:"+ String.valueOf(rightD), 0, 1);" N7 c' g! Q" e1 \/ e
  26.                    Delay.msDelay(100);9 H6 \! Q2 |9 M& S1 W7 _
  27.                    LCD.clear();
    , f8 B6 S  L' v4 t% J
  28.            }
    . }1 m, r3 z2 P, ^0 }, r
  29. 8 J8 _0 x8 ?5 U' a
  30.   }  I1 d" [& s4 c/ M' p) |

  31. ' R7 k- v3 p8 P& d2 i% |0 U) e; \; G
  32.   publicvoid go() {# c5 m& D9 ]0 M2 D3 `
  33.            //准备起步" ]  A, g# G5 Q' u' Y$ \0 C; ?
  34.            //wait for release
    & F( M. o& z( j( I' X$ W! K
  35.            while(Button.readButtons() > 0)
    8 c2 }6 [  l, c; k  @" t
  36.                    ;
    , {1 y, @4 `, A# n9 l8 J1 \
  37.            System.out.println("pressto go");5 R$ o6 y+ n* @& c& Q

  38. 8 S2 d0 a- x6 H" a" a
  39.            Button.waitForAnyPress();
    1 Z% R! h' ~1 m( j5 o0 _. _+ E
  40.            LCD.clear();
    2 T; {" p. j6 f5 S
  41. : \: F* A9 u) J4 l: R0 T
  42.            //初始化7 V3 ^. E9 b: n! a. V  T
  43.            pilot= new DifferentialPilot(rightD, leftD, 13.5, Motor.A, Motor.B, true);
    , X. R- j4 a2 p1 R4 M" V
  44.            pilot.reset();
    * O7 V6 Y/ i* ^9 @

  45. ( W8 U1 a8 _0 T) \/ A7 c; B! B5 P
  46.            Delay.msDelay(3000);( w  v$ x$ h8 ~$ T1 i. G, {: b

  47. $ a* O" A& `+ V8 t0 C
  48.            doublespeed = 10;& R" N0 z" u* A: y
  49.            doubledistance = 0;9 w$ v4 {# h2 v' }
  50. 7 O2 D) p3 i- X( e' G
  51.            //起步加速" S( B! x, z  f: T
  52.            pilot.travel(300,true);9 D9 _6 m7 N# z: e4 T  `

  53. + C& f' x7 [" p
  54.            while(distance < 20) {
    5 W* Z  x. `3 L2 D: A
  55.                    distance= pilot.getMovement().getDistanceTraveled();
    : z$ j- h  U2 T& I8 F/ e- _
  56.                    speed= distance * 5 + 10;
    9 e$ j7 B8 Z6 @9 X  @1 C" y
  57.                    pilot.setRotateSpeed(speed);
    % F/ k5 y  }  t, R6 u7 P) E: O) V
  58.                    Delay.msDelay(100);
      H7 [  \# b* ?! ~+ Z/ |' ]; w
  59.            }) R4 |) r) T* N+ K: ?4 ~- p
  60.            for(int i = 0; i < 10; i++) {
    2 V  l4 C4 C  P) v( i. d, r; e5 x
  61.                    speed+= 5;% ]5 b* n* g& f; a
  62.                    pilot.setRotateSpeed(speed);
    2 e/ r) _% @* O7 c) ^' v7 b- H7 U
  63.                    Delay.msDelay(200);- f; o. ?1 ~1 V; {
  64.            }
    % R2 z. ~  P& F9 A

  65. : ^7 b0 B" _1 t8 I- d& b9 q( v
  66.            //TODO 减速$ c" \9 F& v" E+ U& h( |
  67. * [" ]1 F2 }; j8 f3 {* \
  68.            //停止机能' ^! X/ e2 \5 A6 O& A
  69.            while(pilot.isMoving()) {
    . b" Q" W- \  x
  70.                    if(Button.readButtons() > 0)7 C9 o/ k; ~7 y" l% K: w
  71.                            pilot.stop();
    ) r# J2 ]+ C) ?9 K; X
  72.            }
    ! R1 W: b' a" K6 a% I% ]

  73. % b! |; `: N6 ?6 a2 t5 j& j$ ?  d/ o
  74.            System.out.println("" + pilot.getMovement().getDistanceTraveled());
    * a8 V$ J; B/ A% k( ^9 `! _
  75.            System.out.println(-Motor.A.getTachoCount());5 C) @4 \0 I7 h; d& K, R; R8 A
  76.            System.out.println(-Motor.B.getTachoCount());* l3 E4 i4 q- |" `% {
  77.            Button.waitForAnyPress();
    " \- ?# m# I- ^  s7 l9 V" h$ a  s
  78.   }
    / Q* k) m4 X6 ~% }$ K
  79. ' |! @# @7 P6 ^1 Y/ ~. S
  80.   publicstatic void main(String[] args) {
    # g' o% F! T' {
  81.            Straighttraveler = new Straight();
    * k$ O  @! N  u

  82. 1 S  V3 W. |: v* g
  83.            traveler.adjust();+ ?- }2 A$ }) V% h5 J1 }
  84.            traveler.go();9 k8 W4 a0 [9 m
  85.   }
    5 |7 [3 l* ]* Q, s1 H5 @; I
  86. }
复制代码

7 F+ ?- o( S5 {" F0 B
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 编辑
1 _* l0 S: a$ U) n7 E
2 D6 N: ]2 V- L/ ~& T% E( h% m这一行行代码,C?,暂还不懂,反正看到写代码的都敬仰,这种程序是不是比G(乐高是不是叫G语言)的严谨,用代码程序的机器人都能很好的实现复杂功能
如果您觉得我的帖子对您有用,请不吝给我一个“赞”!
回复

使用道具 举报

 楼主| 发表于 2017-7-26 10:08:44 | 显示全部楼层
clx 发表于 2017-7-26 07:22' A* y9 F9 D0 i' j$ c& v2 ?3 O- z3 E: m
这一行行代码,C?,暂还不懂,反正看到写代码的都敬仰,这种程序是不是比G(乐高是不是叫G语言)的严谨, ...

( @: l, z2 \* e2 S! u! w我用的是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, 2025-9-6 05:59 , Processed in 1.066159 second(s), 20 queries .

Powered by Discuz! X3.5

Copyright © 2001-2020, Tencent Cloud.

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