• Benvenuto in Making Videogames!
  • Condividi la tua passione!
  • Crea il tuo Videogioco!
Benvenuto ospite! Login Registrati



Valutazione discussione:
  • 1 voto(i) - 5 media
  • 1
  • 2
  • 3
  • 4
  • 5
Title: Tutorial 22 - Material Viewer
Modi discussione
#1
Tutorial 22: Material Viewer

[Immagine: 022shot.jpg]

Questo esempio può essere usato per fare giocare con le impostazioni dei materiali e vederne subito i risultati. In questo esempio ci riferiamo solo ai materiali di tipo non-shader.
Abbiamo due nodi di scena per rendere più facilmente le differenze durante le modifiche ai materiali. Inoltre abbiamo un nodo lightscenenode ed è possibile impostare le variabili globali dell'ambiente.
Codice PHP:
#include <irrlicht.h>
#include "driverChoice.h"

using namespace irr;

#ifdef _MSC_VER
#pragma comment(lib, "Irrlicht.lib")
#endif 
Le variabili dentro il namespace vuoto sono globali e ristrette al solo file in uso.
Codice PHP:
namespace
{
    const 
wchar_t* const DriverTypeNames[] =
    {
        
L"NULL",
        
L"SOFTWARE",
        
L"BURNINGSVIDEO",
        
L"DIRECT3D8",
        
L"DIRECT3D9",
        
L"OPENGL",
        
0,
    };

    
// For the gui id's
    
enum EGUI_IDS
    
{
        
GUI_ID_OPEN_TEXTURE 1,
        
GUI_ID_QUIT,
        
GUI_ID_MAX
    
};

    
// Name used in texture selection to clear the textures on the node
    
const core::stringw CLEAR_TEXTURE L"CLEAR texture";

    
// some useful color constants
    
const video::SColor SCOL_BLACK     video::SColor(2550,   0,   0);
    const 
video::SColor SCOL_BLUE      video::SColor(2550,   0,  255);
    const 
video::SColor SCOL_CYAN      video::SColor(2550,  255255);
    const 
video::SColor SCOL_GRAY      video::SColor(255128,128128);
    const 
video::SColor SCOL_GREEN     video::SColor(2550,  255,  0);
    const 
video::SColor SCOL_MAGENTA   video::SColor(2552550,  255);
    const 
video::SColor SCOL_RED       video::SColor(2552550,   0);
    const 
video::SColor SCOL_YELLOW    video::SColor(2552552550);
    const 
video::SColor SCOL_WHITE     video::SColor(255255255255);
};  
// namespace 
Ritorniamo il nuovo numero unico per ciascuna chiamata.
Codice PHP:
s32 makeUniqueId()
{
    static 
int unique GUI_ID_MAX;
    ++
unique;
    return 
unique;

Trovo quale tipo di vertice è richiesto dal materiale in input.
Codice PHP:
video::E_VERTEX_TYPE getVertexTypeForMaterialType(video::E_MATERIAL_TYPE materialType)
{
    
using namespace video;

    switch ( 
materialType )
    {
        case 
EMT_SOLID:
            return 
EVT_STANDARD;

        case 
EMT_SOLID_2_LAYER:
            return 
EVT_STANDARD;

        case 
EMT_LIGHTMAP:
        case 
EMT_LIGHTMAP_ADD:
        case 
EMT_LIGHTMAP_M2:
        case 
EMT_LIGHTMAP_M4:
        case 
EMT_LIGHTMAP_LIGHTING:
        case 
EMT_LIGHTMAP_LIGHTING_M2:
        case 
EMT_LIGHTMAP_LIGHTING_M4:
            return 
EVT_2TCOORDS;

        case 
EMT_DETAIL_MAP:
            return 
EVT_2TCOORDS;

        case 
EMT_SPHERE_MAP:
            return 
EVT_STANDARD;

        case 
EMT_REFLECTION_2_LAYER:
            return 
EVT_2TCOORDS;

        case 
EMT_TRANSPARENT_ADD_COLOR:
            return 
EVT_STANDARD;

        case 
EMT_TRANSPARENT_ALPHA_CHANNEL:
            return 
EVT_STANDARD;

        case 
EMT_TRANSPARENT_ALPHA_CHANNEL_REF:
            return 
EVT_STANDARD;

        case 
EMT_TRANSPARENT_VERTEX_ALPHA:
            return 
EVT_STANDARD;

        case 
EMT_TRANSPARENT_REFLECTION_2_LAYER:
            return 
EVT_2TCOORDS;

        case 
EMT_NORMAL_MAP_SOLID:
        case 
EMT_NORMAL_MAP_TRANSPARENT_ADD_COLOR:
        case 
EMT_NORMAL_MAP_TRANSPARENT_VERTEX_ALPHA:
        case 
EMT_PARALLAX_MAP_SOLID:
        case 
EMT_PARALLAX_MAP_TRANSPARENT_ADD_COLOR:
        case 
EMT_PARALLAX_MAP_TRANSPARENT_VERTEX_ALPHA:
            return 
EVT_TANGENTS;

        case 
EMT_ONETEXTURE_BLEND:
            return 
EVT_STANDARD;

        case 
EMT_FORCE_32BIT:
            return 
EVT_STANDARD;
    }
    return 
EVT_STANDARD;

Controlli della nostra GUI per modificare i valori.
Codice PHP:
class CColorControl : public gui::IGUIElement
{
public:
    
// Constructor
    
CColorControl(gui::IGUIEnvironmentguiEnv, const core::position2d<s32> & pos, const wchar_t *textIGUIElementparents32 id=-)
        : 
gui::IGUIElement(gui::EGUIET_ELEMENTguiEnvparent,idcore::rects32 >(pospos+core::dimension2d<s32>(8075)))
        , 
DirtyFlag(true)
        , 
ColorStatic(0)
        , 
EditAlpha(0)
        , 
EditRed(0)
        , 
EditGreen(0)
        , 
EditBlue(0)
    {
        
using namespace gui;
        
ButtonSetId makeUniqueId();

        const 
core::rects32 rectControls(0,0,AbsoluteRect.getWidth(),AbsoluteRect.getHeight() );
        
IGUIStaticText groupElement guiEnv->addStaticText (L""rectControlstruefalsethis, -1false);
        
groupElement->setNotClipped(true);

        
guiEnv->addStaticText (textcore::rect<s32>(0,0,80,15), falsefalsegroupElement, -1false);

        
EditAlpha addEditForNumbers(guiEnvcore::position2d<s32>(0,15), L"a", -1groupElement );
        
EditRed addEditForNumbers(guiEnvcore::position2d<s32>(0,30), L"r", -1groupElement );
        
EditGreen addEditForNumbers(guiEnvcore::position2d<s32>(0,45), L"g", -1groupElement );
        
EditBlue addEditForNumbers(guiEnvcore::position2d<s32>(0,60), L"b", -1groupElement );

        
ColorStatic guiEnv->addStaticText (L""core::rect<s32>(60,15,80,75), truefalsegroupElement, -1true);

        
guiEnv->addButton (core::rect<s32>(60,35,80,50), groupElementButtonSetIdL"set");
        
SetEditsFromColor(Color);
    }

    
// event receiver
    
virtual bool OnEvent(const SEvent &event)
    {
        if ( 
event.EventType != EET_GUI_EVENT )
            return 
false;

        if ( 
event.GUIEvent.Caller->getID() == ButtonSetId && event.GUIEvent.EventType == gui::EGET_BUTTON_CLICKED )
        {
            
Color GetColorFromEdits();
            
SetEditsFromColor(Color);
        }

        return 
false;
    }

    
// set the color values
    
void setColor(const video::SColorcol)
    {
        
DirtyFlag true;
        
Color col;
        
SetEditsFromColor(Color);
    }

    
// get the color values
    
const video::SColorgetColor() const
    {
        return 
Color;
    }

    
// To reset the dirty flag
    
void resetDirty()
    {
        
DirtyFlag false;
    }

    
// when the color was changed the dirty flag is set
    
bool isDirty() const
    {
        return 
DirtyFlag;
    };

protected:

    
// Add a staticbox for a description + an editbox so users can enter numbers
    
gui::IGUIEditBoxaddEditForNumbers(gui::IGUIEnvironmentguiEnv, const core::position2d<s32> & pos, const wchar_t *texts32 idgui::IGUIElement parent)
    {
        
using namespace gui;

        
core::rects32 rect(pospos+core::dimension2d<s32>(1015));
        
guiEnv->addStaticText (textrectfalsefalseparent, -1false);
        
rect += core::position2d<s32>( 20);
        
rect.LowerRightCorner.+= 20;
        
gui::IGUIEditBoxedit guiEnv->addEditBox(L"0"recttrueparentid);
        return 
edit;
    }

    
// Get the color value from the editfields
    
video::SColor GetColorFromEdits()
    {
        
video::SColor col;

        if (
EditAlpha)
        {
            
u32 alpha core::strtoul10(core::stringc(EditAlpha->getText()).c_str());
            if (
alpha 255)
                
alpha 255;
            
col.setAlpha(alpha);
        }

        if (
EditRed)
        {
            
u32 red core::strtoul10(core::stringc(EditRed->getText()).c_str());
            if (
red 255)
                
red 255;
            
col.setRed(red);
        }

        if (
EditGreen)
        {
            
u32 green core::strtoul10(core::stringc(EditGreen->getText()).c_str());
            if (
green 255)
                
green 255;
            
col.setGreen(green);
        }

        if (
EditBlue)
        {
            
u32 blue core::strtoul10(core::stringc(EditBlue->getText()).c_str());
            if (
blue 255)
                
blue 255;
            
col.setBlue(blue);
        }

        return 
col;
    }

    
// Fill the editfields with the value for the given color
    
void SetEditsFromColor(video::SColor col)
    {
        
DirtyFlag true;
        if ( 
EditAlpha )
            
EditAlpha->setTextcore::stringw(col.getAlpha()).c_str() );
        if ( 
EditRed )
            
EditRed->setTextcore::stringw(col.getRed()).c_str() );
        if ( 
EditGreen )
            
EditGreen->setTextcore::stringw(col.getGreen()).c_str() );
        if ( 
EditBlue )
            
EditBlue->setTextcore::stringw(col.getBlue()).c_str() );
        if ( 
ColorStatic )
            
