Updates to get configurator and g3d viewer compiling under linux

This commit is contained in:
Mark Vejvoda
2010-03-13 10:39:22 +00:00
parent 99b2f6c2ca
commit 02dddacc07
10 changed files with 2290 additions and 0 deletions

View File

@@ -0,0 +1,392 @@
#include "configuration.h"
#include <stdexcept>
#include "xml_parser.h"
#include "util.h"
#include "properties.h"
#include "conversion.h"
using namespace std;
using namespace Shared::Xml;
using namespace Shared::Util;
namespace Configurator{
// ===============================================
// class Configuration
// ===============================================
Configuration::~Configuration(){
for(int i= 0; i<fieldGroups.size(); ++i){
delete fieldGroups[i];
}
}
void Configuration::load(const string &path){
loadStructure(path);
loadValues(fileName);
}
void Configuration::loadStructure(const string &path){
XmlTree xmlTree;
xmlTree.load(path);
const XmlNode *configurationNode= xmlTree.getRootNode();
//title
title= configurationNode->getChild("title")->getAttribute("value")->getValue();
//fileName
fileName= configurationNode->getChild("file-name")->getAttribute("value")->getValue();
//icon
XmlNode *iconNode= configurationNode->getChild("icon");
icon= iconNode->getAttribute("value")->getBoolValue();
if(icon){
iconPath= iconNode->getAttribute("path")->getValue();
}
const XmlNode *fieldGroupsNode= configurationNode->getChild("field-groups");
fieldGroups.resize(fieldGroupsNode->getChildCount());
for(int i=0; i<fieldGroups.size(); ++i){
const XmlNode *fieldGroupNode= fieldGroupsNode->getChild("field-group", i);
FieldGroup *fieldGroup= new FieldGroup();
fieldGroup->load(fieldGroupNode);
fieldGroups[i]= fieldGroup;
}
}
void Configuration::loadValues(const string &path){
Properties properties;
properties.load(path);
for(int i=0; i<fieldGroups.size(); ++i){
FieldGroup *fg= fieldGroups[i];
for(int j=0; j<fg->getFieldCount(); ++j){
Field *f= fg->getField(j);
f->setValue(properties.getString(f->getVariableName()));
}
}
}
void Configuration::save(){
Properties properties;
properties.load(fileName);
for(int i=0; i<fieldGroups.size(); ++i){
FieldGroup *fg= fieldGroups[i];
for(int j=0; j<fg->getFieldCount(); ++j){
Field *f= fg->getField(j);
f->updateValue();
if(!f->isValueValid(f->getValue())){
f->setValue(f->getDefaultValue());
f->updateControl();
}
properties.setString(f->getVariableName(), f->getValue());
}
}
properties.save(fileName);
}
string Field::getInfo() const{
return name+" (default: " + defaultValue + ")";
}
// ===============================================
// class FieldGroup
// ===============================================
FieldGroup::~FieldGroup(){
for(int i= 0; i<fields.size(); ++i){
delete fields[i];
}
}
void FieldGroup::load(const XmlNode *groupNode){
name= groupNode->getAttribute("name")->getValue();
fields.resize(groupNode->getChildCount());
for(int i=0; i<fields.size(); ++i){
const XmlNode *fieldNode= groupNode->getChild("field", i);
Field *f= newField(fieldNode->getAttribute("type")->getValue());
//name
const XmlNode *nameNode= fieldNode->getChild("name");
f->setName(nameNode->getAttribute("value")->getValue());
//variableName
const XmlNode *variableNameNode= fieldNode->getChild("variable-name");
f->setVariableName(variableNameNode->getAttribute("value")->getValue());
//description
const XmlNode *descriptionNode= fieldNode->getChild("description");
f->setDescription(descriptionNode->getAttribute("value")->getValue());
//default
const XmlNode *defaultNode= fieldNode->getChild("default");
f->setDefaultValue(defaultNode->getAttribute("value")->getValue());
f->loadSpecific(fieldNode);
if(!f->isValueValid(f->getDefaultValue())){
throw runtime_error("Default value not valid in field: " + f->getName());
}
fields[i]= f;
}
}
Field *FieldGroup::newField(const string &type){
if(type=="Bool"){
return new BoolField();
}
else if(type=="Int"){
return new IntField();
}
else if(type=="Float"){
return new FloatField();
}
else if(type=="String"){
return new StringField();
}
else if(type=="Enum"){
return new EnumField();
}
else if(type=="IntRange"){
return new IntRangeField();
}
else if(type=="FloatRange"){
return new FloatRangeField();
}
else{
throw runtime_error("Unknown field type: " + type);
}
}
// ===============================================
// class BoolField
// ===============================================
void BoolField::createControl(wxWindow *parent, wxSizer *sizer){
checkBox= new wxCheckBox(parent, -1, Configuration::ToUnicode(""));
checkBox->SetValue(strToBool(value));
sizer->Add(checkBox);
}
void BoolField::updateValue(){
value= boolToStr(checkBox->GetValue());
}
void BoolField::updateControl(){
checkBox->SetValue(strToBool(value));
}
bool BoolField::isValueValid(const string &value){
try{
strToBool(value);
}
catch(const exception &){
return false;
}
return true;
}
// ===============================================
// class IntField
// ===============================================
void IntField::createControl(wxWindow *parent, wxSizer *sizer){
textCtrl= new wxTextCtrl(parent, -1, Configuration::ToUnicode(value.c_str()));
sizer->Add(textCtrl);
}
void IntField::updateValue(){
value= (const char*)wxFNCONV(textCtrl->GetValue());
}
void IntField::updateControl(){
textCtrl->SetValue(Configuration::ToUnicode(value.c_str()));
}
bool IntField::isValueValid(const string &value){
try{
strToInt(value);
}
catch(const exception &){
return false;
}
return true;
}
// ===============================================
// class FloatField
// ===============================================
void FloatField::createControl(wxWindow *parent, wxSizer *sizer){
textCtrl= new wxTextCtrl(parent, -1, Configuration::ToUnicode(value.c_str()));
sizer->Add(textCtrl);
}
void FloatField::updateValue(){
value= (const char*)wxFNCONV(textCtrl->GetValue());
}
void FloatField::updateControl(){
textCtrl->SetValue(Configuration::ToUnicode(value.c_str()));
}
bool FloatField::isValueValid(const string &value){
try{
strToFloat(value);
}
catch(const exception &){
return false;
}
return true;
}
// ===============================================
// class StringField
// ===============================================
void StringField::createControl(wxWindow *parent, wxSizer *sizer){
textCtrl= new wxTextCtrl(parent, -1, Configuration::ToUnicode(value.c_str()));
textCtrl->SetSize(wxSize(3*textCtrl->GetSize().x/2, textCtrl->GetSize().y));
sizer->Add(textCtrl);
}
void StringField::updateValue(){
value= (const char*)wxFNCONV(textCtrl->GetValue());
}
void StringField::updateControl(){
textCtrl->SetValue(Configuration::ToUnicode(value.c_str()));
}
bool StringField::isValueValid(const string &value){
return true;
}
// ===============================================
// class EnumField
// ===============================================
void EnumField::createControl(wxWindow *parent, wxSizer *sizer){
comboBox= new wxComboBox(parent, -1, Configuration::ToUnicode(""), wxDefaultPosition, wxDefaultSize, 0, NULL, wxCB_READONLY);
for(int i=0; i<enumerants.size(); ++i){
comboBox->Append(Configuration::ToUnicode(enumerants[i].c_str()));
}
comboBox->SetValue(Configuration::ToUnicode(value.c_str()));
sizer->Add(comboBox);
}
void EnumField::updateValue(){
value= (const char*)wxFNCONV(comboBox->GetValue());
}
void EnumField::updateControl(){
comboBox->SetValue(Configuration::ToUnicode(value.c_str()));
}
bool EnumField::isValueValid(const string &value){
return true;
}
void EnumField::loadSpecific(const XmlNode *fieldNode){
const XmlNode *enumsNode= fieldNode->getChild("enums");
for(int i=0; i<enumsNode->getChildCount(); ++i){
const XmlNode *enumNode= enumsNode->getChild("enum", i);
enumerants.push_back(enumNode->getAttribute("value")->getValue());
}
};
// ===============================================
// class IntRange
// ===============================================
void IntRangeField::createControl(wxWindow *parent, wxSizer *sizer){
slider= new wxSlider(parent, -1, strToInt(value), min, max, wxDefaultPosition, wxDefaultSize, wxSL_LABELS);
sizer->Add(slider);
}
void IntRangeField::updateValue(){
value= intToStr(slider->GetValue());
}
void IntRangeField::updateControl(){
slider->SetValue(strToInt(value));
}
bool IntRangeField::isValueValid(const string &value){
try{
strToInt(value);
}
catch(const exception &){
return false;
}
return true;
}
void IntRangeField::loadSpecific(const XmlNode *fieldNode){
const XmlNode *minNode= fieldNode->getChild("min");
min= strToInt(minNode->getAttribute("value")->getValue());
const XmlNode *maxNode= fieldNode->getChild("max");
max= strToInt(maxNode->getAttribute("value")->getValue());
}
string IntRangeField::getInfo() const{
return name + " (min: " + intToStr(min)+ ", max: " + intToStr(max) + ", default: " + defaultValue + ")";
}
// ===============================================
// class FloatRangeField
// ===============================================
void FloatRangeField::createControl(wxWindow *parent, wxSizer *sizer){
textCtrl= new wxTextCtrl(parent, -1, Configuration::ToUnicode(value.c_str()));
sizer->Add(textCtrl);
}
void FloatRangeField::updateValue(){
value= (const char*)wxFNCONV(textCtrl->GetValue());
}
void FloatRangeField::updateControl(){
textCtrl->SetValue(Configuration::ToUnicode(value.c_str()));
}
bool FloatRangeField::isValueValid(const string &value){
try{
float f= strToFloat(value);
return f>=min && f<=max;
}
catch(const exception &){
return false;
}
return true;
}
void FloatRangeField::loadSpecific(const XmlNode *fieldNode){
const XmlNode *minNode= fieldNode->getChild("min");
min= strToFloat(minNode->getAttribute("value")->getValue());
const XmlNode *maxNode= fieldNode->getChild("max");
max= strToFloat(maxNode->getAttribute("value")->getValue());
};
string FloatRangeField::getInfo() const{
return name + " (min: " + floatToStr(min)+ ", max: " + floatToStr(max) + ", default: " + defaultValue + ")";
}
}//end namespace

