geo3d 0.0.8 → 0.0.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/geo3d.gemspec +2 -0
- data/lib/geo3d.rb +1 -0
- data/lib/geo3d/version.rb +1 -1
- data/lib/matrix.rb +42 -2
- data/lib/triangle.rb +46 -0
- data/spec/lib/triangle_spec.rb +19 -0
- data/spec/opengl/matrix_spec.rb +95 -0
- metadata +45 -12
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e792232f7a90e668e5cae09575b15574c33c0b30
|
4
|
+
data.tar.gz: 18ccd86ed62ef23860e8bd4bc650958b0401836f
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 048b7fb31747320c8024580e1381b630540442a1810089a9a6b49a94060140b0e8cb56e105927de9c6b15cdacda5e4a753934e2e42578979fb6763b7714a85b1
|
7
|
+
data.tar.gz: 119f28b82c0ed685bbf834e215b80501855520e848daf6a9a2f63e289c768116ead912585fec145d277e30213e0d78b0ae55d60b7e77d37f86aee47d1d981429
|
data/geo3d.gemspec
CHANGED
@@ -21,4 +21,6 @@ Gem::Specification.new do |spec|
|
|
21
21
|
spec.add_development_dependency "bundler", "~> 1.3"
|
22
22
|
spec.add_development_dependency "rake"
|
23
23
|
spec.add_development_dependency "rspec"
|
24
|
+
spec.add_development_dependency "misha-ruby-sdl-ffi"
|
25
|
+
spec.add_development_dependency "ruby-opengl"
|
24
26
|
end
|
data/lib/geo3d.rb
CHANGED
data/lib/geo3d/version.rb
CHANGED
data/lib/matrix.rb
CHANGED
@@ -186,6 +186,15 @@ module Geo3d
|
|
186
186
|
transformed_vector.z = _13 * vec.x + _23 * vec.y + _33 * vec.z + _43 * vec.w
|
187
187
|
transformed_vector.w = _14 * vec.x + _24 * vec.y + _34 * vec.z + _44 * vec.w
|
188
188
|
return transformed_vector
|
189
|
+
elsif Triangle == v.class
|
190
|
+
tri = v
|
191
|
+
transformed_tri = Triangle.new
|
192
|
+
transformed_tri.a = self * tri.a
|
193
|
+
transformed_tri.b = self * tri.b
|
194
|
+
transformed_tri.c = self * tri.c
|
195
|
+
return transformed_tri
|
196
|
+
elsif Array == v.class
|
197
|
+
return v.map { |i| self * i }
|
189
198
|
else
|
190
199
|
scalar = v
|
191
200
|
result._11 = _11 * scalar
|
@@ -238,7 +247,7 @@ module Geo3d
|
|
238
247
|
end
|
239
248
|
|
240
249
|
def transform_coord vec
|
241
|
-
self * Vector.new(
|
250
|
+
self * Vector.new(vec.x, vec.y, vec.z, 1.0)
|
242
251
|
end
|
243
252
|
|
244
253
|
def transform vec
|
@@ -436,7 +445,38 @@ module Geo3d
|
|
436
445
|
end
|
437
446
|
|
438
447
|
def to_s
|
439
|
-
(0..3).to_a.map{ |i| row(i).to_s}.join "\n"
|
448
|
+
(0..3).to_a.map { |i| row(i).to_s }.join "\n"
|
449
|
+
end
|
450
|
+
|
451
|
+
def self.glu_perspective_degrees fovy, aspect, zn, zf
|
452
|
+
fovy = fovy.to_f
|
453
|
+
aspect = aspect.to_f
|
454
|
+
zn = zn.to_f
|
455
|
+
zf = zf.to_f
|
456
|
+
range = zn*Math.tan(Geo3d::Utils.to_radians(fovy/2.0))
|
457
|
+
self.gl_frustum -range*aspect, range*aspect, -range, range, zn, zf
|
458
|
+
end
|
459
|
+
|
460
|
+
def self.gl_frustum l, r, b, t, zn, zf
|
461
|
+
l = l.to_f
|
462
|
+
r = r.to_f
|
463
|
+
b = b.to_f
|
464
|
+
t = t.to_f
|
465
|
+
zn = zn.to_f
|
466
|
+
zf = zf.to_f
|
467
|
+
a = (r+l) / (r-l)
|
468
|
+
b = (t+b) / (t-b)
|
469
|
+
c = -(zf + zn) / (zf - zn)
|
470
|
+
d = -(2 * zf * zn) / (zf - zn)
|
471
|
+
matrix = self.new
|
472
|
+
matrix._11 = 2.0 * zn / (r-l)
|
473
|
+
matrix._31 = a
|
474
|
+
matrix._22 = 2.0 * zn / (t-b) #todo: the man page says multiply this by two, but I don't actually match what glFrustum does if I do
|
475
|
+
matrix._32 = b
|
476
|
+
matrix._33 = c
|
477
|
+
matrix._43 = d
|
478
|
+
matrix._34 = -1.0
|
479
|
+
matrix
|
440
480
|
end
|
441
481
|
|
442
482
|
def self.perspective_fov_rh fovy, aspect, zn, zf
|
data/lib/triangle.rb
ADDED
@@ -0,0 +1,46 @@
|
|
1
|
+
module Geo3d
|
2
|
+
class Triangle
|
3
|
+
attr_accessor :a, :b, :c
|
4
|
+
|
5
|
+
def points
|
6
|
+
[a, b, c]
|
7
|
+
end
|
8
|
+
|
9
|
+
def initialize
|
10
|
+
@a = Vector.new
|
11
|
+
@b = Vector.new
|
12
|
+
@c = Vector.new
|
13
|
+
end
|
14
|
+
|
15
|
+
def flip!
|
16
|
+
@b, @c = @c, @b
|
17
|
+
end
|
18
|
+
|
19
|
+
def flip
|
20
|
+
f = clone
|
21
|
+
f.flip!
|
22
|
+
f
|
23
|
+
end
|
24
|
+
|
25
|
+
def normal
|
26
|
+
(b - a).cross(c - a).normalize
|
27
|
+
end
|
28
|
+
|
29
|
+
def signed_area reference_normal = Vector.new(0,0,-1)
|
30
|
+
sum = Vector.new 0, 0, 0, 0
|
31
|
+
points.each_with_index do |current_point, i|
|
32
|
+
next_point = points[(i == points.size - 1) ? 0 : i+1]
|
33
|
+
sum += current_point.cross next_point
|
34
|
+
end
|
35
|
+
reference_normal.dot(sum) / 2.0
|
36
|
+
end
|
37
|
+
|
38
|
+
def clockwise?
|
39
|
+
signed_area > 0
|
40
|
+
end
|
41
|
+
|
42
|
+
def counter_clockwise?
|
43
|
+
signed_area < 0
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Geo3d::Triangle do
|
4
|
+
it "should detect winding" do
|
5
|
+
[{:a => [0,0,0], :b => [1,0,0], :c => [1,1,0], :expected => "counter-clockwise"},
|
6
|
+
{:a => [0,0,0], :b => [1,0,0], :c => [1,-1,0], :expected => "clockwise"}].each do |data|
|
7
|
+
t = Geo3d::Triangle.new
|
8
|
+
t.a = Geo3d::Vector.new *data[:a]
|
9
|
+
t.b = Geo3d::Vector.new *data[:b]
|
10
|
+
t.c = Geo3d::Vector.new *data[:c]
|
11
|
+
winding = t.counter_clockwise?? 'counter-clockwise' : 'clockwise'
|
12
|
+
winding.should == data[:expected]
|
13
|
+
end
|
14
|
+
end
|
15
|
+
|
16
|
+
it "should calculate normal" do
|
17
|
+
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,95 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Geo3d::Matrix do
|
4
|
+
before :each do
|
5
|
+
@gl_initialized = false
|
6
|
+
require "ruby-sdl-ffi"
|
7
|
+
require "opengl"
|
8
|
+
|
9
|
+
if SDL.Init(SDL::INIT_VIDEO) < 0
|
10
|
+
puts "not able to init"
|
11
|
+
else
|
12
|
+
|
13
|
+
SDL.GL_SetAttribute SDL::GL_RED_SIZE, 5
|
14
|
+
SDL.GL_SetAttribute SDL::GL_GREEN_SIZE, 5
|
15
|
+
SDL.GL_SetAttribute SDL::GL_BLUE_SIZE, 5
|
16
|
+
SDL.GL_SetAttribute SDL::GL_DEPTH_SIZE, 16
|
17
|
+
SDL.GL_SetAttribute SDL::GL_DOUBLEBUFFER, 1
|
18
|
+
|
19
|
+
if 0 == SDL.SetVideoMode(640, 480, SDL.GetVideoInfo.vfmt.BitsPerPixel, SDL::OPENGL)
|
20
|
+
puts "not able to set video mode"
|
21
|
+
else
|
22
|
+
@gl_initialized = true
|
23
|
+
end
|
24
|
+
end
|
25
|
+
raise "opengl not able to initialize" unless @gl_initialized
|
26
|
+
end
|
27
|
+
|
28
|
+
|
29
|
+
it "the right handed view constructor should be functionally equivalent to gluLookAt" do
|
30
|
+
[{:eye => [1, 0, 0], :focus => [100, 0, -100], :up => [0, 1, 0]}].each do |data|
|
31
|
+
eye = Geo3d::Vector.new *data[:eye]
|
32
|
+
focus = Geo3d::Vector.new *data[:eye]
|
33
|
+
up = Geo3d::Vector.new *data[:eye]
|
34
|
+
|
35
|
+
glMatrixMode GL_MODELVIEW
|
36
|
+
glLoadIdentity
|
37
|
+
gluLookAt eye.x, eye.y, eye.z, focus.x, focus.y, focus.z, up.x, up.y, up.z
|
38
|
+
gl_version = Geo3d::Matrix.new *glGetFloatv(GL_MODELVIEW_MATRIX).flatten
|
39
|
+
|
40
|
+
gl_version.should == Geo3d::Matrix.look_at_rh(eye, focus, up)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
it "gl_frustum should be equivalent to opengl glFrustum" do
|
45
|
+
[{:l => -2, :r => 2, :b => -2, :t => 2, :zn => 1, :zf => 1000},
|
46
|
+
{:l => -231, :r => 453, :b => -232, :t => 2786, :zn => 9.221, :zf => 10000}].each do |data|
|
47
|
+
glMatrixMode GL_PROJECTION
|
48
|
+
glLoadIdentity
|
49
|
+
glFrustum data[:l], data[:r], data[:b], data[:t], data[:zn], data[:zf]
|
50
|
+
|
51
|
+
gl_version = Geo3d::Matrix.new *(glGetFloatv(GL_PROJECTION_MATRIX).flatten)
|
52
|
+
geo3d_matrix = Geo3d::Matrix.gl_frustum data[:l], data[:r], data[:b], data[:t], data[:zn], data[:zf]
|
53
|
+
|
54
|
+
gl_version.should == geo3d_matrix
|
55
|
+
end
|
56
|
+
|
57
|
+
end
|
58
|
+
|
59
|
+
it "glu_perspective_degrees should be equivalent to opengl gluPerspective" do
|
60
|
+
[{:fovy_in_degrees => 60, :width => 640, :height => 480, :near => 0.1, :far => 1000}].each do |data|
|
61
|
+
glMatrixMode GL_PROJECTION
|
62
|
+
glLoadIdentity
|
63
|
+
gluPerspective data[:fovy_in_degrees], data[:width].to_f/data[:height].to_f, data[:near], data[:far]
|
64
|
+
|
65
|
+
gl_version = Geo3d::Matrix.new *glGetFloatv(GL_PROJECTION_MATRIX).flatten
|
66
|
+
geo3d_matrix = Geo3d::Matrix.glu_perspective_degrees(data[:fovy_in_degrees], data[:width].to_f/data[:height].to_f, data[:near], data[:far])
|
67
|
+
|
68
|
+
gl_version.should == geo3d_matrix
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
it "should multiply matrices the same way opengl does" do
|
73
|
+
10000.times do
|
74
|
+
a_values = (0..15).to_a.map do |i|
|
75
|
+
rand * rand(100)
|
76
|
+
end
|
77
|
+
|
78
|
+
b_values = (0..15).to_a.map do |i|
|
79
|
+
rand * rand(100)
|
80
|
+
end
|
81
|
+
|
82
|
+
geo3d_matrix = Geo3d::Matrix.new(*b_values) * Geo3d::Matrix.new(*a_values)
|
83
|
+
|
84
|
+
glMatrixMode GL_MODELVIEW
|
85
|
+
glLoadIdentity
|
86
|
+
glLoadMatrixf a_values
|
87
|
+
glMultMatrixf b_values
|
88
|
+
gl_version = Geo3d::Matrix.new *glGetFloatv(GL_MODELVIEW).flatten
|
89
|
+
|
90
|
+
gl_version.should == geo3d_matrix
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
|
95
|
+
end
|
metadata
CHANGED
@@ -1,55 +1,83 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: geo3d
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.9
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Misha Conway
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2014-01-
|
11
|
+
date: 2014-01-19 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- - ~>
|
17
|
+
- - "~>"
|
18
18
|
- !ruby/object:Gem::Version
|
19
19
|
version: '1.3'
|
20
20
|
type: :development
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
|
-
- - ~>
|
24
|
+
- - "~>"
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '1.3'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: rake
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- -
|
31
|
+
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
33
|
version: '0'
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
|
-
- -
|
38
|
+
- - ">="
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '0'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: rspec
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- -
|
45
|
+
- - ">="
|
46
46
|
- !ruby/object:Gem::Version
|
47
47
|
version: '0'
|
48
48
|
type: :development
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- -
|
52
|
+
- - ">="
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: misha-ruby-sdl-ffi
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: ruby-opengl
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - ">="
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - ">="
|
53
81
|
- !ruby/object:Gem::Version
|
54
82
|
version: '0'
|
55
83
|
description: Library for common 3d graphics vector and matrix operations
|
@@ -59,7 +87,7 @@ executables: []
|
|
59
87
|
extensions: []
|
60
88
|
extra_rdoc_files: []
|
61
89
|
files:
|
62
|
-
- .gitignore
|
90
|
+
- ".gitignore"
|
63
91
|
- Gemfile
|
64
92
|
- LICENSE.txt
|
65
93
|
- README.md
|
@@ -70,12 +98,15 @@ files:
|
|
70
98
|
- lib/matrix.rb
|
71
99
|
- lib/plane.rb
|
72
100
|
- lib/quaternion.rb
|
101
|
+
- lib/triangle.rb
|
73
102
|
- lib/utils.rb
|
74
103
|
- lib/vector.rb
|
75
104
|
- spec/lib/matrix_spec.rb
|
76
105
|
- spec/lib/plane_spec.rb
|
77
106
|
- spec/lib/quaternion_spec.rb
|
107
|
+
- spec/lib/triangle_spec.rb
|
78
108
|
- spec/lib/vector_spec.rb
|
109
|
+
- spec/opengl/matrix_spec.rb
|
79
110
|
- spec/spec_helper.rb
|
80
111
|
homepage: https://github.com/MishaConway/geo3d
|
81
112
|
licenses:
|
@@ -87,17 +118,17 @@ require_paths:
|
|
87
118
|
- lib
|
88
119
|
required_ruby_version: !ruby/object:Gem::Requirement
|
89
120
|
requirements:
|
90
|
-
- -
|
121
|
+
- - ">="
|
91
122
|
- !ruby/object:Gem::Version
|
92
123
|
version: '0'
|
93
124
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
94
125
|
requirements:
|
95
|
-
- -
|
126
|
+
- - ">="
|
96
127
|
- !ruby/object:Gem::Version
|
97
128
|
version: '0'
|
98
129
|
requirements: []
|
99
130
|
rubyforge_project:
|
100
|
-
rubygems_version: 2.1
|
131
|
+
rubygems_version: 2.2.1
|
101
132
|
signing_key:
|
102
133
|
specification_version: 4
|
103
134
|
summary: Library for common 3d graphics vector and matrix operations
|
@@ -105,5 +136,7 @@ test_files:
|
|
105
136
|
- spec/lib/matrix_spec.rb
|
106
137
|
- spec/lib/plane_spec.rb
|
107
138
|
- spec/lib/quaternion_spec.rb
|
139
|
+
- spec/lib/triangle_spec.rb
|
108
140
|
- spec/lib/vector_spec.rb
|
141
|
+
- spec/opengl/matrix_spec.rb
|
109
142
|
- spec/spec_helper.rb
|