Skip to content
anbuf edited this page Jul 13, 2013 · 19 revisions

This little tutorial will guide you through the very first steps towards using ShadingZen in your project. We will clone the project's repo at GitHub, create a new Android activity and reference ShadingZen from that activity.

You can clone the ShadingZen_HelloWorld repository as this guide is a walkthrough for that example.

Downloading the source code

ShadingZen has no binary distribution at the moment. ShandingZen's code is the best documentation you can find out there, always ask for the source code of the libraries your using in your software! Before proceeding please read the GitHub's excellent guide on how to fork a repo.

To clone the project into your eclipse workspace:

git clone https://github.com/{your-username}/ShadingZen.git
# Clones your fork of the repo into the current directory in terminal

By following the fork-clone procedure you can also contribute back to ShadingZen with you changes by sending a pull request

Building with Maven

The most easy way to build ShadingZen is to use Maven. You can also create a new android project and import the files but it is a long road. For this guide we will assume we are just interested in building the library apk with Maven and then use it from eclipse. Download and install Maven before proceeding.

To build ShadingZen run the following command to execute the maven build:

mvn clean install

To build and deploy the examples run the following in the given example directory:

mvn clean install android:deploy

Once the library has been installed into Maven repository add the following dependency to your project:

<dependency>
        <groupId>org.traxnet</groupId>
        <artifactId>shadingzen</artifactId>
        <version>1.0-beta2-SNAPSHOT</version>
        <type>apklib</type>
    </dependency>

Hello world activity

Create a new Android Application, you can change some options accordingly but we are choosing a Blank Activity:

We need to add a reference to our previously clone ShadingZen project. Open the Activity project properties (not the ShadingZen project properties) and select Java Build Path, add a reference to the ShadingZen apk.

You need to add a reference here to:

Open the file res/layout/activity_main.xml in xml mode. Remove the TexView and any other UI component besides the root RelativeLayout and add a new RelativeLayout with an id (android:id="@+id/fullscreen_content"), the file contents should be something similar to this:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity"
>

<RelativeLayout
    android:id="@+id/fullscreen_content"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:gravity="center"
    android:keepScreenOn="true"
    android:textColor="#33b5e5"
    android:textSize="50sp"
    android:textStyle="bold" />

</RelativeLayout>

It now time to add some setup code to create a GLSurfaceView, the engine renderer and wire everything. ShadingZen comes with a default GLSurfaceView called EngineGLSurfaceView, use it unless you need advance features.

Next step requires us to open MainActivity.java and modify the class to something similar to this:

package com.example.shadingzen_helloworld;

import org.traxnet.shadingzen.core.EgineGLSurfaceView;
import org.traxnet.shadingzen.core.Renderer;

import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
import android.widget.RelativeLayout;
import com.example.shadingzen_helloworld.R;

public class MainActivity extends Activity {
EgineGLSurfaceView _surfaceView;
Renderer _openglRenderer;

@Override
protected void onCreate(Bundle savedInstanceState) {
	super.onCreate(savedInstanceState);
	setContentView(R.layout.activity_main);
	
	RelativeLayout layout = (RelativeLayout) findViewById(R.id.fullscreen_content);
	
	RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.MATCH_PARENT, RelativeLayout.LayoutParams.MATCH_PARENT);   
            // Create the renderer thread and the surface view we will drawing to
	_openglRenderer = new org.traxnet.shadingzen.core.Renderer(this);
    _surfaceView = new EgineGLSurfaceView(this, _openglRenderer);
    
    layout.addView(_surfaceView, params);
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
	// Inflate the menu; this adds items to the action bar if it is present.
	getMenuInflater().inflate(R.menu.activity_main, menu);
	return true;
}

}