View File

@@ -0,0 +1,250 @@
#ifndef _CONFIGURATOR_CONFIGURATION_H_
#define _CONFIGURATOR_CONFIGURATION_H_
#include <string>
#include <vector>
#include <wx/wx.h>
#include "xml_parser.h"
using std::string;
using std::vector;
using Shared::Xml::XmlNode;
namespace Configurator{
// ===============================================
// class Global functions
// ===============================================
class Field;
class FieldGroup;
// ===============================
// class Configuration
// ===============================
class Configuration{
public:
typedef vector<FieldGroup*> FieldGroups;
private:
string title;
string fileName;
bool icon;
string iconPath;
FieldGroups fieldGroups;
public:
~Configuration();
void load(const string &path);
void loadStructure(const string &path);
void loadValues(const string &path);
void save();
const string &getTitle() const {return title;}
const string &getFileName() const {return fileName;}
bool getIcon() const {return icon;}
const string &getIconPath() const {return iconPath;}
int getFieldGroupCount() const {return fieldGroups.size();}
FieldGroup *getFieldGroup(int i) const {return fieldGroups[i];}
static wxString ToUnicode(const char* str) {
return wxString(str, wxConvUTF8);
}
static wxString ToUnicode(const string& str) {
return wxString(str.c_str(), wxConvUTF8);
}
};
// ===============================
// class FieldGroup
// ===============================
class FieldGroup{
public:
typedef vector<Field*> Fields;
private:
Fields fields;
string name;
public:
~FieldGroup();
int getFieldCount() const {return fields.size();}
Field *getField(int i) const {return fields[i];}
const string &getName() const {return name;}
void load(const XmlNode *groupNode);
private:
Field *newField(const string &type);
};
// ===============================
// class Field
// ===============================
class Field{
protected:
string name;
string variableName;
string description;
string value;
string defaultValue;
public:
virtual ~Field() {};
const string &getName() const {return name;}
const string &getVariableName() const {return variableName;}
const string &getDescription() const {return description;}
const string &getValue() const {return value;}
const string &getDefaultValue() const {return defaultValue;}
void setName(const string &name) {this->name= name;}
void setVariableName(const string &variableName) {this->variableName= variableName;}
void setDescription(const string &description) {this->description= description;}
void setValue(const string &value) {this->value= value;}
void setDefaultValue(const string &defaultValue) {this->defaultValue= defaultValue;}
virtual void loadSpecific(const XmlNode *fieldNode){};
virtual string getInfo() const;
virtual void createControl(wxWindow *parent, wxSizer *sizer)= 0;
virtual void updateValue()= 0;
virtual void updateControl()= 0;
virtual bool isValueValid(const string &value)= 0;
};
// ===============================
// class BoolField
// ===============================
class BoolField: public Field{
private:
wxCheckBox *checkBox;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
};
// ===============================
// class IntField
// ===============================
class IntField: public Field{
private:
wxTextCtrl *textCtrl;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
};
// ===============================
// class FloatField
// ===============================
class FloatField: public Field{
private:
wxTextCtrl *textCtrl;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
};
// ===============================
// class StringField
// ===============================
class StringField: public Field{
private:
wxTextCtrl *textCtrl;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
};
// ===============================
// class EnumField
// ===============================
class EnumField: public Field{
private:
wxComboBox *comboBox;
vector<string> enumerants;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
virtual void loadSpecific(const XmlNode *fieldNode);
};
// ===============================
// class IntRangeField
// ===============================
class IntRangeField: public Field{
private:
wxSlider *slider;
int min;
int max;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
virtual void loadSpecific(const XmlNode *fieldNode);
virtual string getInfo() const;
};
// ===============================
// class FloatRangeField
// ===============================
class FloatRangeField: public Field{
private:
wxTextCtrl *textCtrl;
float min;
float max;
public:
virtual void createControl(wxWindow *parent, wxSizer *sizer);
virtual void updateValue();
virtual void updateControl();
virtual bool isValueValid(const string &value);
virtual void loadSpecific(const XmlNode *fieldNode);
virtual string getInfo() const;
};
}//end namespace
#endif

