先展示效果图
适用场景:加载的obj模型需要发生形变,同时还要展示模型的纹理效果,可以使用到面料模拟或者弹性物体的模拟当中
具体实现方案:
1、读取obj文件中的vt的值,存起来
2、读取f值,存v索引和vt索引
3、根据存储的v索引和vt索引新增uv数据
4、将整个uv数组放入到模型当中
5、读取模型的uv,使用纹理加载器加载图片,放入到模型上
然后就是上代码了~
function loadFromUrl(url) {return fetch(url).then(response => response.text()).then(objData => {const lines = objData.split('\n');let vertices = [];let faceTriIds = [];let vt = [];let uv = [];let uvIndex = [];for (const line of lines) {const parts = line.split(' ').filter(part => part!== '');if (parts[0] === 'v') {// 将顶点坐标依次存入一维数组vertices.push(parseFloat(parts[1]));vertices.push(parseFloat(parts[2]));vertices.push(parseFloat(parts[3]));} else if (parts[0] === 'f') {const facePart = parts[1].split('/');const facePart02 = parts[2].split('/');const facePart03 = parts[3].split('/');faceTriIds.push(Number(facePart[0])-1,Number(facePart02[0])-1,Number(facePart03[0])-1);// 获取uv的索引-->找到值存入uv中uvIndex[Number(facePart[0])-1] = Number(facePart[1])-1uvIndex[Number(facePart02[0])-1] = Number(facePart02[1])-1uvIndex[Number(facePart03[0])-1] = Number(facePart03[1])-1} else if (parts[0] === 'vt') {vt.push(parseFloat(parts[1]),parseFloat(parts[2]))}}// 遍历uv --> 根据索引找到具体的uv值for (let i = 0; i < uvIndex.length; i++) {uv[i*2] = vt[uvIndex[i]*2]uv[i*2+1] = vt[uvIndex[i]*2+1]}return { vertices, faceTriIds, uv };}).catch(error => {console.error('Error loading OBJ file from URL:', error);return null;});
}export default loadFromUrl;
应该还算清晰明了的吧
就这样~~~~