Skip to content

Commit a762901

Browse files
committed
Removed FieldEnv stars, optimized castRay() more
The stars in the sky were pretty warped, so decided to remove them until I can make a better star field texture Moved inverse determinant division and multiplication after "in triangle" calculations to speed up collision detection some more.
1 parent 6144326 commit a762901

File tree

7 files changed

+57
-15
lines changed

7 files changed

+57
-15
lines changed

Source/js/pxlNav/core/Colliders.js

Lines changed: 44 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,11 @@
1818
// https://github.com/mrdoob/three.js/blob/dev/build/three.core.js
1919
// ( Since the source is split up, I'm just linking to the main file )
2020
//
21+
// Couldn't get the above working 100%, so made `castRay()` for Vector Ray to Triangle collision
22+
// It works with floor and interactable colliders, but slightly heavier than the other method
23+
// Looked to this PDF for Moller-Trumbore Ray-Intersect, pages 4 & 5
24+
// https://cadxfem.org/inf/Fast%20MinimumStorage%20RayTriangle%20Intersection.pdf
25+
//
2126
// I implemented a per-pxlRoom hash grid for ground collision detection,
2227
// As ray casting to all polygons in a scene is inefficient
2328
// While also using the logic outlined in the book as used in Three.js, I've adapted it to my needs --
@@ -37,7 +42,7 @@ import {
3742
AdditiveBlending
3843
} from "../../libs/three/three.module.min.js";
3944

40-
import { VERBOSE_LEVEL, COLLIDER_TYPE } from "./Enums.js";
45+
import { VERBOSE_LEVEL, COLLIDER_TYPE, GEOMETRY_SIDE } from "./Enums.js";
4146

