hedgewars/uStore.pas
branchsdl2transition
changeset 11362 ed5a6478e710
parent 11360 7a7611adf715
parent 11317 62287d4044e7
child 11367 a91c4c4fd85c
--- a/hedgewars/uStore.pas	Tue Nov 10 18:16:35 2015 +0100
+++ b/hedgewars/uStore.pas	Tue Nov 10 20:43:13 2015 +0100
@@ -1,6 +1,6 @@
 (*
  * Hedgewars, a free turn based strategy game
- * Copyright (c) 2004-2013 Andrey Korotaev <unC0Rr@gmail.com>
+ * Copyright (c) 2004-2015 Andrey Korotaev <unC0Rr@gmail.com>
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
@@ -13,7 +13,7 @@
  *
  * You should have received a copy of the GNU General Public License
  * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
  *)
 
 {$INCLUDE "options.inc"}
@@ -21,7 +21,7 @@
 
 unit uStore;
 interface
-uses StrUtils, SysUtils, uConsts, SDLh, GLunit, uTypes, uLandTexture, uCaptions, uChat;
+uses SysUtils, uConsts, SDLh, GLunit, uTypes, uLandTexture, uCaptions, uChat;
 
 procedure initModule;
 procedure freeModule;
@@ -42,12 +42,14 @@
 function  LoadDataImageAltFile(const path: TPathType; const filename, altFile: shortstring; imageFlags: LongInt): PSDL_Surface;
 
 procedure LoadHedgehogHat(var HH: THedgehog; newHat: shortstring);
+procedure LoadHedgehogHat2(var HH: THedgehog; newHat: shortstring; allowSurfReuse: boolean);
+
+procedure InitZoom(zoom: real);
+
 procedure SetupOpenGL;
-procedure SetScale(f: GLfloat);
 function  RenderHelpWindow(caption, subcaption, description, extra: ansistring; extracolor: LongInt; iconsurf: PSDL_Surface; iconrect: PSDL_Rect): PTexture;
 procedure RenderWeaponTooltip(atype: TAmmoType);
 procedure ShowWeaponTooltip(x, y: LongInt);
-procedure FreeWeaponTooltip;
 procedure MakeCrossHairs;
 {$IFDEF USE_VIDEO_RECORDING}
 procedure InitOffscreenOpenGL;
@@ -58,32 +60,50 @@
 procedure SetSkyColor(r, g, b: real);
 
 implementation
-uses uMisc, uConsole, uVariables, uUtils, uTextures, uRender, uRenderUtils, uCommands
-    , uPhysFSLayer
-    , uDebug
+uses uMisc, uConsole, uVariables, uUtils, uTextures, uRender, uRenderUtils,
+     uCommands, uPhysFSLayer, uDebug
     {$IFDEF USE_CONTEXT_RESTORE}, uWorld{$ENDIF};
 
 //type TGPUVendor = (gvUnknown, gvNVIDIA, gvATI, gvIntel, gvApple);
 
-var MaxTextureSize: LongInt;
+var 
     SDLwindow: PSDL_Window;
     SDLGLcontext: PSDL_GLContext;
     squaresize : LongInt;
     numsquares : LongInt;
     ProgrTex: PTexture;
 
+    prevHat: shortstring;
+    tmpHatSurf: PSDL_Surface;
+
 const
     cHHFileName = 'Hedgehog';
     cCHFileName = 'Crosshair';
 
-function WriteInRect(Surface: PSDL_Surface; X, Y: LongInt; Color: LongWord; Font: THWFont; s: ansistring): TSDL_Rect;
+procedure freeTmpHatSurf();
+begin
+    if tmpHatSurf = nil then exit;
+    SDL_FreeSurface(tmpHatSurf);
+    tmpHatSurf:= nil;
+    prevHat:= 'NoHat';
+end;
+
+procedure InitZoom(zoom: real);
+begin
+    SetScale(zoom);
+    // make sure view limits are updated
+    // because SetScale() doesn't do it, if zoom=cScaleFactor
+    updateViewLimits();
+end;
+
+function WriteInRect(Surface: PSDL_Surface; X, Y: LongInt; Color: LongWord; Font: THWFont; s: PChar): TSDL_Rect;
 var w, h: LongInt;
     tmpsurf: PSDL_Surface;
     clr: TSDL_Color;
     finalRect: TSDL_Rect;
 begin
 w:= 0; h:= 0; // avoid compiler hints
-TTF_SizeUTF8(Fontz[Font].Handle, Str2PChar(s), @w, @h);
+TTF_SizeUTF8(Fontz[Font].Handle, s, @w, @h);
 finalRect.x:= X + cFontBorder + 2;
 finalRect.y:= Y + cFontBorder;
 finalRect.w:= w + cFontBorder * 2 + 4;
