├── .gitignore ├── README.md ├── app_package ├── .gitignore ├── package.json ├── src │ ├── Playground │ │ └── playground.ts │ ├── index.ts │ └── playgroundRunner.ts └── tsconfig.json ├── docs ├── bundle.js └── index.html ├── package.json └── test_package ├── .gitignore ├── package.json ├── src └── index.js ├── webpack.build.config.js └── webpack.dev.config.js /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | package-lock.json 3 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Babylon.js NPM Package Template 2 | 3 | ## Quick Start Guide 4 | 5 | 1. Use GitHub to create `your-new-repo` from this template 6 | 2. In the directory in which you want to develop, clone `your-new-repo` 7 | 3. `cd your-new-repo` 8 | 4. `npm install`: NPM will install required dependencies for all projects 9 | 5. `npm run dev`: NPM will build all projects in watch mode and launch a 10 | test page 11 | 12 | ## About This Repository 13 | 14 | This repository is intended to be a "jumping off point" for moving 15 | ideas from prototyping into active development. The tools supplied and 16 | practices established by this repository are focused on setting up 17 | a simple, versatile, and reliable workflow for creating Babylon.js 18 | experiences which can subsequently be integrated in other projects for 19 | circulation. For more information, check out the 20 | [docs page](https://TODO-make-a-docs-page-for-this). 21 | 22 | ## Repository Structure 23 | 24 | This repository (and any new repository built using it as a template) has 25 | three principle sections: the `app_package`, the `test_package`, and 26 | the `root`. 27 | 28 | ### The `app_package` 29 | 30 | The `app_package`, consisting of the "app_package" directory and everything 31 | in it, is the core of this repository which everything else exists to 32 | support. It is an NPM package which is intended to encapsulate the 33 | Babylon.js experience -- and *only* the Babylon.js experience -- for which 34 | this repository was created. It shouldexpose a minimal outward-facing 35 | contract (i.e., as few public methodsas possible) so that it can be as easy 36 | as possible to add to Web apps, PWAs, and whatever other platforms will be 37 | used to circulate this experience. Of the three sections of this 38 | repository, this is the only one designed to be exported as a separate NPM 39 | package for integration intosubsequent projects. 40 | 41 | ### The `test_package` 42 | 43 | The `test_package`, consisting of the "test_package" directory and 44 | everything in it, exists exclusively as a test harness for the 45 | `app_package`. Essentially `test_package` is a minimalistic standalone Web 46 | app which consumes `app_package` through NPM in the same way a real 47 | shipping experience might. This allows the usage, integration, and 48 | functionality of `app_package` to be tested in isolation, decoupling the 49 | development of the 3D experience itself from the development of the Web app/ 50 | PWA/etc. in which it will eventually be circulated. 51 | 52 | ### The `root` 53 | 54 | The `root`, consisting of the repository's root directory and everything in 55 | it, exists only to provide "glue" and development shortcuts making the 56 | `app_package` and the `test_package` easier to use. 57 | 58 | - **`npm install`**: Running this command in the root directory will 59 | recursively install all NPM dependencies for the root, `app_package`, 60 | and `test_package`. 61 | - **`npm run dev`**: Running this command in the root directory is a 62 | shortcut for running the same command in both `app_package` and 63 | `test_package`. This will cause both packages to be built in watch mode, 64 | launching a browser showing the `test_package` experience which will be 65 | updated and redeployed whenever the files in `app_package` and 66 | `test_package` are changed. 67 | - **`npm run build`**: Running this command in the root directory is a 68 | shortcut for running the same command in `app_package` and `test_package` 69 | sequentially. This will cause both packages to be built and a standalone 70 | single-page Web app to be output in the "docs" directory, which can be 71 | set up to be hosted as a 72 | [GitHub Pages](https://guides.github.com/features/pages/) site. 73 | 74 | ### The Missing Piece: Asset Hosting 75 | 76 | Notably missing from this repository is any provision for hosting 77 | assets -- 3D models, textures, sound files, and so on which are used by 78 | `app_package` as part of the Babylon.js experience. The reason for this 79 | is that asset development for 3D experiences generally follows a very 80 | different workflow from software development, often requiring different 81 | source control, access, licensing, deployment, and many other 82 | considerations. For this reason, we recommend keeping asset 83 | development/hosting and code development/hosting separate, especially 84 | during experience maturation, to allow these dissimiliar tasks to be 85 | addressed independently with task-appropriate solutions. Consequently, 86 | asset hosting is excluded from this repository's intended responsibilities 87 | and is instead left to its sibling repository, the 88 | [asset-host-template](https://github.com/BabylonJS/asset-host-template). 89 | 90 | ## Getting Started 91 | 92 | All steps assume a git- and NPM-enabled command line or terminal. For a 93 | more in-depth tutorial, please consult the [Golden Path tutorial in the 94 | docs](https://TODO-make-a-docs-page-for-this) 95 | 96 | ### Bootstrapping 97 | 98 | 1. Create a new repository using this repo as a template repository. In 99 | the following steps, this new repository will be called `your-new-repo`. 100 | 2. Clone `your-new-repo` locally. 101 | 3. `cd` to the root of your clone. 102 | 4. Run `npm install` to install all the NPM dependencies for 103 | `your-new-repo`. 104 | 5. Run `npm run dev` to run a dev build. After a moment, your default 105 | browser should open to http://localhost:8080, which will display the 106 | `test_package` experience. 107 | 108 | ### Changing the Experience 109 | 110 | 1. In your preferred code editor, open ./app_package/src/Playground/ 111 | playground.ts. This file contains the default experience source code. 112 | 2. In playground.ts, change the line that sets `sphere.position.y = 1` to 113 | set it to `3` instead. 114 | 3. Save your changes. After a moment, the browser page which launched 115 | showing the `test_package` should automatically reload, showing the effect 116 | of your changes. 117 | 4. If you are starting from code you explored in the TypeScript Playground, 118 | you can try copy-pasting your Playground code to replace the `Playground` 119 | class in playground.ts. **NOTE**: Depending on what features your code 120 | uses, this may not work out-of-the-box if the features you're using aren't 121 | imported in playground.ts by default. 122 | 123 | ### Moving Beyond playground.ts 124 | 125 | Playground.ts exists to provide a familiar "landing site" for developers 126 | progressing their Babylon.js ideas from exploration in (for example) 127 | the TypeScript Playground to maturation in the npm-package-template. 128 | However, for these ideas to mature into a clean, robust, and maintainable 129 | codebase, the code should move beyond Playground-specific practices such 130 | as the use of the `BABYLON` namespace and `import "*"`. For this reason, it 131 | is recommended that, soon after repo creation, all functionality should be 132 | moved out of playground.ts into independent files, whereupon Playground.ts 133 | should be deleted. To illustrate this, the following example shows how one 134 | might port over the 135 | [Simple Sinusoid Bouncing Ball](https://playground.babylonjs.com/#8WLKPR) 136 | Playground. 137 | 138 | ```ts 139 | class Playground { 140 | public static CreateScene(engine: BABYLON.Engine, canvas: HTMLCanvasElement): BABYLON.Scene { 141 | const scene = new BABYLON.Scene(engine); 142 | const sphere = BABYLON.Mesh.CreateSphere("sphere", 16, 2, scene); 143 | sphere.position.y = 1; 144 | BABYLON.Mesh.CreateGround("ground1", 6, 6, 2, scene); 145 | scene.createDefaultCameraOrLight(); 146 | 147 | scene.onBeforeRenderObservable.runCoroutineAsync(function* () { 148 | for (let frameCount = 0; true; ++frameCount) { 149 | sphere.position.y = 1 + 2 * Math.abs(Math.sin(frameCount / 16)); 150 | yield; 151 | } 152 | }()); 153 | 154 | return scene; 155 | } 156 | } 157 | ``` 158 | 159 | 1. After finishing step 4 in the prior section, the above Playground code 160 | should have been pasted over the Playground code in playground.ts, leaving 161 | the imports at the top and the export at the bottom of that file intact. 162 | The bouncing ball should already be visible in the `test_package` page. 163 | 2. Rather than create our scene from a static method in an empty class, we 164 | wish to create a scene type to represent this specific scene. To do this, 165 | we create a new file called bouncingBallScene.ts adjacent to 166 | playgroundRunner.ts, filling it with the following contents adapted from 167 | the original Playground code: 168 | ```ts 169 | import { Engine, Mesh, Scene } from "@babylonjs/core"; 170 | 171 | export class BouncingBallScene extends Scene { 172 | constructor (engine: Engine) { 173 | super(engine); 174 | const sphere = Mesh.CreateSphere("sphere", 16, 2, this); 175 | sphere.position.y = 1; 176 | Mesh.CreateGround("ground1", 6, 6, 2, this); 177 | this.createDefaultCameraOrLight(); 178 | 179 | this.onBeforeRenderObservable.runCoroutineAsync(function* () { 180 | for (let frameCount = 0; true; ++frameCount) { 181 | sphere.position.y = 1 + 2 * Math.abs(Math.sin(frameCount / 16)); 182 | yield; 183 | } 184 | }()); 185 | } 186 | } 187 | 188 | ``` 189 | 3. We may also choose to create a bouncingBall.ts file to factor out 190 | functionality further, modifying bouncingBallScene.ts to use it. 191 | ```ts 192 | import { Mesh, Scene, TransformNode } from "@babylonjs/core"; 193 | 194 | export class BouncingBall extends TransformNode { 195 | constructor (scene: Scene) { 196 | super("bouncingBall", scene); 197 | const sphere = Mesh.CreateSphere("sphere", 16, 2, scene); 198 | sphere.setParent(this); 199 | 200 | this.position.y = 1; 201 | 202 | scene.onBeforeRenderObservable.runCoroutineAsync(this._bounceCoroutine()); 203 | } 204 | 205 | private *_bounceCoroutine() { 206 | for (let frameCount = 0; true; ++frameCount) { 207 | sphere.position.y = 1 + 2 * Math.abs(Math.sin(frameCount / 16)); 208 | yield; 209 | } 210 | } 211 | } 212 | ``` 213 | 214 | ```ts 215 | import { Engine, Scene } from "@babylonjs/core"; 216 | import { BouncingBall } from "./bouncingBall"; 217 | 218 | export class BouncingBallScene extends Scene { 219 | constructor (engine: Engine) { 220 | super(engine); 221 | new BouncingBall(this); 222 | Mesh.CreateGround("ground1", 6, 6, 2, this); 223 | this.createDefaultCameraOrLight(); 224 | } 225 | } 226 | 227 | ``` 228 | 4. We can now change playgroundRunner.ts create the `BouncingBallScene` 229 | intead of calling into Playground code. 230 | ```ts 231 | ... 232 | const canvas = options.canvas; 233 | const engine = new Engine(canvas); 234 | let scene = new BouncingBallScene(engine); 235 | ... 236 | ``` 237 | 5. Now that all references to playground.ts are removed, we can rename 238 | playgroundRunner.ts to runtime.ts (or something similar to signify that it 239 | no longer runs Playground code) and delete the Playground folder 240 | altogether. 241 | 6. With these steps done, the code from our Playground-based exploration 242 | has been neatly refactored into multiple clean TypeScript files, ready to 243 | continue maturing into a robust, maintainable, and sustainable codebase. 244 | 245 | ## Licensing 246 | 247 | This template repository is intended to be used as a starting point for 248 | other projects, so its own license is not expected to persist into those 249 | projects. By default, NPM packages automatically adopt the ISC license, 250 | so that default choice is left intact in the three package.json files 251 | present in this template. 252 | -------------------------------------------------------------------------------- /app_package/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | lib/ 3 | package-lock.json 4 | -------------------------------------------------------------------------------- /app_package/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "app_package", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "lib/index.js", 6 | "types": "lib", 7 | "scripts": { 8 | "build": "tsc -p .", 9 | "dev": "tsc --watch -p ." 10 | }, 11 | "keywords": [], 12 | "author": "", 13 | "license": "ISC", 14 | "devDependencies": { 15 | "typescript": "^4.4.3" 16 | }, 17 | "dependencies": { 18 | "@babylonjs/core": "^4.2.0", 19 | "@babylonjs/gui": "^4.2.0", 20 | "@babylonjs/inspector": "^4.2.0", 21 | "@babylonjs/loaders": "^4.2.0", 22 | "@babylonjs/materials": "^4.2.0", 23 | "@babylonjs/post-processes": "^4.2.0", 24 | "@babylonjs/procedural-textures": "^4.2.0", 25 | "@babylonjs/serializers": "^4.2.0", 26 | "ammojs-typed": "^1.0.6", 27 | "cannon-es": "^0.18.0", 28 | "earcut": "^2.2.3" 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /app_package/src/Playground/playground.ts: -------------------------------------------------------------------------------- 1 | import * as BABYLON from "@babylonjs/core"; 2 | import "@babylonjs/loaders"; 3 | 4 | class Playground { 5 | public static CreateScene(engine: BABYLON.Engine, canvas: HTMLCanvasElement): BABYLON.Scene { 6 | // This creates a basic Babylon Scene object (non-mesh) 7 | var scene = new BABYLON.Scene(engine); 8 | 9 | // This creates and positions a free camera (non-mesh) 10 | var camera = new BABYLON.FreeCamera("camera1", new BABYLON.Vector3(0, 5, -10), scene); 11 | 12 | // This targets the camera to scene origin 13 | camera.setTarget(BABYLON.Vector3.Zero()); 14 | 15 | // This attaches the camera to the canvas 16 | camera.attachControl(canvas, true); 17 | 18 | // This creates a light, aiming 0,1,0 - to the sky (non-mesh) 19 | var light = new BABYLON.HemisphericLight("light1", new BABYLON.Vector3(0, 1, 0), scene); 20 | 21 | // Default intensity is 1. Let's dim the light a small amount 22 | light.intensity = 0.7; 23 | 24 | // Our built-in 'sphere' shape. Params: name, subdivs, size, scene 25 | var sphere = BABYLON.Mesh.CreateSphere("sphere1", 16, 2, scene); 26 | 27 | // Move the sphere upward 1/2 its height 28 | sphere.position.y = 1; 29 | 30 | // Our built-in 'ground' shape. Params: name, width, depth, subdivs, scene 31 | var ground = BABYLON.Mesh.CreateGround("ground1", 6, 6, 2, scene); 32 | 33 | return scene; 34 | } 35 | } 36 | 37 | export function CreatePlaygroundScene(engine: BABYLON.Engine, canvas: HTMLCanvasElement): BABYLON.Scene { 38 | return Playground.CreateScene(engine, canvas); 39 | } 40 | -------------------------------------------------------------------------------- /app_package/src/index.ts: -------------------------------------------------------------------------------- 1 | export * from "./playgroundRunner" 2 | -------------------------------------------------------------------------------- /app_package/src/playgroundRunner.ts: -------------------------------------------------------------------------------- 1 | import { Engine } from "@babylonjs/core"; 2 | import { CreatePlaygroundScene } from "./Playground/playground"; 3 | 4 | export interface InitializeBabylonAppOptions { 5 | canvas: HTMLCanvasElement; 6 | assetsHostUrl?: string; 7 | } 8 | 9 | export function initializeBabylonApp(options: InitializeBabylonAppOptions) { 10 | if (options.assetsHostUrl) { 11 | console.log("Assets host URL: " + options.assetsHostUrl!); 12 | } else { 13 | console.log("No assets host URL provided"); 14 | } 15 | 16 | const canvas = options.canvas; 17 | const engine = new Engine(canvas); 18 | const scene = CreatePlaygroundScene(engine, canvas); 19 | engine.runRenderLoop(() => { 20 | scene.render(); 21 | }); 22 | window.addEventListener("resize", () => { 23 | engine.resize(); 24 | }); 25 | } 26 | 27 | -------------------------------------------------------------------------------- /app_package/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | /* Visit https://aka.ms/tsconfig.json to read more about this file */ 4 | 5 | /* Projects */ 6 | // "incremental": true, /* Enable incremental compilation */ 7 | // "composite": true, /* Enable constraints that allow a TypeScript project to be used with project references. */ 8 | // "tsBuildInfoFile": "./", /* Specify the folder for .tsbuildinfo incremental compilation files. */ 9 | // "disableSourceOfProjectReferenceRedirect": true, /* Disable preferring source files instead of declaration files when referencing composite projects */ 10 | // "disableSolutionSearching": true, /* Opt a project out of multi-project reference checking when editing. */ 11 | // "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */ 12 | 13 | /* Language and Environment */ 14 | "target": "es6", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */ 15 | "lib": ["es6", "dom"], /* Specify a set of bundled library declaration files that describe the target runtime environment. */ 16 | // "jsx": "preserve", /* Specify what JSX code is generated. */ 17 | // "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */ 18 | // "emitDecoratorMetadata": true, /* Emit design-type metadata for decorated declarations in source files. */ 19 | // "jsxFactory": "", /* Specify the JSX factory function used when targeting React JSX emit, e.g. 'React.createElement' or 'h' */ 20 | // "jsxFragmentFactory": "", /* Specify the JSX Fragment reference used for fragments when targeting React JSX emit e.g. 'React.Fragment' or 'Fragment'. */ 21 | // "jsxImportSource": "", /* Specify module specifier used to import the JSX factory functions when using `jsx: react-jsx*`.` */ 22 | // "reactNamespace": "", /* Specify the object invoked for `createElement`. This only applies when targeting `react` JSX emit. */ 23 | // "noLib": true, /* Disable including any library files, including the default lib.d.ts. */ 24 | // "useDefineForClassFields": true, /* Emit ECMAScript-standard-compliant class fields. */ 25 | 26 | /* Modules */ 27 | "module": "commonjs", /* Specify what module code is generated. */ 28 | "rootDir": "./src", /* Specify the root folder within your source files. */ 29 | // "moduleResolution": "node", /* Specify how TypeScript looks up a file from a given module specifier. */ 30 | // "baseUrl": "./", /* Specify the base directory to resolve non-relative module names. */ 31 | // "paths": {}, /* Specify a set of entries that re-map imports to additional lookup locations. */ 32 | // "rootDirs": [], /* Allow multiple folders to be treated as one when resolving modules. */ 33 | // "typeRoots": [], /* Specify multiple folders that act like `./node_modules/@types`. */ 34 | // "types": [], /* Specify type package names to be included without being referenced in a source file. */ 35 | // "allowUmdGlobalAccess": true, /* Allow accessing UMD globals from modules. */ 36 | // "resolveJsonModule": true, /* Enable importing .json files */ 37 | // "noResolve": true, /* Disallow `import`s, `require`s or ``s from expanding the number of files TypeScript should add to a project. */ 38 | 39 | /* JavaScript Support */ 40 | // "allowJs": true, /* Allow JavaScript files to be a part of your program. Use the `checkJS` option to get errors from these files. */ 41 | // "checkJs": true, /* Enable error reporting in type-checked JavaScript files. */ 42 | // "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from `node_modules`. Only applicable with `allowJs`. */ 43 | 44 | /* Emit */ 45 | "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */ 46 | "declarationMap": true, /* Create sourcemaps for d.ts files. */ 47 | // "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */ 48 | "sourceMap": true, /* Create source map files for emitted JavaScript files. */ 49 | // "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If `declaration` is true, also designates a file that bundles all .d.ts output. */ 50 | "outDir": "./lib", /* Specify an output folder for all emitted files. */ 51 | // "removeComments": true, /* Disable emitting comments. */ 52 | // "noEmit": true, /* Disable emitting files from a compilation. */ 53 | // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ 54 | // "importsNotUsedAsValues": "remove", /* Specify emit/checking behavior for imports that are only used for types */ 55 | // "downlevelIteration": true, /* Emit more compliant, but verbose and less performant JavaScript for iteration. */ 56 | // "sourceRoot": "", /* Specify the root path for debuggers to find the reference source code. */ 57 | // "mapRoot": "", /* Specify the location where debugger should locate map files instead of generated locations. */ 58 | // "inlineSourceMap": true, /* Include sourcemap files inside the emitted JavaScript. */ 59 | // "inlineSources": true, /* Include source code in the sourcemaps inside the emitted JavaScript. */ 60 | // "emitBOM": true, /* Emit a UTF-8 Byte Order Mark (BOM) in the beginning of output files. */ 61 | // "newLine": "crlf", /* Set the newline character for emitting files. */ 62 | // "stripInternal": true, /* Disable emitting declarations that have `@internal` in their JSDoc comments. */ 63 | // "noEmitHelpers": true, /* Disable generating custom helper functions like `__extends` in compiled output. */ 64 | // "noEmitOnError": true, /* Disable emitting files if any type checking errors are reported. */ 65 | // "preserveConstEnums": true, /* Disable erasing `const enum` declarations in generated code. */ 66 | // "declarationDir": "./", /* Specify the output directory for generated declaration files. */ 67 | 68 | /* Interop Constraints */ 69 | // "isolatedModules": true, /* Ensure that each file can be safely transpiled without relying on other imports. */ 70 | // "allowSyntheticDefaultImports": true, /* Allow 'import x from y' when a module doesn't have a default export. */ 71 | "esModuleInterop": true, /* Emit additional JavaScript to ease support for importing CommonJS modules. This enables `allowSyntheticDefaultImports` for type compatibility. */ 72 | // "preserveSymlinks": true, /* Disable resolving symlinks to their realpath. This correlates to the same flag in node. */ 73 | "forceConsistentCasingInFileNames": true, /* Ensure that casing is correct in imports. */ 74 | 75 | /* Type Checking */ 76 | "strict": true, /* Enable all strict type-checking options. */ 77 | // "noImplicitAny": true, /* Enable error reporting for expressions and declarations with an implied `any` type.. */ 78 | // "strictNullChecks": true, /* When type checking, take into account `null` and `undefined`. */ 79 | // "strictFunctionTypes": true, /* When assigning functions, check to ensure parameters and the return values are subtype-compatible. */ 80 | // "strictBindCallApply": true, /* Check that the arguments for `bind`, `call`, and `apply` methods match the original function. */ 81 | // "strictPropertyInitialization": true, /* Check for class properties that are declared but not set in the constructor. */ 82 | // "noImplicitThis": true, /* Enable error reporting when `this` is given the type `any`. */ 83 | // "useUnknownInCatchVariables": true, /* Type catch clause variables as 'unknown' instead of 'any'. */ 84 | // "alwaysStrict": true, /* Ensure 'use strict' is always emitted. */ 85 | // "noUnusedLocals": true, /* Enable error reporting when a local variables aren't read. */ 86 | // "noUnusedParameters": true, /* Raise an error when a function parameter isn't read */ 87 | // "exactOptionalPropertyTypes": true, /* Interpret optional property types as written, rather than adding 'undefined'. */ 88 | // "noImplicitReturns": true, /* Enable error reporting for codepaths that do not explicitly return in a function. */ 89 | // "noFallthroughCasesInSwitch": true, /* Enable error reporting for fallthrough cases in switch statements. */ 90 | // "noUncheckedIndexedAccess": true, /* Include 'undefined' in index signature results */ 91 | // "noImplicitOverride": true, /* Ensure overriding members in derived classes are marked with an override modifier. */ 92 | // "noPropertyAccessFromIndexSignature": true, /* Enforces using indexed accessors for keys declared using an indexed type */ 93 | // "allowUnusedLabels": true, /* Disable error reporting for unused labels. */ 94 | // "allowUnreachableCode": true, /* Disable error reporting for unreachable code. */ 95 | 96 | /* Completeness */ 97 | // "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */ 98 | "skipLibCheck": true /* Skip type checking all .d.ts files. */ 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /docs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Babylon.js NPM Package Template 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "npm-package-template", 3 | "version": "1.0.0", 4 | "description": "", 5 | "private": "true", 6 | "scripts": { 7 | "install": "npm-recursive-install --skip-root", 8 | "dev": "concurrently \"npm --prefix ./app_package run dev\" \"npm --prefix ./test_package run dev\"", 9 | "build": "npm --prefix ./app_package run build && npm --prefix ./test_package run build" 10 | }, 11 | "keywords": [], 12 | "author": "", 13 | "license": "ISC", 14 | "devDependencies": { 15 | "concurrently": "^6.2.1", 16 | "recursive-install": "^1.4.0" 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /test_package/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/ 2 | package-lock.json 3 | -------------------------------------------------------------------------------- /test_package/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "test_package", 3 | "version": "1.0.0", 4 | "description": "", 5 | "private": true, 6 | "scripts": { 7 | "build": "webpack --config webpack.build.config.js", 8 | "dev": "webpack-dev-server --config webpack.dev.config.js" 9 | }, 10 | "keywords": [], 11 | "author": "", 12 | "license": "ISC", 13 | "devDependencies": { 14 | "html-webpack-plugin": "^5.3.2", 15 | "webpack": "^5.52.1", 16 | "webpack-cli": "^4.8.0", 17 | "webpack-dev-server": "^4.2.1" 18 | }, 19 | "dependencies": { 20 | "app_package": "file:../app_package" 21 | } 22 | } 23 | -------------------------------------------------------------------------------- /test_package/src/index.js: -------------------------------------------------------------------------------- 1 | import { initializeBabylonApp } from "app_package"; 2 | 3 | document.body.style.width = "100%"; 4 | document.body.style.height = "100%"; 5 | document.body.style.margin = "0"; 6 | document.body.style.padding = "0"; 7 | 8 | const title = document.createElement("p"); 9 | title.innerText = "Babylon.js NPM Package Template"; 10 | title.style.fontSize = "32pt"; 11 | title.style.textAlign = "center"; 12 | document.body.appendChild(title); 13 | 14 | const div = document.createElement("div"); 15 | div.style.width = "60%"; 16 | div.style.margin = "0 auto"; 17 | div.style.aspectRatio = "16 / 9"; 18 | document.body.appendChild(div); 19 | 20 | const canvas = document.createElement("canvas"); 21 | canvas.id = "renderCanvas"; 22 | canvas.style.width = "100%"; 23 | canvas.style.height = "100%"; 24 | canvas.style.display = "block"; 25 | div.appendChild(canvas); 26 | 27 | let assetsHostUrl; 28 | if (DEV_BUILD) { 29 | assetsHostUrl = "http://127.0.0.1:8181/"; 30 | } else { 31 | assetsHostUrl = "https://nonlocal-assets-host-url/"; 32 | } 33 | initializeBabylonApp({ canvas: canvas, assetsHostUrl: assetsHostUrl }); 34 | -------------------------------------------------------------------------------- /test_package/webpack.build.config.js: -------------------------------------------------------------------------------- 1 | const path = require("path"); 2 | const HtmlWebpackPlugin = require("html-webpack-plugin"); 3 | const { DefinePlugin } = require("webpack"); 4 | 5 | module.exports = { 6 | entry: "./src/index.js", 7 | mode: "development", 8 | devServer: { 9 | open: true, 10 | watchFiles: ["./src/**/*", "../app_package/lib/**/*"] 11 | }, 12 | output: { 13 | path: path.resolve(__dirname, "../docs"), 14 | filename: "bundle.js" 15 | }, 16 | plugins: [ 17 | new DefinePlugin({ 18 | DEV_BUILD: JSON.stringify(false) 19 | }), 20 | new HtmlWebpackPlugin({ title: "Babylon.js NPM Package Template" }) 21 | ], 22 | module: { 23 | rules: [ 24 | { 25 | test: /\.m?js/, 26 | resolve: { 27 | fullySpecified: false 28 | } 29 | } 30 | ], 31 | } 32 | }; 33 | -------------------------------------------------------------------------------- /test_package/webpack.dev.config.js: -------------------------------------------------------------------------------- 1 | const path = require("path"); 2 | const HtmlWebpackPlugin = require("html-webpack-plugin"); 3 | const { DefinePlugin } = require("webpack"); 4 | 5 | module.exports = { 6 | entry: "./src/index.js", 7 | mode: "development", 8 | devServer: { 9 | open: true, 10 | watchFiles: ["./src/**/*", "../app_package/lib/**/*"] 11 | }, 12 | output: { 13 | path: path.resolve(__dirname, "../docs"), 14 | filename: "bundle.js" 15 | }, 16 | plugins: [ 17 | new DefinePlugin({ 18 | DEV_BUILD: JSON.stringify(true) 19 | }), 20 | new HtmlWebpackPlugin({ title: "Babylon.js NPM Package Template" }) 21 | ], 22 | module: { 23 | rules: [ 24 | { 25 | test: /\.m?js/, 26 | resolve: { 27 | fullySpecified: false 28 | } 29 | } 30 | ], 31 | } 32 | }; 33 | --------------------------------------------------------------------------------