Skip to content

Commit

Permalink
Merge branch 'master' into ib/polyfills
Browse files Browse the repository at this point in the history
  • Loading branch information
ibgreen committed Apr 25, 2019
2 parents c65478b + 55d092b commit 4938057
Show file tree
Hide file tree
Showing 46 changed files with 4,433 additions and 1,581 deletions.
1 change: 1 addition & 0 deletions .eslintignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
**/dist/*
**/wip/*
node_modules/
*.min.js
1 change: 1 addition & 0 deletions .prettierignore
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
modules/core/src/node/text-encoding

**/dist/*
**/wip/*
node_modules/
*.min.js
.cache
Expand Down
12 changes: 12 additions & 0 deletions examples/3d-tiles/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
This is a standalone web app using `@loaders.gl/3d-tiles`.

### Usage

Copy the content of this folder to your project.

```bash
# install dependencies
yarn
# bundle and serve the app with webpack
yarn start-local # or yarn start
```
184 changes: 184 additions & 0 deletions examples/3d-tiles/app.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,184 @@
/* eslint-disable no-unused-vars */
import React, {PureComponent} from 'react';
import {render} from 'react-dom';
import DeckGL, {COORDINATE_SYSTEM, PointCloudLayer, OrbitView, LinearInterpolator} from 'deck.gl';

import {Tile3DLoader} from '@loaders.gl/3d-tiles';
import {load, registerLoaders} from '@loaders.gl/core';

function parseSync(arrayBuffer, options, url, loader) {
const result = Tile3DLoader.parseSync(arrayBuffer, options, url, loader);
return result;
}

export const MeshTile3DLoader = {
name: '3D Tile Pointloud',
extensions: ['pnts'],
parseSync,
binary: true
};

registerLoaders(MeshTile3DLoader);

const PNTS_URL = `./PointCloudNormals/PointCloudNormals.pnts`;

const INITIAL_VIEW_STATE = {
target: [0, 0, 0],
rotationX: 0,
rotationOrbit: 0,
orbitAxis: 'Y',
fov: 50,
minZoom: -10,
maxZoom: 10,
zoom: 1
};

const transitionInterpolator = new LinearInterpolator(['rotationOrbit']);

function getDataRange(data, step = 3) {
const mins = [Number.POSITIVE_INFINITY, Number.POSITIVE_INFINITY, Number.POSITIVE_INFINITY];
const maxs = [Number.NEGATIVE_INFINITY, Number.NEGATIVE_INFINITY, Number.NEGATIVE_INFINITY];
const numOfPoints = data.length / step;
for (let i = 0; i < numOfPoints; i++) {
mins[0] = Math.min(mins[0], data[i * step]);
mins[1] = Math.min(mins[1], data[i * step + 1]);
mins[2] = Math.min(mins[2], data[i * step + 2]);

maxs[0] = Math.max(maxs[0], data[i * step]);
maxs[1] = Math.max(maxs[1], data[i * step + 1]);
maxs[2] = Math.max(maxs[2], data[i * step + 2]);
}

return {mins, maxs};
}

