Class: Motor
Overview
Constant Summary collapse
- POLL_INTERVAL =
0.5
Instance Attribute Summary collapse
-
#ratio ⇒ Object
Returns the value of attribute ratio.
Attributes inherited from Brick
Instance Method Summary collapse
-
#backward(options) ⇒ Object
Rotate the motor backwards.
-
#forward(options) ⇒ Object
Rotate the motor forwards.
-
#initialize(nxt, port) ⇒ Motor
constructor
A new instance of Motor.
- #name ⇒ Object
-
#read_state ⇒ Object
Return the current state of the motor as a hash.
-
#reset_tacho ⇒ Object
Resets the motor’s tachometer movement count (i.e.
:degree_countin Motor#state). -
#run(options) ⇒ Object
Low-level command for initiating motor rotation.
-
#stop ⇒ Object
Stop movement.
Constructor Details
#initialize(nxt, port) ⇒ Motor
Returns a new instance of Motor.
33 34 35 36 37 38 39 |
# File 'lib/motor.rb', line 33 def initialize(nxt, port) super(nxt, port) @port = formalize_motor_port_name(port) @ratio = 0 end |
Instance Attribute Details
#ratio ⇒ Object
Returns the value of attribute ratio.
31 32 33 |
# File 'lib/motor.rb', line 31 def ratio @ratio end |
Instance Method Details
#backward(options) ⇒ Object
Rotate the motor backwards. See Motor#forward and Motor#run.
71 72 73 74 75 |
# File 'lib/motor.rb', line 71 def backward() debug(, :backward) [:direction] = -1 return run() end |
#forward(options) ⇒ Object
Rotate the motor forwards. See Motor#run. Examples:
m.forward(:degrees => 360, :power => 20)
The above rotates the motor 360 degrees forward at 20% power.
m.forward(:time => 5)
The above rotates the motor forwards for 5 seconds at 25% power (because 25% is the default).
63 64 65 66 67 |
# File 'lib/motor.rb', line 63 def forward() debug(.to_yaml, :forward) [:direction] = 1 return run() end |
#name ⇒ Object
41 42 43 44 45 46 47 |
# File 'lib/motor.rb', line 41 def name case self.port when NXTComm::MOTOR_A then 'a' when NXTComm::MOTOR_B then 'b' when NXTComm::MOTOR_C then 'c' end end |
#read_state ⇒ Object
Return the current state of the motor as a hash. See NXTComm#get_output_state for info on what data is available here.
79 80 81 82 83 84 85 86 87 |
# File 'lib/motor.rb', line 79 def read_state @log.debug(:read_state) { "getting state"} state = @nxt.get_output_state(@port) @log.debug(:read_state) { "got state" } debug(state, :state) return state end |
#reset_tacho ⇒ Object
Resets the motor’s tachometer movement count (i.e. :degree_count in Motor#state).
212 213 214 215 216 |
# File 'lib/motor.rb', line 212 def reset_tacho @log.debug(:reset_tacho) { "resetting tacho" } @nxt.reset_motor_position(@port, false) @log.debug(:reset_tacho) { "reset tacho" } end |
#run(options) ⇒ Object
Low-level command for initiating motor rotation. Options is a hash with the following keys:
:power-
Power from 0 to 100. Default is 25.
:time-
Maximum time to run the motor in seconds. By default there is no time limit. If :degrees is also specified then the motor will only turn as far as :degrees and will stop and wait out the remaining :time has expired.
:regulate-
False to disable power regulation. It is true (i.e. on)
by default.
:degrees-
The maximum tachometer degrees to turn before automatically
stopping. Use negative values for backward movement (need to
double check that this is in fact true)
:direction-
Direction in which the motor should move. 1 for forward,
-1 for backward. The default is 1 (i.e. forward).
:wait_until_complete-
If true, the motor will block further commands
until this command is complete. This is true by default when :degrees or :time is specified, false by default otherwise. NOTE: currently this setting is always on and cannot be turned off when :time is specified… this will probably be fixed in the future
:brake_on_stop-
If true, the motor will try to hard brake when the
command completes (otherwise when the command finishes the motor may continue to coast for a while – especially at higher power levels). This is true by default when :degrees or :time is specified, false by default otherwise.
Examples:
Rotate backward up to 90 degrees:
m.run(:degrees => 90, :direction => -1)
Rotate forward for 8 seconds at 100% power:
m.run(:time => 8, :power => 100)
Forward for 3 seconds up to 180 degrees at 50% power. If the 180 degree rotation takes only 1 second to complete, the motor will sit there and wait out the full 3 seconds anyway:
m.run(:power => 50, :degrees => 180, :time => 3)
Rotate forward indefinitely (until Motor#stop is called).
m.run
139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 |
# File 'lib/motor.rb', line 139 def run() debug(, :run) if [:power] power = [:power].to_i.abs else power = 25 end time = [:time] || nil regulate = [:regulate] || true regulation_mode = [:regulation_mode] || "speed" degrees = [:degrees] || 0 ratio = [:ratio] || self.ratio direction = [:direction] || 1 # 1 is forward, -1 is backward brake_on_stop = .has_key?(:time) || .has_key?(:degrees) wait_until_complete = .has_key?(:time) || .has_key?(:degrees) brake_on_stop = [:brake_on_stop] if .has_key?(:brake_on_stop) wait_until_complete = [:wait_until_complete] if .has_key?(:wait_until_complete) # FIXME: wait_until_complete MUST be true if a time period is specified, otherwise we have no way of # enforcing the time limit (this is a problem with the way threading is implemented...) wait_until_complete = true if .has_key?(:time) power = direction * power mode = NXTComm::MOTORON mode |= NXTComm::BRAKE if brake_on_stop mode |= NXTComm::REGULATED if regulate if regulate case regulation_mode when "idle" regulation_mode = NXTComm::REGULATION_MODE_IDLE when "speed" regulation_mode = NXTComm::REGULATION_MODE_MOTOR_SPEED when "sync" regulation_mode = NXTComm::REGULATION_MODE_MOTOR_SYNC end else regulation_mode = NXTComm::REGULATION_MODE_IDLE end @log.debug(:run) {"sending run command"} @nxt.set_output_state(@port, power, mode, regulation_mode, ratio, NXTComm::MOTOR_RUN_STATE_RUNNING, degrees) if time.nil? if wait_until_complete @log.debug(:run) {"sleeping until run_state is idle"} until read_state[:run_state] == NXTComm::MOTOR_RUN_STATE_IDLE sleep(POLL_INTERVAL) @log.debug(:run) {"checking run_state again"} end @log.debug(:run) {"run_state is idle"} end else @log.debug(:run) {"waiting #{time} seconds until stop"} sleep(time) @log.debug(:run) {"stopping"} self.stop @log.debug(:run) {"stopped"} end end |
#stop ⇒ Object
Stop movement.
206 207 208 209 |
# File 'lib/motor.rb', line 206 def stop debug(nil, :stop) @nxt.set_output_state(@port, 100, NXTComm::BRAKE, NXTComm::REGULATION_MODE_MOTOR_SPEED, 100, NXTComm::MOTOR_RUN_STATE_IDLE, 0) end |