@@ -91,7 +111,8 @@
 clr.r:= Color shr 16;
 clr.g:= (Color shr 8) and $FF;
 clr.b:= Color and $FF;
-tmpsurf:= TTF_RenderUTF8_Blended(Fontz[Font].Handle, Str2PChar(s), clr);
+tmpsurf:= TTF_RenderUTF8_Blended(Fontz[Font].Handle, s, clr);
+SDLTry(tmpsurf <> nil, 'TTF_RenderUTF8_Blended', true);
 tmpsurf:= doSurfaceConversion(tmpsurf);
 SDLTry(tmpsurf <> nil, 'TTF_RenderUTF8_Blended, doSurfaceConversion', true);
 SDL_UpperBlit(tmpsurf, nil, Surface, @finalRect);
@@ -148,17 +169,23 @@
     foundBot: boolean;
     year, month, md : word;
 begin
-    if cOnlyStats then exit;
+if cOnlyStats then exit;
 r.x:= 0;
 r.y:= 0;
 drY:= - 4;
+{$IFNDEF PAS2C}
 DecodeDate(Date, year, month, md);
+{$ELSE}
+year:= 0;
+month:= 0;
+md:= 0;
+{$ENDIF}
 for t:= 0 to Pred(TeamsCount) do
     with TeamsArray[t]^ do
         begin
-        NameTagTex:= RenderStringTexLim(TeamName, Clan^.Color, Font, cTeamHealthWidth);
+        NameTagTex:= RenderStringTexLim(ansistring(TeamName), Clan^.Color, Font, cTeamHealthWidth);
         if length(Owner) > 0 then
-            OwnerTex:= RenderStringTexLim(Owner, Clan^.Color, Font, cTeamHealthWidth);
+            OwnerTex:= RenderStringTexLim(ansistring(Owner), Clan^.Color, Font, cTeamHealthWidth);
 
         r.x:= 0;
         r.y:= 0;
@@ -224,7 +251,7 @@
         SDL_FreeSurface(texsurf);
         texsurf:= nil;
 
-        AIKillsTex := RenderStringTex(inttostr(stats.AIKills), Clan^.Color, fnt16);
+        AIKillsTex := RenderStringTex(ansistring(inttostr(stats.AIKills)), Clan^.Color, fnt16);
 
         dec(drY, r.h + 2);
         DrawHealthY:= drY;
@@ -232,26 +259,34 @@
             with Hedgehogs[i] do
                 if Gear <> nil then
                     begin
-                    NameTagTex:= RenderStringTexLim(Name, Clan^.Color, fnt16, cTeamHealthWidth);
+                    NameTagTex:= RenderStringTexLim(ansistring(Name), Clan^.Color, fnt16, cTeamHealthWidth);
                     if Hat = 'NoHat' then
                         begin
-                        if ((month = 4) and (md = 20)) then
-                            Hat := 'eastertop'; // Easter
-                        if ((month = 12) and (md = 25)) then
-                            Hat := 'Santa'; // Christmas
-                        if ((month = 10) and (md = 31)) then
+                        if (month = 4) and (md = 20) then
+                            Hat := 'eastertop'   // Easter
+                        else if (month = 12) and ((md = 24) or (md = 25) or (md = 26)) then
+                            Hat := 'Santa'       // Christmas Eve/Christmas/Boxing Day
+                        else if (month = 10) and (md = 31) then
                             Hat := 'fr_pumpkin'; // Halloween/Hedgewars' birthday
                         end;
-                    
+                    if (month = 4) and (md = 1) then
+                        begin
+                        AprilOne:= true;
+                        Hat := 'fr_tomato'; // avoid promoting violence to hedgehogs. see http://hedgewars.org/node/5818
+                        end;
+
                     if Hat <> 'NoHat' then
                         begin
                         if (Length(Hat) > 39) and (Copy(Hat,1,8) = 'Reserved') and (Copy(Hat,9,32) = PlayerHash) then
-                            LoadHedgehogHat(Hedgehogs[i], 'Reserved/' + Copy(Hat,9,Length(Hat)-8))
+                            LoadHedgehogHat2(Hedgehogs[i], 'Reserved/' + Copy(Hat,9,Length(Hat)-8), true)
                         else
-                            LoadHedgehogHat(Hedgehogs[i], Hat);
+                            LoadHedgehogHat2(Hedgehogs[i], Hat, true);
                         end
                     end;
         end;
+
+    freeTmpHatSurf();
+
     MissionIcons:= LoadDataImage(ptGraphics, 'missions', ifCritical);
     iconsurf:= SDL_CreateRGBSurface(SDL_SWSURFACE, 28, 28, 32, RMask, GMask, BMask, AMask);
     if iconsurf <> nil then
@@ -314,7 +349,7 @@
 begin
 AddFileLog('StoreLoad()');
 
