#!/usr/bin/pythonimport Imageimport timeimport systry: opengl_support = True from OpenGL.GL import * from OpenGL.GLUT import * from OpenGL.GLU import *except: opengl_support=Falsetry: psyco_enabled=True import psyco psyco.log() psyco.profile() psyco.full()except: psyco_enabled=False########################################################################################################## class for handling geodata# needs geodata file as param# new_geodata = geodata('filename-without-.dat')## methods: encode() header()# ########################################################################################################class geodata: class openglgeo: # Number of the glut window. window = 0 # A general OpenGL initialization function. Sets all of the initial parameters. def InitGL(self,Width, Height): # We call this right after our OpenGL window is created. glClearColor(0.0, 0.0, 0.0, 0.0) # This Will Clear The Background Color To Black glClearDepth(1.0) # Enables Clearing Of The Depth Buffer glDepthFunc(GL_LESS) # The Type Of Depth Test To Do glEnable(GL_DEPTH_TEST) # Enables Depth Testing glShadeModel(GL_SMOOTH) # Enables Smooth Color Shading glMatrixMode(GL_PROJECTION) glLoadIdentity() # Reset The Projection Matrix # Calculate The Aspect Ratio Of The Window gluPerspective(45.0, float(Width)/float(Height), 0.1, 100.0) glMatrixMode(GL_MODELVIEW) # The function called when our window is resized (which shouldn't happen if you enable fullscreen, below) def ReSizeGLScene(self,Width, Height): if Height == 0: # Prevent A Divide By Zero If The Window Is Too Small Height = 1 glViewport(0, 0, Width, Height) # Reset The Current Viewport And Perspective Transformation glMatrixMode(GL_PROJECTION) glLoadIdentity() gluPerspective(45.0, float(Width)/float(Height), 0.1, 100.0) glMatrixMode(GL_MODELVIEW) # The main drawing function. def DrawGLScene(self): # Clear The Screen And The Depth Buffer glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT) glLoadIdentity() # Reset The View # since this is double buffered, swap the buffers to display what just got drawn. glutSwapBuffers() # The function called whenever a key is pressed. Note the use of Python tuples to pass in: (key, x, y) def keyPressed(*args): global window # If escape is pressed, kill everything. if args[0] == '\033': self=None# sys.exit() def __init__(self): global window # pass arguments to init glutInit([]) # Select type of Display mode: # Double buffer # RGBA color # Alpha components supported # Depth buffer glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH) # get a 640 x 480 window glutInitWindowSize(640, 480) # the window starts at the upper left corner of the screen glutInitWindowPosition(0, 0) # Okay, like the C version we retain the window id to use when closing, but for those of you new # to Python (like myself), remember this assignment would make the variable local and not global # if it weren't for the global declaration at the start of main. window = glutCreateWindow("GEOCONV 0.2") # Register the drawing function with glut, BUT in Python land, at least using PyOpenGL, we need to # set the function pointer and invoke a function to actually register the callback, otherwise it # would be very much like the C version of the code. glutDisplayFunc(self.DrawGLScene) # Uncomment this line to get full screen. #glutFullScreen() # When we are doing nothing, redraw the scene. glutIdleFunc(self.DrawGLScene) # Register the function called when our window is resized. glutReshapeFunc(self.ReSizeGLScene) # Register the function called when the keyboard is pressed. glutKeyboardFunc(self.keyPressed) # Initialize our window. self.InitGL(640, 480) # Start Event Processing Engine # glutMainLoop() class logger: def write(self,some_string): if self.dump: self.log_file.write(str(some_string)) return 0 def __init__(self,filename,to_file_bol=True): self.dump=to_file_bol if self.dump: self.log_file = open(filename+'.log','wb') def __del__(self): if self.dump: self.log_file.close() class geoimage: def _color_value(self,z): return z+50000 def putpixel(self,x,y,z): self.image.putpixel((x,y),self._color_value(z)) def putpixel8x8(self,x,y,z): if isinstance(z,int): for sub_x in range(0,8): for sub_y in range(0,8): self.putpixel(x+sub_x,y+sub_y,z) else: counter=0 for sub_x in range(0,8): for sub_y in range(0,8): self.putpixel(x+sub_x,y+sub_y,max(z[counter])) counter+=1 def __init__(self,filename): self.filename=filename self.image = Image.new('RGB', (2048,2048), (52390)) def __del__(self): self.image.save(self.filename+'.png') def print_progress(self): print "|", #################################################################################################### # # converts bytes hex values # #################################################################################################### def convert_to_hex(self,byte): if len(byte)==0: self.log.write('EOF REACHED') return '00' return hex(ord(byte))[2:].upper().zfill(2) #################################################################################################### # # test if z is > maxz if yes set maxz = z # #################################################################################################### def _maxz(self,z=None): if z: # getting max z if z!=0: if self.maxz == None: self.maxz = z else: if self.maxz < z: self.maxz = z return self.maxz #################################################################################################### # # test if z is < minz if yes set minz = z # #################################################################################################### def _minz(self,z=None): if z: # getting min z if self.minz == None: self.minz = z else: if self.minz > z: self.minz = z return self.minz #################################################################################################### # # getz z value from file # #################################################################################################### def _getz(self,dprint=False): # read bytes z2 = self.convert_to_hex(self.conv_file.read(1)) z1 = self.convert_to_hex(self.conv_file.read(1)) if dprint: self.log.write(z1 + ' ' + z2 + ' ') # converts to int z = int(z1+z2,16) # get the real z1 if z > 55000: z = z - 65336 self._maxz(z) self._minz(z) return z #################################################################################################### # # block 0000 handler # z1 min-z z2 max-z # #################################################################################################### def _handle_block0000(self): # getting the bytes for z1/z2 z1 = self._getz() z2 = self._getz() return z1,z2 #################################################################################################### # # block 0040 handler # return a 8x8 subcell # #################################################################################################### def _handle_block0040(self): # loop 64 times return_data = [] counter = 0 for sub_x in range(0,8): for sub_y in range(0,8): z = self._getz() / 2 if self.image: self.image.putpixel(self.x+sub_x,self.y+sub_y,z) return_data.append(z) counter+=1 return return_data #################################################################################################### # # block 0041 handler # #################################################################################################### def _handle_block0041(self,header): if header == '42': dprint = True self.log.write('\n-------\n') else: dprint = False return_data_sub = [] return_data = [] # loop 64 times for item in range(0,64): # get count of layers layercount = self._getz(dprint) for i in range(0,layercount): z = self._getz(dprint) / 2 return_data_sub.append(z) return_data.append(return_data_sub) if header == '42': dprint = True self.log.write('\n-------\n') go_on=False while go_on==False: position = int(self.conv_file.tell()) testbyte1 = self.conv_file.read(1) testbyte2 = self.conv_file.read(1) if self.convert_to_hex(testbyte2) == '00' and ( (int(self.convert_to_hex(testbyte1),16)>=64 and int(self.convert_to_hex(testbyte1),16)<=99) or self.convert_to_hex(testbyte1)=='00' or self.convert_to_hex(testbyte1)=='40'): go_on=True else: self.log.write(self.convert_to_hex(testbyte1) + ' ' + self.convert_to_hex(testbyte2) + ' ') self.conv_file.seek(position) if header == '42': dprint = True self.log.write('\n-------\n') return return_data #################################################################################################### # # Decodes the geodata # #################################################################################################### def decode(self): #self.glgeo = self.openglgeo() start = time.time() if self.dump_image: self.image = self.geoimage(self.filename) else: self.image =False self.conv_file.seek(18) data=[] counter=0 counter_percent = range(0,256*256,((256*256)/25)) # make x loop for self.x in range(0,2048,8): # make y loop for self.y in range(0,2048,8): if counter in counter_percent: self.print_progress() counter= counter + 1 # reads data header block1 = self.conv_file.read(1) block2 = self.conv_file.read(1) block1_hex = self.convert_to_hex(block1) # handles the data if block1_hex == 'ff': self.log.write('x: %s y: %s block: 00 ERROR \n' %(str(self.x),str(self.y))) elif block1_hex == '00': # get data z1,z2 = self._handle_block0000() if self.image: self.image.putpixel8x8(self.x,self.y,z1) # check for water - z1!=z2 water if z1==z2: data.append([self.x,self.y,z1,'F']) else: for item in range(z1,z2,32): data.append([self.x,self.y,item,'W']) self.log.write('x: %s y: %s block: 00 ok \n' %(str(self.x),str(self.y))) elif block1_hex == '40': z_data = self._handle_block0040() self.log.write('x: %s y: %s block: 40 ok \n' %(str(self.x),str(self.y))) elif int(block1_hex,16)>=64 and int(block1_hex,16)<=99: z_data = self._handle_block0041(block1_hex) if self.image: self.image.putpixel8x8(self.x,self.y,z_data) self.log.write('x: %s y: %s block: %s ok \n' %(str(self.x),str(self.y),block1_hex)) else: self.log.write('x: %s y: %s block00 %s ERROR??? \n' %((str(self.x)),(str(self.y)),block1_hex)) # debug output print str(counter) self.log.write(' minz: %s maxz: %s \n' %(str(self._minz()),str(self._maxz()))) self.image = None end = time.time() print str(end-start) return 'foobar' def header(self): position = int(self.conv_file.tell()) self.conv_file.seek(0) mapx = self.conv_file.read(1) mapx =int(self.convert_to_hex(mapx),16) mapy = self.conv_file.read(1) mapy = int(self.convert_to_hex(mapy),16) self.conv_file.seek(position) return mapx,mapy def __init__(self,filename,log=True,image=True): # init basic vars self.log=self.logger(filename,log) self.dump_image=image self.filename=filename self.minz=None self.maxz=None # open files self.conv_file = open(self.filename+'.dat','rb') def __del__(self): self.conv_file.close() self.log.write('** File closed\n\n')########################################################################################################## Main Function##########################################################################################################field_of_silence = geodata('22_23_conv',False,True)#field_of_silence.decode()#field_of_silence = None#giants_cave = geodata('25_19_conv')#giants_cave.decode()#bla1= geodata('22_22_conv')#bla1.decode()tower_of_insolence = geodata('23_18_conv')tower_of_insolence.decode()