From 084824490eb4ad7983c8d9872966470e6cf7a72c Mon Sep 17 00:00:00 2001 From: Niekes Date: Mon, 15 Jan 2024 15:29:26 +0000 Subject: [PATCH] Change the API in favor of v1.0.0 --- README.md | 126 +++++++++--------- index.js | 19 +-- src/3d.js | 18 +-- src/generator.js | 4 +- src/point.js | 12 +- src/projection-orthographic.js | 4 +- src/rotation.js | 12 +- src/{primitiveShapes => shapes}/cubes.js | 1 + src/{primitiveShapes => shapes}/gridPlanes.js | 0 src/{primitiveShapes => shapes}/lineStrips.js | 0 src/{primitiveShapes => shapes}/lines.js | 0 src/{primitiveShapes => shapes}/planes.js | 0 src/{primitiveShapes => shapes}/points.js | 0 src/{primitiveShapes => shapes}/polygons.js | 0 src/{primitiveShapes => shapes}/triangles.js | 0 tests/3d-test.js | 12 +- tests/linestrips-test.js | 98 +++++++------- tests/planes-test.js | 17 +-- tests/points-test.js | 33 ++--- tests/polygons-test.js | 34 +++-- tests/triangles-test.js | 48 ++----- 21 files changed, 209 insertions(+), 229 deletions(-) rename src/{primitiveShapes => shapes}/cubes.js (99%) rename src/{primitiveShapes => shapes}/gridPlanes.js (100%) rename src/{primitiveShapes => shapes}/lineStrips.js (100%) rename src/{primitiveShapes => shapes}/lines.js (100%) rename src/{primitiveShapes => shapes}/planes.js (100%) rename src/{primitiveShapes => shapes}/points.js (100%) rename src/{primitiveShapes => shapes}/polygons.js (100%) rename src/{primitiveShapes => shapes}/triangles.js (100%) diff --git a/README.md b/README.md index ede6f10..3f1b82c 100644 --- a/README.md +++ b/README.md @@ -43,23 +43,22 @@ For a specific version: ES6: ```js -import { _3d } from 'd3-3d'; +import { triangles3D, cubes3D, gridPlanes3D, points3D, lineStrips3D } from 'd3-3d'; ``` ## API Reference -- [d3.\_3d](#_3d) - create a new 3d function object. -- [_\_3d_.shape](#shape) - set the shape. -- [_\_3d_.x](#x) - set the x accessor. -- [_\_3d_.y](#y) - set the y accessor. -- [_\_3d_.z](#z) - set the z accessor. -- [_\_3d_.scale](#scale) - sets the scale for the projected points. -- [_\_3d_.rotateX](#rotateX) - set the angle for the x rotation. -- [_\_3d_.rotateY](#rotateY) - set the angle for the y rotation. -- [_\_3d_.rotateZ](#rotateZ) - set the angle for the z rotation. -- [_\_3d_.rotateCenter](#rotateCenter) - set the the rotation center. -- [_\_3d_.sort](#sort) - sort the 3d elements by the centroid. -- [_\_3d_.draw](#draw) - draw the 3d elements. +- [triangles3D().x](#x) - set the x accessor. +- [triangles3D().y](#y) - set the y accessor. +- [triangles3D().z](#z) - set the z accessor. +- [triangles3D().scale](#scale) - sets the scale for the projected points. +- [triangles3D().rotateX](#rotateX) - set the angle for the x rotation. +- [triangles3D().rotateY](#rotateY) - set the angle for the y rotation. +- [triangles3D().rotateZ](#rotateZ) - set the angle for the z rotation. +- [triangles3D().rotateCenter](#rotateCenter) - set the the rotation center. +- [triangles3D().origin](#origin) - set the the origin. +- [triangles3D().sort](#sort) - sort the 3d elements by the centroid. +- [triangles3D().draw](#draw) - draw the 3d elements. ### Overview @@ -70,15 +69,15 @@ With **d3-3d** you can easily visualize your 3d data. ```js const data3D = [ [ - [0, -1, 0], - [-1, 1, 0], - [1, 1, 0] + { x: 0, y: -1, z: 0 }, + { x: -1, y: 1, z: 0 }, + { x: 1, y: 1, z: 0 } ] ]; -const triangles3D = d3._3d().scale(100).origin([480, 250]).shape('TRIANGLE'); +const triangles3d = triangles3D().scale(100).origin({ 480, 250 }); -const projectedData = triangles3D(data3D); +const projectedData = triangles3d(data3D); init(projectedData); @@ -89,111 +88,106 @@ function init(data) { } ``` -# d3.\_3d() [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L58 'Source') - -Constructs a new function object with the default settings. - ### Shapes Depending on the shape the input data array has to be accordingly to the shape. -- **POINT** A point is represented by the `` element. It does not have a draw function because it can be represented as a ``. The input data array has to be an array of points where each point has three coordinates which can be accessed via the [x](#x), [y](#y) and [z](#z) accessors. -- **LINE** A line is represented by the `` element. It does not have a draw function because it can be represented as a ``. The input data array has to be an array of lines where each line is defined by a start- and an endpoint. -- **LINE_STRIP** A continuous line is represented by the `` element. The input data array has to be an array of points. Every point will be connected to the next point in the input data array. -- **TRIANGLE** A triangle represented by the `` element. The input data array has to be an array of triangles where each triangle is defined by three points in counter-clockwise order. -- **PLANE** A plane is represented by the `` element. The input data array has to be an array of planes where each plane is defined by four points in counter-clockwise order. -- **GRID** A grid is represented by x planes. The input data array has to be an array of points. The [shape](#shape) function aspects the amount of points per row as a second argument. **d3-3d** will construct planes out of the passed data. - _NOTE:_ A grid has to have always the same number of points per row. Otherwise the code will break. -- **SURFACE** equivalent to `GRID` -- **CUBE** A grid is represented by 4 planes. The input data array has to be an array of cubes where each cube is defined by 8 vertices. To get the orientation and centroid calculation right you should pass in the data like so: +- **points3D** A point is represented by the `` element. It does not have a draw function because it can be represented as a ``. The input data array has to be an array of points where each point has three coordinates which can be accessed via the [x](#x), [y](#y) and [z](#z) accessors. +- **lines3D** A line is represented by the `` element. It does not have a draw function because it can be represented as a ``. The input data array has to be an array of lines where each line is defined by a start- and an endpoint. +- **lineStrips3D** A continuous line is represented by the `` element. The input data array has to be an array of points. Every point will be connected to the next point in the input data array. +- **triangles3D** A triangle represented by the `` element. The input data array has to be an array of triangles where each triangle is defined by three points in counter-clockwise order. +- **planes3D** A plane is represented by the `` element. The input data array has to be an array of planes where each plane is defined by four points in counter-clockwise order. +- **gridPlanes3D** A grid is represented by _x_ planes. The input data array has to be an array of points. **d3-3d** will construct planes out of the passed data. _NOTE:_ A grid has to have always the same number of points per row. Otherwise the code will break. +- **polygons3D** A polygon is represented by the `` element. The input data array has to be an array of polygons where each polygon is defined by _x_ points in counter-clockwise order. +- **cubes3D** A grid is represented by 4 planes. The input data array has to be an array of cubes where each cube is defined by 8 vertices. To get the orientation and centroid calculation right you should pass in the data like so: ![cube](assets/cube.png 'Cube') -# \_3d.shape(shape) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L87 'Source') - -_Default:_ `'POINT'` - -Sets the shape to _shape_. If _shape_ is not specified the current shape will be returned. +#### triangles3D().x(_x_) -If _shape_ is specified, sets the shape to the specified shape and returns the **d3-3d** function object. If _shape_ is not specified, returns the current shape. - -```js -const triangles3D = d3._3d().shape('TRIANGLE'); -``` - -# \_3d.x([x]) [<>](https://github.com/Niekes/d3-3d/blob/master/src/point.js#L1 'Source') - -If _x_ is specified, sets the x accessor to the specified function or number and returns the **d3-3d** function object. If _x_ is not specified, returns the current x accessor, which defaults to: +If _x_ is specified, sets the _x_ accessor to the specified function or number and returns the **d3-3d** function object. If _x_ is not specified, returns the current _x_ accessor, which defaults to: ```js function x(p) { - return p[0]; + return p.x; } ``` This function will be invoked for each point in the input data array. -# \_3d.y([y]) [<>](https://github.com/Niekes/d3-3d/blob/master/src/point.js#L5 'Source') +#### triangles3D().y(_y_) -If _y_ is specified, sets the y accessor to the specified function or number and returns the **d3-3d** function object. If _y_ is not specified, returns the current y accessor, which defaults to: +If _y_ is specified, sets the _y_ accessor to the specified function or number and returns the **d3-3d** function object. If _y_ is not specified, returns the current _y_ accessor, which defaults to: ```js function y(p) { - return p[1]; + return p.y; } ``` This function will be invoked for each point in the input data array. -# \_3d.z([z]) [<>](https://github.com/Niekes/d3-3d/blob/master/src/point.js#L9 'Source') +#### triangles3D().z(_z_) -If _z_ is specified, sets the z accessor to the specified function or number and returns the **d3-3d** function object. If _z_ is not specified, returns the current z accessor, which defaults to: +If _z_ is specified, sets the _z_ accessor to the specified function or number and returns the **d3-3d** function object. If _z_ is not specified, returns the current _z_ accessor, which defaults to: ```js function z(p) { - return p[2]; + return p.z; } ``` This function will be invoked for each point in the input data array. -# \_3d.scale(scale) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L71 'Source') +#### triangles3D().scale(_scale_) + +If _scale_ is specified, sets the _scale_ to the specified number and returns the **d3-3d** function object. If _scale_ is not specified, returns the current _scale_. _Default:_ `1` -If _scale_ is specified, sets the scale to the specified number and returns the **d3-3d** function object. If _scale_ is not specified, returns the current scale. +#### triangles3D().rotateX(_angleX_) -# \_3d.rotateX(angle) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L75 'Source') +If _angleX_ is specified, sets _angleX_ to the specified number and returns the **d3-3d** function object. If _angleX_ is not specified, returns the current _angleX_. _Default:_ `0` -If _angle_ is specified, sets rotateX to the specified number and returns the **d3-3d** function object. If _angle_ is not specified, returns the current angle. +_angleX_ should be expressed in radians, for example: `Math.PI / 4`. -# \_3d.rotateY(angle) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L79 'Source') +#### triangles3D().rotateY(_angleY_) + +If _angleY_ is specified, sets _angleY_ to the specified number and returns the **d3-3d** function object. If _angleY_ is not specified, returns the current _angleY_. _Default:_ `0` -If _angle_ is specified, sets rotateY to the specified number and returns the **d3-3d** function object. If _angle_ is not specified, returns the current angle. +_angleY_ should be expressed in radians, for example: `Math.PI / 4`. + +#### triangles3D().rotateZ(_angleZ_) -# \_3d.rotateZ(angle) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L83 'Source') +If _angleZ_ is specified, sets _angleZ_ to the specified number and returns the **d3-3d** function object. If _angleZ_ is not specified, returns the current _angleZ_. _Default:_ `0` -If _angle_ is specified, sets rotateZ to the specified number and returns the **d3-3d** function object. If _angle_ is not specified, returns the current angle. +_angleZ_ should be expressed in radians, for example: `Math.PI / 4`. + +#### triangles3D().rotateCenter(_rotateCenter_) + +If _rotateCenter_ is specified, sets rotateCenter to the specified point and returns the **d3-3d** function object. If _rotateCenter_ is not specified, returns the current _rotateCenter_. + +_Default:_ `{ x: 0, y: 0, z: 0 }` -# \_3d.rotateCenter(point) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#L87 'Source') +#### triangles3D().origin(_origin_) -_Default:_ `[0, 0, 0]` +If _origin_ is specified, sets origin to the specified point and returns the **d3-3d** function object. If _origin_ is not specified, returns the current _origin_. -If _point_ is specified, sets rotateCenter to the specified point and returns the **d3-3d** function object. If _rotateCenter_ is not specified, returns the current rotateCenter. +_Default:_ `{ x: 0, y: 0 }` -# \_3d.sort(a,b) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#107 'Source') +#### triangles3D().sort() Sorts the elements accordingly to the z coordinate of the calculated centroid. -# \_3d.draw(shape) [<>](https://github.com/Niekes/d3-3d/blob/master/src/3d.js#107 'Source') +#### triangles3D().draw() -Constructs a string for the SVG `` element. Depending on the [shape](#shape) this function will take care how the elements get drawn. For instance, if you choose `'TRIANGLE'` **d3-3d** aspects that you want to draw a triangle with three points and each point has three coordinates. The [_\_3d_.draw](#draw) method will draw a triangle with these three points. If you want to draw a plane, you have to pass in four points and so on. +This function constructs an SVG `` element string based on the chosen [shape](#shapes). For example, selecting triangles3D in **d3-3d** implies drawing a triangle with three points, each having three coordinates `{ x: 0, y: 0, z: 0 }`. The `triangles3D().draw` method facilitates this. To draw a plane, provide four points, and so forth. [![ko-fi](https://ko-fi.com/img/githubbutton_sm.svg)](https://ko-fi.com/A0A3QJPZ9) diff --git a/index.js b/index.js index cb73e19..fae88fc 100644 --- a/index.js +++ b/index.js @@ -1,12 +1,13 @@ /** - * @author Stefan Nieke / http://niekes.com/ + * @author Stefan Nieke (Niekes) + * @description http://niekes.com/ */ export { default as _3d } from './src/3d.js'; -export { cubes3D } from './src/primitiveShapes/cubes.js'; -export { gridPlanes3D } from './src/primitiveShapes/gridPlanes.js'; -export { lines3D } from './src/primitiveShapes/lines.js'; -export { lineStrips3D } from './src/primitiveShapes/lineStrips.js'; -export { planes3D } from './src/primitiveShapes/planes.js'; -export { points3D } from './src/primitiveShapes/points.js'; -export { polygons3D } from './src/primitiveShapes/polygons.js'; -export { triangles3D } from './src/primitiveShapes/triangles.js'; +export { cubes3D } from './src/shapes/cubes.js'; +export { gridPlanes3D } from './src/shapes/gridPlanes.js'; +export { lines3D } from './src/shapes/lines.js'; +export { lineStrips3D } from './src/shapes/lineStrips.js'; +export { planes3D } from './src/shapes/planes.js'; +export { points3D } from './src/shapes/points.js'; +export { polygons3D } from './src/shapes/polygons.js'; +export { triangles3D } from './src/shapes/triangles.js'; diff --git a/src/3d.js b/src/3d.js index 44d8635..6cd2c16 100644 --- a/src/3d.js +++ b/src/3d.js @@ -1,10 +1,10 @@ -import { cube } from './primitiveShapes/cubes.js'; -import { gridPlane } from './primitiveShapes/gridPlanes.js'; -import { lineStrip } from './primitiveShapes/lineStrips.js'; -import { line } from './primitiveShapes/lines.js'; -import { plane } from './primitiveShapes/planes.js'; -import { point } from './primitiveShapes/points.js'; -import { triangle } from './primitiveShapes/triangles.js'; +import { cube } from './shapes/cubes.js'; +import { gridPlane } from './shapes/gridPlanes.js'; +import { lineStrip } from './shapes/lineStrips.js'; +import { line } from './shapes/lines.js'; +import { plane } from './shapes/planes.js'; +import { point } from './shapes/points.js'; +import { triangle } from './shapes/triangles.js'; import { drawLineStrip } from './draw/drawLineStrip.js'; import { drawPlane } from './draw/drawPlane.js'; @@ -18,13 +18,13 @@ import { x as px, y as py, z as pz } from './point.js'; * @author Stefan Nieke / http://niekes.com/ */ export default function () { - var origin = [0, 0], + var origin = { x: 0, y: 0 }, scale = 1, projection = orthographic, angleX = 0, angleY = 0, angleZ = 0, - rotateCenter = [0, 0, 0], + rotateCenter = { x: 0, y: 0, z: 0 }, x = px, y = py, z = pz, diff --git a/src/generator.js b/src/generator.js index 387bae0..7aded41 100644 --- a/src/generator.js +++ b/src/generator.js @@ -13,8 +13,8 @@ export function generator3D(transform, draw) { let angleX = 0; let angleY = 0; let angleZ = 0; - let origin = [0, 0]; - let rotateCenter = [0, 0, 0]; + let origin = { x: 0, y: 0 }; + let rotateCenter = { x: 0, y: 0, z: 0 }; let scale = 1; let x = px; let y = py; diff --git a/src/point.js b/src/point.js index c8ba6ef..8a636f7 100644 --- a/src/point.js +++ b/src/point.js @@ -1,29 +1,29 @@ /** * Returns the x-coordinate of a point in 3D space. * - * @param {Array} p - The point in 3D space represented as an array e.g [0, 1, 0]. + * @param {Object} p - The point in 3D space represented as an object e.g {x: 0, y: 1, z: 0} * @returns {number} The x-coordinate of the point. */ export function x(p) { - return p[0]; + return p.x; } /** * Returns the y-coordinate of a point in 3D space. * - * @param {Array} p - The point in 3D space represented as an array e.g [0, 1, 0]. + * @param {Object} p - The point in 3D space represented as an object e.g x: 0, y: 1, z: 0} * @returns {number} The y-coordinate of the point. */ export function y(p) { - return p[1]; + return p.y; } /** * Returns the z-coordinate of a point in 3D space. * - * @param {Array} p - The point in 3D space represented as an array e.g [0, 1, 0] + * @param {Object} p - The point in 3D space represented as an object e.g {x: 0, y: 1, z: 0} * @returns {number} The z-coordinate of the point. */ export function z(p) { - return p[2]; + return p.z; } diff --git a/src/projection-orthographic.js b/src/projection-orthographic.js index da6f89c..69a94d9 100644 --- a/src/projection-orthographic.js +++ b/src/projection-orthographic.js @@ -18,7 +18,7 @@ export function orthographic(d, options) { * @type {Point2D} */ return { - x: options.origin[0] + options.scale * d.x, - y: options.origin[1] + options.scale * d.y + x: options.origin.x + options.scale * d.x, + y: options.origin.y + options.scale * d.y }; } diff --git a/src/rotation.js b/src/rotation.js index 97b2c5f..b65bc1f 100644 --- a/src/rotation.js +++ b/src/rotation.js @@ -12,17 +12,17 @@ export function rotateRzRyRx(po, angles) { const rc = angles.rotateCenter; - po.x -= rc[0]; - po.y -= rc[1]; - po.z -= rc[2]; + po.x -= rc.x; + po.y -= rc.y; + po.z -= rc.z; const rz = rotateZ(po, angles.z); const ry = rotateY(rz, angles.y); const rx = rotateX(ry, angles.x); - rx.x += rc[0]; - rx.y += rc[1]; - rx.z += rc[2]; + rx.x += rc.x; + rx.y += rc.y; + rx.z += rc.z; return rx; } diff --git a/src/primitiveShapes/cubes.js b/src/shapes/cubes.js similarity index 99% rename from src/primitiveShapes/cubes.js rename to src/shapes/cubes.js index 09461d7..c68402f 100644 --- a/src/primitiveShapes/cubes.js +++ b/src/shapes/cubes.js @@ -53,6 +53,7 @@ export function cube(cubes, options, point, angles) { bottom.face = 'bottom'; cube.faces = [front, back, left, right, top, bottom]; + cube.centroid = { x: (left.centroid.x + right.centroid.x) / 2, y: (top.centroid.y + bottom.centroid.y) / 2, diff --git a/src/primitiveShapes/gridPlanes.js b/src/shapes/gridPlanes.js similarity index 100% rename from src/primitiveShapes/gridPlanes.js rename to src/shapes/gridPlanes.js diff --git a/src/primitiveShapes/lineStrips.js b/src/shapes/lineStrips.js similarity index 100% rename from src/primitiveShapes/lineStrips.js rename to src/shapes/lineStrips.js diff --git a/src/primitiveShapes/lines.js b/src/shapes/lines.js similarity index 100% rename from src/primitiveShapes/lines.js rename to src/shapes/lines.js diff --git a/src/primitiveShapes/planes.js b/src/shapes/planes.js similarity index 100% rename from src/primitiveShapes/planes.js rename to src/shapes/planes.js diff --git a/src/primitiveShapes/points.js b/src/shapes/points.js similarity index 100% rename from src/primitiveShapes/points.js rename to src/shapes/points.js diff --git a/src/primitiveShapes/polygons.js b/src/shapes/polygons.js similarity index 100% rename from src/primitiveShapes/polygons.js rename to src/shapes/polygons.js diff --git a/src/primitiveShapes/triangles.js b/src/shapes/triangles.js similarity index 100% rename from src/primitiveShapes/triangles.js rename to src/shapes/triangles.js diff --git a/tests/3d-test.js b/tests/3d-test.js index e1e2c57..cdacf2e 100644 --- a/tests/3d-test.js +++ b/tests/3d-test.js @@ -4,13 +4,13 @@ import { triangles3D, points3D } from '../index.js'; test('d3-3d has expected defaults', function (t) { const _3d = d3._3d(); - t.deepEqual(_3d.origin(), [0, 0]); + t.deepEqual(_3d.origin(), { x: 0, y: 0 }); t.equal(_3d.scale(), 1); t.equal(_3d.rotateX(), 0); t.equal(_3d.rotateY(), 0); t.equal(_3d.rotateZ(), 0); t.equal(_3d.shape(), 'POINT'); - t.deepEqual(_3d.rotateCenter(), [0, 0, 0]); + t.deepEqual(_3d.rotateCenter(), { x: 0, y: 0, z: 0 }); t.end(); }); @@ -120,18 +120,18 @@ test('d3-3d has expected defaults', (t) => { const triangles = triangles3D(); const points = points3D(); - t.deepEqual(triangles.origin(), [0, 0]); + t.deepEqual(triangles.origin(), { x: 0, y: 0 }); t.equal(triangles.scale(), 1); t.equal(triangles.rotateX(), 0); t.equal(triangles.rotateY(), 0); t.equal(triangles.rotateZ(), 0); - t.deepEqual(triangles.rotationCenter(), [0, 0, 0]); + t.deepEqual(triangles.rotationCenter(), { x: 0, y: 0, z: 0 }); - t.deepEqual(points.origin(), [0, 0]); + t.deepEqual(points.origin(), { x: 0, y: 0 }); t.equal(points.scale(), 1); t.equal(points.rotateX(), 0); t.equal(points.rotateY(), 0); t.equal(points.rotateZ(), 0); - t.deepEqual(points.rotationCenter(), [0, 0, 0]); + t.deepEqual(points.rotationCenter(), { x: 0, y: 0, z: 0 }); t.end(); }); diff --git a/tests/linestrips-test.js b/tests/linestrips-test.js index 8a85821..aa7477b 100644 --- a/tests/linestrips-test.js +++ b/tests/linestrips-test.js @@ -4,16 +4,16 @@ import { lineStrips3D } from '../index.js'; test('linestrip draws correctly', function (t) { var data = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4], - [-3, 0, 2] + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 }, + { x: -3, y: 0, z: 2 } ]; - var ls3D = d3._3d().scale(30).origin([220, 340]).shape('LINE_STRIP'); + var ls3D = d3._3d().scale(30).origin({ x: 220, y: 340 }).shape('LINE_STRIP'); t.equal( ls3D.draw(ls3D([data])[0]), @@ -23,28 +23,28 @@ test('linestrip draws correctly', function (t) { }); test('centroid calculation for linesstrip', function (t) { - var data = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4], - [-3, 0, 2] + const data1 = [ + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 }, + { x: -3, y: 0, z: 2 } ]; - var data2 = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4] + const data2 = [ + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 } ]; - var ls3D = d3._3d().scale(30).origin([220, 340]).shape('LINE_STRIP'); + var ls3D = d3._3d().scale(30).origin({ x: 220, y: 340 }).shape('LINE_STRIP'); - t.deepEqual(ls3D([data])[0].centroid, { x: 0, y: 9, z: 3 }); + t.deepEqual(ls3D([data1])[0].centroid, { x: 0, y: 9, z: 3 }); t.deepEqual(ls3D([data2])[0].centroid, { x: 0.5, y: 5, z: 2.5 }); t.end(); @@ -57,16 +57,16 @@ test('linestrip draws correctly', (t) => { t.plan(1); const data = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4], - [-3, 0, 2] + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 }, + { x: -3, y: 0, z: 2 } ]; - const lineStrip = lineStrips3D().scale(30).origin([220, 340]); + const lineStrip = lineStrips3D().scale(30).origin({ x: 220, y: 340 }); t.equal( lineStrip.draw(lineStrip([data])[0]), @@ -78,28 +78,28 @@ test('linestrip draws correctly', (t) => { test('centroid calculation for linesstrip', (t) => { t.plan(2); - const data = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4], - [-3, 0, 2] + const data1 = [ + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 }, + { x: -3, y: 0, z: 2 } ]; const data2 = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4] + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 } ]; - const lineStrip = lineStrips3D().scale(30).origin([220, 340]); + const lineStrip = lineStrips3D().scale(30).origin({ x: 220, y: 340 }); - t.deepEqual(lineStrip([data])[0].centroid, { x: 0, y: 9, z: 3 }); + t.deepEqual(lineStrip([data1])[0].centroid, { x: 0, y: 9, z: 3 }); t.deepEqual(lineStrip([data2])[0].centroid, { x: 0.5, y: 5, z: 2.5 }); t.end(); diff --git a/tests/planes-test.js b/tests/planes-test.js index bba93ff..8bdb851 100644 --- a/tests/planes-test.js +++ b/tests/planes-test.js @@ -31,12 +31,13 @@ test("draw function of 'planes' draws correctly", function (t) { var _3d = d3._3d().shape('PLANE'); var data = [ [ - [5, 0, 2], - [6, 4, 1], - [4, 5, 8], - [1, 5, 9] + { x: 5, y: 0, z: 2 }, + { x: 6, y: 4, z: 1 }, + { x: 4, y: 5, z: 8 }, + { x: 1, y: 5, z: 9 } ] ]; + t.deepEqual(_3d.draw(_3d(data)[0]), 'M5,0L6,4L4,5L1,5Z'); t.end(); }); @@ -86,10 +87,10 @@ test("draw function of 'planes' draws correctly", (t) => { const data = [ [ - [5, 0, 2], - [6, 4, 1], - [4, 5, 8], - [1, 5, 9] + { x: 5, y: 0, z: 2 }, + { x: 6, y: 4, z: 1 }, + { x: 4, y: 5, z: 8 }, + { x: 1, y: 5, z: 9 } ] ]; t.equal(planes.draw(planes(data)[0]), 'M5,0L6,4L4,5L1,5Z'); diff --git a/tests/points-test.js b/tests/points-test.js index c1758e9..1cf1719 100644 --- a/tests/points-test.js +++ b/tests/points-test.js @@ -11,12 +11,12 @@ test("points don't have draw function", function (t) { test('points3D has expected defaults', (t) => { var _3d = d3._3d(); - t.deepEqual(_3d.origin(), [0, 0]); + t.deepEqual(_3d.origin(), { x: 0, y: 0 }); t.equal(_3d.scale(), 1); t.equal(_3d.rotateX(), 0); t.equal(_3d.rotateY(), 0); t.equal(_3d.rotateZ(), 0); - t.deepEqual(_3d.rotateCenter(), [0, 0, 0]); + t.deepEqual(_3d.rotateCenter(), { x: 0, y: 0, z: 0 }); t.equal(_3d.draw(), undefined); t.equal(typeof _3d.sort, 'function'); t.equal(typeof _3d.x, 'function'); @@ -28,8 +28,8 @@ test('points3D has expected defaults', (t) => { test('access point coords via array', function (t) { var _3d = d3._3d(); var data = [ - [1, 2, 3], - [4, 5, 6] + { x: 1, y: 2, z: 3 }, + { x: 4, y: 5, z: 6 } ]; t.deepEqual(_3d(data)[0].rotated, { x: 1, y: 2, z: 3 }); t.deepEqual(_3d(data)[1].rotated, { x: 4, y: 5, z: 6 }); @@ -94,7 +94,7 @@ test('rotate point 1|1|1 along x axis by 180°', function (t) { }); test('project point 1|1|1 on to screen', function (t) { - var data = [[1, 1, 1]]; + var data = [{ x: 1, y: 1, z: 1 }]; var _3d = d3._3d().scale(100); t.deepEqual(_3d(data)[0].projected, { x: 100, y: 100 }); t.end(); @@ -118,12 +118,12 @@ test('points3D is exported correctly', (t) => { test('points3D has expected defaults', (t) => { const points = points3D(); - t.deepEqual(points.origin(), [0, 0]); + t.deepEqual(points.origin(), { x: 0, y: 0 }); t.equal(points.scale(), 1); t.equal(points.rotateX(), 0); t.equal(points.rotateY(), 0); t.equal(points.rotateZ(), 0); - t.deepEqual(points.rotationCenter(), [0, 0, 0]); + t.deepEqual(points.rotationCenter(), { x: 0, y: 0, z: 0 }); t.equal(points.draw, undefined); t.equal(typeof points.sort, 'function'); t.equal(typeof points.x, 'function'); @@ -134,21 +134,8 @@ test('points3D has expected defaults', (t) => { test('access point coords via array', (t) => { const data = [ - [1, 2, 3], - [4, 5, 6] - ]; - - const points = points3D(); - - t.deepEqual(points(data)[0].rotated, { x: 1, y: 2, z: 3 }); - t.deepEqual(points(data)[1].rotated, { x: 4, y: 5, z: 6 }); - t.end(); -}); - -test('access point coords via array', function (t) { - const data = [ - [1, 2, 3], - [4, 5, 6] + { x: 1, y: 2, z: 3 }, + { x: 4, y: 5, z: 6 } ]; const points = points3D(); @@ -200,7 +187,7 @@ test('rotate point 1|1|1 along x axis by 180°', (t) => { }); test('project point 1|1|1 on to screen', (t) => { - const data = [[1, 1, 1]]; + const data = [{ x: 1, y: 1, z: 1 }]; const points = points3D().scale(100); t.deepEqual(points(data)[0].projected, { x: 100, y: 100 }); diff --git a/tests/polygons-test.js b/tests/polygons-test.js index f014022..b9ba1f7 100644 --- a/tests/polygons-test.js +++ b/tests/polygons-test.js @@ -5,16 +5,16 @@ test('polygons3D draws correctly', function (t) { t.plan(1); const data = [ - [3, 5, 2], - [2, 45, 2], - [1, 1, 2], - [0, 9, 3], - [-1, 3, 2], - [-2, 8, 4], - [-3, 0, 2] + { x: 3, y: 5, z: 2 }, + { x: 2, y: 45, z: 2 }, + { x: 1, y: 1, z: 2 }, + { x: 0, y: 9, z: 3 }, + { x: -1, y: 3, z: 2 }, + { x: -2, y: 8, z: 4 }, + { x: -3, y: 0, z: 2 } ]; - const polygons = polygons3D().scale(30).origin([220, 340]); + const polygons = polygons3D().scale(30).origin({ x: 220, y: 340 }); t.equal( polygons.draw(polygons([data])[0]), @@ -22,3 +22,21 @@ test('polygons3D draws correctly', function (t) { ); t.end(); }); + +test('polygons3D has expected defaults', (t) => { + t.plan(11); + + const polygons = polygons3D(); + t.deepEqual(polygons.origin(), { x: 0, y: 0 }); + t.equal(polygons.scale(), 1); + t.equal(polygons.rotateX(), 0); + t.equal(polygons.rotateY(), 0); + t.equal(polygons.rotateZ(), 0); + t.deepEqual(polygons.rotationCenter(), { x: 0, y: 0, z: 0 }); + t.equal(typeof polygons.draw, 'function'); + t.equal(typeof polygons.sort, 'function'); + t.equal(typeof polygons.x, 'function'); + t.equal(typeof polygons.y, 'function'); + t.equal(typeof polygons.z, 'function'); + t.end(); +}); diff --git a/tests/triangles-test.js b/tests/triangles-test.js index 91f7fc3..337d8e6 100644 --- a/tests/triangles-test.js +++ b/tests/triangles-test.js @@ -30,9 +30,9 @@ test('access triangle coords via array', function (t) { var triangles = d3._3d().shape('TRIANGLE'); var data = [ [ - [0, 0, 0], - [0, 1, 0], - [1, 0, 0] + { x: 0, y: 0, z: 0 }, + { x: 0, y: 1, z: 0 }, + { x: 1, y: 0, z: 0 } ] ]; @@ -199,12 +199,12 @@ test('triangles3D is exported correctly', (t) => { test('triangles3D has expected defaults', (t) => { const triangles = triangles3D(); - t.deepEqual(triangles.origin(), [0, 0]); + t.deepEqual(triangles.origin(), { x: 0, y: 0 }); t.equal(triangles.scale(), 1); t.equal(triangles.rotateX(), 0); t.equal(triangles.rotateY(), 0); t.equal(triangles.rotateZ(), 0); - t.deepEqual(triangles.rotationCenter(), [0, 0, 0]); + t.deepEqual(triangles.rotationCenter(), { x: 0, y: 0, z: 0 }); t.equal(typeof triangles.draw, 'function'); t.equal(typeof triangles.sort, 'function'); t.equal(typeof triangles.x, 'function'); @@ -231,35 +231,19 @@ test('triangle draw', (t) => { t.end(); }); -test('access triangle coords via array', (t) => { - const triangles = triangles3D(); - const data = [ - [ - [1, 2, 3], - [4, 5, 6], - [7, 8, 9] - ] - ]; - - t.deepEqual(triangles(data)[0][0].rotated, { x: 1, y: 2, z: 3 }); - t.deepEqual(triangles(data)[0][1].rotated, { x: 4, y: 5, z: 6 }); - t.deepEqual(triangles(data)[0][2].rotated, { x: 7, y: 8, z: 9 }); - t.end(); -}); - test('access triangle coords via function', (t) => { const data = [ [ - { x: 1, y: 2, z: 3 }, - { x: 4, y: 5, z: 6 }, - { x: 7, y: 8, z: 9 } + { x1: 1, y2: 2, z3: 3 }, + { x1: 4, y2: 5, z3: 6 }, + { x1: 7, y2: 8, z3: 9 } ] ]; const triangles = triangles3D() - .x((d) => d.x) - .y((d) => d.y) - .z((d) => d.z); + .x((d) => d.x1) + .y((d) => d.y2) + .z((d) => d.z3); t.deepEqual(triangles(data)[0][0].rotated, { x: 1, y: 2, z: 3 }); t.deepEqual(triangles(data)[0][1].rotated, { x: 4, y: 5, z: 6 }); @@ -286,10 +270,7 @@ test('triangles are a closed path', function (t) { }); test('triangles are getting drawn counter-clockwise', (t) => { - const triangles = triangles3D() - .x((d) => d.x) - .y((d) => d.y) - .z((d) => d.z); + const triangles = triangles3D(); const data1 = [ [ @@ -334,10 +315,7 @@ test('triangles are getting drawn counter-clockwise', (t) => { }); test("triangles' centroid calculation is correct", (t) => { - const triangles = triangles3D() - .x((d) => d.x) - .y((d) => d.y) - .z((d) => d.z); + const triangles = triangles3D(); const data = [ [