node.js - 如何使用react和express js通过objloader(三个js)导入json对象
问题描述
我尝试使用threejs OBJLoader.json
将大型模型导入我的项目,但似乎我的服务器正在用我的主 HTML 文件替换模型,当它尝试解析并给出错误时注意到:.json
JSON.parse 中位置 0 处的 JSON 中的意外令牌 <
通过在我的 js 文件中使用简单的 require() 调用模型来尝试,并显示:
TypeError:url.lastIndexOf 不是函数
还尝试在所需模型中使用 stringify 并显示:
加载资源失败:net::ERR_CONNECTION_RESET
有threejs
错误对象:
bubbles: false
cancelBubble: false
cancelable: false
composed: false
currentTarget: XMLHttpRequest {onreadystatechange: null, readyState: 4, timeout: 0, withCredentials: false, upload: XMLHttpRequestUpload, …}
defaultPrevented: false
eventPhase: 0
isTrusted: true
lengthComputable: false
loaded: 0
path: []
returnValue: true
srcElement: XMLHttpRequest {onreadystatechange: null, readyState: 4, timeout: 0, withCredentials: false, upload: XMLHttpRequestUpload, …}
target: XMLHttpRequest {onreadystatechange: null, readyState: 4, timeout: 0, withCredentials: false, upload: XMLHttpRequestUpload, …}
timeStamp: 1096.5999999898486
total: 0
type: "error"
__proto__: ProgressEvent
这是我试图加载模型的 js 文件
const THREE = require ('three');
const obj1 = require('../img/orig.json');
const orig = JSON.stringify(obj1);
export default canvas =>{
const info = document.getElementById('three_origami');
let camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 ),
scene = new THREE.Scene(), renderer=new THREE.WebGLRenderer( { antialias: true } );
let group=new THREE.MeshNormalMaterial();
let mouseX = 0, mouseY = 0;
let windowHalfX = window.innerWidth / 2;
let windowHalfY = window.innerHeight / 2;
init();
animate();
function init() {
camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 );
camera.position.z = 40;
scene = new THREE.Scene();
scene.background = new THREE.Color( 0xffffff );
scene.fog = new THREE.Fog( 0xfffff, 1, 10000 );
group = new THREE.Group();
const objLoader = new THREE.ObjectLoader();
objLoader.load(orig, (obj) => {
for ( let i = 0; i <= 300; i ++ ) {
let mesh = new THREE.Mesh( obj.geometry, obj.material );
mesh.position.x = Math.random() * 2000 - 1000;
mesh.position.y = Math.random() * 2000 - 1000;
mesh.position.z = Math.random() * 2000 - 1000;
mesh.rotation.x = Math.random() * 2 * Math.PI;
mesh.rotation.y = Math.random() * 2 * Math.PI;
mesh.matrixAutoUpdate = false;
mesh.updateMatrix();
group.add(mesh);
}
},
null,
(err) => {
console.error('Error', err);
});
scene.add( group );
//
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
info.appendChild( renderer.domElement );
//
//
document.addEventListener( 'mousemove', onDocumentMouseMove, false );
//
window.addEventListener( 'resize', onWindowResize, false );
}
function onWindowResize() {
windowHalfX = window.innerWidth / 2;
windowHalfY = window.innerHeight / 2;
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize( window.innerWidth, window.innerHeight );
}
function onDocumentMouseMove( event ) {
mouseX = ( event.clientX - windowHalfX ) * 10;
mouseY = ( event.clientY - windowHalfY ) * 10;
}
//
function animate() {
requestAnimationFrame( animate );
render();
}
function render() {
let time = Date.now() * 0.001;
let rx = Math.sin( time * 0.7 ) * 0.5,
ry = Math.sin( time * 0.3 ) * 0.5,
rz = Math.sin( time * 0.2 ) * 0.5;
camera.position.x += ( mouseX - camera.position.x ) * 0.05;
camera.position.y += ( - mouseY - camera.position.y ) * 0.05;
camera.lookAt( scene.position );
group.rotation.x = rx;
group.rotation.y = ry;
group.rotation.z = rz;
renderer.render( scene, camera );
}
}
这是我存储库中的 .json 文件:portfolio-final/orig.json
和我的package.json
{
"name": "portfolio-final",
"version": "0.1.0",
"private": true,
"dependencies": {
"@babel/core": "7.1.0",
"@svgr/webpack": "2.4.1",
"babel-core": "7.0.0-bridge.0",
"babel-eslint": "9.0.0",
"babel-jest": "23.6.0",
"babel-loader": "8.0.4",
"babel-plugin-named-asset-import": "^0.2.2",
"babel-preset-react-app": "^5.0.3",
"bfj": "6.1.1",
"case-sensitive-paths-webpack-plugin": "2.1.2",
"chalk": "2.4.1",
"css-loader": "1.0.0",
"dotenv": "6.0.0",
"dotenv-expand": "4.2.0",
"eslint": "5.6.0",
"eslint-config-react-app": "^3.0.3",
"eslint-loader": "2.1.1",
"eslint-plugin-flowtype": "2.50.1",
"eslint-plugin-import": "2.14.0",
"eslint-plugin-jsx-a11y": "6.1.1",
"eslint-plugin-react": "7.11.1",
"express": "^4.16.3",
"file-loader": "2.0.0",
"fs-extra": "7.0.0",
"gsap": "^2.0.2",
"html-webpack-plugin": "4.0.0-alpha.2",
"identity-obj-proxy": "3.0.0",
"jest": "23.6.0",
"jest-pnp-resolver": "1.0.1",
"jest-resolve": "23.6.0",
"mini-css-extract-plugin": "0.4.3",
"node-sass": "^4.9.3",
"optimize-css-assets-webpack-plugin": "5.0.1",
"pnp-webpack-plugin": "1.1.0",
"postcss-flexbugs-fixes": "4.1.0",
"postcss-loader": "3.0.0",
"postcss-preset-env": "6.0.6",
"postcss-safe-parser": "4.0.1",
"react": "^16.5.2",
"react-app-polyfill": "^0.1.3",
"react-dev-utils": "^6.0.4",
"react-dom": "^16.5.2",
"react-redux": "^5.0.7",
"react-router-dom": "^4.3.1",
"react-router-redux": "^4.0.8",
"redux": "^4.0.0",
"resolve": "1.8.1",
"sass-loader": "^7.1.0",
"style-loader": "0.23.0",
"terser-webpack-plugin": "1.1.0",
"three": "^0.97.0",
"url-loader": "1.1.1",
"webpack": "4.19.1",
"webpack-dev-server": "3.1.9",
"webpack-manifest-plugin": "2.0.4",
"workbox-webpack-plugin": "3.6.2",
"xhr": "^2.5.0"
},
"scripts": {
"start": "node server/server.js",
"start-dev": "node scripts/start.js",
"build": "node scripts/build.js",
"test": "node scripts/test.js",
"heroku-postbuild": "yarn run build"
},
"eslintConfig": {
"extends": "react-app"
},
"browserslist": [
">0.2%",
"not dead",
"not ie <= 11",
"not op_mini all"
],
"jest": {
"collectCoverageFrom": [
"src/**/*.{js,jsx}"
],
"resolver": "jest-pnp-resolver",
"setupFiles": [
"react-app-polyfill/jsdom"
],
"testMatch": [
"<rootDir>/src/**/__tests__/**/*.{js,jsx}",
"<rootDir>/src/**/?(*.)(spec|test).{js,jsx}"
],
"testEnvironment": "jsdom",
"testURL": "http://localhost",
"transform": {
"^.+\\.(js|jsx)$": "<rootDir>/node_modules/babel-jest",
"^.+\\.css$": "<rootDir>/config/jest/cssTransform.js",
"^(?!.*\\.(js|jsx|css|json)$)": "<rootDir>/config/jest/fileTransform.js"
},
"transformIgnorePatterns": [
"[/\\\\]node_modules[/\\\\].+\\.(js|jsx)$",
"^.+\\.module\\.(css|sass|scss)$"
],
"moduleNameMapper": {
"^react-native$": "react-native-web",
"^.+\\.module\\.(css|sass|scss)$": "identity-obj-proxy"
},
"moduleFileExtensions": [
"web.js",
"js",
"json",
"web.jsx",
"jsx",
"node",
"xhr"
]
},
"babel": {
"presets": [
"react-app"
]
}
}
非常感谢!
解决方案
编辑:你得到的原因Unexpected token
是你的服务器找不到那个文件,所以它返回一个 404 页面。Three.js 正在尝试将网站解析为 JSON 文件。
默认情况下,当您需要 JSON 文件时,Webpack 在构建时将其包含在包中。在运行时,它只会返回 JSON 对象而不是文件的路径,因为没有 JSON 文件,它与所有其他 Javascript 捆绑在一起。
所以基本上require ('../img/orig.json');
返回 JSON 对象。
JSON.stringify
将 JSON 对象转换为字符串,这不是我们想要的。
您可以使 Webpack 不将 JSON 文件包含到包中,将文件放在目标文件夹中并要求它返回路径,使用file-loader。但是有一个更简单的方法。
ObjectLoader.load
需要一个指向 JSON 文件的 URL,但 ObjectLoader.parse
需要一个 JSON 对象,这正是我们正在寻找的
您可以使用捆绑 json require ('../img/orig.json');
,然后使用它ObjectLoader.parse
来解析 json:
const THREE = require ('three');
const orig = require ('../img/orig.json');
export default canvas =>{
const info = document.getElementById('three_origami');
let camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 ),
scene = new THREE.Scene(), renderer=new THREE.WebGLRenderer( { antialias: true } );
let group=new THREE.MeshNormalMaterial();
let mouseX = 0, mouseY = 0;
let windowHalfX = window.innerWidth / 2;
let windowHalfY = window.innerHeight / 2;
init();
animate();
function init() {
camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 );
camera.position.z = 40;
scene = new THREE.Scene();
scene.background = new THREE.Color( 0xffffff );
scene.fog = new THREE.Fog( 0xfffff, 1, 10000 );
group = new THREE.Group();
const objLoader = new THREE.ObjectLoader();
objLoader.parse(orig, (obj) => {
for ( let i = 0; i <= 300; i ++ ) {
let mesh = new THREE.Mesh( obj.geometry, obj.material );
mesh.position.x = Math.random() * 2000 - 1000;
mesh.position.y = Math.random() * 2000 - 1000;
mesh.position.z = Math.random() * 2000 - 1000;
mesh.rotation.x = Math.random() * 2 * Math.PI;
mesh.rotation.y = Math.random() * 2 * Math.PI;
mesh.matrixAutoUpdate = false;
mesh.updateMatrix();
group.add(mesh);
}
});
scene.add( group );
//
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
info.appendChild( renderer.domElement );
//
//
document.addEventListener( 'mousemove', onDocumentMouseMove, false );
//
window.addEventListener( 'resize', onWindowResize, false );
}
function onWindowResize() {
windowHalfX = window.innerWidth / 2;
windowHalfY = window.innerHeight / 2;
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize( window.innerWidth, window.innerHeight );
}
function onDocumentMouseMove( event ) {
mouseX = ( event.clientX - windowHalfX ) * 10;
mouseY = ( event.clientY - windowHalfY ) * 10;
}
//
function animate() {
requestAnimationFrame( animate );
render();
}
function render() {
let time = Date.now() * 0.001;
let rx = Math.sin( time * 0.7 ) * 0.5,
ry = Math.sin( time * 0.3 ) * 0.5,
rz = Math.sin( time * 0.2 ) * 0.5;
camera.position.x += ( mouseX - camera.position.x ) * 0.05;
camera.position.y += ( - mouseY - camera.position.y ) * 0.05;
camera.lookAt( scene.position );
group.rotation.x = rx;
group.rotation.y = ry;
group.rotation.z = rz;
renderer.render( scene, camera );
}
}
const THREE = require ('three');
const orig = require ('../img/orig.json');
export default canvas =>{
const info = document.getElementById('three_origami');
let camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 ),
scene = new THREE.Scene(), renderer=new THREE.WebGLRenderer( { antialias: true } );
let group=new THREE.MeshNormalMaterial();
let mouseX = 0, mouseY = 0;
let windowHalfX = window.innerWidth / 2;
let windowHalfY = window.innerHeight / 2;
init();
animate();
function init() {
camera = new THREE.PerspectiveCamera( 60, window.innerWidth / window.innerHeight, 1, 10000 );
camera.position.z = 40;
scene = new THREE.Scene();
scene.background = new THREE.Color( 0xffffff );
scene.fog = new THREE.Fog( 0xfffff, 1, 10000 );
group = new THREE.Group();
const objLoader = new THREE.ObjectLoader();
objLoader.parse(orig, (obj) => {
for ( let i = 0; i <= 300; i ++ ) {
let mesh = new THREE.Mesh( obj.geometry, obj.material );
mesh.position.x = Math.random() * 2000 - 1000;
mesh.position.y = Math.random() * 2000 - 1000;
mesh.position.z = Math.random() * 2000 - 1000;
mesh.rotation.x = Math.random() * 2 * Math.PI;
mesh.rotation.y = Math.random() * 2 * Math.PI;
mesh.matrixAutoUpdate = false;
mesh.updateMatrix();
group.add(mesh);
}
});
scene.add( group );
//
renderer.setPixelRatio( window.devicePixelRatio );
renderer.setSize( window.innerWidth, window.innerHeight );
info.appendChild( renderer.domElement );
//
//
document.addEventListener( 'mousemove', onDocumentMouseMove, false );
//
window.addEventListener( 'resize', onWindowResize, false );
}
function onWindowResize() {
windowHalfX = window.innerWidth / 2;
windowHalfY = window.innerHeight / 2;
camera.aspect = window.innerWidth / window.innerHeight;
camera.updateProjectionMatrix();
renderer.setSize( window.innerWidth, window.innerHeight );
}
function onDocumentMouseMove( event ) {
mouseX = ( event.clientX - windowHalfX ) * 10;
mouseY = ( event.clientY - windowHalfY ) * 10;
}
//
function animate() {
requestAnimationFrame( animate );
render();
}
function render() {
let time = Date.now() * 0.001;
let rx = Math.sin( time * 0.7 ) * 0.5,
ry = Math.sin( time * 0.3 ) * 0.5,
rz = Math.sin( time * 0.2 ) * 0.5;
camera.position.x += ( mouseX - camera.position.x ) * 0.05;
camera.position.y += ( - mouseY - camera.position.y ) * 0.05;
camera.lookAt( scene.position );
group.rotation.x = rx;
group.rotation.y = ry;
group.rotation.z = rz;
renderer.render( scene, camera );
}
}
我将其更改objLoader.load('/dist/orig.json')
为objLoader.parse(orig)
并删除了JSON.stringify
.
希望这对你有用。
推荐阅读
- javascript - currentUser 在 firebase 9 中不起作用或不存在
- java - Akka http scala 服务中的锯齿形堆内存模式
- swift - 新的视图控制器在 iPad 上以模态显示而不是全屏显示
- brightway - 自创过程的nan分数
- python - 如何用 Pandas 融化多索引行并维护列中的索引信息?
- wordpress - 访问令牌已过期 PowerBI WordPress
- azure - graphClient.Directory.AdministrativeUnits
- python - 是否有 Pandas 函数来枚举引用另一个数据框的项目?请参阅下面的示例
- sql-server - 我想在 SQL Server 中使用 UNION 和 Group ignore 0 获取结果
- javascript - 如何在 HTML 中的 Select Option 中对齐两个单词