export class App extends PureComponent {
constructor(props) {
super(props);

this.state = {
viewState: INITIAL_VIEW_STATE,
pointsCount: 0,
constantRGBA: null,
colors: null,
positions: null
};

this._onLoad = this._onLoad.bind(this);
this._onViewStateChange = this._onViewStateChange.bind(this);
this._rotateCamera = this._rotateCamera.bind(this);

load(PNTS_URL).then(this._onLoad);
}

_onViewStateChange({viewState}) {
this.setState({viewState});
}

_rotateCamera() {
const {viewState} = this.state;
this.setState({
viewState: {
...viewState,
rotationOrbit: viewState.rotationOrbit + 30,
transitionDuration: 600,
transitionInterpolator,
onTransitionEnd: this._rotateCamera
}
});
}

_onLoad({positions, colors, normals, constantRGBA, featureTableJson}) {
const {mins, maxs} = getDataRange(positions);
let {viewState} = this.state;

if (mins && maxs) {
// File contains bounding box info
viewState = {
...viewState,
target: [(mins[0] + maxs[0]) / 2, (mins[1] + maxs[1]) / 2, (mins[2] + maxs[2]) / 2],
/* global window */
zoom: Math.log2(window.innerWidth / (maxs[0] - mins[0])) - 1
};
}

this.setState(
{
pointsCount: featureTableJson.POINTS_LENGTH,
positions,
colors,
constantRGBA,
normals,
viewState
},
this._rotateCamera
);
}

_renderLayers() {
const {pointsCount, positions, colors, constantRGBA, normals} = this.state;

return (
positions &&
new PointCloudLayer({
data: {
positions: {value: positions, size: 3},
colors: {value: positions, size: 4},
normals: {value: positions, size: 3},
length: positions.length / 3
},
id: '3d-point-cloud-layer',
coordinateSystem: COORDINATE_SYSTEM.IDENTITY,
numInstances: pointsCount,
getPosition: (object, {index, data, target}) => {
target[0] = data.positions.value[index * 3];
target[1] = data.positions.value[index * 3 + 1];
target[2] = data.positions.value[index * 3 + 2];
return target;
},
getColor: colors
? (object, {index, data, target}) => {
target[0] = data.colors.value[index * 3];
target[1] = data.colors.value[index * 3 + 1];
target[2] = data.colors.value[index * 3 + 2];
target[3] = data.colors.size === 4 ? data.colors[index * 3 + 4] : 255;
return target;
}
: constantRGBA
? constantRGBA
: [255, 255, 255],
getNormal: normals
? (object, {index, data, target}) => {
target[0] = data.normals[index * 3];
target[1] = data.normals[index * 3 + 1];
target[2] = data.normals[index * 3 + 2];
return target;
}
: [0, 1, 0],
opacity: 0.5,
pointSize: 1.5
})
);
}

render() {
const {viewState} = this.state;

return (
<DeckGL
views={new OrbitView()}
viewState={viewState}
controller={true}
onViewStateChange={this._onViewStateChange}
layers={this._renderLayers()}
parameters={{
clearColor: [0.07, 0.14, 0.19, 1]
}}
/>
);
}
}

export function renderToDOM(container) {
render(<App />, container);
}
24 changes: 24 additions & 0 deletions examples/3d-tiles/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<!doctype html>
<html>
<head>
<meta charset='UTF-8' />
<title>point-cloud-example</title>
<style>
body {
font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;
font-size: 13px;
-webkit-font-smoothing: antialiased;
margin:0;
padding:0;
overflow:hidden;
}
</style>
</head>
<body/>
<div id="app"></div>
<script src='./app.js'></script>
</body>
<script type="text/javascript">
App.renderToDOM(document.getElementById('app'));
</script>
</html>
24 changes: 24 additions & 0 deletions examples/3d-tiles/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
{
"name": "point-cloud-3d-tiles",
"version": "0.0.0",
"license": "MIT",
"scripts": {
"start": "webpack-dev-server --progress --hot --open",
"start-local": "webpack-dev-server --env.local --progress --hot --open"
},
"dependencies": {
"@loaders.gl/core": "^1.0.1",
"@loaders.gl/3d-tiles": "1.0.1",
"deck.gl": "^7.0.0",
"react": "^16.3.0",
"react-dom": "^16.3.0"
},
"devDependencies": {
"@babel/core": "^7.4.0",
"@babel/preset-react": "^7.0.0",
"babel-loader": "^8.0.5",
"webpack": "^4.20.2",
"webpack-cli": "^3.1.2",
"webpack-dev-server": "^3.1.11"
}
}
35 changes: 35 additions & 0 deletions examples/3d-tiles/webpack.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
const resolve = require('path').resolve;

const CONFIG = {
mode: 'development',

entry: {
app: './app.js'
},

output: {
library: 'App'
},

devServer: {
contentBase: [resolve('.'), resolve('../../modules/3d-tiles/test/data/PointCloud')]
},

module: {
rules: [
{
// Transpile ES6 to ES5 with babel
// Remove if your app does not use JSX or you don't need to support old browsers
test: /\.js$/,
loader: 'babel-loader',
exclude: [/node_modules/],
options: {
presets: ['@babel/preset-react']
}
}
]
}
};

// This line enables bundling against src in this repo rather than installed module
module.exports = env => (env ? require('../webpack.config.local')(CONFIG)(env) : CONFIG);
Loading

0 comments on commit 4938057

Please sign in to comment.