require 'minitest/autorun' require 'geometry/line' describe Geometry::Line do Line = Geometry::Line Point = Geometry::Point describe "when initializing" do it "must accept two named points" do line = Line.new(from:Point[0,0], to:Point[10,10]) line.must_be_kind_of(Line) line.must_be_instance_of(Geometry::TwoPointLine) line.first.must_equal Point[0,0] line.last.must_equal Point[10,10] end it "must accept named start and end points" do line = Line.new(start:Point[0,0], end:Point[10,10]) line.must_be_kind_of(Line) line.must_be_instance_of(Geometry::TwoPointLine) line.first.must_equal Point[0,0] line.last.must_equal Point[10,10] end it "must raise an exception when no arguments are given" do -> { Line.new }.must_raise ArgumentError end end it "create a Line object from 2 Points" do line = Geometry::Line[Geometry::Point[0,0], Geometry::Point[10,10]] assert_kind_of(Geometry::Line, line) assert_kind_of(Geometry::TwoPointLine, line) end it "create a Line object from two arrays" do line = Geometry::Line[[0,0], [10,10]] assert(line.is_a?(Geometry::Line)) assert_kind_of(Geometry::TwoPointLine, line) assert_kind_of(Geometry::Point, line.first) assert_kind_of(Geometry::Point, line.last) end it "create a Line object from two Vectors" do line = Geometry::Line[Vector[0,0], Vector[10,10]] assert(line.is_a?(Geometry::Line)) assert_kind_of(Geometry::TwoPointLine, line) end it "create a Line from a slope and y-intercept" do line = Geometry::Line[0.75, 5] assert(line.is_a?(Geometry::Line)) assert_kind_of(Geometry::SlopeInterceptLine, line) assert_equal(5, line.intercept) assert_equal(0.75, line.slope) end it "create a Line from a Rational slope and y-intercept" do line = Geometry::Line[Rational(3,4), 5] assert_kind_of(Geometry::SlopeInterceptLine, line) assert(line.is_a?(Geometry::Line)) assert_equal(Rational(3,4), line.slope) end it "have a special constructor for horizontal lines" do line = Geometry::Line.horizontal assert(line.horizontal?) end it "have a special constructor for vertical lines" do line = Geometry::Line.vertical assert(line.vertical?) end it "have accessor for y-intercept" do line = Geometry::Line[0.75, 5] assert_equal(5, line.intercept) assert_equal(5, line.intercept(:y)) end it "have accessor for x-intercept" do line = Geometry::Line.vertical(7) assert_equal(7, line.intercept(:x)) end it "return the correct x-intercept for vertical lines" do line = Geometry::Line.vertical(7) assert_equal(7, line.intercept(:x)) end it "return the correct y-intercept for horizontal lines" do line = Geometry::Line.horizontal(4) assert_equal(4, line.intercept(:y)) end it "return nil x-intercept for horizontal lines" do line = Geometry::Line.horizontal assert_nil(line.intercept(:x)) end it "return nil y-intercept for vertical lines" do line = Geometry::Line.vertical assert_nil(line.intercept(:y)) end it "implement inspect" do line = Geometry::Line[[0,0], [10,10]] assert_equal('Line(Point[0, 0], Point[10, 10])', line.inspect) end it "implement to_s" do line = Geometry::Line[[0,0], [10,10]] assert_equal('Line(Point[0, 0], Point[10, 10])', line.to_s) end end describe Geometry::PointSlopeLine do subject { Geometry::PointSlopeLine.new [1,2], 3 } it "must have a slope attribute" do subject.slope.must_equal 3 end it "must handle equality" do line2 = Geometry::PointSlopeLine.new([1,2], 3) line3 = Geometry::PointSlopeLine.new([1,1], 4) subject.must_equal line2 subject.wont_equal line3 end it 'must handle equality with a SlopeInterceptLine' do line2 = Geometry::SlopeInterceptLine.new(3, -1) line3 = Geometry::SlopeInterceptLine.new(4, -1) line2.must_equal subject line3.wont_equal subject end it 'must handle equality with a TwoPointLine' do line2 = Geometry::TwoPointLine.new([1,2], [2,5]) line3 = Geometry::TwoPointLine.new([1,2], [2,4]) line2.must_equal subject line3.wont_equal subject end it 'must know how to be horizontal' do Geometry::PointSlopeLine.new([1,2],0).horizontal?.must_equal true Geometry::PointSlopeLine.new([1,2],1).horizontal?.must_equal false end it 'must know how to be vertical' do Geometry::PointSlopeLine.new([1,2], Float::INFINITY).vertical?.must_equal true Geometry::PointSlopeLine.new([1,2], -Float::INFINITY).vertical?.must_equal true Geometry::PointSlopeLine.new([1,2],1).vertical?.must_equal false end it 'must have an x-intercept' do subject.intercept(:x).must_equal 1 end it 'must not have an x-intercept for horizontal lines' do Geometry::PointSlopeLine.new([1,2], 0).intercept(:x).must_equal nil end it 'must have a y-intercept' do subject.intercept.must_equal -1 end end describe Geometry::SlopeInterceptLine do subject { Geometry::SlopeInterceptLine.new 3, 2 } it "must have a slope attribute" do subject.slope.must_equal 3 end it "must handle equality" do line2 = Geometry::SlopeInterceptLine.new(3, 2) line3 = Geometry::SlopeInterceptLine.new(4, 3) subject.must_equal line2 subject.wont_equal line3 end it 'must handle equality with a PointSlopeLine' do line2 = Geometry::PointSlopeLine.new([0,2], 3) line3 = Geometry::PointSlopeLine.new([0,2], 2) line2.must_equal subject line3.wont_equal subject end it 'must handle equality with a TwoPointLine' do line2 = Geometry::TwoPointLine.new([0,2], [1,5]) line3 = Geometry::TwoPointLine.new([0,2], [1,4]) line2.must_equal subject line3.wont_equal subject end it 'must know how to be horizontal' do Geometry::SlopeInterceptLine.new(0, 2).horizontal?.must_equal true Geometry::SlopeInterceptLine.new(1, 2).horizontal?.must_equal false end it 'must know how to be vertical' do Geometry::SlopeInterceptLine.new(Float::INFINITY, 2).vertical?.must_equal true Geometry::SlopeInterceptLine.new(-Float::INFINITY, 2).vertical?.must_equal true Geometry::SlopeInterceptLine.new(1, 2).vertical?.must_equal false end it 'must have an x-intercept' do subject.intercept(:x).must_equal -2/3 end it 'must not have an x-intercept for horizontal lines' do Geometry::SlopeInterceptLine.new(0, 2).intercept(:x).must_equal nil end it 'must have a y-intercept' do subject.intercept.must_equal 2 end end describe Geometry::TwoPointLine do subject { Geometry::TwoPointLine.new [1,2], [3,4] } it "must have a slope attribute" do subject.slope.must_equal 1 end it "must handle equality" do line2 = Geometry::TwoPointLine.new([1,2], [3,4]) line3 = Geometry::TwoPointLine.new([1,1], [5,5]) subject.must_equal line2 subject.wont_equal line3 end it 'must handle equality with a PointSlopeLine' do line2 = Geometry::PointSlopeLine.new([1,2], 1) line3 = Geometry::PointSlopeLine.new([1,2], 2) line2.must_equal subject line3.wont_equal subject end it 'must handle equality with a SlopeInterceptLine' do line2 = Geometry::SlopeInterceptLine.new(1, 1) line3 = Geometry::SlopeInterceptLine.new(1, -1) line2.must_equal subject line3.wont_equal subject end it 'must know how to be horizontal' do Geometry::TwoPointLine.new([1,2],[2,2]).horizontal?.must_equal true Geometry::TwoPointLine.new([1,2],[3,4]).horizontal?.must_equal false end it 'must know how to be vertical' do Geometry::TwoPointLine.new([1,2], [1,3]).vertical?.must_equal true Geometry::TwoPointLine.new([1,2], [1,-3]).vertical?.must_equal true Geometry::TwoPointLine.new([1,2],[3,4]).vertical?.must_equal false end it 'must have an x-intercept' do subject.intercept(:x).must_equal -1 end it 'must not have an x-intercept for horizontal lines' do Geometry::TwoPointLine.new([1,2],[2,2]).intercept(:x).must_equal nil end it 'must have an x-intercept for vertical lines' do Geometry::TwoPointLine.new([1,2], [1,3]).intercept(:x).must_equal 1 end it 'must have a y-intercept' do subject.intercept.must_equal 1 end end