How to enable the mobile ring event for this code, I’ve tried everything else I can’t → https://jsfiddle.net/IuryBorges/6na9q045/33/
Are you trying to enable orbit controls so you can rotate around or zoom in to the model on mobile?
If so, see the OrbitControls
example: three.js docs
If you look at the code I’m using fragment shader, even the 3D model was made using glsl code, I just want to access Android touch
You can add event listeners with JavaScript directly using the Touch API (outside of ThreeJS). See: Touch events - Web APIs | MDN
i tried to use this but it doesn’t work for some reason:
document.getElementsByTagName(“canvas”)[0].addEventListener(‘touchmove’, function(event) {
alert(“teste”);
event.preventDefault();
var touch = event.touches[0];
this.mousePosition.setX(touch.pageX);
this.mousePosition.setX(this.height - touch.pageY);
}, false);
here is my solution in a similar problem, I think …
First fo all, to have both (mobile and desktop) navigation the better solution I’ve found is having two behavior.
With this solution is possible to manage orbit and click(tap) to manage raycast only when a tap is a real tap and not a pointermove.
For desktop, IOS device and Android.
For Apple device works only pointermove, for Android device it depends from the age.
I’m sorry, I don’t have a sample working now couse the project was changed.
I forgot
of course my orbit is an OrbitControls
I hope it can helps
// mouse event vars
let isSwiping = false;
const delta = 1.5;
let sogliaMove = 0;
let startX;
let startY;
let firstTouch = true;
let firstTime = true;
// device detection
let isMobile = false;
if (
/(android|bb\d+|meego).+mobile|avantgo|bada\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|ipad|iris|kindle|Android|Silk|lge |maemo|midp|mmp|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\.(browser|link)|vodafone|wap|windows (ce|phone)|xda|xiino/i.test(
navigator.userAgent,
)
|| /1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s\-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|\-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw\-(n|u)|c55\/|capi|ccwa|cdm\-|cell|chtm|cldc|cmd\-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc\-s|devi|dica|dmob|do(c|p)o|ds(12|\-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(\-|_)|g1 u|g560|gene|gf\-5|g\-mo|go(\.w|od)|gr(ad|un)|haie|hcit|hd\-(m|p|t)|hei\-|hi(pt|ta)|hp( i|ip)|hs\-c|ht(c(\-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i\-(20|go|ma)|i230|iac( |\-|\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\/)|klon|kpt |kwc\-|kyo(c|k)|le(no|xi)|lg( g|\/(k|l|u)|50|54|\-[a-w])|libw|lynx|m1\-w|m3ga|m50\/|ma(te|ui|xo)|mc(01|21|ca)|m\-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(\-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)\-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|\-([1-8]|c))|phil|pire|pl(ay|uc)|pn\-2|po(ck|rt|se)|prox|psio|pt\-g|qa\-a|qc(07|12|21|32|60|\-[2-7]|i\-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h\-|oo|p\-)|sdk\/|se(c(\-|0|1)|47|mc|nd|ri)|sgh\-|shar|sie(\-|m)|sk\-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h\-|v\-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl\-|tdg\-|tel(i|m)|tim\-|t\-mo|to(pl|sh)|ts(70|m\-|m3|m5)|tx\-9|up(\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|\-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(\-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas\-|your|zeto|zte\-/i.test(
navigator.userAgent.substr(0, 4),
)
) {
isMobile = true;
}
//pointer event works better than touch event
container.style.touchAction = 'none';
if (isMobile) {
container.addEventListener('pointerdown', (event) => {
firstTouch = true;
startX = event.pageX;
startY = event.pageY;
isSwiping = false;
});
container.addEventListener('pointermove', (event) => {
if (firstTouch) {
startX = event.pageX;
startY = event.pageY;
firstTouch = false;
} else {
const diffX = Math.abs(event.pageX - startX);
const diffY = Math.abs(event.pageY - startY);
if (diffX < delta && diffY < delta && sogliaMove > 2) {
// sogliaMove>2 means 2 frame still when isSwiping is true
onDocumentTouchClick(event); // for iOS
}
}
isSwiping = true;
});
container.addEventListener('pointerup', (event) => {
const diffX = Math.abs(event.pageX - startX);
const diffY = Math.abs(event.pageY - startY);
if (diffX < delta && diffY < delta) {
onDocumentMouseClick(event); // Android old: is better desktop solution
}
firstTouch = true;
});
} else {
//desktop behavior
container.addEventListener('pointerdown', (event) => {
isSwiping = false;
startX = event.pageX;
startY = event.pageY;
});
container.addEventListener('pointermove', () => {
isSwiping = true;
});
container.addEventListener('pointerup', (event) => {
const diffX = Math.abs(event.pageX - startX);
const diffY = Math.abs(event.pageY - startY);
if (diffX < delta && diffY < delta) {
onDocumentMouseClick(event);
}
});
}
function onDocumentTouchClick(event) {
event.preventDefault();
scene.updateMatrixWorld();
mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
raycaster.setFromCamera(mouse, camera);
intersects = raycaster.intersectObject(mesh);
if (intersects.length > 0 && firstTouch === false) {
firstTouch = true;
evaluateRaycast();
}
}
function onDocumentMouseClick(event) {
event.preventDefault();
if (!isSwiping) {
scene.updateMatrixWorld();
mouse.x = (event.clientX / window.innerWidth) * 2 - 1;
mouse.y = -(event.clientY / window.innerHeight) * 2 + 1;
raycaster.setFromCamera(mouse, camera);
intersects = raycaster.intersectObject(mesh, true);
if (intersects.length > 0) {
evaluateRaycast(); //it continues
}
}
isSwiping = false;
}