ColorStatic->setBackgroundColor(col);
    }

private:

    
bool DirtyFlag;
    
video::SColor Color;
    
s32 ButtonSetId;
    
gui::IGUIStaticText ColorStatic;
    
gui::IGUIEditBox EditAlpha;
    
gui::IGUIEditBox EditRed;
    
gui::IGUIEditBox EditGreen;
    
gui::IGUIEditBox EditBlue;
}; 
Controlli della GUI per variare tutti colori che tipicamente sono usati nei materiali e nelle luci
Codice PHP:
class CAllColorsControl : public gui::IGUIElement
{
public:
    
// Constructor
    
CAllColorsControl(gui::IGUIEnvironmentguiEnv, const core::position2d<s32> & pos, const wchar_t descriptionbool hasEmissiveIGUIElementparents32 id=-1)
        : 
gui::IGUIElement(gui::EGUIET_ELEMENTguiEnvparent,idcore::rect<s32>(pos,pos+core::dimension2d<s32>(60,250)))
        , 
ControlAmbientColor(0), ControlDiffuseColor(0), ControlSpecularColor(0), ControlEmissiveColor(0)
    {
        
core::rect<s32rect(006015);
        
guiEnv->addStaticText (descriptionrectfalsefalsethis, -1false);
        
createColorControls(guiEnvcore::position2d<s32>(015), hasEmissive);
    }

    
// Destructor
    
virtual ~CAllColorsControl()
    {
        
ControlAmbientColor->drop();
        
ControlDiffuseColor->drop();
        if ( 
ControlEmissiveColor )
            
ControlEmissiveColor->drop();
        
ControlSpecularColor->drop();
    }

    
// Set the color values to those within the material
    
void setColorsToMaterialColors(const video::SMaterial material)
    {
        
ControlAmbientColor->setColor(material.AmbientColor);
        
ControlDiffuseColor->setColor(material.DiffuseColor);
        
ControlEmissiveColor->setColor(material.EmissiveColor);
        
ControlSpecularColor->setColor(material.SpecularColor);
    }

    
// Update all changed colors in the material
    
void updateMaterialColors(video::SMaterial material)
    {
        if ( 
ControlAmbientColor->isDirty() )
            
material.AmbientColor ControlAmbientColor->getColor();
        if ( 
ControlDiffuseColor->isDirty() )
            
material.DiffuseColor ControlDiffuseColor->getColor();
        if ( 
ControlEmissiveColor->isDirty() )
            
material.EmissiveColor ControlEmissiveColor->getColor();
        if ( 
ControlSpecularColor->isDirty() )
            
material.SpecularColor ControlSpecularColor->getColor();
    }

    
// Set the color values to those from the light data
    
void setColorsToLightDataColors(const video::SLight lightData)
    {
        
ControlAmbientColor->setColor(lightData.AmbientColor.toSColor());
        
ControlAmbientColor->setColor(lightData.DiffuseColor.toSColor());
        
ControlAmbientColor->setColor(lightData.SpecularColor.toSColor());
    }

    
// Update all changed colors in the light data
    
void updateLightColors(video::SLight lightData)
    {
        if ( 
ControlAmbientColor->isDirty() )
            
lightData.AmbientColor video::SColorfControlAmbientColor->getColor() );
        if ( 
ControlDiffuseColor->isDirty() )
            
lightData.DiffuseColor video::SColorfControlDiffuseColor->getColor() );
        if ( 
ControlSpecularColor->isDirty() )
            
