geometry 0 → 1
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.
- data/.gitignore +1 -0
- data/LICENSE +21 -0
- data/{README → README.markdown} +0 -0
- data/geometry.gemspec +1 -1
- data/lib/geometry.rb +19 -3
- data/lib/geometry/line.rb +114 -0
- data/lib/geometry/point.rb +45 -0
- data/test/test_geometry.rb +15 -0
- data/test/test_line.rb +1 -1
- data/test/test_point.rb +4 -10
- metadata +8 -5
- data/lib/line.rb +0 -85
- data/lib/point.rb +0 -39
data/.gitignore
CHANGED
data/LICENSE
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
Copyright (c) 2012, Brandon Fosdick <bfoz@bfoz.net>
|
2
|
+
All rights reserved.
|
3
|
+
|
4
|
+
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
5
|
+
that the following conditions are met:
|
6
|
+
|
7
|
+
Redistributions of source code must retain the above copyright notice, this list of conditions and the
|
8
|
+
following disclaimer.
|
9
|
+
Redistributions in binary form must reproduce the above copyright notice, this list of conditions and
|
10
|
+
the following disclaimer in the documentation and/or other materials provided with the distribution.
|
11
|
+
|
12
|
+
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
13
|
+
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
14
|
+
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
15
|
+
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
16
|
+
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
17
|
+
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
18
|
+
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
19
|
+
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
|
20
|
+
TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
21
|
+
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
data/{README → README.markdown}
RENAMED
File without changes
|
data/geometry.gemspec
CHANGED
data/lib/geometry.rb
CHANGED
@@ -1,6 +1,22 @@
|
|
1
|
-
require_relative 'point'
|
2
|
-
require_relative 'line'
|
1
|
+
require_relative 'geometry/point'
|
2
|
+
require_relative 'geometry/line'
|
3
3
|
|
4
4
|
module Geometry
|
5
|
-
|
5
|
+
# :call-seq:
|
6
|
+
# Line[Array, Array] -> TwoPointLine
|
7
|
+
# Line[Point, Point] -> TwoPointLine
|
8
|
+
# Line[Vector, Vector] -> TwoPointLine
|
9
|
+
# Line[y-intercept, slope] -> SlopeInterceptLine
|
10
|
+
# Line[point, slope] -> PointSlopeLine
|
11
|
+
def self.Line(*args)
|
12
|
+
Geometry::Line[*args]
|
13
|
+
end
|
14
|
+
|
15
|
+
# :call-seq:
|
16
|
+
# Point[x,y,z,...]
|
17
|
+
# Point[Point]
|
18
|
+
# Point[Vector]
|
19
|
+
def self.Point(*args)
|
20
|
+
Geometry::Point[*args]
|
21
|
+
end
|
6
22
|
end
|
@@ -0,0 +1,114 @@
|
|
1
|
+
require_relative 'point'
|
2
|
+
|
3
|
+
module Geometry
|
4
|
+
|
5
|
+
=begin rdoc
|
6
|
+
A cluster of objects representing a Line of infinite length
|
7
|
+
|
8
|
+
Supports two-point, slope-intercept, and point-slope initializer forms
|
9
|
+
|
10
|
+
== Usage
|
11
|
+
|
12
|
+
=== Two-point constructors
|
13
|
+
line = Geometry::Line[[0,0], [10,10]]
|
14
|
+
line = Geometry::Line[Geometry::Point[0,0], Geometry::Point[10,10]]
|
15
|
+
line = Geometry::Line[Vector[0,0], Vector[10,10]]
|
16
|
+
|
17
|
+
=== Slope-intercept constructors
|
18
|
+
Geometry::Line[Rational(3,4), 5] # Slope = 3/4, Intercept = 5
|
19
|
+
Geometry::Line[0.75, 5]
|
20
|
+
|
21
|
+
=== Point-slope constructors
|
22
|
+
Geometry::Line(Geometry::Point[0,0], 0.75)
|
23
|
+
Geometry::Line(Vector[0,0], Rational(3,4))
|
24
|
+
|
25
|
+
=== Special constructors (2D only)
|
26
|
+
Geometry::Line.horizontal(y=0)
|
27
|
+
Geometry::Line.vertical(x=0)
|
28
|
+
=end
|
29
|
+
class Line
|
30
|
+
|
31
|
+
# :call-seq:
|
32
|
+
# Line[Array, Array] -> TwoPointLine
|
33
|
+
# Line[Point, Point] -> TwoPointLine
|
34
|
+
# Line[Vector, Vector] -> TwoPointLine
|
35
|
+
# Line[y-intercept, slope] -> SlopeInterceptLine
|
36
|
+
# Line[point, slope] -> PointSlopeLine
|
37
|
+
def self.[](*args)
|
38
|
+
if( 2 == args.size )
|
39
|
+
args.map! {|x| x.is_a?(Array) ? Point[*x] : x}
|
40
|
+
|
41
|
+
# If both args are Points, create a TwoPointLine
|
42
|
+
return TwoPointLine.new(*args) if args.all? {|x| x.is_a?(Vector)}
|
43
|
+
|
44
|
+
# If only the first arg is a Point, create a PointSlopeLine
|
45
|
+
return PointSlopeLine.new(*args) if args.first.is_a?(Vector)
|
46
|
+
|
47
|
+
# Otherise, create a SlopeInterceptLine
|
48
|
+
return SlopeInterceptLine.new(*args)
|
49
|
+
else
|
50
|
+
nil
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def self.horizontal(y_intercept=0)
|
55
|
+
SlopeInterceptLine.new(0, y_intercept)
|
56
|
+
end
|
57
|
+
def self.vertical(x_intercept=0)
|
58
|
+
SlopeInterceptLine.new(1/0.0, x_intercept)
|
59
|
+
end
|
60
|
+
end
|
61
|
+
|
62
|
+
class PointSlopeLine < Line # :nodoc:
|
63
|
+
def initialize(point, slope)
|
64
|
+
@point = point.is_a?(Geometry::Point) ? point : Geometry.Point(point)
|
65
|
+
@slope = slope
|
66
|
+
end
|
67
|
+
def to_s
|
68
|
+
'Line(' + @slope.to_s + ',' + @point.to_s + ')'
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
class SlopeInterceptLine < Line # :nodoc:
|
73
|
+
def initialize(slope, intercept)
|
74
|
+
@slope = slope
|
75
|
+
@intercept = intercept
|
76
|
+
end
|
77
|
+
|
78
|
+
def horizontal?
|
79
|
+
0 == @slope
|
80
|
+
end
|
81
|
+
def vertical?
|
82
|
+
(1/0.0) == @slope
|
83
|
+
end
|
84
|
+
|
85
|
+
def intercept(axis=:y)
|
86
|
+
case axis
|
87
|
+
when :x
|
88
|
+
vertical? ? @intercept : (horizontal? ? nil : (-@intercept/@slope))
|
89
|
+
when :y
|
90
|
+
vertical? ? nil : @intercept
|
91
|
+
end
|
92
|
+
end
|
93
|
+
def slope
|
94
|
+
@slope
|
95
|
+
end
|
96
|
+
|
97
|
+
def to_s
|
98
|
+
'Line(' + @slope.to_s + ',' + @intercept.to_s + ')'
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
class TwoPointLine < Line # :nodoc:
|
103
|
+
attr_reader :first, :last
|
104
|
+
|
105
|
+
def initialize(point0, point1)
|
106
|
+
@first, @last = [point0, point1].map {|p| p.is_a?(Point) ? p : Point[p] }
|
107
|
+
end
|
108
|
+
def inspect
|
109
|
+
'Line(' + @first.to_s + ', ' + @last.to_s + ')'
|
110
|
+
end
|
111
|
+
alias :to_s :inspect
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
@@ -0,0 +1,45 @@
|
|
1
|
+
require 'matrix'
|
2
|
+
|
3
|
+
module Geometry
|
4
|
+
class Point < Vector
|
5
|
+
# An object repesenting a Point in N-dimensional space
|
6
|
+
#
|
7
|
+
# Supports all of the familiar Vector methods and adds convenience
|
8
|
+
# accessors for those variables you learned to hate in your high school
|
9
|
+
# geometry class (x, y, z).
|
10
|
+
#
|
11
|
+
# *Usage*
|
12
|
+
#
|
13
|
+
# point = Geometry::Point[x,y]
|
14
|
+
|
15
|
+
# :call-seq:
|
16
|
+
# Point[x,y,z,...]
|
17
|
+
# Point[Point]
|
18
|
+
# Point[Vector]
|
19
|
+
#
|
20
|
+
# Allow vector-style initialization, but override to support copy-init
|
21
|
+
# from Vector or another Point
|
22
|
+
def self.[](*array)
|
23
|
+
array = array[0] if array[0].is_a?(Array)
|
24
|
+
array = array[0].to_a if array[0].is_a?(Vector)
|
25
|
+
super *array
|
26
|
+
end
|
27
|
+
|
28
|
+
def inspect # :nodoc:
|
29
|
+
'Point' + @elements.inspect
|
30
|
+
end
|
31
|
+
def to_s # :nodoc:
|
32
|
+
'Point' + @elements.to_s
|
33
|
+
end
|
34
|
+
|
35
|
+
def x
|
36
|
+
@elements[0]
|
37
|
+
end
|
38
|
+
def y
|
39
|
+
@elements[1]
|
40
|
+
end
|
41
|
+
def z
|
42
|
+
@elements[2]
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'test/unit'
|
2
|
+
require_relative 'test_unit_extensions'
|
3
|
+
require_relative '../lib/geometry'
|
4
|
+
|
5
|
+
class GeometryTest < Test::Unit::TestCase
|
6
|
+
must "create a Point object" do
|
7
|
+
point = Geometry.Point(2,1)
|
8
|
+
assert_kind_of(Geometry::Point, point)
|
9
|
+
end
|
10
|
+
must "create a Line object" do
|
11
|
+
line = Geometry.Line([0,0], [10,10])
|
12
|
+
assert_kind_of(Geometry::Line, line)
|
13
|
+
assert_kind_of(Geometry::TwoPointLine, line)
|
14
|
+
end
|
15
|
+
end
|
data/test/test_line.rb
CHANGED
data/test/test_point.rb
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
require 'test/unit'
|
2
2
|
require_relative 'test_unit_extensions'
|
3
|
-
require_relative '../lib/point'
|
3
|
+
require_relative '../lib/geometry/point'
|
4
4
|
|
5
5
|
class PointTest < Test::Unit::TestCase
|
6
6
|
must "create a Point object using list syntax" do
|
@@ -10,31 +10,25 @@ class PointTest < Test::Unit::TestCase
|
|
10
10
|
assert_equal(1, point.y)
|
11
11
|
end
|
12
12
|
must "create a Point object from an array" do
|
13
|
-
point = Geometry::Point([3,4])
|
14
|
-
assert_equal(2, point.size)
|
15
|
-
assert_equal(3, point.x)
|
16
|
-
assert_equal(4, point.y)
|
17
|
-
end
|
18
|
-
must "create a Point object from an array using list syntax" do
|
19
13
|
point = Geometry::Point[[3,4]]
|
20
14
|
assert_equal(2, point.size)
|
21
15
|
assert_equal(3, point.x)
|
22
16
|
assert_equal(4, point.y)
|
23
17
|
end
|
24
18
|
must "create a Point object from individual parameters" do
|
25
|
-
point = Geometry
|
19
|
+
point = Geometry::Point[3,4]
|
26
20
|
assert_equal(2, point.size)
|
27
21
|
assert_equal(3, point.x)
|
28
22
|
assert_equal(4, point.y)
|
29
23
|
end
|
30
24
|
must "create a Point object from a Vector" do
|
31
|
-
point = Geometry
|
25
|
+
point = Geometry::Point[Vector[3,4]]
|
32
26
|
assert_equal(2, point.size)
|
33
27
|
assert_equal(3, point.x)
|
34
28
|
assert_equal(4, point.y)
|
35
29
|
end
|
36
30
|
must "create a Point object from a Point" do
|
37
|
-
point = Geometry
|
31
|
+
point = Geometry::Point[Geometry::Point[3,4]]
|
38
32
|
assert_equal(2, point.size)
|
39
33
|
assert_equal(3, point.x)
|
40
34
|
assert_equal(4, point.y)
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: geometry
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: '
|
4
|
+
version: '1'
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-03-
|
12
|
+
date: 2012-03-09 00:00:00.000000000 Z
|
13
13
|
dependencies: []
|
14
14
|
description: Geometric primitives and algorithms for Ruby
|
15
15
|
email:
|
@@ -20,12 +20,14 @@ extra_rdoc_files: []
|
|
20
20
|
files:
|
21
21
|
- .gitignore
|
22
22
|
- Gemfile
|
23
|
-
-
|
23
|
+
- LICENSE
|
24
|
+
- README.markdown
|
24
25
|
- Rakefile
|
25
26
|
- geometry.gemspec
|
26
27
|
- lib/geometry.rb
|
27
|
-
- lib/line.rb
|
28
|
-
- lib/point.rb
|
28
|
+
- lib/geometry/line.rb
|
29
|
+
- lib/geometry/point.rb
|
30
|
+
- test/test_geometry.rb
|
29
31
|
- test/test_line.rb
|
30
32
|
- test/test_point.rb
|
31
33
|
- test/test_unit_extensions.rb
|
@@ -54,6 +56,7 @@ signing_key:
|
|
54
56
|
specification_version: 3
|
55
57
|
summary: Geometric primitives and algoritms
|
56
58
|
test_files:
|
59
|
+
- test/test_geometry.rb
|
57
60
|
- test/test_line.rb
|
58
61
|
- test/test_point.rb
|
59
62
|
- test/test_unit_extensions.rb
|
data/lib/line.rb
DELETED
@@ -1,85 +0,0 @@
|
|
1
|
-
require_relative 'point'
|
2
|
-
|
3
|
-
module Geometry
|
4
|
-
class Line
|
5
|
-
def self.[](*args)
|
6
|
-
Geometry.Line(*args)
|
7
|
-
end
|
8
|
-
def self.horizontal(y_intercept=0)
|
9
|
-
SlopeInterceptLine.new(0, y_intercept)
|
10
|
-
end
|
11
|
-
def self.vertical(x_intercept=0)
|
12
|
-
SlopeInterceptLine.new(1/0.0, x_intercept)
|
13
|
-
end
|
14
|
-
end
|
15
|
-
|
16
|
-
class PointSlopeLine < Line
|
17
|
-
def initialize(point, slope)
|
18
|
-
@point = point.is_a?(Geometry::Point) ? point : Geometry.Point(point)
|
19
|
-
@slope = slope
|
20
|
-
end
|
21
|
-
def to_s
|
22
|
-
'Line(' + @slope.to_s + ',' + @point.to_s + ')'
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
class SlopeInterceptLine < Line
|
27
|
-
def initialize(slope, intercept)
|
28
|
-
@slope = slope
|
29
|
-
@intercept = intercept
|
30
|
-
end
|
31
|
-
|
32
|
-
def horizontal?
|
33
|
-
0 == @slope
|
34
|
-
end
|
35
|
-
def vertical?
|
36
|
-
(1/0.0) == @slope
|
37
|
-
end
|
38
|
-
|
39
|
-
def intercept(axis=:y)
|
40
|
-
case axis
|
41
|
-
when :x
|
42
|
-
vertical? ? @intercept : (horizontal? ? nil : (-@intercept/@slope))
|
43
|
-
when :y
|
44
|
-
vertical? ? nil : @intercept
|
45
|
-
end
|
46
|
-
end
|
47
|
-
def slope
|
48
|
-
@slope
|
49
|
-
end
|
50
|
-
|
51
|
-
def to_s
|
52
|
-
'Line(' + @slope.to_s + ',' + @intercept.to_s + ')'
|
53
|
-
end
|
54
|
-
end
|
55
|
-
|
56
|
-
class TwoPointLine < Line
|
57
|
-
attr_reader :first, :last
|
58
|
-
|
59
|
-
def initialize(point0, point1)
|
60
|
-
@first, @last = [point0, point1].map {|p| p.is_a?(Point) ? p : Geometry.Point(p) }
|
61
|
-
end
|
62
|
-
def inspect
|
63
|
-
'Line(' + @first.to_s + ', ' + @last.to_s + ')'
|
64
|
-
end
|
65
|
-
alias :to_s :inspect
|
66
|
-
end
|
67
|
-
|
68
|
-
def self.Line(*args)
|
69
|
-
if( 2 == args.size )
|
70
|
-
args.map! {|x| x.is_a?(Array) ? Point[*x] : x}
|
71
|
-
|
72
|
-
# If both args are Points, create a TwoPointLine
|
73
|
-
return TwoPointLine.new(*args) if args.all? {|x| x.is_a?(Vector)}
|
74
|
-
|
75
|
-
# If only the first arg is a Point, create a PointSlopeLine
|
76
|
-
return PointSlopeLine.new(*args) if args.first.is_a?(Vector)
|
77
|
-
|
78
|
-
# Otherise, create a SlopeInterceptLine
|
79
|
-
return SlopeInterceptLine.new(*args)
|
80
|
-
else
|
81
|
-
nil
|
82
|
-
end
|
83
|
-
end
|
84
|
-
end
|
85
|
-
|
data/lib/point.rb
DELETED
@@ -1,39 +0,0 @@
|
|
1
|
-
require 'matrix'
|
2
|
-
|
3
|
-
module Geometry
|
4
|
-
class Point < Vector
|
5
|
-
|
6
|
-
# Custom accessors to enable a more natural notation
|
7
|
-
def x
|
8
|
-
@elements[0]
|
9
|
-
end
|
10
|
-
def y
|
11
|
-
@elements[1]
|
12
|
-
end
|
13
|
-
def z
|
14
|
-
@elements[2]
|
15
|
-
end
|
16
|
-
|
17
|
-
# Allow vector-style initialization, but override to
|
18
|
-
# support copy-init from another Vector or Point
|
19
|
-
def self.[](*array)
|
20
|
-
array = array[0] if array[0].is_a?(Array)
|
21
|
-
return Point[*(array[0].to_a)] if array[0].is_a?(Vector)
|
22
|
-
super *array
|
23
|
-
end
|
24
|
-
|
25
|
-
def inspect
|
26
|
-
'Point' + @elements.inspect
|
27
|
-
end
|
28
|
-
def to_s
|
29
|
-
'Point' + @elements.to_s
|
30
|
-
end
|
31
|
-
end
|
32
|
-
|
33
|
-
end
|
34
|
-
|
35
|
-
def Geometry.Point(*args)
|
36
|
-
args[0] = args[0].to_a if args[0].is_a?(Vector)
|
37
|
-
args = args[0] if args[0].is_a?(Array)
|
38
|
-
Geometry::Point[*args]
|
39
|
-
end
|