View File

@@ -0,0 +1,210 @@
#include "main.h"
#include <stdexcept>
#include <wx/wx.h>
#include <wx/sizer.h>
#include <wx/image.h>
#include <wx/bitmap.h>
#include <wx/icon.h>
using namespace std;
namespace Configurator{
// ===============================================
// class MainWindow
// ===============================================
const int MainWindow::margin= 10;
const int MainWindow::panelMargin= 20;
const int MainWindow::gridMarginHorizontal= 30;
const string MainWindow::versionString= "v1.3.5-beta1";
const string MainWindow::winHeader= "Mega-Glest config " + versionString + " - Built: " + __DATE__;
MainWindow::MainWindow() :
wxFrame(
NULL, -1, Configuration::ToUnicode(winHeader),
wxDefaultPosition, wxSize(800, 600)){
SetExtraStyle(wxFRAME_EX_CONTEXTHELP);
configuration.load("configuration.xml");
//Create(NULL, -1, "", wxDefaultPosition, wxDefaultSize, wxCAPTION | wxSYSTEM_MENU);
SetTitle(Configuration::ToUnicode(("Configurator - " + configuration.getTitle() + " - Editing " + configuration.getFileName()).c_str()));
if(configuration.getIcon()){
printf("In [%s::%s] icon = [%s]\n",__FILE__,__FUNCTION__,configuration.getIconPath().c_str());
wxInitAllImageHandlers();
wxIcon icon;
icon.LoadFile(Configuration::ToUnicode(configuration.getIconPath().c_str()), wxBITMAP_TYPE_ICO);
SetIcon(icon);
}
notebook= new wxNotebook(this, -1);
wxSizer *mainSizer= new wxBoxSizer(wxVERTICAL);
wxSizer *topSizer= new wxBoxSizer(wxHORIZONTAL);
topSizer->Add(notebook, 0, wxALL, 0);
mainSizer->Add(topSizer, 0, wxALL, margin);
for(int i=0; i<configuration.getFieldGroupCount(); ++i){
//create page
FieldGroup *fg= configuration.getFieldGroup(i);
wxPanel *panel= new wxPanel(notebook, -1);
notebook->AddPage(panel, Configuration::ToUnicode(fg->getName().c_str()));
//sizers
wxSizer *gridSizer= new wxFlexGridSizer(2, margin, gridMarginHorizontal);
wxSizer *panelSizer= new wxBoxSizer(wxVERTICAL);
panelSizer->Add(gridSizer, 0, wxALL, panelMargin);
panel->SetSizer(panelSizer);
for(int j=0; j<fg->getFieldCount(); ++j){
Field *f= fg->getField(j);
FieldText *staticText= new FieldText(panel, this, f);
staticText->SetAutoLayout(true);
gridSizer->Add(staticText);
f->createControl(panel, gridSizer);
idMap.insert(IdPair(staticText->GetId(), staticText));
}
}
//buttons
wxSizer *bottomSizer= new wxBoxSizer(wxHORIZONTAL);
buttonOk= new wxButton(this, biOk, wxT("OK"));
buttonApply= new wxButton(this, biApply, wxT("Apply"));
buttonCancel= new wxButton(this, biCancel, wxT("Cancel"));
buttonDefault= new wxButton(this, biDefault, wxT("Default"));
bottomSizer->Add(buttonOk, 0, wxALL, margin);
bottomSizer->Add(buttonApply, 0, wxRIGHT | wxDOWN | wxUP, margin);
bottomSizer->Add(buttonCancel, 0, wxRIGHT | wxDOWN | wxUP, margin);
bottomSizer->Add(buttonDefault, 0, wxRIGHT | wxDOWN | wxUP, margin);
infoText= new wxTextCtrl(this, -1, Configuration::ToUnicode("Info text."), wxDefaultPosition, wxDefaultSize, wxTE_MULTILINE | wxTE_READONLY);
infoText->SetSize(infoText->GetSize().x, 2*infoText->GetSize().y/3);
infoText->SetBackgroundColour(buttonOk->GetBackgroundColour());
mainSizer->Add(infoText, 1, wxGROW | wxALL | wxALIGN_CENTER, margin);
mainSizer->Add(bottomSizer, 0, wxALIGN_CENTER);
SetBackgroundColour(buttonOk->GetBackgroundColour());
SetSizerAndFit(mainSizer);
Refresh();
}
void MainWindow::init(){
}
void MainWindow::onButtonOk(wxCommandEvent &event){
configuration.save();
Close();
}
void MainWindow::onButtonApply(wxCommandEvent &event){
configuration.save();
}
void MainWindow::onButtonCancel(wxCommandEvent &event){
Close();
}
void MainWindow::onButtonDefault(wxCommandEvent &event){
for(int i=0; i<configuration.getFieldGroupCount(); ++i){
FieldGroup *fg= configuration.getFieldGroup(i);
for(int j=0; j<fg->getFieldCount(); ++j){
Field *f= fg->getField(j);
f->setValue(f->getDefaultValue());
f->updateControl();
}
}
}
void MainWindow::onClose(wxCloseEvent &event){
Destroy();
}
void MainWindow::onMouseDown(wxMouseEvent &event){
setInfoText("");
}
void MainWindow::setInfoText(const string &str){
infoText->SetValue(Configuration::ToUnicode(str.c_str()));
}
BEGIN_EVENT_TABLE(MainWindow, wxFrame)
EVT_BUTTON(biOk, MainWindow::onButtonOk)
EVT_BUTTON(biApply, MainWindow::onButtonApply)
EVT_BUTTON(biCancel, MainWindow::onButtonCancel)
EVT_BUTTON(biDefault, MainWindow::onButtonDefault)
EVT_CLOSE(MainWindow::onClose)
EVT_LEFT_DOWN(MainWindow::onMouseDown)
END_EVENT_TABLE()
// ===============================================
// class FieldText
// ===============================================
FieldText::FieldText(wxWindow *parent, MainWindow *mainWindow, const Field *field):
wxStaticText(parent, -1, Configuration::ToUnicode(field->getName().c_str()))
{
this->mainWindow= mainWindow;
this->field= field;
}
void FieldText::onHelp(wxHelpEvent &event){
string str= field->getInfo()+".";
if(!field->getDescription().empty()){
str+= "\n"+field->getDescription()+".";
}
mainWindow->setInfoText(str);
}
BEGIN_EVENT_TABLE(FieldText, wxStaticText)
EVT_HELP(-1, FieldText::onHelp)
END_EVENT_TABLE()
// ===============================================
// class App
// ===============================================
bool App::OnInit(){
try{
mainWindow= new MainWindow();
mainWindow->Show();
}
catch(const exception &e){
wxMessageDialog(NULL, Configuration::ToUnicode(e.what()), Configuration::ToUnicode("Exception"), wxOK | wxICON_ERROR).ShowModal();
return 0;
}
return true;
}
int App::MainLoop(){
try{
return wxApp::MainLoop();
}
catch(const exception &e){
wxMessageDialog(NULL, Configuration::ToUnicode(e.what()), Configuration::ToUnicode("Exception"), wxOK | wxICON_ERROR).ShowModal();
return 0;
}
}
int App::OnExit(){
return 0;
}
}//end namespace
IMPLEMENT_APP(Configurator::App)