-if not reload then
+if (not reload) and (not cOnlyStats) then
     for fi:= Low(THWFont) to High(THWFont) do
         with Fontz[fi] do
             begin
@@ -326,8 +361,19 @@
             WriteLnToConsole(msgOK)
             end;
 
-MakeCrossHairs;
-LoadGraves;
+if not cOnlyStats then
+    begin
+    MakeCrossHairs;
+    LoadGraves;
+{$IFDEF IPHONEOS}
+    tmpHatSurf:= LoadDataImage(ptHats, 'chef', ifNone);
+{$ELSE}
+    tmpHatSurf:= LoadDataImage(ptHats, 'Reserved/chef', ifNone);
+{$ENDIF}
+    ChefHatTexture:= Surface2Tex(tmpHatSurf, true);
+    freeTmpHatSurf();
+    end;
+
 if not reload then
     AddProgress;
 
@@ -335,11 +381,13 @@
     with SpritesData[ii] do
         // FIXME - add a sprite attribute to match on rq flags?
         if (((cReducedQuality and (rqNoBackground or rqLowRes)) = 0) or   // why rqLowRes?
-                (not (ii in [sprSky, sprSkyL, sprSkyR, sprHorizont, sprHorizontL, sprHorizontR]))) and
-           (((cReducedQuality and rqPlainSplash) = 0) or ((not (ii in [sprSplash, sprDroplet, sprSDSplash, sprSDDroplet])))) and
-           (((cReducedQuality and rqKillFlakes) = 0) or cSnow or ((not (ii in [sprFlake, sprSDFlake])))) and
-           ((cCloudsNumber > 0) or (ii <> sprCloud)) and
-           ((vobCount > 0) or (ii <> sprFlake)) then
+                (not (ii in [sprSky, sprSkyL, sprSkyR, sprHorizont, sprHorizontL, sprHorizontR])))
+           and (((cReducedQuality and rqPlainSplash) = 0) or ((not (ii in [sprSplash, sprDroplet, sprSDSplash, sprSDDroplet]))))
+           and (((cReducedQuality and rqKillFlakes) = 0) or cSnow or ((not (ii in [sprFlake, sprSDFlake]))))
+           and ((cCloudsNumber > 0) or (ii <> sprCloud))
+           and ((vobCount > 0) or (ii <> sprFlake))
+           and (savesurf or (not cOnlyStats)) // in stats-only only load those which are needed later
+            then
             begin
             if reload then
                 tmpsurf:= Surface
@@ -397,79 +445,58 @@
                 Surface:= nil
         end;
 
-WriteNames(fnt16);
+if not cOnlyStats then
+    begin
+    WriteNames(fnt16);
 
-if not reload then
-    AddProgress;
+    if not reload then
+        AddProgress;
+
+    tmpsurf:= LoadDataImage(ptGraphics, cHHFileName, ifAlpha or ifCritical or ifTransparent);
 
-tmpsurf:= LoadDataImage(ptGraphics, cHHFileName, ifAlpha or ifCritical or ifTransparent);
+    HHTexture:= Surface2Tex(tmpsurf, false);
+    SDL_FreeSurface(tmpsurf);
+
+    InitHealth;
 
-HHTexture:= Surface2Tex(tmpsurf, false);
-SDL_FreeSurface(tmpsurf);
-
-InitHealth;
+    PauseTexture:= RenderStringTex(trmsg[sidPaused], cYellowColor, fntBig);
+    AFKTexture:= RenderStringTex(trmsg[sidAFK], cYellowColor, fntBig);
+    ConfirmTexture:= RenderStringTex(trmsg[sidConfirm], cYellowColor, fntBig);
+    SyncTexture:= RenderStringTex(trmsg[sidSync], cYellowColor, fntBig);
 
-PauseTexture:= RenderStringTex(trmsg[sidPaused], cYellowColor, fntBig);
-AFKTexture:= RenderStringTex(trmsg[sidAFK], cYellowColor, fntBig);
-ConfirmTexture:= RenderStringTex(trmsg[sidConfirm], cYellowColor, fntBig);
-SyncTexture:= RenderStringTex(trmsg[sidSync], cYellowColor, fntBig);
-
-if not reload then
-    AddProgress;
+    if not reload then
+        AddProgress;
 
