Class to Explode craft models

It can be dangerous piloting a ROV through the KM3NeT telescope!

I implemented the ROV explosion in my KM3NeT app when the ROV collides with an optical module.

https://youtu.be/AcwKLJttfvU

https://youtu.be/44iAtkl-93Q

@piinthesky Nice!

@dave1707 , I tried to adapt your code into a single function that could make any Craft model explodable.

It works great on the sphere and the monkey, but not on the warship — you can see all three tested in the code.

I think it’s because I can’t get the vertices of the submeshes.

@John, above you mentioned intending to “add model.submeshIndex and model.submeshCount,” and I see that you did it with submeshCount but apparently not submeshIndex`. Did you provide a different way to get at submeshes, or are they still beyond reach?

@UberGoober - all explode fine for me. Just modified the initial code a bit.


scene = craft.scene()
    scene.sun.rotation=quat.eulerAngles(30,180,0)
    v=scene.camera:add(OrbitViewer,vec3(0,3,10),25, -80, 2000)

    craftEntity=scene:entity()
     craftEntity.model = craft.model(asset.builtin.Primitives.Sphere)
    -- craftEntity.model = craft.model(asset.builtin.Primitives.Monkey)
   -- craftEntity.model = craft.model(asset.builtin.Watercraft.watercraftPack_003_obj)
    craftEntity = explodeyCraft(craftEntity, color(172, 106, 59))
    craftEntity.eulerAngles = vec3(20, 180, -0)

@Bri_G if you comment out the part of explode() that makes the shards move and rotate it’s clear that fewer than half of the shapes are being converted to shards.

@UberGoober - hmmmm, do you think that is because the model has been optimised to remove duplicate vertices? If that’s the case you won’t be able to affect all triangles.

@Bri_G why don’t you think the other data is in submeshes, which not only seems to me the most likely scenario, but is also the one suggested by @John as the source of this kind of problem in this very thread?

@UberGoober - my bad, I need to re-read some of these threads.

@John, above you made this comment regarding trying to get submesh vertices:

As a work around you could export your model as several parts based on material and then attach them all to the same parent entity which would give you the same model but access to all the geometry.

…can you give some demonstration of that? I’d love to have a way to access the submeshes’ geometry, even a convoluted way.

@UberGoober what @John suggested was from within Blender to export a single model for each separate material of the original model and then in Codea to group them back together. This way one could easily manipulate each material/model. This would need some expertise on the Blender side.

@piinthesky thanks for clearing that up! I was genuinely baffled.

@UberGoober Comment out the below line in your explode function of the .zip file and try the explode. Then go thru and try every model in the Watercraft pack. You’ll notice that each model only has parts of the full image. It’s like each image is made up of multiple parts from other models. Looking thru the .obj file I haven’t seen where the model is getting all of the info it needs. It’s like the .obj file doesn’t have all the vertices and it’s getting other information from somewhere else.

            --b.position=b.position+b.vel

@dave1707, I know all that, that’s exactly why I’m asking this question in the first place.

I don’t know why you don’t believe me that it’s all about submeshes, @Bri_G didn’t either until I pointed out to him that @John addresses this issue in one of the other threads about exploding meshes, and he implies it’s all about submeshes.

You can get the number of submeshes out of Craft, you can apply materials individually to submeshes with Craft, but you don’t seem to be able to get the actual vertex information on submeshes out of Craft–in theory, if you could apply a shader to each individual submesh, and there were some variable inside the shader that you could watch, you could harvest the vertex information on the fly.

@UberGoober seems we will just have to beg nicely to @John to make this information accessible.

@UberGoober What is your definition of a subMesh. The “m.submeshCount”gives you the number of color values used in the mtl file. In the robot example, there are 4 colors that can be changed and the submeshCount will give you 4. In the watercraft 001 run below, it gives a count of 7 for submeshCount which matches the number of color groups in the .mtl file for watercraft 001.

Run this code for each of the watercraft models. All of the triangles defined in the .obj file will be colored red. The question is, where is the uncolored part coming from. Looking thru the .obj file, I don’t see anything that tells me.

Some runs will take longer to display because of the number of triangles.

I don’t have all the answers yet. I’m just going by what I’m seeing looking at the images and a dump of the .obj and .mtl files.

viewer.mode=STANDARD

function setup()
    assert(OrbitViewer, "Please include Cameras (not Camera) as a dependency")
    scene=craft.scene()
    v=scene.camera:add(OrbitViewer, vec3(0,0,0), 40, 0, 2000)
    m=scene:entity()

    m.model = craft.model(asset.builtin.Watercraft.watercraftPack_001_obj)

    m.material = craft.material(asset.builtin.Materials.Specular)
    m.material.diffuse=color(255, 255, 255, 255)
    m.position=vec3(0,0,0)    
    print("positions  ",#m.model.positions)
    print("index  ",m.model.indexCount)
    print("vertex  ",m.model.vertexCount) 
    print("=====  Working  =====")       
    for z=1,m.model.indexCount//3 do
        create(z)        
    end
    print("=====  Done  =====")
end

function update(dt)
    scene:update(dt)
end

function draw()
    update(DeltaTime)
    scene:draw() 
end

function create(point)
    tab={}
    for z=(point-1)*3+1,(point-1)*3+3 do
        i=m.model.indices[z]  
        p=m.model.positions[i]
        table.insert(tab,p)
    end
    local r=scene:entity()
    r.model=craft.model()
    r.model.positions={tab[1],tab[2],tab[3]}      
    r.model.indices={1,2,3}
    r.model.colors={color(255),color(255),color(255)}
    r.model.uvs={vec2(1,0),vec2(0,0),vec2(0,1)}
    r.material = craft.material(asset.builtin.Materials.Basic)
    r.material.diffuse=color(255,0,0)
end

@dave1707 if m.positions does not give you all the vertices you will not see all of them. I think it will only give you the positions of the first mesh.

I wonder if by bypassing craft and using @yojimbo2000 objloader one could access all the vertices?

@dave1707 I’m not sure you’re correct in defining submeshes as simply color values. Submeshes are, I believe, separate geometries, and that’s the reason you can change their color values independently. They’re not, I don’t think, just designated color areas on a single mesh. Plus the word “mesh” in “submesh” is kind of a clue, to me, that they’re meshes.

In my experience with trying to apply shaders to Craft models, if I only apply the shader to one submesh I get results like the watercraft ship–it only applies to one piece.

In the end it doesn’t really matter because the goal is the same–I want to be able to apply an effect to an entire model, not just part of it–and no matter what the proper definition of submeshes is, they seem to be the things that hold the key to this.

@piinthesky I guess there’s only one way to find out…

OTOH if you were able to decipher the yojimbo code you might find out how to access sub meshes directly on the Craft OBJ models also…

yes, that is what i meant.
the obj files are obj files-it’s just whether you try to read via craft or via objloader.
There is also the pseudoMesh code from @LoopSpace. Unfortunately i don’t have the time at the moment to play around with all this.

I have played with the PseudoMesh code a little bit, I don’t think it addresses sub meshes.