├── .babelrc ├── .gitignore ├── LICENSE ├── README.md ├── package-lock.json ├── package.json ├── src ├── app │ └── application.ts ├── assets │ ├── box.jpg │ └── skybox │ │ ├── bk.png │ │ ├── dn.png │ │ ├── ft.png │ │ ├── lf.png │ │ ├── rt.png │ │ └── up.png ├── favicon.png ├── index.html ├── main.ts ├── polyfills.ts └── style.scss ├── tsconfig.json ├── webpack.common.js ├── webpack.dev.js └── webpack.prod.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | [ 4 | "env", 5 | { 6 | "targets": { 7 | "browsers": [ 8 | "last 2 versions", 9 | "safari >= 7", 10 | "ie >= 10" 11 | ] 12 | } 13 | } 14 | ] 15 | ] 16 | } 17 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | 8 | # Runtime data 9 | pids 10 | *.pid 11 | *.seed 12 | *.pid.lock 13 | 14 | # Directory for instrumented libs generated by jscoverage/JSCover 15 | lib-cov 16 | 17 | # Coverage directory used by tools like istanbul 18 | coverage 19 | 20 | # nyc test coverage 21 | .nyc_output 22 | 23 | # Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files) 24 | .grunt 25 | 26 | # Bower dependency directory (https://bower.io/) 27 | bower_components 28 | 29 | # node-waf configuration 30 | .lock-wscript 31 | 32 | # Compiled binary addons (https://nodejs.org/api/addons.html) 33 | build/Release 34 | 35 | # Dependency directories 36 | node_modules/ 37 | jspm_packages/ 38 | dist/ 39 | 40 | # TypeScript v1 declaration files 41 | typings/ 42 | 43 | # Optional npm cache directory 44 | .npm 45 | 46 | # Optional eslint cache 47 | .eslintcache 48 | 49 | # Optional REPL history 50 | .node_repl_history 51 | 52 | # Output of 'npm pack' 53 | *.tgz 54 | 55 | # Yarn Integrity file 56 | .yarn-integrity 57 | 58 | # dotenv environment variables file 59 | .env 60 | 61 | # next.js build output 62 | .next 63 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019 鸿则 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Webpack Typescript Starter 2 | ==== 3 | 4 | webpack starter for typescript 5 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "webpack-typescript-starter", 3 | "version": "0.0.1", 4 | "license": "MIT", 5 | "scripts": { 6 | "start": "webpack-dev-server --config webpack.dev.js --port=3100", 7 | "build": "webpack --config webpack.dev.js", 8 | "build:prod": "webpack --config webpack.prod.js" 9 | }, 10 | "devDependencies": { 11 | "@babel/core": "^7.6.4", 12 | "@babel/preset-env": "^7.6.3", 13 | "@types/stats.js": "^0.17.0", 14 | "babel-loader": "^8.0.6", 15 | "babel-preset-env": "^1.7.0", 16 | "clean-webpack-plugin": "^3.0.0", 17 | "copy-webpack-plugin": "^5.0.4", 18 | "css-loader": "^3.2.0", 19 | "html-webpack-plugin": "^3.2.0", 20 | "mini-css-extract-plugin": "^0.8.0", 21 | "node-sass": "^4.13.0", 22 | "sass-loader": "^8.0.0", 23 | "style-loader": "^1.0.0", 24 | "ts-loader": "^6.2.1", 25 | "typescript": "^3.6.4", 26 | "webpack": "^4.41.2", 27 | "webpack-cli": "^3.3.9", 28 | "webpack-merge": "^4.2.2" 29 | }, 30 | "dependencies": { 31 | "stats.js": "^0.17.0", 32 | "three": "^0.111.0" 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/app/application.ts: -------------------------------------------------------------------------------- 1 | import Stats from 'stats.js'; 2 | import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'; 3 | import { Scene, PerspectiveCamera, WebGLRenderer, BoxGeometry, MeshBasicMaterial, Mesh, TextureLoader, DoubleSide } from 'three'; 4 | 5 | export class Application { 6 | private scene: Scene; 7 | private camera: PerspectiveCamera; 8 | private renderer: WebGLRenderer; 9 | private stats: Stats; 10 | 11 | constructor() { 12 | this.scene = new Scene(); 13 | this.camera = new PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000); 14 | this.renderer = new WebGLRenderer({ antialias: true }); 15 | this.renderer.setSize(window.innerWidth, window.innerHeight); 16 | document.body.appendChild(this.renderer.domElement); 17 | window.addEventListener('resize', () => this.onWindowResize()); 18 | 19 | const textureLoader = new TextureLoader(); 20 | 21 | const boxTexture = textureLoader.load('./assets/box.jpg'); 22 | 23 | const boxGeometry = new BoxGeometry(1, 1, 1); 24 | const meshBasicMaterial = new MeshBasicMaterial({ map: boxTexture, side: DoubleSide }); 25 | const mesh = new Mesh(boxGeometry, meshBasicMaterial); 26 | mesh.name = 'box'; 27 | 28 | const skyboxGeometry = new BoxGeometry(200, 200, 200); 29 | const skyboxMaterials = [ 30 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/rt.png'), side: DoubleSide }), 31 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/lf.png'), side: DoubleSide }), 32 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/up.png'), side: DoubleSide }), 33 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/dn.png'), side: DoubleSide }), 34 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/bk.png'), side: DoubleSide }), 35 | new MeshBasicMaterial({ map: textureLoader.load('./assets/skybox/ft.png'), side: DoubleSide }), 36 | ]; 37 | const skyboxMesh = new Mesh(skyboxGeometry, skyboxMaterials); 38 | skyboxMesh.name = 'skyboxMesh'; 39 | 40 | this.camera.position.set(0, 0, 5); 41 | 42 | this.scene.add(mesh); 43 | this.scene.add(skyboxMesh); 44 | 45 | this.stats = new Stats(); 46 | this.stats.showPanel(0); 47 | window.document.body.appendChild(this.stats.dom); 48 | 49 | new OrbitControls(this.camera, this.renderer.domElement); 50 | 51 | this.render(); 52 | } 53 | 54 | private render() { 55 | this.stats.begin(); 56 | window.requestAnimationFrame(() => this.render()); 57 | const skyboxMesh = this.scene.getObjectByName('skyboxMesh'); 58 | 59 | skyboxMesh.rotation.y += 0.001; 60 | 61 | this.renderer.render(this.scene, this.camera); 62 | this.stats.end(); 63 | } 64 | 65 | private onWindowResize() { 66 | this.renderer.setSize(window.innerWidth, window.innerHeight); 67 | this.camera.aspect = window.innerWidth / window.innerHeight; 68 | this.camera.updateProjectionMatrix(); 69 | } 70 | 71 | } 72 | -------------------------------------------------------------------------------- /src/assets/box.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/box.jpg -------------------------------------------------------------------------------- /src/assets/skybox/bk.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/bk.png -------------------------------------------------------------------------------- /src/assets/skybox/dn.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/dn.png -------------------------------------------------------------------------------- /src/assets/skybox/ft.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/ft.png -------------------------------------------------------------------------------- /src/assets/skybox/lf.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/lf.png -------------------------------------------------------------------------------- /src/assets/skybox/rt.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/rt.png -------------------------------------------------------------------------------- /src/assets/skybox/up.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/assets/skybox/up.png -------------------------------------------------------------------------------- /src/favicon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/favicon.png -------------------------------------------------------------------------------- /src/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Webpack Typescript Starter 9 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /src/main.ts: -------------------------------------------------------------------------------- 1 | import { Application } from './app/application'; 2 | 3 | if(process.env.NODE_ENV !== 'production') { 4 | console.warn('Webpack is running in development mode!'); 5 | } 6 | 7 | new Application(); 8 | -------------------------------------------------------------------------------- /src/polyfills.ts: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hungtcs-lab/three-js-demo/d31708d4a5bc13348c6b3f36f368030560c37692/src/polyfills.ts -------------------------------------------------------------------------------- /src/style.scss: -------------------------------------------------------------------------------- 1 | 2 | html, body { 3 | width: 100vw; 4 | margin: 0; 5 | height: 100vh; 6 | padding: 0; 7 | overflow: hidden; 8 | } 9 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es5", 4 | "module": "commonjs", 5 | "sourceMap": true, 6 | "esModuleInterop": true 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /webpack.common.js: -------------------------------------------------------------------------------- 1 | const HtmlWebpackPlugin = require('html-webpack-plugin'); 2 | const CopyWebpackPlugin = require('copy-webpack-plugin'); 3 | const { CleanWebpackPlugin } = require('clean-webpack-plugin'); 4 | 5 | module.exports = { 6 | entry: { 7 | main: './src/main.ts', 8 | style: './src/style.scss', 9 | polyfills: './src/polyfills.ts', 10 | }, 11 | module: { 12 | rules: [ 13 | { 14 | test: /\.ts$/, 15 | use: [ 16 | { 17 | loader: 'babel-loader', 18 | options: { 19 | presets: ['@babel/preset-env'] 20 | }, 21 | }, 22 | { 23 | loader: 'ts-loader', 24 | }, 25 | ], 26 | exclude: /node_modules/, 27 | }, 28 | { 29 | test: /\.s[ac]ss$/i, 30 | use: [ 31 | 'style-loader', 32 | 'css-loader', 33 | 'sass-loader', 34 | ], 35 | }, 36 | ], 37 | }, 38 | plugins: [ 39 | new CleanWebpackPlugin(), 40 | new HtmlWebpackPlugin({ 41 | template: './src/index.html', 42 | }), 43 | new CopyWebpackPlugin([ 44 | { from: './src/assets', to: 'assets' }, 45 | { from: './src/favicon.png', to: 'favicon.png' }, 46 | ]), 47 | ], 48 | resolve: { 49 | extensions: [ '.tsx', '.ts', '.js' ], 50 | }, 51 | }; 52 | -------------------------------------------------------------------------------- /webpack.dev.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | const merge = require('webpack-merge'); 3 | const common = require('./webpack.common'); 4 | 5 | module.exports = merge(common, { 6 | mode: 'development', 7 | output: { 8 | path: path.resolve(__dirname, 'dist'), 9 | filename: '[name].js', 10 | }, 11 | devtool: 'eval-source-map' 12 | }); 13 | -------------------------------------------------------------------------------- /webpack.prod.js: -------------------------------------------------------------------------------- 1 | const path = require('path'); 2 | const merge = require('webpack-merge'); 3 | const common = require('./webpack.common'); 4 | const MiniCssExtractPlugin = require('mini-css-extract-plugin'); 5 | 6 | module.exports = merge(common, { 7 | mode: 'production', 8 | output: { 9 | path: path.resolve(__dirname, 'dist'), 10 | filename: '[name].[hash].js', 11 | }, 12 | module: { 13 | rules: [ 14 | { 15 | test: /\.s[ac]ss$/i, 16 | use: [ 17 | { 18 | loader: MiniCssExtractPlugin.loader, 19 | }, 20 | { 21 | loader: 'css-loader', 22 | }, 23 | { 24 | loader: 'sass-loader', 25 | }, 26 | ], 27 | }, 28 | ], 29 | }, 30 | plugins: [ 31 | new MiniCssExtractPlugin({ 32 | filename: '[name].[hash].css', 33 | chunkFilename: '[id].[hash].css', 34 | }), 35 | ], 36 | optimization: { 37 | splitChunks: { 38 | cacheGroups: { 39 | commons: { 40 | test: /[\\/]node_modules[\\/]/, 41 | name: (module, chunks, cacheGroupKey) => { 42 | const moduleFileName = module.identifier().split('/').reduceRight(item => item); 43 | // const allChunksNames = chunks.map((item) => item.name).join('~'); 44 | return `${cacheGroupKey}-${moduleFileName}`; 45 | }, 46 | chunks: 'all' 47 | }, 48 | }, 49 | }, 50 | }, 51 | performance: { 52 | hints: false, 53 | }, 54 | }); 55 | --------------------------------------------------------------------------------