大力的凳子 · threejs ...· 2 周前 · |
刚毅的海龟 · threejs---删除模型上的自定义标签( ...· 2 周前 · |
腹黑的脆皮肠 · threejs关键帧动画原理 - CSDN文库· 2 周前 · |
聪明伶俐的跑步鞋 · 解决threejs对mesh进行clone后 ...· 1 周前 · |
欢快的茶叶 · Threejs进阶之三:通过GUI修改glt ...· 1 周前 · |
博学的企鹅 · 献给心脏表情包 - 快看漫画· 1 年前 · |
冲动的梨子 · 斗罗大陆:同样是看穿了小舞魂兽的身份,为什么 ...· 1 年前 · |
面冷心慈的弓箭 · 圣母 - 720P|1080P高清下载 - ...· 1 年前 · |
憨厚的佛珠 · 东风公司2022年销量数据呈现“四个上升”- ...· 1 年前 · |
深情的炒粉 · 《急先锋》仅2.41亿 ...· 1 年前 · |
我正在使用ThreeJS开发一个web应用程序,它显示一个实体列表,每个实体都有相应的“查看”和“隐藏”按钮;例如,entityName 视图隐藏 。当用户单击 查看 按钮时,将调用以下函数并将实体成功绘制到屏幕上。
function loadOBJFile(objFile){
/* material of OBJ model */
var OBJMaterial = new THREE.MeshPhongMaterial({color: 0x8888ff});
var loader = new THREE.OBJLoader();
loader.load(objFile, function (object){
object.traverse (function (child){
if (child instanceof THREE.Mesh) {
child.material = OBJMaterial;
object.position.y = 0.1;
scene.add(object);
function addEntity(object) {
loadOBJFile(object.name);
}
在单击 Hide 按钮时,将调用以下函数:
function removeEntity(object){
scene.remove(object.name);
}
问题是,当 Hide 按钮被点击时,实体一旦加载就不会从屏幕中删除。要让 隐藏 按钮工作,我该怎么做?
我做了个小实验。我在
addEntity
函数中的
scene.add(object);
后面添加了
scene.remove(object.name);
,因此,当单击“查看”按钮时,没有绘制任何实体(正如预期的那样),这意味着
scene.remove(object.name);
在
addEntity
中工作得很好。但是我仍然不知道如何在removeEntity(object)中使用它。
另外,我检查了scene.children的内容,结果显示: object Object,object object
完整代码: http://devplace.in/~harman/model_display1.php.html
如果需要更多细节,请询问。我使用ThreeJS的rev-59-dev和rev-60进行测试。
谢谢。:)
我认为看到你对addEntity和removeEntity代码的使用会很有帮助,但我的第一个想法是,你实际上是在设置object.name吗?在scene.add(Object)之前尝试一下您的加载器;如下所示:
object.name = "test_name";
scene.add(object);
可能发生的情况是,Object3D的默认“名称”为"",因此,当您随后调用removeEntity函数时,由于场景对象名称为"“,因此调用失败。
另外,我注意到你把object.name传给了你的加载器?这是您存储资源的URL的地方吗?如果是这样的话,我建议使用Object3D内置的.userData方法来存储该信息,并保留name字段以用于场景识别。
编辑:对新添加的代码的响应
首先要注意的是,在你的对象名中包含"/“不是一个好主意,它似乎工作得很好,但你永远不知道是否有一些算法会决定转义该字符串并破坏你的项目。
第二件事就是我已经看过你的代码了,它实际上是直接的。您的删除函数正在尝试按名称删除,您需要一个Object3D才能删除。试试这个:
function removeEntity(object) {
var selectedObject = scene.getObjectByName(object.name);
scene.remove( selectedObject );
animate();
}
在这里,您可以看到我通过传入
Object3D
标记的
name
属性在Three.js
Scene
中查找您的对象。希望这能有所帮助
我和你有同样的问题。我尝试了这段代码,它工作得很好:当您创建对象时,将这个object.is_ob = true
function loadOBJFile(objFile){
/* material of OBJ model */
var OBJMaterial = new THREE.MeshPhongMaterial({color: 0x8888ff});
var loader = new THREE.OBJLoader();
loader.load(objFile, function (object){
object.traverse (function (child){
if (child instanceof THREE.Mesh) {
child.material = OBJMaterial;
object.position.y = 0.1;
// add this code
object.is_ob = true;
scene.add(object);
function addEntity(object) {
loadOBJFile(object.name);
}
然后删除你的对象,试试下面的代码:
function removeEntity(object){
var obj, i;
for ( i = scene.children.length - 1; i >= 0 ; i -- ) {
obj = scene.children[ i ];
if ( obj.is_ob) {
scene.remove(obj);
}
试一试,告诉我这是否有效,似乎三个js在添加到场景中后无法识别对象。但是通过这个技巧,它起作用了。
你可以使用这个
function removeEntity(object) {
var scene = document.querySelectorAll("scene"); //clear the objects from the scene
for (var i = 0; i < scene.length; i++) { //loop through to get all object in the scene
var scene =document.getElementById("scene");
scene.removeChild(scene.childNodes[0]); //remove all specified objects
}
clearScene: function() {
var objsToRemove = _.rest(scene.children, 1);
_.each(objsToRemove, function( object ) {
scene.remove(object);
},
它使用undescore.js遍历场景中的所有子对象(第一个除外)(这是我用来清除场景的代码的一部分)。只需确保在删除 后至少渲染一次场景,否则画布不会更改!不需要“特殊的”obj标志或类似的东西。
此外,您不能按名称删除对象,而只能按对象本身删除,因此调用
scene.remove(object);
而不是
scene.remove(object.name);
就足够了
PS:
_.each
是
underscore.js
的一个函数
使用:scene.remove( object )时,对象将从场景中移除,但与其的碰撞仍处于启用状态!
要删除与对象的拼接,您可以使用它(对于数组):objectsArray.splice(i,1);
示例:
for (var i = 0; i < objectsArray.length; i++) {
//::: each object ::://
var object = objectsArray[i];
//::: remove all objects from the scene ::://
scene.remove(object);
//::: remove all objects from the array ::://
objectsArray.splice(i, 1);
}
我来晚了,但在看了答案后,需要说更多的澄清。
您编写的remove函数
function removeEntity(object) {
// scene.remove(); it expects as a parameter a THREE.Object3D and not a string
scene.remove(object.name); // you are giving it a string => it will not remove the object
}
从Three.js场景中删除3D对象的好做法
function removeObject3D(object3D) {
if (!(object3D instanceof THREE.Object3D)) return false;
// for better memory management and performance
object.geometry.dispose();
if (object.material instanceof Array) {
// for better memory management and performance
object.material.forEach(material => material.dispose());
} else {
// for better memory management and performance
object.material.dispose();
object.removeFromParent(); // the parent might be the scene or another Object3D, but it is sure to be removed this way
return true;
}
我改进了removeObject3D的易卜拉欣代码,添加了一些几何或材质检查
removeObject3D(object) {
if (!(object instanceof THREE.Object3D)) return false;
// for better memory management and performance
if (object.geometry) {
object.geometry.dispose();
if (object.material) {
if (object.material instanceof Array) {
// for better memory management and performance
object.material.forEach(material => material.dispose());
} else {
// for better memory management and performance
object.material.dispose();