lightData.SpecularColor video::SColorf(ControlSpecularColor->getColor() );
    }

    
// To reset the dirty flags
    
void resetDirty()
    {
        
ControlAmbientColor->resetDirty();
        
ControlDiffuseColor->resetDirty();
        
ControlSpecularColor->resetDirty();
        if ( 
ControlEmissiveColor )
            
ControlEmissiveColor->resetDirty();
    }

protected:
    
void createColorControls(gui::IGUIEnvironmentguiEnv, const core::position2d<s32> & posbool hasEmissive)
    {
        
ControlAmbientColor = new CColorControlguiEnvposL"ambient"this);
        
ControlDiffuseColor = new CColorControlguiEnvpos core::position2d<s32>(075), L"diffuse"this );
        
ControlSpecularColor = new CColorControlguiEnvpos core::position2d<s32>(0150), L"specular"this );
        if ( 
hasEmissive )
        {
            
ControlEmissiveColor = new CColorControlguiEnvpos core::position2d<s32>(0225), L"emissive"this );
        }
    }

private:
    
CColorControl*  ControlAmbientColor;
    
CColorControl*  ControlDiffuseColor;
    
CColorControl*  ControlSpecularColor;
    
CColorControl*  ControlEmissiveColor;
}; 
Controlli della GUI per fornire una selezione di texture disponibili.
Codice PHP:
class CTextureControl : public gui::IGUIElement
{
public:
    
CTextureControl(gui::IGUIEnvironmentguiEnvvideo::IVideoDriver driver, const core::position2d<s32> & posIGUIElementparents32 id=-1)
    : 
gui::IGUIElement(gui::EGUIET_ELEMENTguiEnvparent,idcore::rect<s32>(pos,pos+core::dimension2d<s32>(100,15)))
    , 
DirtyFlag(true), ComboTexture(0)
    {
        
core::rect<s32rectCombo(00AbsoluteRect.getWidth(),AbsoluteRect.getHeight());
        
ComboTexture guiEnv->addComboBox (rectCombothis);
        
updateTextures(driver);
    }

    
virtual bool OnEvent(const SEvent &event)
    {
        if ( 
event.EventType != EET_GUI_EVENT )
            return 
false;

        if ( 
event.GUIEvent.Caller == ComboTexture && event.GUIEvent.EventType == gui::EGET_COMBO_BOX_CHANGED )
        {
            
DirtyFlag true;
        }

        return 
false;
    }

    
// Workaround for a problem with comboboxes.
    // We have to get in front when the combobox wants to get in front or combobox-list might be drawn below other elements.
    
virtual bool bringToFront(IGUIElementelement)
    {
        
bool result gui::IGUIElement::bringToFront(element);
        if ( 
Parent && element == ComboTexture )
            
result &= Parent->bringToFront(this);
        return 
result;
    }

    
// return selected texturename (if any, otherwise 0)
    
const wchar_t getSelectedTextureName() const
    {
        
s32 selected ComboTexture->getSelected();
        if ( 
selected )
            return 
0;
        return 
ComboTexture->getItem(selected);
    }

    
// reset the dirty flag
    
void resetDirty()
    {
        
DirtyFlag false;
    }

    
// when the texture was changed the dirty flag is set
    
bool isDirty() const
    {
        return 
DirtyFlag;
    };

    
// Put the names of all currently loaded textures in a combobox
    
void updateTextures(video::IVideoDriver driver)
    {
        
s32 oldSelected ComboTexture->getSelected();
        
s32 selectNew = -1;
        const 
wchar_t oldTextureName 0;
        if ( 
oldSelected >= )
        {
            
oldTextureName ComboTexture->getItem(oldSelected);
        }
        
ComboTexture->clear();
        for ( 
u32 i=0driver->getTextureCount(); ++)
        {
            
video::ITexture texture driver->getTextureByIndex(i);
            
core::stringw nametexture->getName() );
            
ComboTexture->addItemname.c_str() );
            if ( 
oldTextureName && selectNew && name == oldTextureName )
                
selectNew i;
        }

        
