Example of four bots playing BIS in classic mode:
Category Archives: OsX
YAogl Scene Graph Debugger
Da der Import einer Szene aus externen Tools zu Aufwendig ist, habe ich den internen Szenengraph um einen Debug-Modus ergänzt. Zudem konnte durch Optimierung der Vektor-Berechnungen etwa 6% und durch Umstellung der OpenGL Befehlsfolge noch einmal 4% Leistungsverbesserung erzielt werden. Die Berechnung und Darstellung einer Szene benötigt nun weniger Ressourcen als das Abspielen eines Internet-Videos.
Aufbau des mechanischen Orbits:
Hier experimentiere ich mit der Szenen-Beleuchtung:
If your GLSL shader stopped working under OsX
Add following line to your code: #extension GL_ARB_explicit_attrib_location : enable
YAOGL Buttons, Picking, Messaging and Low Level Logic
Low Level Logic is now directly accessible in 3d space (done with an additional render pass because of some OpenGL ES limitations).
You can now add buttons, pick objects and send messages. Also object to object messaging is now possible (e.g. follow me with 5 seconds delay):
YAOgl: Advanced HID example
An atlantic manta (modeled with Sculptris) and its little blue offspring (modeled and rigged with Blender)
I’m using this scene to check my exporter-scripts against the latest application updates.
YAOgl: Human Interface Devices
It is now possible to use HI Devices like gamepads, joysticks for object or camera movement.
Here is a short demonstration of this feature:
YAHIDAnimator* gamepad = [world createHIDAnimator];
[gamepad addListener:[voxelCubeImp rotation] factor:90];
YABasicAnimator* rotZ = [world createBasicAnimator];
[rotZ setProgress:harmonic];
[rotZ setInterval:0.5f];
[rotZ addListener:[voxelCubeImp rotation] factor:5];
[rotZ setInfluence:z];
This new animation class can be combined with any other animation method:
Real-time iso-surface extraction
The iso-surface of a voxel map is now simultaneously updated with the change of voxel-densities. In this demo following code was used to produce a growing cube effect:
const char growth = 120 / 10;
for(int i = 0; i <= 25; i++) {
int xP = 10 + (rand() % (33 - 20));
int zP = 10 + (rand() % (33 - 20));
if( (xP > 12 && xP < 20) && (zP > 12 && zP < 20) )
continue;
int yP = 1;
while(yP < 31 && [voxelMap getVoxel:xP :yP :zP] > 1 )
yP++;
if(yP < 15) {
char d = [voxelMap getVoxel:xP :yP - 1 :zP];
if(d < 120)
[voxelMap setVoxel:d + growth x:xP y:yP -1 z:zP];
else
[voxelMap setVoxel:growth x:xP y:yP z:zP];
}
}
if(voxelMap.hasChanged) {
[voxelMap updateIso];
[voxelMapIngredient updateTriangles:[voxelMap vbo]];
}
For each frame about 25 voxels are changed. The method updateIso is used to recalculate the mesh data. The voxel algorithm is fast enough to run exclusively on the CPU.
YAOgl Voxel Engine: stitching and compression
Voxel maps are now partially compressed (the inactive parts) and the borders of clusters are now stitched together. Im now using cubic projection for texture generation.
Here are some further examples:
A Cube
YAVoxelMap* voxelMap = [[YAVoxelMap alloc] initDimensions:vMapDimensionX :vMapDimensionY :vMapDimensionZ];
for (int x = 0; x < vMapDimensionX; x++)
for (int y = 0; y < vMapDimensionY; y++)
for (int z = 0; z < vMapDimensionZ; z++)
if(x == 0 || x == (vMapDimensionX - 1) || y == 0 || y == (vMapDimensionY - 1) || z == 0 || z == (vMapDimensionZ - 1))
[voxelMap setVoxel: -1 x:x y:y z:z];
else {
[voxelMap setVoxel: +1 x:x y:y z:z];
if( (y % 5 > 1 && y % 5 < 4) && ( (x % 5 > 1 && x % 5 < 4) || (z % 5 > 1 && z % 5 < 4) ) )
[voxelMap setVoxel: -124 x:x y:y z:z];
}
[voxelMap calcIso];
A Ball
YAVoxelMap* voxelMap = [[YAVoxelMap alloc] initDimensions:vMapDimensionX :vMapDimensionY :vMapDimensionZ];
for (int x = 0; x < vMapDimensionX; x++)
for (int y = 0; y < vMapDimensionY; y++)
for (int z = 0; z < vMapDimensionZ; z++)
if(x == 0 || x == (vMapDimensionX - 1) || y == 0 || y == (vMapDimensionY - 1) || z == 0 || z == (vMapDimensionZ - 1))
[voxelMap setVoxel: -125 x:x y:y z:z];
else {
const float minDist = (1.0/32.0);
const float center = vMapDimensionX / 2;
const float dist = sqrt(pow(center - x, 2) + pow(center - y, 2) + pow(center - z, 2));
const float max = sqrt(pow(center - vMapDimensionX, 2) + pow(center - vMapDimensionY, 2) + pow(center - vMapDimensionZ, 2));
float distPercent = dist / max;
char density = (distPercent < 0.5) ? 127 : -127;
if(fabs(distPercent - 0.5) < minDist) {
float isoDensity = fabs(distPercent - 0.5)/minDist * 125.0;
if (distPercent < 0.5)
density = MAX(1, isoDensity);
else
density = MIN(-1,-isoDensity);
}
[voxelMap setVoxel:density x:x y:y z:z];
}
[voxelMap calcIso];
A simple terrain
I'm using a simple height map for this example. The values are than mapped like a "bar chart" in the voxel map.
for(int z = 0; z < vMapDimensionZ; z++)
for(int x = 0; x < vMapDimensionX; x++) {
float zPercent = (float)z / (float)vMapDimensionZ;
float xPercent = (float)x / (float)vMapDimensionX;
float f1 = ( sinf( zPercent * 8 * M_PI ) * 0.4 + 0.5 ) * (blockResolution * 5) ;
float f2 = ( sinf( xPercent * 10 * M_PI ) * 0.4 + 0.5 ) * (maxHeight / 5) ;
float f3 = (cosf(xPercent * zPercent * 8 * M_PI ) * 0.4 + 0.5) * (maxHeight / 5) ;
float f4 = ( sinf( pow(zPercent, xPercent) * 8 * M_PI ) * 0.4 + 0.5 ) * (blockResolution * 5) ;
float f5 = ( cosf( M_PI / tanf(zPercent) * 8 * M_PI ) * 0.4 + 1.5 ) * (blockResolution * 5) ;
float result = f5/5 + f1 + f2 - f3 + f4;
field[x][z] = result;
}
Here is a short video of the terrain:
YAOGL: Voxel Cell
A quick example of a voxel cell consisting of 32.000 samples rendered in real-time:
For reasons of simplicity the cell was sliced over the z-axis.
The voxel cell is rendered in a separate coordinate system and can be manipulated like any other object.
YAOGL Bones and Joints
You can now optionally add skeletal-data to your model. Bones (represented as matrices in modelspace) and Joints (as axis with head pitch and roll) are handled in vertex and geometry units of the GPU.
NSString *modelFile = @"armatureProbe"; NSString *ingredientName = @"probe"; YAIngredient *ingredient = [world createIngredient:ingredientName]; [ingredient setModel:modelFile]; [world addShapeShifter:modelFile];
The shape-shifter template will than connect itself to every instantiation of the inhered model, creating a copy of the default pose.
For example to access your “shape-shifting” data as joints use:
NSMutableDictionary* joints = [probeImp joints]; YAShaper* upperBone = [joints objectForKey:@"upperBone"];
Movements can be created (as usual) by animation-objects or with a json stream (for example from kinect or openSim)
{
"Name": "upperBone",
"Id": 1,
"Parent": 0,
"Joint": [ 0.000000, -0.000000, 1.015570 ],
"Quaternion": [ 0.000000, 0.000000, 0.000000, 1.000000],
"Bone": [ 1.000000, 0.000000, 0.000000, 0.000000,
0.000000, 1.000000, 0.000000, 0.000000,
0.000000, 0.000000, 1.000000, 0.000000,
0.000000, 0.000000, -0.000000, 1.000000
]
}
Here is an unrelaistic example from my unit tests where the pitch and roll of a joint are simultaneously modified.



