Why my import * as THREE from *three* didn't work?

I need to use three.js to do my school work and when I try run the code, appear nothing.
I already did
npm install --global webpack
npm install --global webpack-cli
and put my server to run

this is my code:

<head>

    <title>My first three.js app</title>

    <style>

        body { margin: 0; }

        canvas { display: block; }

    </style>

</head>

<body>

    <script>

        import * as THREE from 'three'; <!-- this didnt work -->

        var scene = new THREE.Scene();

        var camera = new THREE.PerspectiveCamera( 75, window.innerWidth / window.innerHeight, 0.1, 1000 );

        var renderer = new THREE.WebGLRenderer();

        renderer.setSize( window.innerWidth, window.innerHeight );

        document.body.appendChild( renderer.domElement );

        var geometry = new THREE.BoxGeometry();

        var material = new THREE.MeshBasicMaterial( { color: 0x00ff00 } );

        var cube = new THREE.Mesh( geometry, material );

        scene.add( cube );

        camera.position.z = 5;

        var animate = function () {

            requestAnimationFrame( animate );

            cube.rotation.x += 0.01;

            cube.rotation.y += 0.01;

            renderer.render( scene, camera );

        };

        animate();

    </script>

</body>

Did you install three as well (npm install three)? Is there any error in the browser console?

1 Like

I don’t know about webpack . But you can still use

<script src="https://threejs.org/build/three.js"></script> 

on your head tag and this will link to three.js and everything should work fine…

yes, when I used

it worked, but when I change to import * as THREE from ‘three’; all I see is a white screen

script src=“node_modules\three\build\three.min.js”

Depending on your server / local setup you probably cannot import this way from node_modules. It also wouldn’t work when you try to release the app later.

It won’t be possible to help unless we’d see your webpack.config, package.json, or browser console error.

In browsers you can’t use so called “bare imports”. There are two recommended workflows.

You can then write the import like so:

import * as THREE from 'https://cdn.jsdelivr.net/npm/three@0.117.1/build/three.module.js';

Besides, you can only use ES6 import syntax when you enhance the script tag like so:

<script type="module">

I already did
npm install --global webpack
npm install --global webpack-cli

im not sure im reading this right, but in modern environments (webpack et al) you don’t mess with script tags, and usually you don’t touch html files. index.html is an entry point, mostly auto-generated.

your code lives in index.js, you can import from three from there (if you have npm installed it).

i would suggest you start with codesandbox: https://codesandbox.io/s/vanilla
it gives you a proper dev env, you can run code right there, no installation, and if you’re happy just click on download and it zips up a ready-made dev environment (using parcel, which is similar to webpack).

I would like to add, that you can use imports without webpack, by providing a literal path from your script (or .html in your case). For example if you have node_modules and index.html in the same directory, then you could add a script like:

<script type="module">

        import * as THREE from './node_modules/three/build/three.module.js';

        // rest of your app
</script>

You should report this to your teacher / mentor. If you are learning three.js this is not exactly three.js related and may be complicated on their own. Someone should ensure that all students get the same code and that it can run for everyone.

I have a good idea of why you could be having this problem. You are using node right? what server are you using to serve it? Express? my guess is that youre not serving node_modules in you public_dirrname.

Problems with ES6 Imports in threejs using node 14? (No Webpack or Babel) if so, take a look at this page.

If you want to use es6 modules, and are using nodejs, and express, you don’t need to serve the whole node_modules folder with all it’s subfolders just to get three.js.

One option you have,
Is, you can add a static path to your server code for the specific file or folder you want to serve.
eg,

app.use('/build/three.module.js', express.static(path.join(__dirname, '../../node_modules/three/build/three.module.js')));

Then in your JavaScript,

import * as THREE from '/build/three.module.js';

Now when your browser asks for /build/three.module.js , the server will know what to give it back.

if you write
import * as THREE from 'three';

Your html client doesn’t know what three is, unless you do all kinds of things before hand, for example, try webpack, or many other bundlers. You will need to tell webpack what three is, so that it can present it in some way that the browser will then understand what three is.

See my boilerplate for an example, where I create static routes to specific library files and/or folders, rather than use bundlers. (but only if you are interested in using typescript)

git clone https://github.com/Sean-Bradley/Three.js-TypeScript-Boilerplate.git
cd Three.js-TypeScript-Boilerplate
npm install -g typescript
npm install
npm run dev

Open in visual studio code and/or visit http://127.0.0.1:3000/

use

git checkout statsgui

If you want to see a version of the boilerplate also linking stats.js and dat.gui panels. And see how I explicitly reference these in the server code without needing to serve the whole node_modules folder, or copy any of the threejs files to somewhere in the static root folder served by nodejs, or use webpack, rollup, et al.

The bottom line, is that your browser doesn’t know what three is unless you tell it.