// add another name which can be used to clear the texture
        
ComboTexture->addItemCLEAR_TEXTURE.c_str() );
        if ( 
CLEAR_TEXTURE == oldTextureName )
            
selectNew ComboTexture->getItemCount()-1;

        if ( 
selectNew >= )
            
ComboTexture->setSelected(selectNew);

        
DirtyFlag true;
    }

private:
    
bool DirtyFlag;
    
gui::IGUIComboBox ComboTexture;
}; 
Un controllo che permette di impostare alcuni valori del materiale di un meshscenenode
Codice PHP:
struct SMeshNodeControl
{
    
// constructor
    
SMeshNodeControl()
        : 
Initialized(false), Driver(0), MeshManipulator(0), SceneNode(0), SceneNode2T(0), SceneNodeTangents(0)
        , 
AllColorsControl(0), ButtonLighting(0), InfoLighting(0), ComboMaterial(0), TextureControl1(0), TextureControl2(0), ControlVertexColors(0)
    {
    }

    
// Destructor
    
virtual ~SMeshNodeControl()
    {
        if ( 
TextureControl1 )
            
TextureControl1->drop();
        if ( 
TextureControl2 )
            
TextureControl2->drop();
        if ( 
ControlVertexColors )
            
ControlVertexColors->drop();
        if ( 
AllColorsControl )
            
AllColorsControl->drop();
    }

    
void init(scene::IMeshSceneNodenodeIrrlichtDevice device, const core::position2d<s32> & pos, const wchar_t description)
    {
        if ( 
Initialized || !node || !device// initializing twice or with invalid data not allowed
            
return;

        
Driver device->getVideoDriver ();
        
gui::IGUIEnvironmentguiEnv device->getGUIEnvironment();
        
scene::ISceneManagersmgr device->getSceneManager();
        
MeshManipulator smgr->getMeshManipulator();

        
SceneNode node;
        
scene::IMeshManipulator meshManip smgr->getMeshManipulator();

        
scene::IMesh mesh2T meshManip->createMeshWith2TCoords(node->getMesh());
        
SceneNode2T smgr->addMeshSceneNode(mesh2T0, -1SceneNode->getPosition(), SceneNode->getRotation(), SceneNode->getScale() );
        
mesh2T->drop();

        
scene::IMesh meshTangents meshManip->createMeshWithTangents(node->getMesh(), falsefalsefalse);
        
SceneNodeTangents smgr->addMeshSceneNode(meshTangents0, -1
                                            
SceneNode->getPosition(), SceneNode->getRotation(), SceneNode->getScale() );
        
meshTangents->drop();

        
video::SMaterial material SceneNode->getMaterial(0);
        
material.Lighting true;
        
AllColorsControl = new CAllColorsControl(guiEnvposdescriptiontrueguiEnv->getRootGUIElement());
        
AllColorsControl->setColorsToMaterialColors(material);

        
core::rect<s32rectBtn(pos core::position2d<s32>(0320), core::dimension2d<s32>(6015));
        
ButtonLighting guiEnv->addButton (rectBtn0, -1L"Lighting");
        
ButtonLighting->setIsPushButton(true);
        
ButtonLighting->setPressed(material.Lighting);
        
core::rect<s32rectInforectBtn.LowerRightCorner.XrectBtn.UpperLeftCorner.YrectBtn.LowerRightCorner.X+40rectBtn.UpperLeftCorner.Y+15 );
        
InfoLighting guiEnv->addStaticText(L""rectInfotruefalse );
        
InfoLighting->setTextAlignment(gui::EGUIA_CENTERgui::EGUIA_CENTER );

        
core::rect<s32rectCombo(pos.XrectBtn.LowerRightCorner.Ypos.X+100rectBtn.LowerRightCorner.Y+15);
        
ComboMaterial guiEnv->addComboBox (rectCombo);
        for ( 
int i=0<= (int)video::EMT_ONETEXTURE_BLEND; ++)
        {
            
ComboMaterial->addItemcore::stringw(video::sBuiltInMaterialTypeNames[i]).c_str() );
        }
        
ComboMaterial->setSelected( (s32)material.MaterialType );

        
core::position2d<s32posTex(rectCombo.UpperLeftCorner.X,rectCombo.LowerRightCorner.Y);
        
TextureControl1 = new CTextureControl(guiEnvDriverposTexguiEnv->getRootGUIElement());
        
posTex.+= 15;
        
TextureControl2 = new CTextureControl(guiEnvDriverposTexguiEnv->getRootGUIElement());

        
core::position2d<s32posVertexColorsposTex.XposTex.15);
        
