2d4156d6466764df359ec0a2177940f0f65eed22
[minwii.git] / src / pgu / hexvid.py
1 """Hexagonal tile engine.
2
3 <p>Note -- this engine is not finished. Sprites are not supported. It
4 can still be useful for using the level editor, and for rendering hex
5 terrains, however. If you are able to update it and use it in a real game,
6 help would be greatly appreciated!</p>
7
8 <p>please note that this file is alpha, and is subject to modification in
9 future versions of pgu!</p>
10
11 """
12 print 'pgu.hexvid','This module is alpha, and is subject to change.'
13
14 from pgu.vid import *
15 import pygame
16
17
18 class Hexvid(Vid):
19 """Create an hex vid engine. See [[vid]]"""
20 def update(self,screen):
21 return self.paint(screen)
22
23 def paint(self,screen):
24 sw,sh = screen.get_width(),screen.get_height()
25 self.view.w,self.view.h = sw,sh
26
27 tlayer = self.tlayer
28 blayer = self.blayer
29 #zlayer = self.zlayer
30 w,h = len(tlayer[0]),len(tlayer)
31
32 #iso_w,iso_h,iso_z,tile_w,tile_h,base_w,base_h = self.iso_w,self.iso_h,self.iso_z,self.tile_w,self.tile_h,self.base_w,self.base_h
33
34 tile_w,tile_h = self.tile_w,self.tile_h
35 tile_w2,tile_h2 = tile_w/2,tile_h/2
36
37 view = self.view
38 adj = self.adj = pygame.Rect(-self.view.x,-self.view.y,0,0)
39
40 w,h = len(tlayer[0]),len(tlayer)
41 tiles = self.tiles
42
43 #""
44 if self.bounds == None:
45 tmp,y1 = self.tile_to_view((0,0))
46 x1,tmp = self.tile_to_view((0,h+1))
47 tmp,y2 = self.tile_to_view((w+1,h+1))
48 x2,tmp = self.tile_to_view((w+1,0))
49 self.bounds = pygame.Rect(x1,y1,x2-x1,y2-y1)
50 print self.bounds
51 #""
52
53 if self.bounds != None: self.view.clamp_ip(self.bounds)
54
55 ox,oy = self.screen_to_tile((0,0))
56 sx,sy = self.tile_to_view((ox,oy))
57 dx,dy = sx - self.view.x,sy - self.view.y
58
59 bot = 1
60
61 tile_wi = tile_w + tile_w/2
62 tile_wi2 = tile_wi/2
63
64 #dx += tile_w/2
65
66 for i2 in xrange(-bot,self.view.h/tile_h2+bot*3): #NOTE: 3 seems a bit much, but it works.
67 tx,ty = ox + i2/2 + i2%2,oy + i2/2
68 x,y = (i2%2)*tile_wi2 + dx,i2*tile_h2 + dy
69
70 #to adjust for the -1 in i1
71 x,tx,ty = x-tile_wi,tx-1,ty+1
72
73 x -= tile_w/2
74 for i1 in xrange(-1,self.view.w/tile_wi+1):
75 if ty >= 0 and ty < h and tx >= 0 and tx < w:
76 if blayer != None:
77 n = blayer[ty][tx]
78 if n != 0:
79 t = tiles[n]
80 if t != None and t.image != None:
81 screen.blit(t.image,(x,y))
82 n = tlayer[ty][tx]
83 if n != 0:
84 t = tiles[n]
85 if t != None and t.image != None:
86 screen.blit(t.image,(x,y))
87
88
89 tx += 1
90 ty -= 1
91 x += tile_wi
92
93 return [pygame.Rect(0,0,screen.get_width(),screen.get_height())]
94
95 def view_to_tile(self,pos):
96 x,y = pos
97 #x = x + (self.tile_w*1/2)
98
99 x,y = int(x*4/(self.tile_w*3)), y*2/self.tile_h
100 nx = (x + y) / 2
101 ny = (y - x) / 2
102 return nx,ny
103
104 def tile_to_view(self,pos):
105 x,y = pos
106 nx = x - y
107 ny = x + y
108 nx,ny = int(nx*(self.tile_w*3)/4), ny*self.tile_h/2
109
110 #nx = nx - (self.tile_w*1/2)
111 return nx,ny
112
113 def screen_to_tile(self,pos): #NOTE HACK : not sure if the 3/8 is right or not, but it is pretty close...
114 pos = pos[0]+self.view.x + self.tile_w*3/8,pos[1]+self.view.y
115 pos = self.view_to_tile(pos)
116 return pos
117
118 def tile_to_screen(self,pos):
119 pos = self.tile_to_view(pos)
120 pos = pos[0]-self.view.x,pos[1]-self.view.y
121 return pos
122
123
124 def tga_load_tiles(self,fname,size,tdata={}):
125 Vid.tga_load_tiles(self,fname,size,tdata)
126
127 self.tile_w,self.tile_h = size