104
source/configurator/main.h Normal file
View File

@@ -0,0 +1,104 @@
#ifndef _CONFIGURATOR_MAIN_H_
#define _CONFIGURATOR_MAIN_H_
#include <map>
#include <wx/wx.h>
#include <wx/cshelp.h>
#include <wx/notebook.h>
#include <wx/sizer.h>
#include "configuration.h"
using std::pair;
using std::map;
namespace Configurator{
// ===============================
// class MainWindow
// ===============================
class MainWindow: public wxFrame{
private:
DECLARE_EVENT_TABLE()
private:
typedef pair<int, wxWindow*> IdPair;
typedef map<int, wxWindow*> IdMap;
private:
static const int margin;
static const int panelMargin;
static const int gridMarginHorizontal;
enum ButtonId{
biOk,
biApply,
biCancel,
biDefault
};
private:
IdMap idMap;
Configuration configuration;
wxButton *buttonOk;
wxButton *buttonApply;
wxButton *buttonCancel;
wxButton *buttonDefault;
wxNotebook *notebook;
wxTextCtrl *infoText;
public:
MainWindow();
void init();
static const string versionString;
static const string winHeader;
void onButtonOk(wxCommandEvent &event);
void onButtonApply(wxCommandEvent &event);
void onButtonCancel(wxCommandEvent &event);
void onButtonDefault(wxCommandEvent &event);
void onClose(wxCloseEvent &event);
void onMouseDown(wxMouseEvent &event);
void setInfoText(const string &str);
};
// ===============================
// class FieldText
// ===============================
class FieldText: public wxStaticText{
private:
MainWindow *mainWindow;
const Field *field;
private:
DECLARE_EVENT_TABLE()
public:
FieldText(wxWindow *parentm, MainWindow *mainWindow, const Field *field);
void onHelp(wxHelpEvent &event);
};
// ===============================
// class App
// ===============================
class App: public wxApp{
private:
MainWindow *mainWindow;
public:
virtual bool OnInit();
virtual int MainLoop();
virtual int OnExit();
};
}//end namespace
DECLARE_APP(Configurator::App)
#endif

