Die folgende Grafik wurde per JavaScript mit Hilfe des JSG3D-Moduls generiert. Beachte dass beim Verändern der Fenstergrösse die Grösse der Grafik automatisch neu berechnet und die Grafik neu gezeichnet wird.
var halfPlaneSpan = 6 * Math.PI;
var numAreasPerLine = 150;
var numAreasPerLine2 = 400;
CreateHeart();
function DrawArrow( g3d ) {
// Arrow in the background
g3d.SetMarkerAttr( 'Arrow2', 14, 'black', 'black', 2 );
g3d.SetLineAttr( 'rgba(0,0,0,1)', 2 );
g3d.Arrow3D( [0,0,0], [0,20,0] );
}
function DrawDecorations( g3d ) {
// Axes and colored Lines
var dxy = 2 * halfPlaneSpan / numAreasPerLine2;
g3d.SetMarkerAttr( 'Arrow2', 14, 'black', 'black', 2 );
g3d.Arrow3D( [0,0,0], [15,0,0] );
g3d.Line3D( [0,0,0], [0,-20,0] );
g3d.Arrow3D( [0,0,0], [0,0,13] );
g3d.SetLineAttr( 'rgba(0,0,0,0.3)', 2 );
g3d.Arrow3D( [0,0,0], [0,20,0] );
var poly = g3d.PolygonFromFunc( {
Func: function( x, p ) { return [ x, 0, Math.pow( x*x, 0.3 ) ]; },
Min: 0, Max: halfPlaneSpan, Steps: numAreasPerLine2/2
} );
g3d.SetLineAttr( 'yellow', 2 );
g3d.Polygon3D( poly );
var poly = g3d.PolygonFromFunc( {
Func: function( x, p ) {
var z = Math.pow( Math.sin( 15 * Math.pow( ell(x,0), 0.1 ) ), 2 ) * 1 * Math.pow( x*x, 0.3 );
return [ x, 0, z ];
},
Min: 0, Max: halfPlaneSpan, Steps: numAreasPerLine2/2
} );
g3d.SetLineAttr( 'blue', 3.5 );
g3d.Polygon3D( poly );
g3d.SetTextAttr( 'Arial', 18, 'black', 'bold', 'normal', 'center', 'middle' );
var offset = 1;
g3d.Text3D( 'X', [15+offset,0,0] );
g3d.Text3D( 'Y', [0,20+offset,0] );
g3d.Text3D( 'Z', [0,0,13+offset] );
}
function CreateHeart() {
// Init 3D module and create 3D graphic
var g3d = NewGraph3D( {
BeforeDrawFunc: DrawArrow,
AfterDrawFunc: DrawDecorations,
SceneSize: 2*halfPlaneSpan, ScaleRef: 800, AutoScalePix: true,
CamViewCenter: JsgVect3.New(2.5,2.5,2), CamHAng: -75, CamVAng: 35, CamDist: 150,
Zoom: 1.7, Aperture: 0.9
} );
// define the various area attributes and lighting
var data1 = new JsgEleData( {
AreaDrawMode: 3,
AreaAttrFunc: AreaColorChanger,
Lighting: {
ApplyCamLight: false,
ApplyPhong: false,
ApplyAmbient: false
},
BackLighting: {
Dimm: 0.9
}
} );
var data2 = new JsgEleData( {
AreaDrawMode: 2,
AreaAttrFunc: AreaColorChanger,
Lighting: {
ApplyCamLight: true,
ApplyPhong: true,
ApplyAmbient: true,
CamRefl: 0.2,
AmbiRefl: 0.05,
DiffRefl: 0.5,
SpecRefl: 1,
Shiny: 8,
DiffXRay: 1,
SpecXRay: 1
},
BackLighting: {
Dimm: 0.9
}
} );
var data3 = new JsgEleData( {
AreaDrawMode: 3,
Attr: {
AreaColor: JsgColor.BW(2),
AreaBackColor: JsgColor.White(),
LineColor: JsgColor.BW(0.5),
AreaBackLineColor: JsgColor.BW(0.25),
LineWidth: 1
},
Lighting: {
ApplyCamLight: false,
ApplyPhong: false,
ApplyAmbient: false
},
BackLighting: {
Dimm: 0.9
}
} );
g3d.SetAmbientLight( JsgColor.White() );
g3d.SetCameraLight( JsgColor.White() );
g3d.AddLightSource( {
LightColor: JsgColor.White(),
DiffInt: 0.4,
SpecInt: 0.9,
LightDir: JsgVect3.New(20,50,100)
} );
g3d.AddLightSource( {
LightColor: JsgColor.RGB(1,1,0.8),
DiffInt: 0.9,
SpecInt: 1,
LightPos: JsgVect3.New(-10,-10,10)
} );
g3d.AddLightSource( {
LightColor: JsgColor.RGB(0.4,0.4,1),
DiffInt: 0.5,
SpecInt: 1,
LightPos: JsgVect3.New(10,10,10)
} );
g3d.AddAreasFromVectGrid( CreateVectGrid( -halfPlaneSpan, 0, 0, halfPlaneSpan, numAreasPerLine ), data1 );
g3d.AddAreasFromVectGrid( CreateVectGrid( 0, halfPlaneSpan, 0, halfPlaneSpan, numAreasPerLine2 ), data2 );
g3d.AddAreasFromVectGrid( CreateVectGrid( -halfPlaneSpan, 0, -halfPlaneSpan, 0, numAreasPerLine ), data3 );
}
function AreaColorChanger( g3d, aArea, aAreaAttr ) {
var c = g3d.GraphEleCenter( aArea );
var r = Math.pow( ell( c[0], c[1] ), 0.1 );
var val = 1-Math.pow( Math.sin( 15 * r ), 2 );
if (r > Math.PI/2) {
if (r > 1.05*Math.PI/2) {
var alpha = Math.exp( - Math.pow( 15 * (r - (1.04 * Math.PI/2)), 4 ) );
JsgColor.SetRGBA( aAreaAttr.AreaColor, 1, val, 0, alpha );
JsgColor.SetRGBA( aAreaAttr.AreaBackColor, 1, val, 0, alpha );
JsgColor.SetRGBA( aAreaAttr.LineColor, 1, val, 0, alpha );
JsgColor.SetRGBA( aAreaAttr.AreaBackLineColor, 1, val, 0, alpha );
} else {
JsgColor.SetRGB( aAreaAttr.AreaColor, 1, val, 0 );
JsgColor.SetRGB( aAreaAttr.AreaBackColor, 1, val, 0 );
JsgColor.SetRGB( aAreaAttr.LineColor, 1, val, 0 );
JsgColor.SetRGB( aAreaAttr.AreaBackLineColor, 1, val, 0 );
}
} else {
JsgColor.SetRGB( aAreaAttr.AreaColor, 1, val, val );
JsgColor.SetRGB( aAreaAttr.AreaBackColor, 1, val, val );
JsgColor.SetRGB( aAreaAttr.LineColor, 1, val, val );
JsgColor.SetRGB( aAreaAttr.AreaBackLineColor, 1, val, val );
}
}
function CreateVectGrid( XStart, XEnd, YStart, YEnd, resolution ) {
var dxy = 2 * halfPlaneSpan / resolution;
var dxy2 = dxy / 2;
var grid = [];
for (var y = YStart; y <= YEnd+dxy2; y += dxy) {
var line = [];
for (var x = XStart; x <= XEnd+dxy2; x += dxy) {
var z = Math.pow( Math.sin( 15 * Math.pow( ell(x,y), 0.1 ) ), 2 ) * 1 * Math.pow( x*x + y*y, 0.3 );
line.push( [ x, y, z ] );
}
grid.push( line );
}
return grid;
}
function ell( x, y ) {
return x*x - 1.2*Math.abs(x)*y + y*y;
}