rmath3d_plain 1.2.3 → 1.2.4

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4afeec14769aedc4dc064924600f42123b7db3001dd1d9b04887ea72226a6e62
4
- data.tar.gz: 65f26f341e1c5c13e2e1971131132c7d641e1ac2cc1ee1abc1cc9a92c47f2731
3
+ metadata.gz: 569f5334bd7df6cf7e0f7a857ae589bc8258b0940913807ebaa2dcae60bf711e
4
+ data.tar.gz: 5f5cf50b25ad23c0a51574f6a4d83ac45cfc820e9c5a337591d66a7574c47145
5
5
  SHA512:
6
- metadata.gz: dc52e86e9d990b0bfe033c399dbcf5da0b2eefd2309b37ce539bfaf420c58fbd8a526e4723c511d92ab5f473ea7257a696126f39b79606342dcfb91840273759
7
- data.tar.gz: a197442846a593aa7d54a63609aa9ba3eebebdd6a2fa7b984def5741f077ec3e6322770164d2e200718769635f24a1cd58b3cc1ceb5a9bf1770336e81d7a822a
6
+ metadata.gz: 13a0b47c640f875de55331962edc75ee9f48f43554e196b98073c297b7ebf6f02e47449c0280f4f9a377a281d0c2607a154a37838cdbaf2d90aa6536a7429c72
7
+ data.tar.gz: da55b4c5ed4322637162396c67ff45d2f2c870ec7242592309d9bc31dce68e9b3014449bc4f781cde6754cc02e1ce5f5aacbcb98f57cbe867d031dc37a07338d
data/ChangeLog CHANGED
@@ -1,3 +1,7 @@
1
+ 2020-07-23 vaiorabbit <http://twitter.com/vaiorabbit>
2
+
3
+ * rmath3d.c, rmath3d_plain.rb (RMtx4): Added lookAtLH, perspectiveLH, etc.
4
+
1
5
  2020-06-21 vaiorabbit <http://twitter.com/vaiorabbit>
2
6
 
3
7
  * rmath3d.c, rmath3d_plain.rb (RMtx4): Added argument 'ndc_homogeneous' for projection matrix APIs.
File without changes
data/README.md CHANGED
@@ -4,7 +4,7 @@
4
4
 
5
5
  rmath3d is a math module for 3D game programming and computer graphics.
6
6
 
7
- * Last Update: Jun 21, 2020
7
+ * Last Update: Jul 23, 2020
8
8
  * Since: Jul 20, 2008
9
9
 
