Data commit
This commit is contained in:
parent
7387c8f97b
commit
cb5bb5e222
199093 changed files with 3378972 additions and 0 deletions
63
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-1.rb
Normal file
63
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-1.rb
Normal file
|
|
@ -0,0 +1,63 @@
|
|||
require 'tk'
|
||||
|
||||
$root = TkRoot.new("title" => "Pendulum Animation")
|
||||
$canvas = TkCanvas.new($root) do
|
||||
width 320
|
||||
height 200
|
||||
create TkcLine, 0,25,320,25, 'tags' => 'plate', 'width' => 2, 'fill' => 'grey50'
|
||||
create TkcOval, 155,20,165,30, 'tags' => 'pivot', 'outline' => "", 'fill' => 'grey50'
|
||||
create TkcLine, 1,1,1,1, 'tags' => 'rod', 'width' => 3, 'fill' => 'black'
|
||||
create TkcOval, 1,1,2,2, 'tags' => 'bob', 'outline' => 'black', 'fill' => 'yellow'
|
||||
end
|
||||
$canvas.raise('pivot')
|
||||
$canvas.pack('fill' => 'both', 'expand' => true)
|
||||
|
||||
$Theta = 45.0
|
||||
$dTheta = 0.0
|
||||
$length = 150
|
||||
$homeX = 160
|
||||
$homeY = 25
|
||||
|
||||
def show_pendulum
|
||||
angle = $Theta * Math::PI / 180
|
||||
x = $homeX + $length * Math.sin(angle)
|
||||
y = $homeY + $length * Math.cos(angle)
|
||||
$canvas.coords('rod', $homeX, $homeY, x, y)
|
||||
$canvas.coords('bob', x-15, y-15, x+15, y+15)
|
||||
end
|
||||
|
||||
def recompute_angle
|
||||
scaling = 3000.0 / ($length ** 2)
|
||||
# first estimate
|
||||
firstDDTheta = -Math.sin($Theta * Math::PI / 180) * scaling
|
||||
midDTheta = $dTheta + firstDDTheta
|
||||
midTheta = $Theta + ($dTheta + midDTheta)/2
|
||||
# second estimate
|
||||
midDDTheta = -Math.sin(midTheta * Math::PI / 180) * scaling
|
||||
midDTheta = $dTheta + (firstDDTheta + midDDTheta)/2
|
||||
midTheta = $Theta + ($dTheta + midDTheta)/2
|
||||
# again, first
|
||||
midDDTheta = -Math.sin(midTheta * Math::PI / 180) * scaling
|
||||
lastDTheta = midDTheta + midDDTheta
|
||||
lastTheta = midTheta + (midDTheta + lastDTheta)/2
|
||||
# again, second
|
||||
lastDDTheta = -Math.sin(lastTheta * Math::PI/180) * scaling
|
||||
lastDTheta = midDTheta + (midDDTheta + lastDDTheta)/2
|
||||
lastTheta = midTheta + (midDTheta + lastDTheta)/2
|
||||
# Now put the values back in our globals
|
||||
$dTheta = lastDTheta
|
||||
$Theta = lastTheta
|
||||
end
|
||||
|
||||
def animate
|
||||
recompute_angle
|
||||
show_pendulum
|
||||
$after_id = $root.after(15) {animate}
|
||||
end
|
||||
|
||||
show_pendulum
|
||||
$after_id = $root.after(500) {animate}
|
||||
|
||||
$canvas.bind('<Destroy>') {$root.after_cancel($after_id)}
|
||||
|
||||
Tk.mainloop
|
||||
57
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-2.rb
Normal file
57
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-2.rb
Normal file
|
|
@ -0,0 +1,57 @@
|
|||
Shoes.app(:width => 320, :height => 200) do
|
||||
@centerX = 160
|
||||
@centerY = 25
|
||||
@length = 150
|
||||
@diameter = 15
|
||||
|
||||
@Theta = 45.0
|
||||
@dTheta = 0.0
|
||||
|
||||
stroke gray
|
||||
strokewidth 3
|
||||
line 0,25,320,25
|
||||
oval 155,20,10
|
||||
|
||||
stroke black
|
||||
@rod = line(@centerX, @centerY, @centerX, @centerY + @length)
|
||||
@bob = oval(@centerX - @diameter, @centerY + @length - @diameter, 2*@diameter)
|
||||
|
||||
animate(24) do |i|
|
||||
recompute_angle
|
||||
show_pendulum
|
||||
end
|
||||
|
||||
def show_pendulum
|
||||
angle = (90 + @Theta) * Math::PI / 180
|
||||
x = @centerX + (Math.cos(angle) * @length).to_i
|
||||
y = @centerY + (Math.sin(angle) * @length).to_i
|
||||
|
||||
@rod.remove
|
||||
strokewidth 3
|
||||
@rod = line(@centerX, @centerY, x, y)
|
||||
@bob.move(x-@diameter, y-@diameter)
|
||||
end
|
||||
|
||||
def recompute_angle
|
||||
scaling = 3000.0 / (@length **2)
|
||||
# first estimate
|
||||
firstDDTheta = -Math.sin(@Theta * Math::PI / 180) * scaling
|
||||
midDTheta = @dTheta + firstDDTheta
|
||||
midTheta = @Theta + (@dTheta + midDTheta)/2
|
||||
# second estimate
|
||||
midDDTheta = -Math.sin(midTheta * Math::PI / 180) * scaling
|
||||
midDTheta = @dTheta + (firstDDTheta + midDDTheta)/2
|
||||
midTheta = @Theta + (@dTheta + midDTheta)/2
|
||||
# again, first
|
||||
midDDTheta = -Math.sin(midTheta * Math::PI / 180) * scaling
|
||||
lastDTheta = midDTheta + midDDTheta
|
||||
lastTheta = midTheta + (midDTheta + lastDTheta)/2
|
||||
# again, second
|
||||
lastDDTheta = -Math.sin(lastTheta * Math::PI/180) * scaling
|
||||
lastDTheta = midDTheta + (midDDTheta + lastDDTheta)/2
|
||||
lastTheta = midTheta + (midDTheta + lastDTheta)/2
|
||||
# Now put the values back in our globals
|
||||
@dTheta = lastDTheta
|
||||
@Theta = lastTheta
|
||||
end
|
||||
end
|
||||
104
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-3.rb
Normal file
104
Task/Animate-a-pendulum/Ruby/animate-a-pendulum-3.rb
Normal file
|
|
@ -0,0 +1,104 @@
|
|||
#!/bin/ruby
|
||||
|
||||
begin; require 'rubygems'; rescue; end
|
||||
|
||||
require 'gosu'
|
||||
include Gosu
|
||||
|
||||
# Screen size
|
||||
W = 640
|
||||
H = 480
|
||||
|
||||
# Full-screen mode
|
||||
FS = false
|
||||
|
||||
# Screen update rate (Hz)
|
||||
FPS = 60
|
||||
|
||||
class Pendulum
|
||||
|
||||
attr_accessor :theta, :friction
|
||||
|
||||
def initialize( win, x, y, length, radius, bob = true, friction = false)
|
||||
@win = win
|
||||
@centerX = x
|
||||
@centerY = y
|
||||
@length = length
|
||||
@radius = radius
|
||||
@bob = bob
|
||||
@friction = friction
|
||||
|
||||
@theta = 60.0
|
||||
@omega = 0.0
|
||||
@scale = 2.0 / FPS
|
||||
end
|
||||
|
||||
def draw
|
||||
@win.translate(@centerX, @centerY) {
|
||||
@win.rotate(@theta) {
|
||||
@win.draw_quad(-1, 0, 0x3F_FF_FF_FF, 1, 0, 0x3F_FF_FF_00, 1, @length, 0x3F_FF_FF_00, -1, @length, 0x3F_FF_FF_FF )
|
||||
if @bob
|
||||
@win.translate(0, @length) {
|
||||
@win.draw_quad(0, -@radius, Color::RED, @radius, 0, Color::BLUE, 0, @radius, Color::WHITE, -@radius, 0, Color::BLUE )
|
||||
}
|
||||
end
|
||||
}
|
||||
}
|
||||
end
|
||||
|
||||
def update
|
||||
# Thanks to Hugo Elias for the formula (and explanation thereof)
|
||||
@theta += @omega
|
||||
@omega = @omega - (Math.sin(@theta * Math::PI / 180) / (@length * @scale))
|
||||
@theta *= 0.999 if @friction
|
||||
end
|
||||
|
||||
end # Pendulum class
|
||||
|
||||
class GfxWindow < Window
|
||||
|
||||
def initialize
|
||||
# Initialize the base class
|
||||
super W, H, FS, 1.0 / FPS * 1000
|
||||
# self.caption = "You're getting sleeeeepy..."
|
||||
self.caption = "Ruby/Gosu Pendulum Simulator (Space toggles friction)"
|
||||
|
||||
@n = 1 # Try changing this number!
|
||||
@pendulums = []
|
||||
(1..@n).each do |i|
|
||||
@pendulums.push Pendulum.new( self, W / 2, H / 10, H * 0.75 * (i / @n.to_f), H / 60 )
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
def draw
|
||||
@pendulums.each { |pen| pen.draw }
|
||||
end
|
||||
|
||||
def update
|
||||
@pendulums.each { |pen| pen.update }
|
||||
end
|
||||
|
||||
def button_up(id)
|
||||
if id == KbSpace
|
||||
@pendulums.each { |pen|
|
||||
pen.friction = !pen.friction
|
||||
pen.theta = (pen.theta <=> 0) * 45.0 unless pen.friction
|
||||
}
|
||||
else
|
||||
close
|
||||
end
|
||||
end
|
||||
|
||||
def needs_cursor?()
|
||||
true
|
||||
end
|
||||
|
||||
end # GfxWindow class
|
||||
|
||||
begin
|
||||
GfxWindow.new.show
|
||||
rescue Exception => e
|
||||
puts e.message, e.backtrace
|
||||
gets
|
||||
end
|
||||
Loading…
Add table
Add a link
Reference in a new issue