-// name of weapons in ammo menu
-for ai:= Low(TAmmoType) to High(TAmmoType) do
-    with Ammoz[ai] do
+    // name of weapons in ammo menu
+    for ai:= Low(TAmmoType) to High(TAmmoType) do
+        with Ammoz[ai] do
+            begin
+            TryDo(length(trAmmo[NameId]) > 0,'No default text/translation found for ammo type #' + intToStr(ord(ai)) + '!',true);
+            tmpsurf:= TTF_RenderUTF8_Blended(Fontz[CheckCJKFont(trAmmo[NameId],fnt16)].Handle, PChar(trAmmo[NameId]), cWhiteColorChannels);
+            TryDo(tmpsurf <> nil,'Name-texture creation for ammo type #' + intToStr(ord(ai)) + ' failed!',true);
+            tmpsurf:= doSurfaceConversion(tmpsurf);
+            FreeAndNilTexture(NameTex);
+            NameTex:= Surface2Tex(tmpsurf, false);
+            SDL_FreeSurface(tmpsurf)
+            end;
+
+    // number of weapons in ammo menu
+    for i:= Low(CountTexz) to High(CountTexz) do
         begin
-        TryDo(trAmmo[NameId] <> '','No default text/translation found for ammo type #' + intToStr(ord(ai)) + '!',true);
-        tmpsurf:= TTF_RenderUTF8_Blended(Fontz[CheckCJKFont(trAmmo[NameId],fnt16)].Handle, Str2PChar(trAmmo[NameId]), cWhiteColorChannels);
-        TryDo(tmpsurf <> nil,'Name-texture creation for ammo type #' + intToStr(ord(ai)) + ' failed!',true);
+        tmpsurf:= TTF_RenderUTF8_Blended(Fontz[fnt16].Handle, Str2PChar(IntToStr(i) + 'x'), cWhiteColorChannels);
         tmpsurf:= doSurfaceConversion(tmpsurf);
-        FreeTexture(NameTex);
-        NameTex:= Surface2Tex(tmpsurf, false);
+        FreeAndNilTexture(CountTexz[i]);
+        CountTexz[i]:= Surface2Tex(tmpsurf, false);
         SDL_FreeSurface(tmpsurf)
         end;
 
-// number of weapons in ammo menu
-for i:= Low(CountTexz) to High(CountTexz) do
-    begin
-    tmpsurf:= TTF_RenderUTF8_Blended(Fontz[fnt16].Handle, Str2PChar(IntToStr(i) + 'x'), cWhiteColorChannels);
-    tmpsurf:= doSurfaceConversion(tmpsurf);
-    FreeTexture(CountTexz[i]);
-    CountTexz[i]:= Surface2Tex(tmpsurf, false);
-    SDL_FreeSurface(tmpsurf)
+    if not reload then
+        AddProgress;
     end;
 
-if not reload then
-    AddProgress;
 IMG_Quit();
 end;
 
-{$IF DEFINED(USE_S3D_RENDERING) OR DEFINED(USE_VIDEO_RECORDING)}
-procedure CreateFramebuffer(var frame, depth, tex: GLuint);
-begin
-    glGenFramebuffersEXT(1, @frame);
-    glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, frame);
-    glGenRenderbuffersEXT(1, @depth);
-    glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, depth);
-    glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT, cScreenWidth, cScreenHeight);
-    glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, depth);
-    glGenTextures(1, @tex);
-    glBindTexture(GL_TEXTURE_2D, tex);
-    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8,  cScreenWidth, cScreenHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, nil);
-    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
-    glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
-    glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, tex, 0);
-end;
-
-procedure DeleteFramebuffer(var frame, depth, tex: GLuint);
-begin
-    glDeleteTextures(1, @tex);
-    glDeleteRenderbuffersEXT(1, @depth);
-    glDeleteFramebuffersEXT(1, @frame);
-end;
-{$ENDIF}
-
 procedure StoreRelease(reload: boolean);
 var ii: TSprite;
     ai: TAmmoType;
@@ -488,6 +515,7 @@
 SDL_FreeSurface(MissionIcons);
 
 // free the textures declared in uVariables
+FreeAndNilTexture(ChefHatTexture);
 FreeAndNilTexture(CrosshairTexture);
 FreeAndNilTexture(WeaponTooltipTex);
 FreeAndNilTexture(PauseTexture);
@@ -532,17 +560,8 @@
                 end;
             end;
         end;
-{$IFDEF USE_VIDEO_RECORDING}
-    if defaultFrame <> 0 then
-        DeleteFramebuffer(defaultFrame, depthv, texv);
-{$ENDIF}
-{$IFDEF USE_S3D_RENDERING}
-    if (cStereoMode = smHorizontal) or (cStereoMode = smVertical) then
-        begin
-        DeleteFramebuffer(framel, depthl, texl);
-        DeleteFramebuffer(framer, depthr, texr);
-        end
-{$ENDIF}
+
+RendererCleanup();
 end;
 
 
@@ -550,23 +569,47 @@
 var s: shortstring;
 begin
 str(Hedgehog.Gear^.Health, s);