ControlVertexColors = new CColorControlguiEnvposVertexColorsL"Vertex colors"guiEnv->getRootGUIElement());

        
video::S3DVertex vertices =  (video::S3DVertex *)node->getMesh()->getMeshBuffer(0)->getVertices();
        if ( 
vertices )
        {
            
ControlVertexColors->setColor(vertices[0].Color);
        }

        
Initialized true;
    }

    
void update()
    {
        if ( !
Initialized )
            return;

        
video::SMaterial material SceneNode->getMaterial(0);
        
video::SMaterial material2T SceneNode2T->getMaterial(0);
        
video::SMaterial materialTangents SceneNodeTangents->getMaterial(0);

        
s32 selectedMaterial ComboMaterial->getSelected();
        if ( 
selectedMaterial >= (s32)video::EMT_SOLID && selectedMaterial <= (s32)video::EMT_ONETEXTURE_BLEND)
        {
            
video::E_VERTEX_TYPE vertexType getVertexTypeForMaterialType((video::E_MATERIAL_TYPE)selectedMaterial);
            switch ( 
vertexType )
            {
                case 
video::EVT_STANDARD:
                    
material.MaterialType = (video::E_MATERIAL_TYPE)selectedMaterial;
                    
SceneNode->setVisible(true);
                    
SceneNode2T->setVisible(false);
                    
SceneNodeTangents->setVisible(false);
                    break;
                case 
video::EVT_2TCOORDS:
                    
material2T.MaterialType = (video::E_MATERIAL_TYPE)selectedMaterial;
                    
SceneNode->setVisible(false);
                    
SceneNode2T->setVisible(true);
                    
SceneNodeTangents->setVisible(false);
                    break;
                case 
video::EVT_TANGENTS:
                    
materialTangents.MaterialType = (video::E_MATERIAL_TYPE)selectedMaterial;
                    
SceneNode->setVisible(false);
                    
SceneNode2T->setVisible(false);
                    
SceneNodeTangents->setVisible(true);
                    break;
            }
        }

        
updateMaterial(material);
        
updateMaterial(material2T);
        
updateMaterial(materialTangents);

        if ( 
ButtonLighting->isPressed() )
            
InfoLighting->setText(L"on");
        else
            
InfoLighting->setText(L"off");

        
AllColorsControl->resetDirty();
        
TextureControl1->resetDirty();
        
TextureControl2->resetDirty();
        
ControlVertexColors->resetDirty();
    }

    