327
source/g3d_viewer/main.cpp Normal file
View File

@@ -0,0 +1,327 @@
#include "main.h"
#include <stdexcept>
#include "graphics_factory_gl.h"
#include "graphics_interface.h"
#include "util.h"
#include "conversion.h"
using namespace Shared::Platform;
using namespace Shared::Graphics;
using namespace Shared::Graphics::Gl;
using namespace Shared::Util;
using namespace std;
namespace Shared{ namespace G3dViewer{
// ===============================================
// class Global functions
// ===============================================
wxString ToUnicode(const char* str) {
return wxString(str, wxConvUTF8);
}
wxString ToUnicode(const string& str) {
return wxString(str.c_str(), wxConvUTF8);
}
// ===============================================
// class MainWindow
// ===============================================
const string MainWindow::versionString= "v1.3.5-beta1";
const string MainWindow::winHeader= "G3D viewer " + versionString + " - Built: " + __DATE__;
MainWindow::MainWindow(const string &modelPath)
: wxFrame(NULL, -1, ToUnicode(winHeader),wxPoint(Renderer::windowX, Renderer::windowY),
wxSize(Renderer::windowW, Renderer::windowH))
{
//getGlPlatformExtensions();
renderer= Renderer::getInstance();
this->modelPath= modelPath;
model= NULL;
playerColor= Renderer::pcRed;
speed= 0.025f;
glCanvas = new GlCanvas(this);
//getGlPlatformExtensions();
//glCanvas->SetCurrent();
//renderer->init();
menu= new wxMenuBar();
//menu
menuFile= new wxMenu();
menuFile->Append(miFileLoad, wxT("Load"));
menu->Append(menuFile, wxT("File"));
//mode
menuMode= new wxMenu();
menuMode->AppendCheckItem(miModeNormals, wxT("Normals"));
menuMode->AppendCheckItem(miModeWireframe, wxT("Wireframe"));
menuMode->AppendCheckItem(miModeGrid, wxT("Grid"));
menu->Append(menuMode, wxT("Mode"));
//mode
menuSpeed= new wxMenu();
menuSpeed->Append(miSpeedSlower, wxT("Slower"));
menuSpeed->Append(miSpeedFaster, wxT("Faster"));
menu->Append(menuSpeed, wxT("Speed"));
//custom color
menuCustomColor= new wxMenu();
menuCustomColor->AppendCheckItem(miColorRed, wxT("Red"));
menuCustomColor->AppendCheckItem(miColorBlue, wxT("Blue"));
menuCustomColor->AppendCheckItem(miColorYellow, wxT("Yellow"));
menuCustomColor->AppendCheckItem(miColorGreen, wxT("Green"));
menu->Append(menuCustomColor, wxT("Custom Color"));
menuMode->Check(miModeGrid, true);
menuCustomColor->Check(miColorRed, true);
SetMenuBar(menu);
//misc
model= NULL;
rotX= 0.0f;
rotY= 0.0f;
zoom= 1.0f;
lastX= 0;
lastY= 0;
anim= 0.0f;
CreateStatusBar();
timer = new wxTimer(this);
timer->Start(100);
glCanvas->SetFocus();
}
MainWindow::~MainWindow(){
delete renderer;
delete model;
delete timer;
delete glCanvas;
}
void MainWindow::init(){
glCanvas->SetCurrent();
renderer->init();
if(!modelPath.empty()){
Model *tmpModel= new ModelGl();
printf("In [%s::%s] modelPath = [%s]\n",__FILE__,__FUNCTION__,modelPath.c_str());
renderer->loadTheModel(tmpModel, modelPath);
model= tmpModel;
GetStatusBar()->SetStatusText(ToUnicode(getModelInfo().c_str()));
}
//SetTitle(ToUnicode(winHeader + "; " + modelPath));
}
void MainWindow::onPaint(wxPaintEvent &event){
renderer->reset(GetClientSize().x, GetClientSize().y, playerColor);
renderer->transform(rotX, rotY, zoom);
renderer->renderGrid();
renderer->renderTheModel(model, anim);
glCanvas->SwapBuffers();
}
void MainWindow::onClose(wxCloseEvent &event){
delete this;
}
void MainWindow::onMouseMove(wxMouseEvent &event){
int x= event.GetX();
int y= event.GetY();
wxPaintEvent paintEvent;
if(event.LeftIsDown()){
rotX+= clamp(lastX-x, -10, 10);
rotY+= clamp(lastY-y, -10, 10);
onPaint(paintEvent);
}
else if(event.RightIsDown()){
zoom*= 1.0f+(lastX-x+lastY-y)/100.0f;
zoom= clamp(zoom, 0.1f, 10.0f);
onPaint(paintEvent);
}
lastX= x;
lastY= y;
}
void MainWindow::onMenuFileLoad(wxCommandEvent &event){
string fileName;
wxFileDialog fileDialog(this);
fileDialog.SetWildcard(wxT("G3D files (*.g3d)|*.g3d"));
if(fileDialog.ShowModal()==wxID_OK){
delete model;
Model *tmpModel= new ModelGl();
renderer->loadTheModel(tmpModel, (const char*)wxFNCONV(fileDialog.GetPath().c_str()));
model= tmpModel;
GetStatusBar()->SetStatusText(ToUnicode(getModelInfo().c_str()));
}
}
void MainWindow::onMenuModeNormals(wxCommandEvent &event){
renderer->toggleNormals();
menuMode->Check(miModeNormals, renderer->getNormals());
}
void MainWindow::onMenuModeWireframe(wxCommandEvent &event){
renderer->toggleWireframe();
menuMode->Check(miModeWireframe, renderer->getWireframe());
}
void MainWindow::onMenuModeGrid(wxCommandEvent &event){
renderer->toggleGrid();
menuMode->Check(miModeGrid, renderer->getGrid());
}
void MainWindow::onMenuSpeedSlower(wxCommandEvent &event){
speed/= 1.5f;
}
void MainWindow::onMenuSpeedFaster(wxCommandEvent &event){
speed*= 1.5f;
}
void MainWindow::onMenuColorRed(wxCommandEvent &event){
playerColor= Renderer::pcRed;
menuCustomColor->Check(miColorRed, true);
menuCustomColor->Check(miColorBlue, false);
menuCustomColor->Check(miColorYellow, false);
menuCustomColor->Check(miColorGreen, false);
}
void MainWindow::onMenuColorBlue(wxCommandEvent &event){
playerColor= Renderer::pcBlue;
menuCustomColor->Check(miColorRed, false);
menuCustomColor->Check(miColorBlue, true);
menuCustomColor->Check(miColorYellow, false);
menuCustomColor->Check(miColorGreen, false);
}
void MainWindow::onMenuColorYellow(wxCommandEvent &event){
playerColor= Renderer::pcYellow;
menuCustomColor->Check(miColorRed, false);
menuCustomColor->Check(miColorBlue, false);
menuCustomColor->Check(miColorYellow, true);
menuCustomColor->Check(miColorGreen, false);
}
void MainWindow::onMenuColorGreen(wxCommandEvent &event){
playerColor= Renderer::pcGreen;
menuCustomColor->Check(miColorRed, false);
menuCustomColor->Check(miColorBlue, false);
menuCustomColor->Check(miColorYellow, false);
menuCustomColor->Check(miColorGreen, true);
}
void MainWindow::onTimer(wxTimerEvent &event){
wxPaintEvent paintEvent;
anim= anim+speed;
if(anim>1.0f){
anim-= 1.f;
}
onPaint(paintEvent);
}
string MainWindow::getModelInfo(){
string str;
if(model!=NULL){
str+= "Meshes: "+intToStr(model->getMeshCount());
str+= ", Vertices: "+intToStr(model->getVertexCount());
str+= ", Triangles: "+intToStr(model->getTriangleCount());
str+= ", Version: "+intToStr(model->getFileVersion());
}
return str;
}
BEGIN_EVENT_TABLE(MainWindow, wxFrame)
EVT_TIMER(-1, MainWindow::onTimer)
EVT_CLOSE(MainWindow::onClose)
EVT_MENU(miFileLoad, MainWindow::onMenuFileLoad)
EVT_MENU(miModeWireframe, MainWindow::onMenuModeWireframe)
EVT_MENU(miModeNormals, MainWindow::onMenuModeNormals)
EVT_MENU(miModeGrid, MainWindow::onMenuModeGrid)
EVT_MENU(miSpeedFaster, MainWindow::onMenuSpeedFaster)
EVT_MENU(miSpeedSlower, MainWindow::onMenuSpeedSlower)
EVT_MENU(miColorRed, MainWindow::onMenuColorRed)
EVT_MENU(miColorBlue, MainWindow::onMenuColorBlue)
EVT_MENU(miColorYellow, MainWindow::onMenuColorYellow)
EVT_MENU(miColorGreen, MainWindow::onMenuColorGreen)
END_EVENT_TABLE()
// =====================================================
// class GlCanvas
// =====================================================
GlCanvas::GlCanvas(MainWindow * mainWindow):
wxGLCanvas(mainWindow, -1, wxDefaultPosition)
{
this->mainWindow = mainWindow;
}
void GlCanvas::onMouseMove(wxMouseEvent &event){
mainWindow->onMouseMove(event);
}
BEGIN_EVENT_TABLE(GlCanvas, wxGLCanvas)
EVT_MOTION(GlCanvas::onMouseMove)
END_EVENT_TABLE()
// ===============================================
// class App
// ===============================================
bool App::OnInit(){
std::string modelPath;
if(argc==2){
modelPath= wxFNCONV(argv[1]);
}
mainWindow= new MainWindow(modelPath);
mainWindow->Show();
mainWindow->init();
return true;
}
int App::MainLoop(){
try{
return wxApp::MainLoop();
}
catch(const exception &e){
wxMessageDialog(NULL, ToUnicode(e.what()), ToUnicode("Exception"), wxOK | wxICON_ERROR).ShowModal();
return 0;
}
}
int App::OnExit(){
return 0;
}
}}//end namespace
IMPLEMENT_APP(Shared::G3dViewer::App)