-FreeTexture(Hedgehog.HealthTagTex);
-Hedgehog.HealthTagTex:= RenderStringTex(s, Hedgehog.Team^.Clan^.Color, fnt16)
+FreeAndNilTexture(Hedgehog.HealthTagTex);
+Hedgehog.HealthTagTex:= RenderStringTex(ansistring(s), Hedgehog.Team^.Clan^.Color, fnt16)
 end;
 
 function LoadImage(const filename: shortstring; imageFlags: LongInt): PSDL_Surface;
 var tmpsurf: PSDL_Surface;
     s: shortstring;
+    rwops: PSDL_RWops;
 begin
     LoadImage:= nil;
     WriteToConsole(msgLoading + filename + '.png [flags: ' + inttostr(imageFlags) + '] ');
 
     s:= filename + '.png';
-    tmpsurf:= IMG_Load_RW(rwopsOpenRead(s), true);
+
+    rwops:= nil;
+    tmpsurf:= nil;
 
+    if pfsExists(s) then
+        begin
+        // get data source
+        rwops:= rwopsOpenRead(s);
+
+        // load image with SDL (with freesrc param set to true)
+        if rwops <> nil then
+            tmpsurf:= IMG_Load_RW(rwops, true);
+        end;
+
+    // loading failed
     if tmpsurf = nil then
         begin
-        OutError(msgFailed, (imageFlags and ifCritical) <> 0);
+        // output sdl error if loading failed when data source was available
+        if rwops <> nil then
+            begin
+            // anounce that loading failed
+            OutError(msgFailed, false);
+
+            SDLTry(false, 'LoadImage', (imageFlags and ifCritical) <> 0);
+            // rwops was already freed by IMG_Load_RW
+            rwops:= nil;
+            end else
+            OutError(msgFailed, (imageFlags and ifCritical) <> 0);
         exit;
         end;
 
@@ -635,43 +678,39 @@
 end;
 
 procedure LoadHedgehogHat(var HH: THedgehog; newHat: shortstring);
-var texsurf: PSDL_Surface;
+begin
+    LoadHedgehogHat2(HH, newHat, false);
+end;
+
+procedure LoadHedgehogHat2(var HH: THedgehog; newHat: shortstring; allowSurfReuse: boolean);
 begin
     // free the mem of any previously assigned texture.  This was previously only if the new one could be loaded, but, NoHat is usually a better choice
     if HH.HatTex <> nil then
+        FreeAndNilTexture(HH.HatTex);
+
+    // load new hat surface if this hat is different than the one already loaded
+    if newHat <> prevHat then
         begin
-        FreeTexture(HH.HatTex);
-        HH.HatTex:= nil
+        freeTmpHatSurf();
+        tmpHatSurf:= LoadDataImage(ptHats, newHat, ifNone);
         end;
-    texsurf:= LoadDataImage(ptHats, newHat, ifNone);
+
 AddFileLog('Hat => '+newHat);
     // only do something if the hat could be loaded
-    if texsurf <> nil then
+    if tmpHatSurf <> nil then
         begin
 AddFileLog('Got Hat');
 
         // assign new hat to hedgehog
-        HH.HatTex:= Surface2Tex(texsurf, true);
-
-        // cleanup: free temporary surface mem
-        SDL_FreeSurface(texsurf)
-        end;
-end;
+        HH.HatTex:= Surface2Tex(tmpHatSurf, true);
 
-function glLoadExtension(extension : shortstring) : boolean;
-begin
-{$IF GLunit = gles11}
-    // FreePascal doesnt come with OpenGL ES 1.1 Extension headers
-    extension:= extension; // avoid hint
-    glLoadExtension:= false;
-    AddFileLog('OpenGL - "' + extension + '" skipped')
-{$ELSE}
-    glLoadExtension:= glext_LoadExtension(extension);
-    if glLoadExtension then
-        AddFileLog('OpenGL - "' + extension + '" loaded')
-    else
-        AddFileLog('OpenGL - "' + extension + '" failed to load');
-{$ENDIF}
+        // remember that this hat was used last
+        if allowSurfReuse then
+            prevHat:= newHat
+        // cleanup: free temporary surface mem
+        else
+            freeTmpHatSurf();
+        end;
 end;
 
 procedure SetupOpenGLAttributes;
@@ -679,6 +718,9 @@
 {$IFDEF IPHONEOS}
     SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 0);
     SDL_GL_SetAttribute(SDL_GL_RETAINED_BACKING, 1);
+ 
+    SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 1);
+    SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 1);
 {$ELSE}
     SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
 {$ENDIF}
@@ -693,15 +735,9 @@
 
 procedure SetupOpenGL;
 var buf: array[byte] of char;
-    AuxBufNum: LongInt = 0;
-    tmpstr: AnsiString;
-    tmpint: LongInt;
-    tmpn: LongInt;
 begin
     AddFileLog('Setting up OpenGL (using driver: ' + shortstring(SDL_GetCurrentVideoDriver()) + ')');
 