void updateTextures()
    {
        
TextureControl1->updateTextures(Driver);
        
TextureControl2->updateTextures(Driver);
    }

protected:

    
void updateMaterial(video::SMaterial material)
    {
        
AllColorsControl->updateMaterialColors(material);
        
material.Lighting ButtonLighting->isPressed();
        if ( 
TextureControl1->isDirty() )
        {
            
material.TextureLayer[0].Texture Driver->getTextureio::path(TextureControl1->getSelectedTextureName()) );
        }
        if ( 
TextureControl2->isDirty() )
        {
            
material.TextureLayer[1].Texture Driver->getTextureio::path(TextureControl2->getSelectedTextureName()) );
        }
        if ( 
ControlVertexColors->isDirty() )
        {
            
MeshManipulator->setVertexColors (SceneNode->getMesh(), ControlVertexColors->getColor());
            
MeshManipulator->setVertexColors (SceneNode2T->getMesh(), ControlVertexColors->getColor());
            
MeshManipulator->setVertexColors (SceneNodeTangents->getMesh(), ControlVertexColors->getColor());
        }
    }

    
bool Initialized;
    
video::IVideoDriver *       Driver;
    
scene::IMeshManipulator*    MeshManipulator;
    
scene::IMeshSceneNode*      SceneNode;
    
scene::IMeshSceneNode*      SceneNode2T;
    
scene::IMeshSceneNode*      SceneNodeTangents;
    
CAllColorsControl*          AllColorsControl;
    
gui::IGUIButton *           ButtonLighting;
    
gui::IGUIStaticText*        InfoLighting;
    
gui::IGUIComboBox *         ComboMaterial;
    
CTextureControl*            TextureControl1;
    
CTextureControl*            TextureControl2;
    
CColorControl*              ControlVertexColors;
}; 
Controllo che permette di impostare il colore di uno lightscenenode.
Codice PHP:
struct SLightNodeControl
{
    
// constructor
    
SLightNodeControl() : Initialized(false), SceneNode(0), AllColorsControl(0)
    {
    }

    
virtual ~SLightNodeControl()
    {
        if ( 
AllColorsControl )
            
AllColorsControl->drop();
    }

    
void init(scene::ILightSceneNodenodegui::IGUIEnvironmentguiEnv, const core::position2d<s32> & pos, const wchar_t description)
    {
        if ( 
Initialized || !node || !guiEnv// initializing twice or with invalid data not allowed
            
return;
        
SceneNode node;
        
AllColorsControl = new CAllColorsControl(guiEnvposdescriptionfalseguiEnv->getRootGUIElement());
        const 
video::SLight lightData SceneNode->getLightData();
        
AllColorsControl->setColorsToLightDataColors(lightData);
        
Initialized true;
    }

    
void update()
    {
        if ( !
Initialized )
            return;

        
video::SLight lightData SceneNode->getLightData();
        
AllColorsControl->updateLightColors(lightData);
    }

protected:
    
bool Initialized;
    
scene::ILightSceneNodeSceneNode;
    
CAllColorsControlAllColorsControl;
}; 
Configurazioni dell'applicazione
Codice PHP:
struct SConfig
{
    
SConfig()
    : 
RenderInBackground(true)
    , 
DriverType(video::EDT_BURNINGSVIDEO)
    , 
ScreenSize(640480)
    {
    }

    
bool RenderInBackground;
    
video::E_DRIVER_TYPE DriverType;
    
core::dimension2d<u32ScreenSize;
}; 
Classe per l'applicazione principale
Codice PHP:
class CApp : public IEventReceiver
{
    
friend int main(int argcchar *argv[]);

public:
    
// constructor
    
CApp()
    : 
IsRunning(false)
    , 
Device(0)
    , 
Camera(0)
    , 
GlobalAmbient(0)
    {
    }

    
// destructor
    
~CApp()
    {
    }

    
// stop running - will quit at end of mainloop
    
void stopApp()
    {
        
IsRunning false;
    }

    
// Event handler
    
virtual bool OnEvent(const SEvent &event)
    {
        if (
event.EventType == EET_GUI_EVENT)
        {
            
gui::IGUIEnvironmentenv Device->getGUIEnvironment();

            switch(
event.GUIEvent.EventType)
            {
                case 
gui::EGET_MENU_ITEM_SELECTED:
                {
                    
gui::IGUIContextMenumenu = (gui::IGUIContextMenu*)event.GUIEvent.Caller;
                    
s32 id menu->getItemCommandId(menu->getSelectedItem());

                    switch(
id)
                    {
                        case 
GUI_ID_OPEN_TEXTURE// File -> Open Texture
                            
env->addFileOpenDialog(L"Please select a texture file to open");
                        break;
                        case 
GUI_ID_QUIT// File -> Quit
                            
stopApp();
                        break;
                    }
                }
                break;

                case 
gui::EGET_FILE_SELECTED:
                {
                    
// load the model file, selected in the file open dialog
                    
gui::IGUIFileOpenDialogdialog =
                        (
gui::IGUIFileOpenDialog*)event.GUIEvent.Caller;
                    
loadTexture(io::path(dialog->getFileName()).c_str());
                }
                break;

                default:
                break;
            }
        }

        return 
false;
    }

protected:

    
// Application initialization
    // returns true when it was successful initialized, otherwise false.
    
bool init(int argcchar *argv[])
    {
        
// ask user for driver
        
Config.DriverType=driverChoiceConsole();
        if (
Config.DriverType==video::EDT_COUNT)
            return 
false;

        
// create the device with the settings from our config
        
Device createDevice(Config.DriverTypeConfig.ScreenSize);
        if (!
Device)
            return 
false;
        
Device->setWindowCaptionDriverTypeNames[Config.DriverType] );
        
Device->setEventReceiver(this);

        
scene::ISceneManagersmgr Device->getSceneManager();
        
video::IVideoDriver driver Device->getVideoDriver ();
        
gui::IGUIEnvironmentguiEnv Device->getGUIEnvironment();

        
// set a nicer font
        
gui::IGUISkinskin guiEnv->getSkin();
        
gui::IGUIFontfont guiEnv->getFont("../../media/fonthaettenschweiler.bmp");
        if (
font)
            
skin->setFont(font);

        
// remove some alpha value because it makes those menus harder to read otherwise
        
video::SColor col3dHighLightskin->getColor(gui::EGDC_APP_WORKSPACE) );
        
col3dHighLight.setAlpha(255);
        
video::SColor colHighLightcol3dHighLight );
        