129
source/g3d_viewer/main.h Normal file
View File

@@ -0,0 +1,129 @@
#ifndef _SHADER_G3DVIEWER_MAIN_H_
#define _SHADER_G3DVIEWER_MAIN_H_
#include <string>
#include <wx/wx.h>
#include <wx/glcanvas.h>
#include "renderer.h"
//#include "util.h"
//using Shared::Platform::Window;
//using Shared::Platform::MouseState;
using std::string;
namespace Shared{ namespace G3dViewer{
class GlCanvas;
// ===============================
// class MainWindow
// ===============================
class MainWindow: public wxFrame{
private:
DECLARE_EVENT_TABLE()
public:
static const string versionString;
static const string winHeader;
enum MenuId{
miFileLoad,
miModeWireframe,
miModeNormals,
miModeGrid,
miSpeedSlower,
miSpeedFaster,
miColorRed,
miColorBlue,
miColorYellow,
miColorGreen
};
private:
GlCanvas *glCanvas;
Renderer *renderer;
wxTimer *timer;
wxMenuBar *menu;
wxMenu *menuFile;
wxMenu *menuMode;
wxMenu *menuSpeed;
wxMenu *menuCustomColor;
Model *model;
string modelPath;
float speed;
float anim;
float rotX, rotY, zoom;
int lastX, lastY;
Renderer::PlayerColor playerColor;
public:
MainWindow(const string &modelPath);
~MainWindow();
void init();
void Notify();
void onPaint(wxPaintEvent &event);
void onClose(wxCloseEvent &event);
void onMenuFileLoad(wxCommandEvent &event);
void onMenuModeNormals(wxCommandEvent &event);
void onMenuModeWireframe(wxCommandEvent &event);
void onMenuModeGrid(wxCommandEvent &event);
void onMenuSpeedSlower(wxCommandEvent &event);
void onMenuSpeedFaster(wxCommandEvent &event);
void onMenuColorRed(wxCommandEvent &event);
void onMenuColorBlue(wxCommandEvent &event);
void onMenuColorYellow(wxCommandEvent &event);
void onMenuColorGreen(wxCommandEvent &event);
void onMouseMove(wxMouseEvent &event);
void onTimer(wxTimerEvent &event);
string getModelInfo();
};
// =====================================================
// class GlCanvas
// =====================================================
class GlCanvas: public wxGLCanvas {
private:
DECLARE_EVENT_TABLE()
public:
GlCanvas(MainWindow *mainWindow);
void onMouseMove(wxMouseEvent &event);
void onPaint(wxPaintEvent &event);
private:
MainWindow *mainWindow;
};
// ===============================
// class App
// ===============================
class App: public wxApp{
private:
MainWindow *mainWindow;
public:
virtual bool OnInit();
virtual int MainLoop();
virtual int OnExit();
};
}}//end namespace
DECLARE_APP(Shared::G3dViewer::App)
#endif