-    AuxBufNum:= AuxBufNum;
-
     // TODO: this function creates an opengles1.1 context
     // un-comment below and add proper logic to support opengles2.0
     //SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 2);
@@ -711,130 +747,9 @@
     SDLTry(SDLGLcontext <> nil, 'SDLGLcontext', true);
     SDLTry(SDL_GL_SetSwapInterval(1) = 0, 'SDL_GL_SetSwapInterval', true);
 
-    // get the max (h and v) size for textures that the gpu can support
-    glGetIntegerv(GL_MAX_TEXTURE_SIZE, @MaxTextureSize);
-    if MaxTextureSize <= 0 then
-        begin
-        MaxTextureSize:= 1024;
-        AddFileLog('OpenGL Warning - driver didn''t provide any valid max texture size; assuming 1024');
-        end
-    else if (MaxTextureSize < 1024) and (MaxTextureSize >= 512) then
-        begin
-        cReducedQuality := cReducedQuality or rqNoBackground;
-        AddFileLog('Texture size too small for backgrounds, disabling.');
-        end;
-
-    // everyone loves debugging
-    AddFileLog('OpenGL-- Renderer: ' + shortstring(pchar(glGetString(GL_RENDERER))));
-    AddFileLog('  |----- Vendor: ' + shortstring(pchar(glGetString(GL_VENDOR))));
-    AddFileLog('  |----- Version: ' + shortstring(pchar(glGetString(GL_VERSION))));
-    AddFileLog('  |----- Texture Size: ' + inttostr(MaxTextureSize));
-{$IFDEF USE_VIDEO_RECORDING}
-    glGetIntegerv(GL_AUX_BUFFERS, @AuxBufNum);
-    AddFileLog('  |----- Number of auxiliary buffers: ' + inttostr(AuxBufNum));
-{$ENDIF}
-    AddFileLog('  \----- Extensions: ');
-
-    // fetch extentions and store them in string
-    tmpstr := StrPas(PChar(glGetString(GL_EXTENSIONS)));
-    tmpn := WordCount(tmpstr, [' ']);
-    tmpint := 1;
-
-    repeat
-    begin
-        // print up to 3 extentions per row
-        // ExtractWord will return empty string if index out of range
-        AddFileLog(TrimRight(
-            ExtractWord(tmpint, tmpstr, [' ']) + ' ' +
-            ExtractWord(tmpint+1, tmpstr, [' ']) + ' ' +
-            ExtractWord(tmpint+2, tmpstr, [' '])
-        ));
-        tmpint := tmpint + 3;
-    end;
-    until (tmpint > tmpn);
-    AddFileLog('');
+    RendererSetup();
 
-    defaultFrame:= 0;
-{$IFDEF USE_VIDEO_RECORDING}
-    if GameType = gmtRecord then
-    begin
-        if glLoadExtension('GL_EXT_framebuffer_object') then
-        begin
-            CreateFramebuffer(defaultFrame, depthv, texv);
-            glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, defaultFrame);
-            AddFileLog('Using framebuffer for video recording.');
-        end
-        else if AuxBufNum > 0 then
-        begin
-            glDrawBuffer(GL_AUX0);
-            glReadBuffer(GL_AUX0);
-            AddFileLog('Using auxiliary buffer for video recording.');
-        end
-        else
-        begin
-            glDrawBuffer(GL_BACK);
-            glReadBuffer(GL_BACK);
-            AddFileLog('Warning: off-screen rendering is not supported; using back buffer but it may not work.');
-        end;
-    end;
-{$ENDIF}
-
-{$IFDEF USE_S3D_RENDERING}
-    if (cStereoMode = smHorizontal) or (cStereoMode = smVertical) then
-    begin
-        // prepare left and right frame buffers and associated textures
-        if glLoadExtension('GL_EXT_framebuffer_object') then
-            begin
-            CreateFramebuffer(framel, depthl, texl);
-            CreateFramebuffer(framer, depthr, texr);
-
-            // reset
-            glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, defaultFrame)
-            end
-        else
-            cStereoMode:= smNone;
-    end;
-{$ENDIF}
-
-    // set view port to whole window
-    glViewport(0, 0, cScreenWidth, cScreenHeight);
-
-    glMatrixMode(GL_MODELVIEW);
-    // prepare default translation/scaling
-    glLoadIdentity();
-    glScalef(2.0 / cScreenWidth, -2.0 / cScreenHeight, 1.0);
-    glTranslatef(0, -cScreenHeight / 2, 0);
-
-    // enable alpha blending
-    glEnable(GL_BLEND);
-    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
-    // disable/lower perspective correction (will not need it anyway)
-    glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_FASTEST);
-    // disable dithering
-    glDisable(GL_DITHER);
-    // enable common states by default as they save a lot
-    glEnable(GL_TEXTURE_2D);
-    glEnableClientState(GL_VERTEX_ARRAY);
-    glEnableClientState(GL_TEXTURE_COORD_ARRAY);
-end;
-
-procedure SetScale(f: GLfloat);
-begin
-// leave immediately if scale factor did not change
-    if f = cScaleFactor then
-        exit;
-
-    if f = cDefaultZoomLevel then
-        glPopMatrix         // return to default scaling
-    else                    // other scaling
-        begin
-        glPushMatrix;       // save default scaling
-        glLoadIdentity;
-        glScalef(f / cScreenWidth, -f / cScreenHeight, 1.0);
-        glTranslatef(0, -cScreenHeight / 2, 0);
-        end;
-
-    cScaleFactor:= f;
+// gl2 init/matrix code was here, but removed
 end;
 
 ////////////////////////////////////////////////////////////////////////////////