skin->setColor(gui::EGDC_HIGH_LIGHTcolHighLight );
        
skin->setColor(gui::EGDC_3D_HIGH_LIGHTcol3dHighLight );

        
// Add some textures which are useful to test material settings
        
createDefaultTextures(driver);

        
// create a menu
        
gui::IGUIContextMenu menuBar guiEnv->addMenu();
        
menuBar->addItem(L"File", -1truetrue);

        
gui::IGUIContextMenusubMenuFile menuBar->getSubMenu(0);
        
subMenuFile->addItem(L"Open texture ..."GUI_ID_OPEN_TEXTURE);
        
subMenuFile->addSeparator();
        
subMenuFile->addItem(L"Quit"GUI_ID_QUIT);

        
// a static camera
        
Camera smgr->addCameraSceneNode (0core::vector3df(000),
                                            
core::vector3df(00100),
                                            -
1);

        
// add the nodes which are used to show the materials
        
scene::IMeshSceneNodenodeL smgr->addCubeSceneNode (30.0f0, -1,
                                           
core::vector3df(-350100),
                                           
core::vector3df(000),
                                           
core::vector3df(1.0f1.0f1.0f));
        
NodeLeft.initnodeLDevicecore::position2d<s32>(10,20), L"left node" );

        
scene::IMeshSceneNodenodeR smgr->addCubeSceneNode (30.0f0, -1,
                                           
core::vector3df(350100),
                                           
core::vector3df(000),
                                           
core::vector3df(1.0f1.0f1.0f));
        
NodeRight.initnodeRDevicecore::position2d<s32>(530,20), L"right node" );

        
// add one light
        
scene::ILightSceneNodenodeLight smgr->addLightSceneNode(0core::vector3df(000),
                                                        
video::SColorf(1.0f1.0f1.0f),
                                                        
100.0f);
        
LightControl.init(nodeLightguiEnvcore::position2d<s32>(270,20), L"light" );

        
// one large cube around everything. That's mainly to make the light more obvious.
        
scene::IMeshSceneNodebackgroundCube smgr->addCubeSceneNode (200.0f0, -1core::vector3df(000),
                                           
core::vector3df(4500),
                                           
core::vector3df(1.0f1.0f1.0f));
        
backgroundCube->getMaterial(0).BackfaceCulling false;         // we are within the cube, so we have to disable backface culling to see it
        
backgroundCube->getMaterial(0).EmissiveColor.set(255,50,50,50); // we keep some self lighting to keep texts visible

        // set the ambient light value
        
GlobalAmbient = new CColorControlguiEnvcore::position2d<s32>(270300), L"global ambient"guiEnv->getRootGUIElement());
        
GlobalAmbient->setColorsmgr->getAmbientLight().toSColor() );

        return 
true;
    }

    
// Update one frame
    
bool update()
    {
        
using namespace irr;

        
video::IVideoDrivervideoDriver =  Device->getVideoDriver();
        if ( !
Device->run() )
            return 
false;

        if ( 
Device->isWindowActive() || Config.RenderInBackground )
        {
            
gui::IGUIEnvironmentguiEnv Device->getGUIEnvironment();
            
scene::ISceneManagersmgr Device->getSceneManager();
            
gui::IGUISkin skin guiEnv->getSkin();

            
// update our controls
            
NodeLeft.update();
            
NodeRight.update();
            
LightControl.update();

            
// update ambient light settings
            
if ( GlobalAmbient->isDirty() )
            {
                
smgr->setAmbientLightGlobalAmbient->getColor() );
                
GlobalAmbient->resetDirty();
            }

            
// draw everything
            
video::SColor bkColorskin->getColor(gui::EGDC_APP_WORKSPACE) );
            
