Closed ghost closed 2 years ago
Look at the basic example: https://github.com/marcofugaro/three-projected-material/blob/5e0ed6d0be30db43850384fb09acb7400a2d718f/examples/basic.html#L23
if you replace
-import ProjectedMaterial from './lib/ProjectedMaterial.module.js'
+import ProjectedMaterial from 'https://cdn.skypack.dev/three-projected-material@v2.0.5'
everything works as expected.
Thanks, but I still have:
material.onBeforeRender is not a function error
Strange..
Could you post your full code? I can't debug that
Sure, below is an absolute minimal file:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Test</title>
<style>
body {
margin: 0;
}
#instructions {
width: 100%;
height: 100%;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
text-align: center;
font-size: 14px;
cursor: pointer;
}
</style>
</head>
<body>
<div id="blocker">
<div id="instructions">
<p style="font-size:36px">
Click to unlock
</p>
</div>
</div>
<script type="module">
import {
Color,
Camera,
Texture,
BackSide,
FrontSide,
DoubleSide,
BoxGeometry,
PlaneGeometry,
Vector2,
Vector3,
Mesh,
TextureLoader,
MeshStandardMaterial,
Raycaster,
Scene,
PerspectiveCamera,
WebGLRenderer,
sRGBEncoding,
GridHelper,
AxesHelper,
AmbientLight,
} from "https://cdn.skypack.dev/three@0.136.0";
import { PointerLockControls } from "https://cdn.skypack.dev/three@0.136.0/examples/jsm/controls/PointerLockControls.js";
import ProjectedMaterial from 'https://cdn.skypack.dev/three-projected-material@v2.0.5/';
let time
let prevTime = performance.now();
const velocity = new Vector3();
const direction = new Vector3();
const vertex = new Vector3();
const objects = [];
let moveForward = false;
let moveBackward = false;
let moveLeft = false;
let moveRight = false;
let canJump = false;
let raycaster
let onKeyDown
let onKeyUp
let scene, camera, renderer, blocker, instructions, controls, should_request_frame = true;
let texture_dict = {}
function get_texture(name) {
if (name in texture_dict) {
return texture_dict[name];
}
else {
texture_dict[name] = new TextureLoader().load('path_to_texts/' + name + '.png');
return texture_dict[name];
}
}
async function init() {
onKeyDown = function (event) {
switch (event.code) {
case 'ArrowUp':
case 'KeyW':
moveForward = true;
break;
case 'ArrowLeft':
case 'KeyA':
moveLeft = true;
break;
case 'ArrowDown':
case 'KeyS':
moveBackward = true;
break;
case 'ArrowRight':
case 'KeyD':
moveRight = true;
break;
case 'Space':
if (canJump === true) velocity.y += 350;
canJump = false;
break;
}
};
onKeyUp = function (event) {
switch (event.code) {
case 'ArrowUp':
case 'KeyW':
moveForward = false;
break;
case 'ArrowLeft':
case 'KeyA':
moveLeft = false;
break;
case 'ArrowDown':
case 'KeyS':
moveBackward = false;
break;
case 'ArrowRight':
case 'KeyD':
moveRight = false;
break;
}
};
document.addEventListener('keydown', onKeyDown);
document.addEventListener('keyup', onKeyUp);
raycaster = new Raycaster(new Vector3(), new Vector3(0, - 1, 0), 0, 10);
scene = new Scene();
camera = new PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
renderer = new WebGLRenderer();
renderer.setSize(window.innerWidth, window.innerHeight);
renderer.outputEncoding = sRGBEncoding;
document.body.appendChild(renderer.domElement);
camera.position.x = 0;
camera.position.y = 2;
camera.position.z = 0;
camera.lookAt(-35, 0, 135);
controls = new PointerLockControls(camera, document.body);
blocker = document.getElementById('blocker');
instructions = document.getElementById('instructions');
instructions.addEventListener('click', function () {
controls.lock();
});
controls.addEventListener('lock', function () {
instructions.style.display = 'none';
blocker.style.display = 'none';
});
controls.addEventListener('unlock', function () {
blocker.style.display = 'block';
instructions.style.display = '';
});
controls.addEventListener("change", animate);
window.addEventListener('resize', animate);
scene.add(controls.getObject());
const size = 260;
const divisions = 260;
var grid = new GridHelper(size, divisions, 0x444444, 0x888888);
scene.add(grid);
const axesHelper = new AxesHelper(260);
scene.add(axesHelper);
var ambientLight = new AmbientLight(0xfcfcfc, 1.6);
scene.add(ambientLight);
const geometry = new PlaneGeometry(10, 10);
const material = new ProjectedMaterial({
camera: camera, // the camera that acts as a projector
texture: get_texture("c_nm"), // the texture being projected
textureScale: 0.8, // scale down the texture a bit
textureOffset: new Vector2(0.1, 0.1), // you can translate the texture if you want
cover: true, // enable background-size: cover behaviour, by default it's like background-size: contain
color: '#ccc', // the color of the object if it's not projected on
roughness: 0.3, // you can pass any other option that belongs to MeshPhysicalMaterial
})
const plane = new Mesh(geometry, material);
plane.position.set(-20, 0, 0)
scene.add(plane);
}
const animate = function () {
if (controls.isLocked === true) {
raycaster.ray.origin.copy(controls.getObject().position);
raycaster.ray.origin.y -= 10;
const intersections = raycaster.intersectObjects(objects, false);
const onObject = intersections.length > 0;
const delta = 0.02//(time - prevTime) / 1000;
velocity.x -= velocity.x * 10.0 * delta;
velocity.z -= velocity.z * 10.0 * delta;
velocity.y -= 9.8 * 100.0 * delta; // 100.0 = mass
direction.z = Number(moveForward) - Number(moveBackward);
direction.x = Number(moveRight) - Number(moveLeft);
direction.normalize(); // this ensures consistent movements in all directions
const speed = 750;
if (moveForward || moveBackward) velocity.z -= direction.z * speed * delta;
if (moveLeft || moveRight) velocity.x -= direction.x * speed * delta;
if (onObject === true) {
velocity.y = Math.max(0, velocity.y);
canJump = true;
}
controls.moveRight(- velocity.x * delta);
controls.moveForward(- velocity.z * delta);
controls.getObject().position.y += (velocity.y * delta); // new behavior
let min_height = 21.8;
if (controls.getObject().position.y < min_height) {
velocity.y = 0;
controls.getObject().position.y = min_height;
canJump = true;
}
}
renderer.render(scene, camera);
requestAnimationFrame(animate);
return;
};
await init();
animate()
</script>
</body>
</html>
Fixed in v2.1.0, your example should work fine now.
Using this lib with skypack leads to a black screen:
Any idea what is going on? Note: camera and texture have to be expressed with object syntax
Thank you