00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "openglserver.h"
00024 #include <SDL/SDL.h>
00025 #include <zeitgeist/scriptserver/scriptserver.h>
00026 #include <zeitgeist/fileserver/fileserver.h>
00027 #include <zeitgeist/logserver/logserver.h>
00028
00029 using namespace std;
00030
00031 namespace kerosin
00032 {
00033 class MapHolder
00034 {
00035 public:
00037 #if HAVE_HASH_MAP
00038 typedef hash_map<string, unsigned int> TProgramCache;
00039 #else
00040 typedef map<string, unsigned int> TProgramCache;
00041 #endif
00042 TProgramCache mPrograms;
00043 };
00044 }
00045
00046 using namespace boost;
00047 using namespace kerosin;
00048 using namespace zeitgeist;
00049
00050 OpenGLServer::OpenGLServer() : Leaf(), mExtensionReg(new GLExtensionReg()),
00051 mWantsToQuit(false), mHolder( new MapHolder() )
00052 {
00053 }
00054
00055 OpenGLServer::~OpenGLServer()
00056 {
00057 SDL_Quit();
00058 }
00059
00060 boost::shared_ptr<GLExtensionReg> OpenGLServer::GetExtensionReg() const
00061 {
00062 return mExtensionReg;
00063 }
00064
00065 void OpenGLServer::Quit()
00066 {
00067 mWantsToQuit = true;
00068 }
00069
00070 bool OpenGLServer::WantsToQuit() const
00071 {
00072 return mWantsToQuit;
00073 }
00074
00075 void OpenGLServer::Update()
00076 {
00077
00078 SDL_Event event;
00079
00080
00081 while( SDL_PollEvent( &event ) )
00082 {
00083 }
00084 }
00085
00086 void OpenGLServer::SwapBuffers() const
00087 {
00088 SDL_GL_SwapBuffers();
00089 }
00090
00091 unsigned int OpenGLServer::LoadARBProgram(GLenum , const char* )
00092 {
00093 #if 0
00094
00095 if (!mExtensionReg->Has_GL_ARB_vertex_program())
00096 {
00097 return 0;
00098 }
00099
00100
00101 MapHolder::TProgramCache::iterator entry = mHolder->mPrograms.find(fileName);
00102
00103 if (entry != mHolder->mPrograms.end())
00104 {
00105
00106 return (*entry).second;
00107 }
00108
00109 unsigned int id = 0;
00110
00111
00112 shared_ptr<FileServer> fileServer = shared_static_cast<FileServer>(GetCore()->Get("/sys/server/file"));
00113 salt::RFile *file = fileServer->Open(fileName);
00114
00115 if (!file) return 0;
00116
00117 unsigned char *buffer = new unsigned char[file->Size()+1];
00118 file->Read(buffer, file->Size());
00119
00120 glGenProgramsARB(1, &id);
00121 glBindProgramARB(target, id);
00122
00123
00124 glProgramStringARB(target, GL_PROGRAM_FORMAT_ASCII_ARB, file->Size(), buffer);
00125
00126
00127 delete file;
00128 delete []buffer;
00129
00130 const unsigned char* error = glGetString(GL_PROGRAM_ERROR_STRING_ARB);
00131
00132
00133 if (error[0] != 0)
00134 {
00135 int i;
00136 glDeleteProgramsARB(1, &id);
00137 glGetIntegerv(GL_PROGRAM_ERROR_POSITION_ARB, &i);
00138 GetCore()->GetLogServer()->Error() << "ERROR: Loading ARB program (Pos: " << i << ")..." << endl;
00139 GetCore()->GetLogServer()->Error() << " => " << error << endl;
00140 return 0;
00141 }
00142
00143
00144 mHolder->mPrograms[fileName] = id;
00145
00146 return id;
00147 #else
00148 return 0;
00149 #endif
00150 }
00151
00152 unsigned int OpenGLServer::LoadARBVertexProgram(const char* fileName)
00153 {
00154
00155 if (!mExtensionReg->Has_GL_ARB_vertex_program())
00156 {
00157 return 0;
00158 }
00159
00160 return LoadARBProgram(GL_VERTEX_PROGRAM_ARB, fileName);
00161 }
00162
00163 unsigned int OpenGLServer::LoadARBFragmentProgram(const char* )
00164 {
00165
00166
00167
00168
00169
00170
00171
00172 return 0;
00173 }
00174
00178 bool OpenGLServer::ConstructInternal()
00179 {
00180 int result = SDL_Init(SDL_INIT_VIDEO);
00181
00182 if( result < 0 )
00183 {
00184 GetLog()->Error() << "ERROR: (OpenGLServer) Could not init SDL."
00185 << "SDL_Init returned error "
00186 << result << "\n";
00187 return false;
00188 }
00189
00190 const SDL_VideoInfo* info = SDL_GetVideoInfo();
00191
00192 int redBits;
00193 int greenBits;
00194 int blueBits;
00195 int alphaBits;
00196 int depthBits;
00197 int stencilBits;
00198 bool doubleBuffer;
00199 bool fullScreen;
00200 int xRes, yRes;
00201 string title;
00202
00203 bool getConfig =
00204 (
00205 GetScript()->GetVariable("Viewport.RedBits", redBits) &&
00206 GetScript()->GetVariable("Viewport.GreenBits", greenBits) &&
00207 GetScript()->GetVariable("Viewport.BlueBits", blueBits) &&
00208 GetScript()->GetVariable("Viewport.AlphaBits", alphaBits) &&
00209 GetScript()->GetVariable("Viewport.DepthBits", depthBits) &&
00210 GetScript()->GetVariable("Viewport.StencilBits", stencilBits) &&
00211 GetScript()->GetVariable("Viewport.DoubleBuffer", doubleBuffer) &&
00212 GetScript()->GetVariable("Viewport.FullScreen", fullScreen) &&
00213 GetScript()->GetVariable("Viewport.XRes", xRes) &&
00214 GetScript()->GetVariable("Viewport.YRes", yRes) &&
00215 GetScript()->GetVariable("Application.Title", title)
00216 );
00217
00218 if (! getConfig)
00219 {
00220 GetLog()->Error()
00221 << "(OpenGLServer) error reading config from ScriptServer\n";
00222 return false;
00223 }
00224
00225 GetLog()->Normal() << "(OpenGLServer) bits per channel (RGB): "
00226 << redBits << " "
00227 << greenBits << " "
00228 << blueBits << "\n";
00229
00230 GetLog()->Normal() << "(OpenGLServer)"
00231 << " depth bits= " << depthBits
00232 << " alpha depth= " << alphaBits
00233 << " stencil depth= " << stencilBits
00234 << "\n";
00235
00236 GetLog()->Normal() << "(OpenGLServer)"
00237 << " doubleBuffer= " << doubleBuffer
00238 << " fullScreen= " << fullScreen
00239 << "\n";
00240
00241 GetLog()->Normal() << "(OpenGLServer)"
00242 << " xRes = " << xRes
00243 << " yRes = " << yRes
00244 << "\n";
00245
00246 SDL_GL_SetAttribute(SDL_GL_RED_SIZE, redBits);
00247 SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, greenBits);
00248 SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, blueBits);
00249 SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE, alphaBits);
00250 SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, depthBits);
00251 SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, stencilBits);
00252 SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, doubleBuffer ? 1:0);
00253
00254 int flags = SDL_OPENGL;
00255 if (fullScreen)
00256 {
00257 flags |= SDL_FULLSCREEN;
00258 }
00259
00260 SDL_Surface *screen = SDL_SetVideoMode
00261 (xRes, yRes, info->vfmt->BitsPerPixel, flags);
00262
00263 if (screen == 0)
00264 {
00265 GetLog()->Error()
00266 << "ERROR: (OpenGLServer) SDL_SetVideoMode() failed\n";
00267 return false;
00268 }
00269
00270 SDL_WarpMouse(xRes/2,yRes/2);
00271 SDL_WM_SetCaption(title.c_str(), NULL);
00272
00273 mExtensionReg->Init();
00274
00275
00276 mSupportsFancyLighting = true;
00277
00278
00279
00280
00281
00282 mSupportsFancyLighting = false;
00283
00284
00285 glClear(GL_COLOR_BUFFER_BIT);
00286
00287 GetLog()->Normal() << "(OpenGLServer) Initialized OpenGL Window\n";
00288
00289 const unsigned char* glRenderer = glGetString(GL_RENDERER);
00290 const unsigned char* glVersion = glGetString(GL_VERSION);
00291 const unsigned char* glExtensions = glGetString(GL_EXTENSIONS);
00292
00293 GetLog()->Normal() << "(OpenGLServer) GL_RENDERER: " << glRenderer << "\n";
00294 GetLog()->Normal() << "(OpenGLServer) GL_VERSION: " << glVersion << "\n";
00295 GetLog()->Normal() << "(OpenGLServer) GL_EXTENSIONS: " << glExtensions << "\n";
00296 GetLog()->Normal() << "(OpenGLServer) GL_MAX_LIGHTS: " << GL_MAX_LIGHTS << "\n";
00297
00298
00299 for (int i=0;i<GL_MAX_LIGHTS;++i)
00300 {
00301 mAvailableLights.insert(GL_LIGHT0+i);
00302 }
00303
00304 return true;
00305 }
00306
00307 void OpenGLServer::ToggleFancyLighting()
00308 {
00309 if (mSupportsFancyLighting)
00310 mSupportsFancyLighting = false;
00311 else
00312 mSupportsFancyLighting = true;
00313 }
00314
00315 int
00316 OpenGLServer::AllocLight()
00317 {
00318 if (mAvailableLights.size() == 0)
00319 {
00320 return -1;
00321 }
00322
00323 TLightSet::iterator iter = mAvailableLights.begin();
00324 int l = (*iter);
00325 mAvailableLights.erase(iter);
00326
00327 return l;
00328 }
00329
00330 void
00331 OpenGLServer::PutLight(int l)
00332 {
00333 glDisable(l);
00334 mAvailableLights.insert(l);
00335 }
00336
00337