void *ThreeDeeApp (void *param)
{
	queue *fifo;
	int msg, buff = 0;
	fifo = (queue *)param;
	
	float Yrotation = 0;
	assets = new Obj3d(true);
	
	EGLinit(eglDisplay, eglSurface);

	if (1==preRender())
	{
		EGLdeinit(eglDisplay);
		exit(1);
	}

	assets->start(g_hTXShaderProgram, "resources/models/tumbler/BatMobil.obj", *assets);

    if(!assets->getScene())
	{
		printf("scene could not be loaded\n");	
		exit(1);
	}

	printf("scene loaded\n");
	
	for (;;)
	{
		if(!fifo->empty)
		{
			pthread_mutex_lock(fifo->mut);
			queueDel(fifo, &msg);
			pthread_mutex_unlock(fifo->mut);
			pthread_cond_signal(fifo->notFull);
			//printf("3D app: received %i\n", msg);
		}
		if (msg != buff)
		{
			Yrotation = msg - buff;
			buff = msg;
			Render(assets, 0, Yrotation*3, 0, 0);
		} else 
		{
			Render(assets, 0, 0, 0, 0);	
		}
		Yrotation = 0;
		//msg=0;

		eglSwapBuffers(eglDisplay, eglSurface);
	}

	RenderCleanup(assets);
	
	// cleanup
	DestroyShaders();
	EGLdeinit(eglDisplay);

	return (NULL);
}
avtDataObject_p
IceTNetworkManager::Render(
    bool checkThreshold, intVector networkIds,
    bool getZBuffer, int annotMode, int windowID,
    bool leftEye)
{
    int t0 = visitTimer->StartTimer();
    DataNetwork *origWorkingNet = workingNet;
    avtDataObject_p retval;

    EngineVisWinInfo &viswinInfo = viswinMap[windowID];
    viswinInfo.markedForDeletion = false;
    VisWindow *viswin = viswinInfo.viswin;
    std::vector<avtPlot_p>& imageBasedPlots = viswinInfo.imageBasedPlots;

    renderings = 0;

    TRY
    {
        this->StartTimer();

        RenderSetup(windowID, networkIds, getZBuffer,
            annotMode, leftEye, checkThreshold);

        bool plotDoingTransparencyOutsideTransparencyActor = false;
        for(size_t i = 0 ; i < networkIds.size() ; i++)
        {
            workingNet = NULL;
            UseNetwork(networkIds[i]);
            if(this->workingNet->GetPlot()->ManagesOwnTransparency())
            {
                plotDoingTransparencyOutsideTransparencyActor = true;
            }
        }
        workingNet = NULL;

        // We can't easily figure out a compositing order, which IceT requires
        // in order to properly composite transparent geometry.  Thus if there
        // is some transparency, fallback to our parent implementation.
        avtTransparencyActor* trans = viswin->GetTransparencyActor();
        bool transparenciesExist = trans->TransparenciesExist()
                           ||  plotDoingTransparencyOutsideTransparencyActor;
        if (transparenciesExist)
        {
            debug2 << "Encountered transparency: falling back to old "
                      "SR / compositing routines." << std::endl;

            retval = NetworkManager::RenderInternal();
        }
        else
        {
            bool needZB = !imageBasedPlots.empty() ||
                          renderState.shadowMap  ||
                          renderState.depthCues;

            // Confusingly, we need to set the input to be *opposite* of what VisIt
            // wants.  This is due to (IMHO) poor naming in the IceT case; on the
            // input side:
            //     ICET_DEPTH_BUFFER_BIT set:     do Z-testing
            //     ICET_DEPTH_BUFFER_BIT not set: do Z-based compositing.
            // On the output side:
            //     ICET_DEPTH_BUFFER_BIT set:     readback of Z buffer is allowed
            //     ICET_DEPTH_BUFFER_BIT not set: readback of Z does not work.
            // In VisIt's case, we calculated a `need Z buffer' predicate based
            // around the idea that we need the Z buffer to do Z-compositing.
            // However, IceT \emph{always} needs the Z buffer internally -- the
            // flag only differentiates between `compositing' methodologies
            // (painter-style or `over' operator) on input.
            GLenum inputs = ICET_COLOR_BUFFER_BIT;
            GLenum outputs = ICET_COLOR_BUFFER_BIT;
            // Scratch all that, I guess.  That might be the correct way to go
            // about things in the long run, but IceT only gives us back half an
            // image if we don't set the depth buffer bit.  The compositing is a
            // bit wrong, but there's not much else we can do..
            // Consider removing the `hack' if a workaround is found.
            if (/*hack*/true/*hack*/) // || !this->MemoMultipass(viswin))
            {
                inputs |= ICET_DEPTH_BUFFER_BIT;
            }
            if(needZB)
            {
                outputs |= ICET_DEPTH_BUFFER_BIT;
            }
            ICET(icetInputOutputBuffers(inputs, outputs));

            // If there is a backdrop image, we need to tell IceT so that it can
            // composite correctly.
            if(viswin->GetBackgroundMode() != AnnotationAttributes::Solid)
            {
                ICET(icetEnable(ICET_CORRECT_COLORED_BACKGROUND));
            }
            else
            {
                ICET(icetDisable(ICET_CORRECT_COLORED_BACKGROUND));
            }

            if (renderState.renderOnViewer)
            {
                RenderCleanup();
                avtDataObject_p dobj = NULL;
                CATCH_RETURN2(1, dobj);
            }

            debug5 << "Rendering " << viswin->GetNumPrimitives()
                   << " primitives." << endl;

            int width, height, width_start, height_start;
            // This basically gets the width and the height.
            // The distinction is for 2D rendering, where we only want the
            // width and the height of the viewport.
            viswin->GetCaptureRegion(width_start, height_start, width, height,
                                     renderState.viewportedMode);

            this->TileLayout(width, height);

            CallInitializeProgressCallback(this->RenderingStages());

            // IceT mode is different from the standard network manager; we don't
            // need to create any compositor or anything: it's all done under the
            // hood.
            // Whether or not to do multipass rendering (opaque first, translucent
            // second) is all handled in the callback; from our perspective, we
            // just say draw, read back the image, and post-process it.

            // IceT sometimes omits large parts of Curve plots when using the
            // REDUCE strategy. Use a different compositing strategy for Curve
            // plots to avoid the problem.
            if(viswin->GetWindowMode() == WINMODE_CURVE)
                ICET(icetStrategy(ICET_STRATEGY_VTREE));
            else
                ICET(icetStrategy(ICET_STRATEGY_REDUCE));

            ICET(icetDrawFunc(render));
            ICET(icetDrawFrame());

            // Now that we're done rendering, we need to post process the image.
            debug3 << "IceTNM: Starting readback." << std::endl;
            avtImage_p img = this->Readback(viswin, needZB);

            // Now its essentially back to the same behavior as our parent:
            //  shadows
            //  depth cueing
            //  post processing

            if (renderState.shadowMap)
                this->RenderShadows(img);

            if (renderState.depthCues)
                this->RenderDepthCues(img);

            // If the engine is doing more than just 3D annotations,
            // post-process the composited image.
            RenderPostProcess(img);

            CopyTo(retval, img);
        }

        RenderCleanup();
    }
    CATCHALL
    {
        RenderCleanup();
        RETHROW;
    }
    ENDTRY

    workingNet = origWorkingNet;
    visitTimer->StopTimer(t0, "Ice-T Render");
    return retval;
}