@@ -853,15 +768,16 @@
         squaresize:= texsurf^.w shr 1;
         numsquares:= texsurf^.h div squaresize;
         SDL_FreeSurface(texsurf);
+        {$IFNDEF PAS2C}
         with mobileRecord do
             if GameLoading <> nil then
                 GameLoading();
-
+        {$ENDIF}
         end;
 
     TryDo(ProgrTex <> nil, 'Error - Progress Texure is nil!', true);
 
-    glClear(GL_COLOR_BUFFER_BIT);
+    RenderClear();
     if Step < numsquares then
         r.x:= 0
     else
@@ -874,17 +790,19 @@
     DrawTextureFromRect( -squaresize div 2, (cScreenHeight - squaresize) shr 1, @r, ProgrTex);
 
     SwapBuffers;
+
     inc(Step);
 end;
 
 procedure FinishProgress;
 begin
+    {$IFNDEF PAS2C}
     with mobileRecord do
         if GameLoaded <> nil then
             GameLoaded();
+    {$ENDIF}
     WriteLnToConsole('Freeing progress surface... ');
-    FreeTexture(ProgrTex);
-    ProgrTex:= nil;
+    FreeAndNilTexture(ProgrTex);
     Step:= 0
 end;
 
@@ -897,10 +815,10 @@
     tmpline, tmpline2, tmpdesc: ansistring;
 begin
 // make sure there is a caption as well as a sub caption - description is optional
-if caption = '' then
-    caption:= '???';
-if subcaption = '' then
-    subcaption:= _S' ';
+if length(caption) = 0 then
+    caption:= ansistring('???');
+if length(subcaption) = 0 then
+    subcaption:= ansistring(_S' ');
 
 font:= CheckCJKFont(caption,fnt16);
 font:= CheckCJKFont(subcaption,font);
@@ -917,13 +835,13 @@
 // TODO: Recheck height/position calculation
 
 // get caption's dimensions
-TTF_SizeUTF8(Fontz[font].Handle, Str2PChar(caption), @i, @j);
+TTF_SizeUTF8(Fontz[font].Handle, PChar(caption), @i, @j);
 // width adds 36 px (image + space)
 w:= i + 36 + wa;
 h:= j + ha;
 
 // get sub caption's dimensions
-TTF_SizeUTF8(Fontz[font].Handle, Str2PChar(subcaption), @i, @j);
+TTF_SizeUTF8(Fontz[font].Handle, PChar(subcaption), @i, @j);
 // width adds 36 px (image + space)
 if w < (i + 36 + wa) then
     w:= i + 36 + wa;
@@ -931,23 +849,23 @@
 
 // get description's dimensions
 tmpdesc:= description;
-while tmpdesc <> '' do
+while length(tmpdesc) > 0 do
     begin
     tmpline:= tmpdesc;
-    SplitByChar(tmpline, tmpdesc, '|');
-    if tmpline <> '' then
+    SplitByCharA(tmpline, tmpdesc, '|');
+    if length(tmpline) > 0 then
         begin
-        TTF_SizeUTF8(Fontz[font].Handle, Str2PChar(tmpline), @i, @j);
+        TTF_SizeUTF8(Fontz[font].Handle, PChar(tmpline), @i, @j);
         if w < (i + wa) then
             w:= i + wa;
         inc(h, j + ha)
         end
     end;
 
-if extra <> '' then
+if length(extra) > 0 then
     begin
     // get extra label's dimensions
-    TTF_SizeUTF8(Fontz[font].Handle, Str2PChar(extra), @i, @j);
+    TTF_SizeUTF8(Fontz[font].Handle, PChar(extra), @i, @j);
     if w < (i + wa) then
         w:= i + wa;
     inc(h, j + ha);
@@ -968,31 +886,34 @@
 DrawRoundRect(@r, cWhiteColor, cNearBlackColor, tmpsurf, true);
 
 // render caption
