├── .babelrc ├── .gitignore ├── dist ├── app.bundle.js ├── index.html └── space.jpg ├── package-lock.json ├── package.json ├── src ├── Animation.js ├── Loader.js └── index.js └── webpack.config.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": ["@babel/preset-env"], 3 | "plugins": ["@babel/plugin-proposal-class-properties"] 4 | } -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | -------------------------------------------------------------------------------- /dist/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 7 | 8 | Three.js 9 | 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /dist/space.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/helloroman/threejs-2020/d1a035175093ed367e290cac54fbe864c2bbfd45/dist/space.jpg -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "threejs", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "index.js", 6 | "scripts": { 7 | "watch": "webpack --watch", 8 | "server": "webpack-dev-server --open", 9 | "build": "webpack", 10 | "start": "parallelshell 'npm run watch' 'npm run server'" 11 | }, 12 | "keywords": [], 13 | "author": "", 14 | "license": "ISC", 15 | "dependencies": { 16 | "browser-sync": "^2.26.7", 17 | "onchange": "^7.0.2", 18 | "parallelshell": "^3.0.1", 19 | "three": "^0.116.1", 20 | "webpack": "^4.43.0", 21 | "webpack-cli": "^3.3.11", 22 | "webpack-dev-server": "^3.11.0" 23 | }, 24 | "devDependencies": { 25 | "@babel/core": "^7.9.6", 26 | "@babel/plugin-proposal-class-properties": "^7.8.3", 27 | "@babel/preset-env": "^7.9.6", 28 | "babel-loader": "^8.1.0" 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/Animation.js: -------------------------------------------------------------------------------- 1 | import * as THREE from 'three'; 2 | 3 | export class Animation { 4 | constructor(loader) { 5 | this.loader = loader; 6 | this.pointLight = new THREE.PointLight(0xffffff, 1); 7 | this.pointLight2 = new THREE.PointLight(0xffffff, .5); 8 | this.pointLight.position.set(10,10,10); 9 | this.pointLight2.position.set(-30,-10,10); 10 | this.loader.scene.add(this.pointLight, this.pointLight2); 11 | this.createCloud(); 12 | } 13 | 14 | createCloud = () => { 15 | this.cloud = new THREE.Object3D(); 16 | let pos = 0; 17 | for (let i = 0; i <= 100; i++) { 18 | const color = new THREE.Color(`hsl(${150+Math.random()*60}, 100%, 35%)`); 19 | const cubeMaterial = new THREE.MeshLambertMaterial({ color }) 20 | const cubeGeometry = new THREE.BoxGeometry(Math.random() * 50,Math.random() * 2,Math.random() * 10); 21 | const newSphere = new THREE.Mesh(cubeGeometry, cubeMaterial); 22 | newSphere.position.set(pos/3, -50 + pos * 2, 0); 23 | this.cloud.add(newSphere); 24 | pos++; 25 | } 26 | this.loader.scene.add(this.cloud); 27 | } 28 | 29 | update = () => { 30 | } 31 | } -------------------------------------------------------------------------------- /src/Loader.js: -------------------------------------------------------------------------------- 1 | import * as THREE from 'three'; 2 | 3 | export class Loader { 4 | constructor(Animation) { 5 | this.setupScene(); 6 | this.setupCamera(); 7 | this.setupRenderer(); 8 | this.animation = new Animation(this); 9 | this.loop(); 10 | 11 | window.addEventListener('resize', this.handleResize); 12 | } 13 | 14 | setupScene = () => { 15 | this.scene = new THREE.Scene(); 16 | } 17 | 18 | setupCamera = () => { 19 | const aspectRatio = window.innerWidth / window.innerHeight; 20 | this.camera = new THREE.PerspectiveCamera(80, aspectRatio, 0.0001, 10000); 21 | this.camera.position.set(0, 0, 50); 22 | } 23 | 24 | setupRenderer = () => { 25 | this.renderer = new THREE.WebGLRenderer({ antialias: true, alpha: true }); 26 | this.renderer.setSize(window.innerWidth, window.innerHeight); 27 | document.body.appendChild(this.renderer.domElement); 28 | } 29 | 30 | handleResize = () => { 31 | const {innerWidth, innerHeight} = window; 32 | this.renderer.setSize(innerWidth, innerHeight); 33 | this.camera.aspect = innerWidth / innerHeight; 34 | this.camera.updateProjectionMatrix(); 35 | } 36 | 37 | loop = () => { 38 | if (this.animation.update) { 39 | this.animation.update(); 40 | } 41 | this.renderer.render(this.scene, this.camera); 42 | requestAnimationFrame(this.loop); 43 | } 44 | } -------------------------------------------------------------------------------- /src/index.js: -------------------------------------------------------------------------------- 1 | import { Loader } from './Loader'; 2 | import { Animation } from './Animation'; 3 | 4 | new Loader(Animation); -------------------------------------------------------------------------------- /webpack.config.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | 3 | module.exports = { 4 | mode: 'development', 5 | entry: { 6 | app: './src/index.js', 7 | }, 8 | devServer: { 9 | contentBase: './dist', 10 | }, 11 | module: { 12 | rules: [ 13 | { test: /\.js$/, exclude: /node_modules/, loader: "babel-loader" } 14 | ], 15 | }, 16 | output: { 17 | filename: '[name].bundle.js', 18 | path: path.resolve(__dirname, 'dist'), 19 | }, 20 | }; --------------------------------------------------------------------------------