The normals in my hip are again a byproduct of packing. You want to be explicit and throw in a normal sop before the assemble, and dial the threshold for sharp/smooth to whatever you need.
Materials were trickier. I've done a hacky way here, I suspect there's a cleaner method. This gets a bit vexy, I've explained as best I could.
A material sop adds a @shop_materialpath attribute, but you can do this yourself in vex if you want complete control. I put 4 materials in /obj/mat/mat1, /obj/mat/mat2, /obj/mat/mat3, /obj/mat/mat4. If I set in a wrangle @shop_materialpath='/obj/mat/mat1', then that will be assigned.
But here, I want to broadly match the colour assignment you're using in the adjust colour sop. It's too tricky to do this after the assignment, but because your pop colour is a grayscale ramp, easier to do this before the adjust.
So we assume for a 0 to 1 colour ramp, and we want to assign the 4 materials within that range. If we store the material paths in an array, use a chramp to remap that 0 to 1 colour range to 0 to 4, then we can refer to the array elements from that index. The wrangle looks like this:
string mats[] = {'mat1','mat2','mat3','mat4'};
s@shop_materialpath = '/obj/mat/'+mats[int(chramp('mapping',@Cd.r))];
@shop_materialpath needs to be an attribute at the primitive level, and by default a copytopoints won't copy any attribute to primitives. As such I added an entry to the 'attribute from target' multiparm on the copytopoints, set it to primitive, and pointed it to shop_materialpath.
I tweaked a few settings on the materials, so some are rough, some are sharp, some are transparent, you can see them doing stuff in the viewport.