videoDriver->beginScene(truetruebkColor);

            
smgr->drawAll();
            
guiEnv->drawAll();

            
videoDriver->endScene();
        }

        return 
true;
    }

    
// Run the application. Our main loop.
    
void run()
    {
        
IsRunning true;

        if ( !
Device )
            return;

        
// main application loop
        
while(IsRunning)
        {
            if ( !
update() )
                break;

            
Device->sleep);
        }
    }

    
// Close down the application
    
void quit()
    {
        
IsRunning false;
        
GlobalAmbient->drop();
        
GlobalAmbient NULL;
        if ( 
Device )
        {
            
Device->closeDevice();
            
Device->drop();
            
Device NULL;
        }
    }

    
// Create some useful textures.
    // Note that the function put readability over speed, you shouldn't use setPixel at runtime but for initialization it's nice.
    
void createDefaultTextures(video::IVideoDriver driver)
    {
        const 
u32 width 256;
        const 
u32 height 256;
        
video::IImage imageA8R8G8B8 driver->createImage (video::ECF_A8R8G8B8core::dimension2d<u32>(widthheight));
        if ( !
imageA8R8G8B8 )
            return;
        const 
u32 pitch imageA8R8G8B8->getPitch();

        
// some nice square-pattern with 9 typical colors
        
for ( u32 y 0height; ++ )
        {
            for ( 
u32 x 0pitch; ++)
            {
                if ( 
height/)
                {
                    if ( 
width/)
                        
imageA8R8G8B8->setPixel (xySCOL_BLACK);
                    else if ( 
2*width/)
                        
imageA8R8G8B8->setPixel (xySCOL_BLUE);
                    else
                        
imageA8R8G8B8->setPixel (xySCOL_CYAN);
                }
                else if ( 
2*height/)
                {
                    if ( 
width/)
                        
imageA8R8G8B8->setPixel (xySCOL_GRAY);
                    else if ( 
2*width/)
                        
imageA8R8G8B8->setPixel (xySCOL_GREEN);
                    else
                        
imageA8R8G8B8->setPixel (xySCOL_MAGENTA);
                }
                else
                {
                    if ( 
width/)
                        
imageA8R8G8B8->setPixel (xySCOL_RED);
                    else if ( 
2*width/)
                        
imageA8R8G8B8->setPixel (xySCOL_YELLOW);
                    else
                        
imageA8R8G8B8->setPixel (xySCOL_WHITE);
                }
            }
        }
        
driver->addTexture (io::path("CARO_A8R8G8B8"), imageA8R8G8B8);

        
// all white
        
imageA8R8G8B8->fill(SCOL_WHITE);
        
driver->addTexture (io::path("WHITE_A8R8G8B8"), imageA8R8G8B8);

        
// all black
        
imageA8R8G8B8->fill(SCOL_BLACK);
        
driver->addTexture (io::path("BLACK_A8R8G8B8"), imageA8R8G8B8);

        
// gray-scale
        
for ( u32 y 0height; ++ )
        {
            for ( 
u32 x 0pitch; ++)
            {
                
imageA8R8G8B8->setPixel (xyvideo::SColor(yx,x,x) );
            }
        }
        
driver->addTexture (io::path("GRAYSCALE_A8R8G8B8"), imageA8R8G8B8);

        
imageA8R8G8B8->drop();
    }

    
// Load a texture and make sure nodes know it when more textures are available.
    
void loadTexture(const io::path &name)
    {
        
Device->getVideoDriver()->getTexture(name);
        
NodeLeft.updateTextures();
        
NodeRight.updateTextures();
    }

private:
    
SConfig                     Config;
    
volatile bool               IsRunning;
    
IrrlichtDevice *            Device;
    
scene::ICameraSceneNode *   Camera;
    
SMeshNodeControl            NodeLeft;
    
SMeshNodeControl            NodeRight;
    
SLightNodeControl           LightControl;
    
CColorControl *             GlobalAmbient;
}; 
Il nostro main risulterà molto corto perché è tutto fatto nelle classi da richiamare.
Codice PHP:
int main(int argcchar *argv[])
{
    
CApp APP;

    if ( !
APP.init(argcargv) )
    {
        
printf("init failed\n");
        return 
1;
    }

    
APP.run();
    
APP.quit();

    return 
0;


Versione pdf scaricabile da QUI
 
Reply
  


Discussioni simili
Discussione Autore Risposte Letto Ultimo messaggio
  Tutorial 9 - Mesh Viewer Chip 0 718 16-08-2015, 11:41 AM
Ultimo messaggio: Chip

Vai al forum:


Browsing: 1 Ospite(i)