10
10
  * rmath3d (C Extension Library Implementation) [![Gem Version](https://badge.fury.io/rb/rmath3d.svg)](https://badge.fury.io/rb/rmath3d) [![Gem](https://img.shields.io/gem/dt/rmath3d.svg)](https://rubygems.org/gems/rmath3d)
@@ -33,14 +33,8 @@ rmath3d is a math module for 3D game programming and computer graphics.
33
33
  Notice: This library provides native extension. You must setup develop environment (or DevKit) before installation.
34
34
 
35
35
  * Ruby
36
- * ruby 2.0.0p247 (2013-06-27 revision 41674) [x86_64-darwin12.4.0]
37
- * ruby 2.0.0p247 (2013-06-27) [i386-mingw32] With Development Kit installed.
38
- * I used: DevKit-mingw64-32-4.7.2-20130224-1151-sfx.exe
39
- * Unpack the archive -> "> ruby dk.rb init" -> edit config.yml (just add your ruby foldier) -> "> ruby dk.rb install"
40
- * Ref.: http://blog.mattwynne.net/2010/10/12/installing-ruby-gems-with-native-extensions-on-windows/
41
- * ruby 2.2.2p95 (2015-04-13 revision 50295) [x86_64-darwin14]
42
- * Ruby 1.9.3 and prior versions are no longer supported.
43
- * Ref.: https://www.ruby-lang.org/en/news/2015/02/23/support-for-ruby-1-9-3-has-ended/
36
+ * ruby 2.7.1p83 (2020-03-31 revision a0c7c23c9c) [x64-mingw32]
37
+ * Ruby 2.3 and prior versions are no longer supported.
44
38
 
45
39
  ## Building rmath3d.{so|bundle} ##
46
40
 
@@ -1904,7 +1904,7 @@ module RMath3D
1904
1904
  end
1905
1905
 
1906
1906
  #
1907
- # call-seq: perspectiveRH(width,height,znear,zfar,ndc_convention) -> self
1907
+ # call-seq: perspectiveLH(width,height,znear,zfar,ndc_convention) -> self
1908
1908
  #
1909
1909
  # Builds a perspective projection matrix for a right-handed coordinate system from:
1910
1910
  # * View volume width (+width+)
@@ -1913,13 +1913,12 @@ module RMath3D
1913
1913
  # * Far clip plane distance (+zfar+)
1914
1914
  # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
1915
1915
  #
1916
- def perspectiveRH( width, height, znear, zfar, ndc_homogeneous = true)
1917
- perspectiveOffCenterRH(-width/2.0, width/2.0, -height/2.0, height/2.0, znear, zfar, ndc_homogeneous )
1918
- return self
1916
+ def perspectiveLH( width, height, znear, zfar, ndc_homogeneous = true)
1917
+ return perspectiveOffCenterLH(-width/2.0, width/2.0, -height/2.0, height/2.0, znear, zfar, ndc_homogeneous )
1919
1918
  end
1920
1919
 
1921
1920
  #
1922
- # call-seq: perspectiveFovRH(fovy,aspect,znear,zfar,ndc_homogeneous) -> self
1921
+ # call-seq: perspectiveFovLH(fovy,aspect,znear,zfar,ndc_homogeneous) -> self
1923
1922
  #
1924
1923
  # Builds a perspective projection matrix for a right-handed coordinate system from:
1925
1924
  # * Field of view in y direction (+fovy+ radian)
@@ -1928,24 +1927,123 @@ module RMath3D
1928
1927
  # * Far clip plane distance (+zfar+)
1929
1928
  # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
1930
1929
  #
1931
- def perspectiveFovRH( fovy_radian, aspect, znear, zfar, ndc_homogeneous = true)
1932
- f = Math::tan( fovy_radian / 2.0 )
1933
- f = 1.0 / f
1930
+ def perspectiveFovLH( fovy_radian, aspect, znear, zfar, ndc_homogeneous = true)
1931
+ # Ref.: https://www.scratchapixel.com/lessons/3d-basic-rendering/perspective-and-orthographic-projection-matrix/opengl-perspective-projection-matrix
1932
+ top = Math::tan(fovy_radian / 2.0) * znear
1933
+ bottom = -top
1934
+ right = top * aspect
1935
+ left = -right
1936
+ return perspectiveOffCenterLH(left, right, bottom, top, znear, zfar, ndc_homogeneous)
1937
+ end
1934
1938
 
1939
+ #
1940
+ # call-seq: perspectiveOffCenterLH(left,right,bottom,top,znear,zfar) -> self
1941
+ #
1942
+ # Builds a perspective projection matrix for a right-handed coordinate system from:
1943
+ # * Minimum value of the view volume width (+left+)
1944
+ # * Maximum value of the view volume width (+right+)
1945
+ # * Minimum value of the view volume height (+bottom+)
1946
+ # * Maximum value of the view volume height (+top+)
1947
+ # * Near clip plane distance (+znear+)
1948
+ # * Far clip plane distance (+zfar+)
1949
+ # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
1950
+ #
1951
+ def perspectiveOffCenterLH( left, right, bottom, top, znear, zfar, ndc_homogeneous = true)
1952
+ a = (right+left) / (right-left)
1953
+ b = (top+bottom) / (top-bottom)
1935
1954
  c = ndc_homogeneous ? -(zfar+znear) / (zfar-znear) : -zfar / (zfar-znear)
1936
1955
  d = ndc_homogeneous ? -(2*znear*zfar) / (zfar-znear) : -(znear*zfar) / (zfar-znear)
1937
1956
 
1938
- setIdentity()
1939
- setElement( 0, 0, f / aspect )
1940
- setElement( 1, 1, f )
1941
- setElement( 2, 2, c )
1957
+ setZero()
1958
+
1959
+ setElement( 0, 0, 2*znear/(right-left) )
1960
+ setElement( 0, 2, -a )
1961
+ setElement( 1, 1, 2*znear/(top-bottom) )
1962
+ setElement( 1, 2, -b )
1963
+ setElement( 2, 2, -c )
1942
1964
  setElement( 2, 3, d )
1943
- setElement( 3, 2, -1.0 )
1944
- setElement( 3, 3, 0.0 )
1965
+ setElement( 3, 2, 1.0 )
1966
+
1967
+ return self
1968
+ end
1969
+
1970
+ #
1971
+ # call-seq: orthoLH(width,height,znear,zfar) -> self
1972
+ #
1973
+ # Builds a orthogonal projection matrix for a right-handed coordinate system from:
1974
+ # * View volume width (+width+)
1975
+ # * View volume height (+height+)
1976
+ # * Near clip plane distance (+znear+)
1977
+ # * Far clip plane distance (+zfar+)
1978
+ # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
1979
+ #
1980
+ def orthoLH( width, height, znear, zfar, ndc_homogeneous = true)
1981
+ orthoOffCenterLH( -width/2.0, width/2.0, -height/2.0, height/2.0, znear, zfar, ndc_homogeneous )
1982
+ return self
1983
+ end
1984
+
1985
+ #
1986
+ # call-seq: orthoOffCenterLH(left,right,bottom,top,znear,zfar) -> self
1987
+ #
1988
+ # Builds a orthogonal projection matrix for a right-handed coordinate system from:
1989
+ # * Minimum value of the view volume width (+left+)
1990
+ # * Maximum value of the view volume width (+right+)
1991
+ # * Minimum value of the view volume height (+bottom+)
1992
+ # * Maximum value of the view volume height (+top+)
1993
+ # * Near clip plane distance (+znear+)
1994
+ # * Far clip plane distance (+zfar+)
1995
+ # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
1996
+ #
1997
+ def orthoOffCenterLH( left, right, bottom, top, znear, zfar, ndc_homogeneous = true)
1998
+ tx = -(right+left) / (right-left)
1999
+ ty = -(top+bottom) / (top-bottom)
2000
+ tz = ndc_homogeneous ? -(zfar+znear) / (zfar-znear) : -znear / (zfar-znear)
2001
+
2002
+ setIdentity()
2003
+
2004
+ setElement( 0, 0, 2.0/(right-left) )
2005
+ setElement( 0, 3, tx )
2006
+ setElement( 1, 1, 2.0/(top-bottom) )
2007
+ setElement( 1, 3, ty )
2008
+ setElement( 2, 2, (ndc_homogeneous ? 2.0 : 1.0)/(zfar-znear) )
2009
+ setElement( 2, 3, tz )
1945
2010
 
1946
2011
  return self
1947
2012
  end
1948
2013
 
2014
+ #
2015
+ # call-seq: perspectiveRH(width,height,znear,zfar,ndc_convention) -> self
2016
+ #
2017
+ # Builds a perspective projection matrix for a right-handed coordinate system from:
2018
+ # * View volume width (+width+)
2019
+ # * View volume height (+height+)
2020
+ # * Near clip plane distance (+znear+)
2021
+ # * Far clip plane distance (+zfar+)
2022
+ # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
2023
+ #
2024
+ def perspectiveRH( width, height, znear, zfar, ndc_homogeneous = true)
2025
+ return perspectiveOffCenterRH(-width/2.0, width/2.0, -height/2.0, height/2.0, znear, zfar, ndc_homogeneous )
2026
+ end
2027
+
2028
+ #
2029
+ # call-seq: perspectiveFovRH(fovy,aspect,znear,zfar,ndc_homogeneous) -> self
2030
+ #
2031
+ # Builds a perspective projection matrix for a right-handed coordinate system from:
2032
+ # * Field of view in y direction (+fovy+ radian)
2033
+ # * Aspect ratio (+aspect+)
2034
+ # * Near clip plane distance (+znear+)
2035
+ # * Far clip plane distance (+zfar+)
2036
+ # * Set true for the environment with Z coordinate ranges from -1 to +1 (OpenGL), and false otherwise (Direct3D, Metal) (+ndc_homogeneous+)
2037
+ #
2038
+ def perspectiveFovRH( fovy_radian, aspect, znear, zfar, ndc_homogeneous = true)
2039
+ # Ref.: https://www.scratchapixel.com/lessons/3d-basic-rendering/perspective-and-orthographic-projection-matrix/opengl-perspective-projection-matrix
2040
+ top = Math::tan(fovy_radian / 2.0) * znear
2041
+ bottom = -top
2042
+ right = top * aspect
2043
+ left = -right
2044
+ return perspectiveOffCenterRH(left, right, bottom, top, znear, zfar, ndc_homogeneous)
2045
+ end
2046
+
1949
2047
  #
1950
2048
  # call-seq: perspectiveOffCenterRH(left,right,bottom,top,znear,zfar) -> self
1951
2049
  #
@@ -1964,7 +2062,7 @@ module RMath3D
1964
2062
  c = ndc_homogeneous ? -(zfar+znear) / (zfar-znear) : -zfar / (zfar-znear)
1965
2063
  d = ndc_homogeneous ? -(2*znear*zfar) / (zfar-znear) : -(znear*zfar) / (zfar-znear)
1966
2064
 
1967
- setIdentity()
2065
+ setZero()
1968
2066
 
1969
2067
  setElement( 0, 0, 2*znear/(right-left) )
1970
2068
  setElement( 0, 2, a )
@@ -1973,7 +2071,6 @@ module RMath3D
1973
2071
  setElement( 2, 2, c )
1974
2072
  setElement( 2, 3, d )
1975
2073
  setElement( 3, 2, -1.0 )
1976
- setElement( 3, 3, 0.0 )
1977
2074
 
1978
2075
  return self
1979
2076
  end
@@ -485,6 +485,29 @@ class TC_RMtx4 < Minitest::Test
485
485
  end
486
486
  end
487
487
 
488
+ def test_lookAtLH
489
+ pEye = RVec3.new( 10, 10, 10 )
490
+ vDir = ( RVec3.new(0,0,0) - pEye ).normalize! # staring at (0,0,0)
491
+ vUp = RVec3.new( 0, 1, 0 )
492
+ vRight = RVec3.cross( vUp, vDir ).normalize!
493
+ vUp = RVec3.cross( vDir, vRight ).normalize!
494
+
495
+ m0 = RMtx4.new( vRight.x, vRight.y, vRight.z, -RVec3.dot(pEye,vRight),
496
+ vUp.x, vUp.y, vUp.z, -RVec3.dot(pEye,vUp),
497
+ vDir.x, vDir.y, vDir.z, -RVec3.dot(pEye,vDir),
498
+ 0.0, 0.0, 0.0, 1.0 )
499
+
500
+ m1 = RMtx4.new.lookAtLH( RVec3.new(10,10,10), # posistion
501
+ RVec3.new(0,0,0), # at
502
+ RVec3.new(0,1,0) ) # up
503
+
504
+ for r in 0...4 do
505
+ for c in 0...4 do
506
+ assert_in_delta( m0.getElement(r,c), m1.getElement(r,c), @tolerance )
507
+ end
508
+ end
509
+ end
510
+
488
511
  def test_lookAtRH
489
512
  pEye = RVec3.new( 10, 10, 10 )
490
513
  vDir = ( pEye - RVec3.new(0,0,0) ).normalize! # staring at (0,0,0)
@@ -540,15 +563,15 @@ class TC_RMtx4 < Minitest::Test
540
563
  fovy = 2.0 * Math::atan( (height/2.0) / z_n )
541
564
  f = 1.0/Math::tan( fovy/2.0 )
542
565
 
543
- m2 = RMtx4.new( f/aspect, 0.0, 0.0, 0.0,
544
- 0.0, f, 0.0, 0.0,
545
- 0.0, 0.0, (z_f+z_n)/(z_n-z_f), 2*z_f*z_n/(z_n-z_f),
546
- 0.0, 0.0, -1.0, 0.0 )
566
+ m2 = RMtx4.new( f/aspect, 0.0, 0.0, 0.0,
567
+ 0.0, f, 0.0, 0.0,
568
+ 0.0, 0.0, -(z_f+z_n)/(z_f-z_n), -2*z_f*z_n/(z_f-z_n),
569
+ 0.0, 0.0, -1.0, 0.0 )
547
570
  m3 = RMtx4.new.perspectiveFovRH( fovy, aspect, z_n, z_f, true );
548
571
 
549
572
  for r in 0...4 do
550
573
  for c in 0...4 do
551
- assert_in_delta( m2.getElement(r,c), m2.getElement(r,c), @tolerance )
574
+ assert_in_delta( m2.getElement(r,c), m3.getElement(r,c), @tolerance )
552
575
  end
553
576
  end
554
577
 
@@ -572,6 +595,67 @@ class TC_RMtx4 < Minitest::Test
572
595
  end
573
596
  end
574
597
 
598
+ def test_perspectiveLH
599
+ left = -640.0
600
+ right = 640.0
601
+ bottom = -360.0
602
+ top = 360.0
603
+ z_n = 1.0
604
+ z_f = 1000.0
605
+ width = right - left
606
+ height = top - bottom
607
+ aspect = width/height
608
+
609
+ # RMtx4#perspectiveLH
610
+ m0 = RMtx4.new( 2*z_n/width, 0.0, 0.0, 0.0,
611
+ 0.0, 2*z_n/height, 0.0, 0.0,
612
+ 0.0, 0.0, (z_f+z_n)/(z_f-z_n), -2.0*z_f*z_n / (z_f-z_n),
613
+ 0.0, 0.0, 1.0, 0.0 )
614
+ m1 = RMtx4.new.perspectiveLH( width, height, z_n, z_f, true )
615
+
616
+ for r in 0...4 do
617
+ for c in 0...4 do
618
+ assert_in_delta( m0.getElement(r,c), m1.getElement(r,c), @tolerance )
619
+ end
620
+ end
621
+
622
+ # RMtx4#perspectiveFovLH
623
+
624
+ # [NOTE] tan(fovy/2) == (height/2)/z_n
625
+ fovy = 2.0 * Math::atan( (height/2.0) / z_n )
626
+ f = 1.0/Math::tan( fovy/2.0 )
627
+
628
+ m2 = RMtx4.new( f/aspect, 0.0, 0.0, 0.0,
629
+ 0.0, f, 0.0, 0.0,
630
+ 0.0, 0.0, (z_f+z_n)/(z_f-z_n), -2.0*z_f*z_n/(z_f-z_n),
631
+ 0.0, 0.0, 1.0, 0.0 )
632
+ m3 = RMtx4.new.perspectiveFovLH( fovy, aspect, z_n, z_f, true );
633
+ for r in 0...4 do
634
+ for c in 0...4 do
635
+ assert_in_delta( m2.getElement(r,c), m3.getElement(r,c), @tolerance )
636
+ end
637
+ end
638
+
639
+ # RMtx4#perspectiveOffCenterLH
640
+
641
+ a = (right+left)/(right-left)
642
+ b = (top+bottom)/(top-bottom)
643
+ c = -(z_f+z_n)/(z_f-z_n)
644
+ d = -2.0*z_f*z_n/(z_f-z_n)
645
+ m4 = RMtx4.new( 2*z_n/(right-left), 0.0, -a, 0.0,
646
+ 0.0, 2*z_n/(top-bottom), -b, 0.0,
647
+ 0.0, 0.0, -c, d,
648
+ 0.0, 0.0, 1.0, 0.0 )
649
+
650
+ m5 = RMtx4.new.perspectiveOffCenterLH( left, right, bottom, top, z_n, z_f, true )
651
+
652
+ for r in 0...4 do
653
+ for c in 0...4 do
654
+ assert_in_delta( m4.getElement(r,c), m5.getElement(r,c), @tolerance )
655
+ end
656
+ end
657
+ end
658
+
575
659
  # http://pyopengl.sourceforge.net/documentation/manual/glOrtho.3G.xml
576
660
  def test_orthoRH
577
661
  left = -640.0
@@ -616,6 +700,49 @@ class TC_RMtx4 < Minitest::Test
616
700
  end
617
701
  end
618
702
 
703
+ def test_orthoLH
704
+ left = -640.0
705
+ right = 640.0
706
+ bottom = -360.0
707
+ top = 360.0
708
+ z_n = 1.0
709
+ z_f = 1000.0
710
+ width = right - left
711
+ height = top - bottom
712
+
713
+ # RMtx4#orthoLH
714
+ tx = -(right+left)/width
715
+ ty = -(top+bottom)/height
716
+ tz = -(z_f+z_n)/(z_f-z_n)
717
+ m0 = RMtx4.new( 2.0/width, 0.0, 0.0, tx,
718
+ 0.0, 2.0/height, 0.0, ty,
719
+ 0.0, 0.0, 2.0/(z_f-z_n), tz,
720
+ 0.0, 0.0, 0.0, 1.0 )
721
+ m1 = RMtx4.new.orthoLH( width, height, z_n, z_f, true )
722
+
723
+ for r in 0...4 do
724
+ for c in 0...4 do
725
+ assert_in_delta( m0.getElement(r,c), m1.getElement(r,c), @tolerance )
726
+ end
727
+ end
728
+
729
+ # RMtx4#orthoOffCenterLH
730
+ tx = -(right+left)/(right-left)
731
+ ty = -(top+bottom)/(top-bottom)
732
+ tz = -(z_f+z_n)/(z_f-z_n)
733
+ m2 = RMtx4.new( 2.0/(right-left), 0.0, 0.0, tx,
734
+ 0.0, 2.0/(top-bottom), 0.0, ty,
735
+ 0.0, 0.0, 2.0/(z_f-z_n), tz,
736
+ 0.0, 0.0, 0.0, 1.0 )
737
+ m3 = RMtx4.new.orthoOffCenterLH( left, right, bottom, top, z_n, z_f, true )
738
+
739
+ for r in 0...4 do
740
+ for c in 0...4 do
741
+ assert_in_delta( m2.getElement(r,c), m3.getElement(r,c), @tolerance )
742
+ end
743
+ end
744
+ end
745
+
619
746
  def test_unary_operators
620
747
  # RMtx4#+@
621
748
  m0 = RMtx4.new( 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 )
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rmath3d_plain
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.3
4
+ version: 1.2.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - vaiorabbit
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-06-21 00:00:00.000000000 Z
11
+ date: 2020-07-23 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: 'Provides vector2/3/4, matrix2x2/3x3/4x4 and quaternion in plain Ruby
14
14
  form.