4247
// Some assumptions are made here, as collision meshes are ussually low poly
4348
// A grid size of 100 is assumed for -+500 unit bounds
@@ -518,9 +523,20 @@ export class Colliders{
518523
// -- -- --
519524

520525
// Moller-Trumbore triangle ray intersection
521-
// The other ray casting methods have issues to be worked out
526+
// The other ray casting method has issues to be worked out
522527
// This is the general purpose rayCaster for now
523-
castRay( roomName, origin, direction, colliderType=COLLIDER_TYPE.FLOOR, multiHits=true ){
528+
// Implemented to be side-non-specific, as the ray may be cast from any direction
529+
// Ray intersection for front facing or back facing triangles
530+
// ** This is assuming Three.js is using right-handed winding order **
531+
//
532+
// Using - Scalar Triple Product; Cramer's Rule - Determinant of a 3x3 matrix
533+
// u = (origin - v0) . (direction x edge1) / (edge0 . (direction x edge1))
534+
// v = (origin - v0) . (edge0 x direction) / (edge0 . (direction x edge1))
535+
// t = (v1 - origin) . (edge1 x direction) / (edge0 . (direction x edge1))
536+
// Pages 4 & 5 -
537+
// https://cadxfem.org/inf/Fast%20MinimumStorage%20RayTriangle%20Intersection.pdf
538+
//
539+
castRay( roomName, origin, direction, colliderType=COLLIDER_TYPE.FLOOR, geoSide=GEOMETRY_SIDE.DOUBLE, multiHits=true ){
524540

525541
if( !this.roomColliderData.hasOwnProperty( roomName ) || !this.roomColliderData[ roomName ].hasOwnProperty( colliderType ) ){
526542
this.error( "Room '" + roomName + "' does not have collider data for type: " + colliderType );
@@ -534,16 +550,24 @@ export class Colliders{
534550
let gridX = Math.floor(origin.x * gridSizeInv);
535551
let gridZ = Math.floor(origin.z * gridSizeInv);
536552
let gridKey = this.getGridKey(gridX, gridZ);
537-
//console.log( origin, direction, gridKey );
538553

539-
554+
// Default checks for front and back facing triangles
555+
let backFaceCheck = 1;
556+
let frontFaceCheck = 1;
557+
if( geoSide == GEOMETRY_SIDE.FRONT ){
558+
backFaceCheck = 0;
559+
}else if( geoSide == GEOMETRY_SIDE.BACK ){
560+
frontFaceCheck = 0;
561+
}
562+
540563
if (!roomData['faceGridGroup'].hasOwnProperty(gridKey)) return [];
541564
let faceKeys = roomData['faceGridGroup'][gridKey];
542565
//let faceKeys = Object.keys( roomData['faceVerts'] );
543566

544567
let hits = [];
545568
let retHits = {};
546569

570+
547571
faceKeys.forEach(faceKey => {
548572
let faceVerts = roomData['faceVerts'][faceKey];
549573
let v0 = faceVerts['verts'][0];
@@ -553,22 +577,29 @@ export class Colliders{
553577
let edge0 = faceVerts['edge0']; // v1.clone().sub(v0);
554578
let edge1 = faceVerts['edge1']; // v2.clone().sub(v0);
555579
let directionCross = direction.clone().cross(edge1);
556-
let isFacing = edge0.dot( directionCross );
580+
let isFacing = edge0.dot( directionCross ); // Determinant of the matrix
557581

558-
if( isFacing > -this.epsilon && isFacing < this.epsilon ) return; // This ray is parallel to this triangle.
582+
// Triangle is parallel to the ray
583+
// This allows negative facing triangles to be detected
584+
if( isFacing*backFaceCheck > -this.epsilon && isFacing*frontFaceCheck < this.epsilon ) return; // This ray is parallel to this triangle.
559585

560-
let factor = 1.0 / isFacing;
586+
// Calculate barycentric coordinates
587+
561588
let edgeOrig = origin.clone().sub(v0);
562-
let u = factor * edgeOrig.dot( directionCross );
589+
let u = edgeOrig.dot( directionCross );
563590

564-
if( u < 0.0 || u > 1.0 ) return;
591+
if( u < 0.0 || u > isFacing ) return; // Invalid barcentric coordinate, outside of triangle
565592

566593
let crossOrig = edgeOrig.clone().cross(edge0);
567-
let v = factor * direction.dot( crossOrig );
594+
let v = direction.dot( crossOrig );
595+
596+
if( v < 0.0 || u + v > isFacing) return; // Invalid barcentric coordinate, outside of triangle
568597

569-
if( v < 0.0 || u + v > 1.0) return;
598+
let factor = 1.0 / isFacing; // Inverted Determinant to reduce divisions, Scale factor for ray intersection
599+
u *= factor;
600+
v *= factor;
570601

571-
let dist = factor * edge1.dot( crossOrig );
602+
let dist = factor * edge1.dot( crossOrig ); // 'dist' is 't' in the Moller-Trumbore algorithm
572603

573604
if( dist > this.epsilon ){ // ray intersection
574605
let intersectionPoint = origin.clone().add( direction.clone().multiplyScalar(dist) );

Source/js/pxlNav/core/Enums.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,15 @@ export const COLLIDER_TYPE = {
5050
'CLICKABLE' : 9 // Mouse clickable
5151
};
5252

53+
// Geometry side types
54+
// Used when casting rays to determine which side of the geometry was hit
55+
// More specifics will be added as needed
56+
export const GEOMETRY_SIDE = {
57+
'FRONT' : 0,
58+
'BACK' : 1,
59+
'DOUBLE' : 2
60+
};
61+
5362
// Camera event types
5463
// Subscribe to the pxlCamera object using these event types
5564
// `pxlNav.pxlCamera.subscribe( CAMERA_EVENT.MOVE, function() { ... } );`
@@ -110,5 +119,6 @@ export const pxlEnums = {
110119
'SHADOW_MAP' : SHADOW_MAP,
111120
'CAMERA_EVENT' : CAMERA_EVENT,
112121
'COLLIDER_TYPE' : COLLIDER_TYPE,
122+
'GEOMETRY_SIDE' : GEOMETRY_SIDE,
113123
'COLOR_SHIFT' : COLOR_SHIFT
114124
};

Source/js/pxlNav/effects/particles/FloatingDust.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ export class FloatingDust extends ParticleBase{
4848
lightPos:{value:lightPosArr}
4949
};
5050
//let mtl = this.pxlFile.pxlShaderBuilder( snowUniforms, snowFallVert( true ), snowFallVert() );
51+
console.log(proxDist);
5152
let mtl = this.room.pxlFile.pxlShaderBuilder( dustUniforms, dustVert( lightPosArr.length, proxDist ), dustFrag() );
5253
mtl.side=DoubleSide;
5354
mtl.transparent=true;

Source/js/pxlNav/effects/particles/shaders/FloatingDust.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -142,7 +142,7 @@ export function dustVert( lightCount, proxDistance=120 ){
142142
vec2 camXZ=cameraPosition.xz;
143143
pos.xz= mod( pos.xz-camXZ, PROX) + camXZ - PROX*.5;
144144
145-
float pScalar = max( 0., (1.-length(pos-cameraPosition )*PROX_INV) );
145+
float pScalar = clamp( (1.-length(pos-cameraPosition )*PROX_INV)*1.5, 0.0, 1.0 );
146146
float aMult = min(1.0, pScalar*3.0);
147147
vAlpha = (seeds.x*.5+.7) * aMult;
148148
-12.5 KB
Loading

docs/js/pxlNav.esm.js

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
-12.5 KB
Loading

0 commit comments

Comments
 (0)