import pygame, math, random
from pygame.locals import *

class mice(pygame.sprite.Sprite):
	def __init__(self):
		pygame.sprite.Sprite.__init__(self)
		self.button = None
		self.position = None
		self.pressed = None
		self.raize = None
		
		self.image = pygame.Surface((0,0))
		self.image.set_colorkey((255,255,255))
		
	def update(self):
		self.button = pygame.mouse.get_pressed()	
		self.position = pygame.mouse.get_pos()
		if True in self.button :
			if self.pressed != True:
				self.raize = True
			else:
				self.raize = False
			self.pressed = True
		else:
			self.pressed = False
			self.raize = False
#--------------------------------------------------------------
#--------------------------------------------------------------
#--------------------------------------------------------------
class carree(pygame.sprite.Sprite):
	def redraw(self,pos):
		accum = int(10 * math.sqrt(self.size))		#around the its center
		self.image = pygame.Surface((accum,accum))#will redraw its image
		self.rect = self.image.get_rect()			#and recalculate its rect
		self.rect.center = pos
		self.image.set_colorkey((1,1,1))
		#self.image.fill((0,0,0))
		pygame.draw.rect(self.image,self.color,(2,2,self.rect.w-4,self.rect.h-4))
		self.wander, self.fear = (pos,0.0,0), (pos,0.0,0)

	def __init__(self,pos,color,spec,nfo,force=0):
		pygame.sprite.Sprite.__init__(self)
		self.move = [self.go_up, self.go_down, self.go_left, self.go_right]
		(self.pool, self.grp, self.limit, self.vibe) = self.nfo = nfo	#info about the game land
		(self.death, self.birth, self.procreate) = self.spec = spec		#info about about the unit
		self.color = color															#identificator
		if force == 0:						#you can initiate a size
			self.size = self.birth		#that is not directly the
		else:									#the same as the birth size
			self.size = force				#your sprite will begin with
		self.redraw(pos)
	
	def grow(self,size):
		if self.color != coal:
			self.size += size									#the size is an area
		#------------------------------
		if self.size >= self.procreate:				#when the size reach its limit
			while self.size > self.death:		#it multiply as mutch time its
				self.size -= self.birth			#its size equal the multiple of
				if self.color == coal:
					force = random.randint(int(self.death*10),int(self.procreate*10))/10.0
				else:
					force = 0
				self.grp.add(carree(self.rect.center,self.color,self.spec,self.nfo,force))
				self.go_rnd()				#its original size
		if self.size <= self.death:
			self.pool += self.size		#it's size is not lost
			self.grp.remove(self)		#it is recycled in the pool
		#------------------------------
		else:
			self.redraw(self.rect.center)
		
	def collide_with(self,other):
		if self.size <= other.size or other.color == coal:	#all carree must pull each other by size priority, 
			if self.rect.centerx < other.rect.centerx:		#if two carree are at the same 
				self.go_left()											#size , both are pulled at 
			elif self.rect.centerx > other.rect.centerx:		#opposite direction,but for  
				self.go_right()										#pulles at two carree of different 
			if self.rect.centery < other.rect.centery: 		#size, the smallest is opposite direction															
				self.go_up()											#
			elif self.rect.centery > other.rect.centery:		#
				self.go_down()											#
			if self.rect.centerx == other.rect.centerx and self.rect.centery == other.rect.centery:
				self.go_rnd()											#
			elif self.size > other.size and self.color != other.color and other.color != coal:
				other.grow(-0.1)		#little addition to the rule bigger square eat smaller
				self.grow(0.1)			#not the same color, it eat him slow and painfully

	def go_up(self):
		self.rect.centery -= 1
		self.vibe.append((self.rect.center, self.size))		#store movement
		
	def go_down(self):
		self.rect.centery += 1
		self.vibe.append((self.rect.center, self.size))
				
	def go_left(self):
		self.rect.centerx -= 1
		self.vibe.append((self.rect.center, self.size))
		
	def go_right(self):
		self.rect.centerx += 1
		self.vibe.append((self.rect.center, self.size))

	def go_rnd(self):
		random.choice(self.move)()

	def update(self):
		if self.limit.contains(self.rect) == False:
			self.grow(-0.1)		#all sprite that go out screen will perish
			self.pool += 0.1		#dont worry , it's size is returned to the pool
		for other in pygame.sprite.spritecollide(self, self.grp,0):
			if other != self and (self.color != coal or (self.color == coal and other.color == coal)):
					self.collide_with(other)
		#---------------------------------------
		


		
#--------------------------------------------------------------
#--------------------------------------------------------------
#--------------------------------------------------------------
pygame.init()
pygame.display.set_caption("Martin")
pygame.mouse.set_visible(1)
clock = pygame.time.Clock()
screen = pygame.display.set_mode((300, 300))
offscr = screen.get_rect()
end = False
mice = mice()
#-------------------------------------------------
spiele = pygame.sprite.Group()
vibe = []
pool = 999.0
nfo = (pool, spiele, offscr, vibe)

coal, coal_spec = (51,51,51), (0.1,2.0,5.0)
green, green_spec = (0,200,0), (0.3,0.4,0.5)
red = (200,0,0)
blue = (0,0,200)
spec = (0.9, 1.0, 9.0)

pos = (random.randint(10,280),random.randint(10,280))
rock = carree(pos,green,green_spec,nfo,20.0)
spiele.add(rock)
rock.grow(0)

pos = (random.randint(10,280),random.randint(10,280))
vege = carree(pos,coal,coal_spec,nfo,20.0)
spiele.add(vege)
vege.grow(0)

pos = (40,260)
spiele.add(carree(pos,blue,spec,nfo))
pos = (260,40)
spiele.add(carree(pos,red,spec,nfo))
#-------------------------------------------------
#-------------------------------------------------
while end == False :	
	clock.tick(30)
	pygame.display.flip()
	mice.update()
	for event in pygame.event.get():
    		if event.type == QUIT:
        			end = True
	#=======================================================
	vibe = []
	screen.fill((255,255,255))
	spiele.update()
	spiele.draw(screen)

	#======================================================