-r:= WriteInRect(tmpsurf, 36 + cFontBorder + 2, ha, $ffffffff, font, caption);
+r:= WriteInRect(tmpsurf, 36 + cFontBorder + 2, ha, $ffffffff, font, PChar(caption));
 // render sub caption
-r:= WriteInRect(tmpsurf, 36 + cFontBorder + 2, r.y + r.h, $ffc7c7c7, font, subcaption);
+r:= WriteInRect(tmpsurf, 36 + cFontBorder + 2, r.y + r.h, $ffc7c7c7, font, PChar(subcaption));
 
 // render all description lines
 tmpdesc:= description;
-while tmpdesc <> '' do
+while length(tmpdesc) > 0 do
     begin
     tmpline:= tmpdesc;
-    SplitByChar(tmpline, tmpdesc, '|');
+    SplitByCharA(tmpline, tmpdesc, '|');
     r2:= r;
-    if tmpline <> '' then
+    if length(tmpline) > 0 then
         begin
-        r:= WriteInRect(tmpsurf, cFontBorder + 2, r.y + r.h, $ff707070, font, tmpline);
+        r:= WriteInRect(tmpsurf, cFontBorder + 2, r.y + r.h, $ff707070, font, PChar(tmpline));
 
         // render highlighted caption (if there is a ':')
         tmpline2:= _S'';
-        SplitByChar(tmpline, tmpline2, ':');
-        if tmpline2 <> _S'' then
-            WriteInRect(tmpsurf, cFontBorder + 2, r2.y + r2.h, $ffc7c7c7, font, tmpline + ':');
+        SplitByCharA(tmpline, tmpline2, ':');
+        if length(tmpline2) > 0 then
+            begin
+            tmpline:= tmpline + ':';
+            WriteInRect(tmpsurf, cFontBorder + 2, r2.y + r2.h, $ffc7c7c7, font, PChar(tmpline));
+            end;
         end
     end;
 
-if extra <> '' then
-    r:= WriteInRect(tmpsurf, cFontBorder + 2, r.y + r.h, extracolor, font, extra);
+if length(extra) > 0 then
+    r:= WriteInRect(tmpsurf, cFontBorder + 2, r.y + r.h, extracolor, font, PChar(extra));
 
 r.x:= cFontBorder + 6;
 r.y:= cFontBorder + 4;
@@ -1019,7 +940,7 @@
         end;
 
 // free old texture
-FreeWeaponTooltip;
+FreeAndNilTexture(WeaponTooltipTex);
 
 // image region
 i:= LongInt(atype) - 1;
@@ -1059,13 +980,6 @@
     DrawTexture(x, y, WeaponTooltipTex)
 end;
 
-procedure FreeWeaponTooltip;
-begin
-// free the existing texture (if there is any)
-FreeTexture(WeaponTooltipTex);
-WeaponTooltipTex:= nil
-end;
-
 {$IFDEF USE_VIDEO_RECORDING}
 procedure InitOffscreenOpenGL;
 begin
@@ -1171,10 +1085,11 @@
     SDLTry(SDLwindow <> nil, 'SDL_CreateWindow', true);
 
     SetupOpenGL();
+
     if reinit then
         begin
         // clean the window from any previous content
-        glClear(GL_COLOR_BUFFER_BIT);
+        RenderClear();
         if SuddenDeathDmg then
             SetSkyColor(SDSkyColor.r * (SDTint/255) / 255, SDSkyColor.g * (SDTint/255) / 255, SDSkyColor.b * (SDTint/255) / 255)
         else if ((cReducedQuality and rqNoBackground) = 0) then
@@ -1209,7 +1124,7 @@
 
 procedure SetSkyColor(r, g, b: real);
 begin
-    glClearColor(r, g, b, 0.99)
+    RenderSetClearColor(r, g, b, 0.99)
 end;
 
 procedure initModule;
@@ -1219,6 +1134,7 @@
     RegisterVariable('fullscr', @chFullScr, true);
 
     cScaleFactor:= 2.0;
+    updateViewLimits();
     Step:= 0;
     ProgrTex:= nil;
     SupportNPOTT:= false;
@@ -1233,11 +1149,26 @@
         CountTexz[i] := nil;
     SDLwindow:= nil;
     SDLGLcontext:= nil;
+
+    prevHat:= 'NoHat';
+    tmpHatSurf:= nil;
 end;
 
 procedure freeModule;
+var fi: THWFont;
 begin
     StoreRelease(false);
+    // make sure fonts are cleaned up
+    for fi:= Low(THWFont) to High(THWFont) do
+        with Fontz[fi] do
+            begin
+            if Handle <> nil then
+                begin
+                TTF_CloseFont(Handle);
+                Handle:= nil;
+                end;
+            end;
+
     TTF_Quit();
     SDL_GL_DeleteContext(SDLGLcontext);
     SDL_DestroyWindow(SDLwindow);