This repository has been archived on 2021-07-14. You can view files and clone it, but cannot push or open issues or pull requests.
scriptcraft/src/main/js/modules/drone/sphere.js

397 lines
9.4 KiB
JavaScript

'use strict';
/*global module*/
/************************************************************************
### Drone.sphere() method
Creates a sphere.
#### Parameters
* block - The block the sphere will be made of.
* radius - The radius of the sphere.
#### Example
To create a sphere of Iron with a radius of 10 blocks...
sphere( blocks.iron, 10);
![sphere example](img/sphereex1.png)
Spheres are time-consuming to make. You *can* make large spheres (250 radius) but expect the
server to be very busy for a couple of minutes while doing so.
***/
function sphere( block, radius ) {
var lastRadius = radius,
slices = [ [ radius , 0 ] ],
diameter = radius * 2,
bm = this.getBlockIdAndMeta( block ),
r2 = radius * radius,
i = 0,
newRadius,
yOffset,
sr,
sh,
v,
h;
if ( radius > 127 ) {
throw new Error('Sphere radius must be less than 128 blocks');
}
for ( i = 0; i <= radius; i++ ) {
newRadius = Math.round( Math.sqrt( r2 - i * i ) );
if ( newRadius == lastRadius ) {
slices[ slices.length - 1 ][ 1 ]++;
} else {
slices.push( [ newRadius , 1 ] );
}
lastRadius = newRadius;
}
this.chkpt( 'sphere' );
//
// mid section
//
this.up( radius - slices[0][1] )
.cylinder( block, radius, ( slices[0][1]*2 ) - 1, { blockType: bm[0], meta: bm[1] } )
.down( radius - slices[0][1] );
yOffset = -1;
for ( i = 1; i < slices.length; i++ ) {
yOffset += slices[i-1][1];
sr = slices[i][0];
sh = slices[i][1];
v = radius + yOffset;
h = radius - sr;
// northern hemisphere
this.up( v )
.fwd( h )
.right( h )
.cylinder( block, sr, sh, { blockType: bm[0], meta: bm[1] } )
.left( h )
.back( h )
.down( v );
// southern hemisphere
v = radius - ( yOffset + sh + 1 );
this.up( v )
.fwd( h )
.right( h )
.cylinder( block, sr, sh, { blockType: bm[0], meta: bm[1]} )
.left( h )
.back( h )
.down( v );
}
return this.move( 'sphere' );
}
/************************************************************************
### Drone.sphere0() method
Creates an empty sphere.
#### Parameters
* block - The block the sphere will be made of.
* radius - The radius of the sphere.
#### Example
To create a sphere of Iron with a radius of 10 blocks...
sphere0( blocks.iron, 10);
Spheres are time-consuming to make. You *can* make large spheres (250 radius) but expect the
server to be very busy for a couple of minutes while doing so.
***/
function sphere0(block,radius)
{
var lastRadius = radius,
slices = [ [ radius, 0 ] ],
diameter = radius * 2,
bm = this.getBlockIdAndMeta( block ),
r2 = radius*radius,
i,
newRadius,
sr,
sh,
v,
h,
len,
yOffset;
if ( radius > 127 ) {
throw new Error('Sphere radius must be less than 128 blocks');
}
for ( i = 0; i <= radius; i++ ) {
newRadius = Math.round( Math.sqrt( r2 - i * i ) );
if ( newRadius == lastRadius ) {
slices[ slices.length - 1 ][ 1 ]++;
} else {
slices.push( [ newRadius, 1 ] );
}
lastRadius = newRadius;
}
this.chkpt( 'sphere0' );
//
// mid section
//
this.up( radius - slices[0][1] )
.arc({ blockType: bm[0],
meta: bm[1],
radius: radius,
strokeWidth: 2,
stack: (slices[0][1]*2)-1,
fill: false
})
.down( radius - slices[0][1] );
yOffset = -1;
len = slices.length;
for ( i = 1; i < len; i++ ) {
yOffset += slices[i-1][1];
sr = slices[i][0];
sh = slices[i][1];
v = radius + yOffset;
h = radius-sr;
// northern hemisphere
// .cylinder(block,sr,sh,{blockType: bm[0],meta: bm[1]})
this.up( v ).fwd( h ).right( h )
.arc({
blockType: bm[0],
meta: bm[1],
radius: sr,
stack: sh,
fill: false,
strokeWidth: i < len - 1 ? 1 + ( sr - slices[ i + 1 ][ 0 ] ) : 1
})
.left( h ).back( h ).down( v );
// southern hemisphere
v = radius - ( yOffset + sh + 1 );
this.up( v ).fwd( h ).right( h )
.arc({
blockType: bm[0],
meta: bm[1],
radius: sr,
stack: sh,
fill: false,
strokeWidth: i < len - 1 ? 1 + ( sr - slices[ i + 1 ][ 0 ] ) : 1
})
.left( h ).back( h ). down( v );
}
this.move( 'sphere0' );
return this;
}
/************************************************************************
### Drone.hemisphere() method
Creates a hemisphere. Hemispheres can be either north or south.
#### Parameters
* block - the block the hemisphere will be made of.
* radius - the radius of the hemisphere
* northSouth - whether the hemisphere is 'north' or 'south'
#### Example
To create a wood 'north' hemisphere with a radius of 7 blocks...
hemisphere(blocks.oak, 7, 'north');
![hemisphere example](img/hemisphereex1.png)
***/
function hemisphere( block, radius, northSouth ) {
var lastRadius = radius,
slices = [ [ radius, 0 ] ],
diameter = radius * 2,
bm = this.getBlockIdAndMeta(block),
r2 = radius * radius,
i = 0,
newRadius;
if ( radius > 255 ) {
throw new Error('Hemisphere radius must be less than 256 blocks');
}
for ( i = 0; i <= radius; i++ ) {
newRadius = Math.round( Math.sqrt( r2 - i * i ) );
if ( newRadius == lastRadius ) {
slices[ slices.length - 1 ][ 1 ]++;
} else {
slices.push( [ newRadius, 1 ] );
}
lastRadius = newRadius;
}
this.chkpt( 'hsphere' );
//
// mid section
//
if ( northSouth == 'north' ) {
this.cylinder( block, radius, slices[0][1], { blockType: bm[0], meta: bm[1] } );
} else {
this.up( radius - slices[0][1] )
.cylinder( block, radius, slices[0][1], { blockType: bm[0], meta: bm[1] } )
.down( radius - slices[0][1] );
}
var yOffset = -1;
for ( i = 1; i < slices.length; i++ ) {
yOffset += slices[i-1][1];
var sr = slices[i][0];
var sh = slices[i][1];
var v = yOffset, h = radius-sr;
if ( northSouth == 'north' ) {
// northern hemisphere
this.up( v ).fwd( h ).right( h )
.cylinder( block, sr, sh, { blockType: bm[0], meta: bm[1] } )
.left( h ).back( h ).down( v );
} else {
// southern hemisphere
v = radius - ( yOffset + sh + 1 );
this.up( v ).fwd( h ).right( h )
.cylinder( block, sr, sh, { blockType: bm[0], meta: bm[1] } )
.left( h ).back( h ).down( v );
}
}
return this.move( 'hsphere' );
}
/************************************************************************
### Drone.hemisphere0() method
Creates a hollow hemisphere. Hemispheres can be either north or south.
#### Parameters
* block - the block the hemisphere will be made of.
* radius - the radius of the hemisphere
* northSouth - whether the hemisphere is 'north' or 'south'
#### Example
To create a glass 'north' hemisphere with a radius of 20 blocks...
hemisphere0(blocks.glass, 20, 'north');
![hemisphere example](img/hemisphereex2.png)
***/
function hemisphere0( block, radius, northSouth ) {
if ( radius > 255 ) {
throw new Error('Hemisphere radius must be less than 256 blocks');
}
var lastRadius = radius,
slices = [ [ radius, 0 ] ],
diameter = radius * 2,
bm = this.getBlockIdAndMeta(block),
r2 = radius * radius,
i = 0,
len,
newRadius;
if ( radius > 255 ) {
throw new Error('Hemisphere radius must be less than 256 blocks');
}
for ( i = 0; i <= radius; i++ ) {
newRadius = Math.round( Math.sqrt( r2 - i * i ) );
if ( newRadius == lastRadius ) {
slices[ slices.length - 1 ][ 1 ]++;
} else {
slices.push( [ newRadius, 1 ] );
}
lastRadius = newRadius;
}
this.chkpt( 'hsphere0' );
//
// mid section
//
if ( northSouth == 'north' ) {
this.arc({
blockType: bm[0],
meta: bm[1],
radius: radius,
strokeWidth: 1,
stack: slices[0][1],
fill: false
});
} else {
this.up( radius - slices[0][1] );
this.arc({
blockType: bm[0],
meta: bm[1],
radius: radius,
strokeWidth: 1,
stack: slices[0][1],
fill: false
});
this.down( radius - slices[0][1] );
}
var yOffset = -1;
len = slices.length;
for ( i = 1; i < slices.length; i++ ) {
yOffset += slices[i-1][1];
var sr = slices[i][0];
var sh = slices[i][1];
var v = yOffset, h = radius-sr;
if ( northSouth == 'north' ) {
// northern hemisphere
this.up( v )
.fwd( h )
.right( h );
this.arc( {
blockType: bm[0],
meta: bm[1],
radius: sr,
stack: sh,
fill: false,
strokeWidth: i < len - 1 ? 1 + ( sr - slices[ i + 1 ][ 0 ] ) : 1
} );
this.left( h )
.back( h )
.down( v );
} else {
// southern hemisphere
v = radius - ( yOffset + sh + 1 );
this.up( v )
.fwd( h )
.right( h );
this.arc({
blockType: bm[0],
meta: bm[1],
radius: sr,
stack: sh,
fill: false,
strokeWidth: i < len - 1 ? 1 + ( sr - slices[ i + 1 ][ 0 ] ) : 1
});
this.left( h )
.back( h )
.down( v );
}
}
return this.move( 'hsphere0' );
}
module.exports = function(Drone){
Drone.extend( sphere );
Drone.extend( sphere0 );
Drone.extend( hemisphere );
Drone.extend( hemisphere0 );
};