View File

@@ -0,0 +1,306 @@
#include "renderer.h"
#include "opengl.h"
//#include "texture_gl.h"
#include "graphics_factory_gl.h"
#include "graphics_interface.h"
//#include "factory_repository.h"
using namespace Shared::Graphics;
using namespace Shared::Graphics::Gl;
namespace Shared{ namespace G3dViewer{
// ===============================================
// class MeshCallbackTeamColor
// ===============================================
void MeshCallbackTeamColor::execute(const Mesh *mesh){
//team color
if(mesh->getCustomTexture() && teamTexture!=NULL){
//texture 0
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
//set color to interpolation
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_INTERPOLATE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB, GL_TEXTURE1);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_RGB, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_RGB, GL_SRC_ALPHA);
//set alpha to 1
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_TEXTURE);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
//texture 1
glActiveTexture(GL_TEXTURE1);
glMultiTexCoord2f(GL_TEXTURE1, 0.f, 0.f);
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, static_cast<const Texture2DGl*>(teamTexture)->getHandle());
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_MODULATE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB, GL_PRIMARY_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB, GL_SRC_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB, GL_PREVIOUS);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB, GL_SRC_COLOR);
//set alpha to 1
glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_REPLACE);
glTexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA, GL_PRIMARY_COLOR);
glTexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA, GL_SRC_ALPHA);
glActiveTexture(GL_TEXTURE0);
}
else{
glActiveTexture(GL_TEXTURE1);
glDisable(GL_TEXTURE_2D);
glActiveTexture(GL_TEXTURE0);
glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
}
}
// ===============================================
// class Renderer
// ===============================================
Renderer::Renderer(){
normals= false;
wireframe= false;
grid= true;
modelRenderer = NULL;
textureManager = NULL;
}
Renderer::~Renderer(){
delete modelRenderer;
delete textureManager;
}
Renderer * Renderer::getInstance(){
static Renderer * renderer = new Renderer();
return renderer;
}
void Renderer::transform(float rotX, float rotY, float zoom){
assertGl();
glMatrixMode(GL_MODELVIEW);
glRotatef(rotY, 1.0f, 0.0f, 0.0f);
glRotatef(rotX, 0.0f, 1.0f, 0.0f);
glScalef(zoom, zoom, zoom);
Vec4f pos(-8.0f, 5.0f, 10.0f, 0.0f);
glLightfv(GL_LIGHT0,GL_POSITION, pos.ptr());
assertGl();
}
void Renderer::checkGlCaps(){
//opengl 1.3
if(!isGlVersionSupported(1, 3, 0)){
string message;
message += "Your system supports OpenGL version \"";
message += getGlVersion() + string("\"\n");
message += "Glest needs at least version 1.3 to work\n";
message += "You may solve this problem by installing your latest video card drivers";
throw runtime_error(message.c_str());
}
//opengl 1.4 or extension
if(!isGlVersionSupported(1, 4, 0)){
checkExtension("GL_ARB_texture_env_crossbar", "Glest");
}
}
void Renderer::checkExtension(const string &extension, const string &msg){
if(!isGlExtensionSupported(extension.c_str())){
string str= "OpenGL extension not supported: " + extension + ", required for " + msg;
throw runtime_error(str);
}
}
void Renderer::init(){
assertGl();
//!!!glInitNames();
//!!!checkGlCaps();
GraphicsFactory *gf= new GraphicsFactoryGl();
GraphicsInterface::getInstance().setFactory(gf);
modelRenderer= gf->newModelRenderer();
textureManager= gf->newTextureManager();
//red tex
customTextureRed= textureManager->newTexture2D();
customTextureRed->getPixmap()->init(1, 1, 3);
customTextureRed->getPixmap()->setPixel(0, 0, Vec3f(1.f, 0.f, 0.f));
//blue tex
customTextureBlue= textureManager->newTexture2D();
customTextureBlue->getPixmap()->init(1, 1, 3);
customTextureBlue->getPixmap()->setPixel(0, 0, Vec3f(0.f, 0.f, 1.f));
//yellow tex
customTextureYellow= textureManager->newTexture2D();
customTextureYellow->getPixmap()->init(1, 1, 3);
customTextureYellow->getPixmap()->setPixel(0, 0, Vec3f(1.f, 1.f, 0.f));
//green
customTextureGreen= textureManager->newTexture2D();
customTextureGreen->getPixmap()->init(1, 1, 3);
customTextureGreen->getPixmap()->setPixel(0, 0, Vec3f(0.f, 0.5f, 0.f));
glClearColor(0.3f, 0.3f, 0.3f, 1.0f);
glEnable(GL_TEXTURE_2D);
glFrontFace(GL_CW);
glEnable(GL_CULL_FACE);
glEnable(GL_DEPTH_TEST);
glEnable(GL_ALPHA_TEST);
glAlphaFunc(GL_GREATER, 0.5f);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
Vec4f diffuse= Vec4f(1.0f, 1.0f, 1.0f, 1.0f);
Vec4f ambient= Vec4f(0.3f, 0.3f, 0.3f, 1.0f);
Vec4f specular= Vec4f(0.1f, 0.1f, 0.1f, 1.0f);
glLightfv(GL_LIGHT0,GL_AMBIENT, ambient.ptr());
glLightfv(GL_LIGHT0,GL_DIFFUSE, diffuse.ptr());
glLightfv(GL_LIGHT0,GL_SPECULAR, specular.ptr());
glColorMaterial(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE);
glEnable(GL_COLOR_MATERIAL);
assertGl();
}
void Renderer::reset(int w, int h, PlayerColor playerColor){
assertGl();
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glViewport(0, 0, w, h);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
gluPerspective(60.0f, static_cast<float>(w)/h, 1.0f, 200.0f);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef(0, -1.5, -5);
Texture2D *customTexture;
switch(playerColor){
case pcRed:
customTexture= customTextureRed;
break;
case pcBlue:
customTexture= customTextureBlue;
break;
case pcYellow:
customTexture= customTextureYellow;
break;
case pcGreen:
customTexture= customTextureGreen;
break;
default:
assert(false);
}
meshCallbackTeamColor.setTeamTexture(customTexture);
if(wireframe){
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
glDisable(GL_TEXTURE_2D);
glDisable(GL_LIGHTING);
glDisable(GL_LIGHT0);
}
else{
glEnable(GL_TEXTURE_2D);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
}
assertGl();
}
void Renderer::renderGrid(){
if(grid){
float i;
assertGl();
glPushAttrib(GL_ENABLE_BIT);
glDisable(GL_TEXTURE_2D);
glDisable(GL_LIGHTING);
glBegin(GL_LINES);
glColor3f(1.0f, 1.0f, 1.0f);
for(i=-10.0f; i<=10.0f; i+=1.0f){
glVertex3f(i, 0.0f, 10.0f);
glVertex3f(i, 0.0f, -10.0f);
}
for(i=-10.0f; i<=10.0f; i+=1.0f){
glVertex3f(10.f, 0.0f, i);
glVertex3f(-10.f, 0.0f, i);
}
glEnd();
glPopAttrib();
assertGl();
}
}
void Renderer::toggleNormals(){
normals= normals? false: true;
}
void Renderer::toggleWireframe(){
wireframe= wireframe? false: true;
}
void Renderer::toggleGrid(){
grid= grid? false: true;
}
void Renderer::loadTheModel(Model *model, string file){
model->setTextureManager(textureManager);
model->loadG3d(file);
textureManager->init();
}
void Renderer::renderTheModel(Model *model, float f){
if(model != NULL){
modelRenderer->begin(true, true, !wireframe, &meshCallbackTeamColor);
model->updateInterpolationData(f, true);
modelRenderer->render(model);
if(normals){
glPushAttrib(GL_ENABLE_BIT);
glDisable(GL_LIGHTING);
glDisable(GL_TEXTURE_2D);
glColor3f(1.0f, 1.0f, 1.0f);
modelRenderer->renderNormalsOnly(model);
glPopAttrib();
}
modelRenderer->end();
}
}
}}//end namespace