At this point we should be able to run the application in our prefered android device supporting OpenGL 2.0 or with the emulator (OpenGL 2.0 within the emulator requires the very lastest platform tools and a emulator's host machine with a GPU). Since there are not objects to be drawn the screen will be black.

Adding something to the screen

Download this image:

and this 3D mesh file:

And drop them into a new folder called raw within the res folder of the HelloWorld Activity we are creating.

ShadingZen offer an abstract class called GameInfo with basic glue for game logic, user input handling and scene drawing. We are going now to create a derived class and implement the required methods for our little Hello World application.

Crate a new class derived from org.traxnet.shadingzen.core.GameInfo which implements InputController (name it HelloWorldGameInfo):

Add the following protected members to it:

protected Scene _gameScene;
protected Camera _currentCamera;

ShadingZen needs a scene and a camera, we will be instate both at HelloWorldGameInfo constructor:

_gameScene = new Scene();
Engine.getSharedInstance().pushScene(_gameScene);
    
    
 _currentCamera = new Camera();
_currentCamera.setValues(new Vector3(0.0f, 0.0f, -8.0f), 1.5f, 4.0f/3.0f, 1.f, 200.0f);
    
// Setup the engine to use the view's size as the OpenGL viewport
_currentCamera.setViewportSize(Engine.getSharedInstance().getViewWidth(), Engine.getSharedInstance().getViewHeight());

Engine.getSharedInstance().setCurrentCamera(_currentCamera);
Engine.getSharedInstance().getRenderService().setClearColor(new Vector4(1.0f, 1.0f, 1.0f, 1.f));

Its time to load the res/raw/cubetex02.png and res/raw/inflated_cube2.obj files we added to the project. To do that we need to create a class derived from Actor. Actor is the base class for all 3D objects in ShadingZen. Its an abstract class with some basic logic for position, rotation and rendering. Its counter part for 2D objects is Node2d.

Create a new class named TestCube derived from org.traxnet.shadingzen.core.Actor with the following code:

public class TestCube extends Actor {
    OBJMesh _mesh;
    ShadersProgram _program;
    Renderer _openglRenderer;
    BitmapTexture _texture;
    float _time = 0.f;

public TestCube(){
    _mesh = (OBJMesh) ResourcesManager.getSharedInstance().factory(OBJMesh.class, this, "cubletable_"+UUID.randomUUID().toString(), R.raw.inflated_cube);


    _program = (ShadersProgram)ResourcesManager.getSharedInstance().factory(ShadersProgram.class, (Entity)this, "PieceShader1", 0);   
    if(!_program.isProgramDefined()){
        _program.setName("PieceShader1");
        _program.attachVertexShader(ResourcesManager.getSharedInstance().loadResourceString(R.raw.shader_simple_vertex));
        _program.attachFragmentShader(ResourcesManager.getSharedInstance().loadResourceString(R.raw.shader_simple_fragment));
        _program.setProgramsDefined();
    }
    _mesh.attachProgram(_program);
    BitmapTexture.Parameters params = new BitmapTexture.Parameters();
    _texture = (BitmapTexture) ResourcesManager.getSharedInstance().factory(BitmapTexture.class, (Entity)this, "cubletableTexture_"+UUID.randomUUID().toString(), R.raw.cubetext02, params);
}

@Override
protected void onUpdate(float deltaTime) {
    _time += deltaTime;

}

@Override
public void onDraw(RenderService renderer) throws Exception {
    // Send down a render task to the renderer. This RenderTask handles rendering of OBJMeshes
    RenderModelTask task = RenderModelTask.buildTask(_program, _mesh, this.getWorldModelMatrix(), _texture);
    
    float r = FloatMath.cos(_time);
    float g = FloatMath.sin(_time*0.4f);
    task.setDiffuseColor(r, g, 0.3f, 1.f);
    task.setAmbientColor(0.2f, 0.2f, 0.2f, 0.f);

    renderer.addRenderTask(task);

}

@Override
public void onLoad() {


}

@Override
public void onUnload() {
    

}

}

Go back to MainActivity.java code and add the following private method:

protected void loadGameInfo(){
    Engine engine = Engine.getSharedInstance(); // Singleton!
    GameInfo gameInfo = new HelloWorldGameInfo();
    
    engine.pushInputController((InputController) gameInfo);
    gameInfo.onGameStart();
    engine.setGameInfo(gameInfo);
}

And a onPostCreate method:

@Override
protected void onPostCreate(Bundle savedInstanceState) {
    super.onPostCreate(savedInstanceState);
    
    loadGameInfo();
}

And go back to HelloWorldGameInfo.java and modify its onGameStart method as follows:

@Override
public void onGameStart() {
    // Spawn a new entity of type TestCube
    _gameScene.spawn(TestCube.class, null, "TestCube01");
}

Launch the example in your device or the emulator and something similar should appear:

Next steps

Read the library code Luke!

Clone this wiki locally