View File

@@ -0,0 +1,103 @@
#ifndef _SHADER_G3DVIEWER_RENDERER_H_
#define _SHADER_G3DVIEWER_RENDERER_H_
/*
#include "model_renderer.h"
#include "texture_manager.h"
#include "model.h"
#include "texture.h"
*/
#include "model_renderer.h"
#include "texture_manager.h"
#include "model.h"
#include "texture.h"
//#include "model_manager.h"
//#include "graphics_factory_gl.h"
using Shared::Graphics::ModelRenderer;
using Shared::Graphics::TextureManager;
using Shared::Graphics::Model;
using Shared::Graphics::Texture2D;
//#include "model_renderer.h"
using Shared::Graphics::MeshCallback;
using Shared::Graphics::Mesh;
using Shared::Graphics::Texture;
namespace Shared{ namespace G3dViewer{
// ===============================================
// class MeshCallbackTeamColor
// ===============================================
class MeshCallbackTeamColor: public MeshCallback{
private:
const Texture *teamTexture;
public:
void setTeamTexture(const Texture *teamTexture) {this->teamTexture= teamTexture;}
virtual void execute(const Mesh *mesh);
};
// ===============================
// class Renderer
// ===============================
class Renderer{
public:
static const int windowX= 100;
static const int windowY= 100;
static const int windowW= 640;
static const int windowH= 480;
public:
enum PlayerColor{
pcRed,
pcBlue,
pcYellow,
pcGreen
};
private:
bool wireframe;
bool normals;
bool grid;
ModelRenderer *modelRenderer;
TextureManager *textureManager;
Texture2D *customTextureRed;
Texture2D *customTextureBlue;
Texture2D *customTextureYellow;
Texture2D *customTextureGreen;
MeshCallbackTeamColor meshCallbackTeamColor;
Renderer();
void checkGlCaps();
void checkExtension(const string &extension, const string &msg);
public:
~Renderer();
static Renderer *getInstance();
void init();
void reset(int w, int h, PlayerColor playerColor);
void transform(float rotX, float rotY, float zoom);
void renderGrid();
bool getNormals() const {return normals;}
bool getWireframe() const {return wireframe;}
bool getGrid() const {return grid;}
void toggleNormals();
void toggleWireframe();
void toggleGrid();
void loadTheModel(Model *model, string file);
void renderTheModel(Model *model, float f);
};
}}//end namespace
#endif