--- /dev/null
+
+import pygame
+
+from OpenGL.GL import *
+from OpenGL.GLU import *
+
+def init(w, h):
+ pygame.init()
+ pygame.display.set_mode((w,h), pygame.OPENGL|pygame.DOUBLEBUF|pygame.FULLSCREEN)
+# pygame.display.set_mode((w,h),pygame.OPENGL|pygame.DOUBLEBUF)
+
+ glClearColor(0.0, 0.0, 0.0, 1.0)
+ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT)
+
+ glMatrixMode(GL_PROJECTION);
+ glLoadIdentity();
+ gluOrtho2D(0, w, 0, h);
+ glMatrixMode(GL_MODELVIEW);
+
+ #set up texturing
+ glEnable(GL_TEXTURE_2D)
+ glEnable(GL_BLEND);
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA)
+
+
+def load_image(image):
+ textureSurface = pygame.image.load(image)
+
+ textureData = pygame.image.tostring(textureSurface, "RGBA", 1)
+
+ width = textureSurface.get_width()
+ height = textureSurface.get_height()
+
+ texture = glGenTextures(1)
+ glBindTexture(GL_TEXTURE_2D, texture)
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
+ glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, textureData )
+
+ return texture, width, height
+
+
+def delTexture(texture):
+ glDeleteTextures(texture)
+
+
+def createTexDL(texture, width, height):
+ newList = glGenLists(1)
+ glNewList(newList,GL_COMPILE);
+ glBindTexture(GL_TEXTURE_2D, texture)
+ glBegin(GL_QUADS)
+ glTexCoord2f(0, 0); glVertex2f(0, 0) # Bottom Left Of The Texture and Quad
+ glTexCoord2f(0, 1); glVertex2f(0, height) # Top Left Of The Texture and Quad
+ glTexCoord2f(1, 1); glVertex2f( width, height) # Top Right Of The Texture and Quad
+ glTexCoord2f(1, 0); glVertex2f(width, 0) # Bottom Right Of The Texture and Quad
+ glEnd()
+ glEndList()
+
+ return newList
+
+def create_texture(image):
+ textureSurface = pygame.image.load(image)
+
+ textureData = pygame.image.tostring(textureSurface, "RGBA", 1)
+
+ width = textureSurface.get_width()
+ height = textureSurface.get_height()
+
+ texture = glGenTextures(1)
+ glBindTexture(GL_TEXTURE_2D, texture)
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
+ glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR)
+ glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, textureData )
+
+ newList = glGenLists(1)
+ glNewList(newList,GL_COMPILE);
+ glBindTexture(GL_TEXTURE_2D, texture)
+ glBegin(GL_QUADS)
+ glTexCoord2f(0, 0); glVertex2f(0, 0) # Bottom Left Of The Texture and Quad
+ glTexCoord2f(0, 1); glVertex2f(0, height) # Top Left Of The Texture and Quad
+ glTexCoord2f(1, 1); glVertex2f( width, height) # Top Right Of The Texture and Quad
+ glTexCoord2f(1, 0); glVertex2f(width, 0) # Bottom Right Of The Texture and Quad
+ glEnd()
+ glEndList()
+
+ return newList
+
+
+
+def delDL(list):
+ glDeleteLists(list, 1)
--- /dev/null
+#!/usr/bin/env python
+#coding:utf-8
+
+import pygame
+import pygame.midi
+import gutil as gu
+import os
+import math
+import random
+import threading
+from pygame.locals import *
+from OpenGL.GL import *
+import psyco
+import time
+import sys
+
+CURRENT_DIR = os.path.dirname(__file__)
+INSTRUMENT = 0
+
+WIDTH = 1024
+HEIGHT = 768
+KEY_MAP = os.path.join(CURRENT_DIR,"key.txt")
+FPS = 60
+MIDI_PORT = 2
+
+#min_note = 46
+#max_note = 75
+#number_of_notes = max_note - min_note + 1
+#theta2r = math.pi / 180
+
+new_key = [48,50,52,53,54,55,57,59,60,62,64,65,67,69,71,72,74,76]
+number_of_notes = len(new_key)
+space = WIDTH / number_of_notes
+
+class AnoEngine:
+ def __init__(self,writer,output=0):
+ pygame.midi.init()
+ self.midiout = pygame.midi.Output(MIDI_PORT)
+ self.INSTRUMENT = 0 #0:Piano#19:Organ,56:Trympet
+ self.set_instrument(self.INSTRUMENT)
+ self.sustain = False
+ self.default_volume = 128
+ self.writer = writer
+ self.on_notes = []
+ self.keys = {}
+ self.mouse_key = 0
+ #for i in xrange(number_of_notes + 1):
+ # self.keys[i] = min_note + i
+ self.key_map = self.load_key_map(KEY_MAP)
+
+ def set_instrument(self,instrument):
+ self.INSTRUMENT = instrument
+ self.midiout.set_instrument(instrument)
+
+ def rebus_sustain(self):
+ if self.sustain:
+ self.sustain = False
+ else:
+ self.sustain = True
+
+ def note_on(self,no,vol=100):
+ if not no in self.on_notes:
+ self.midiout.note_on(no,vol)
+ self.on_notes.append(no)
+
+ def note_off(self,no):
+ if no in self.on_notes:
+ self.midiout.note_off(no,0)
+ self.on_notes.remove(no)
+
+ def load_key_map(self,filename):
+ dic = {}
+ for line in open(filename,"r"):
+ if line[0] == "#":
+ pass
+ else:
+ [key,no,x,y] = [l.strip() for l in line.split(",")]
+ dic[eval(key)] = (int(no),(int(x),int(y)))
+ return dic
+
+ def on_event(self,events):
+ for event in events:
+ if event.type == KEYDOWN:
+ if event.key in self.key_map:
+ self.note_on(self.key_map[event.key][0])
+ self.writer.start(self.key_map[event.key][1])
+ if event.key == K_ESCAPE:
+ exit()
+ elif event.type == KEYUP:
+ if event.key in self.key_map:
+ self.note_off(self.key_map[event.key][0])
+ elif event.type == MOUSEBUTTONDOWN:
+ if event.button == 1:
+ (x,y) = pygame.mouse.get_pos()
+ y = HEIGHT - y
+ #key = self.keys[x // space]
+ key = new_key[x // space]
+ if y < (HEIGHT / 2):
+ self.note_on(key)
+ self.writer.start((x,y))
+ self.mouse_key = key
+ else:
+ self.note_on(key)
+ self.writer.start((x,y))
+ self.mouse_key = key
+ elif event.button == 2:
+ self.rebus_sustain()
+ elif event.type == MOUSEBUTTONUP:
+ if event.button == 1:
+ (x,y) = pygame.mouse.get_pos()
+ y = HEIGHT - y
+ key = [x // space]
+ self.note_off(self.mouse_key)
+ elif event.type == QUIT:
+ exit()
+
+class Circle:
+ def __init__(self,tex_lis):
+ self.maxrate = 2.0
+ self.tex_lis = tex_lis
+ self.on = False
+ self.x,self.y = (-100,-100)
+ self.ratep = 0.02
+ self.rate = 0
+
+ def draw(self):
+ if self.on:
+ glLoadIdentity()
+ glTranslatef(self.x - self.rate * 500,self.y - self.rate * 500,0)
+ glScale(self.rate,self.rate,0)
+ glCallList(self.tex_lis)
+
+ def start(self,(x,y)):
+ self.on = True
+ self.x,self.y = x,y
+ self.rate = 0
+
+ def update(self):
+ if self.on:
+ self.rate = self.rate + self.ratep
+ if self.rate > self.maxrate:
+ self.on = False
+ self.x,self.y = (-100,-100)
+
+class Line:
+ def __init__(self,tex_lis):
+ self.maxrate = 1.0
+ self.tex_lis = tex_lis
+ self.on = False
+ self.x,self.y = 0,0
+ self.ratep = 0.02
+ self.rate = 0
+ self.theta = 0
+
+ def draw(self):
+ if self.on:
+ glLoadIdentity()
+ glTranslatef(self.x - 750,self.y - 750,0)
+ glTranslatef(750,750,0)
+ glRotatef(self.theta,0,0,1)
+ glTranslatef(-750,-750,0)
+ glCallList(self.tex_lis)
+
+ def start(self,(x,y)):
+ self.on = True
+ self.x,self.y = x,y
+ self.rate = 0
+ self.theta = random.randint(0,360)
+
+ def update(self):
+ if self.on:
+ self.rate = self.rate + self.ratep
+ if self.rate > self.maxrate:
+ self.on = False
+ self.x,self.y = 0,0
+
+class Square:
+ def __init__(self,tex_lis):
+ self.maxrate = 2.0
+ self.tex_lis = tex_lis
+ self.on = False
+ self.x,self.y = (-100,-100)
+ self.ratep = 0.02
+ self.rate = 0
+ self.angle = 0
+ self.anglep = 1
+
+ def draw(self):
+ if self.on:
+ glLoadIdentity()
+ glTranslatef(self.x - self.rate * 500,self.y - self.rate * 500,0)
+ glScale(self.rate,self.rate,0)
+ glTranslatef(500,500,0)
+ glRotatef(self.angle,0,0,1)
+ glTranslatef(-500,-500,0)
+ glCallList(self.tex_lis)
+
+ def start(self,(x,y)):
+ self.on = True
+ self.x,self.y = x,y
+ self.rate = 0
+ self.anglep = random.choice((-1,1))
+ self.angle = random.randint(0,360)
+
+ def update(self):
+ if self.on:
+ self.rate = self.rate + self.ratep
+ self.angle = self.angle + self.anglep
+ if self.rate > self.maxrate:
+ self.on = False
+ self.x,self.y = (-100,-100)
+
+class Triangle:
+ def __init__(self,tex_lis):
+ self.maxrate = 2.0
+ self.tex_lis = tex_lis
+ self.on = False
+ self.x,self.y = (-100,-100)
+ self.ratep = 0.02
+ self.rate = 0
+ self.angle = 0
+ self.anglep = 1
+
+ def draw(self):
+ if self.on:
+ glLoadIdentity()
+ glTranslatef(self.x - self.rate * 500,self.y - self.rate * 500,0)
+ glScale(self.rate,self.rate,0)
+ glTranslatef(500,500,0)
+ glRotatef(self.angle,0,0,1)
+ glTranslatef(-500,-500,0)
+ glCallList(self.tex_lis)
+
+ def start(self,(x,y)):
+ self.on = True
+ self.x,self.y = x,y
+ self.rate = 0
+ self.anglep = random.choice((-1,1))
+ self.angle = random.randint(0,360)
+
+ def update(self):
+ if self.on:
+ self.rate = self.rate + self.ratep
+ self.angle = self.angle + self.anglep
+ if self.rate > self.maxrate:
+ self.on = False
+ self.x,self.y = (-100,-100)
+
+
+class Writer:
+ def __init__(self):
+ circle_tex = gu.create_texture(os.path.join(CURRENT_DIR,"circlet.png"))
+ square_tex = gu.create_texture(os.path.join(CURRENT_DIR,"squaret.png"))
+ line_tex = gu.create_texture(os.path.join(CURRENT_DIR,"line2t.png"))
+ triangle_tex = gu.create_texture(os.path.join(CURRENT_DIR,"trianglet.png"))
+ self.circles = [Circle(circle_tex) for i in xrange(8)]
+ self.squares = [Square(square_tex) for i in xrange(8)]
+ self.lines = [Line(line_tex) for i in xrange(8)]
+ self.triangles = [Triangle(triangle_tex) for i in xrange(8)]
+
+ def draw(self):
+ for c in self.circles:
+ c.draw()
+ for s in self.squares:
+ s.draw()
+ for l in self.lines:
+ l.draw()
+ for t in self.triangles:
+ t.draw()
+
+ def start(self,(x,y)):
+ r = random.choice((0,1,2,3))
+ if r == 0:
+ for c in self.circles:
+ if not c.on:
+ c.start((x,y))
+ return
+ elif r == 1:
+ for s in self.squares:
+ if not s.on:
+ s.start((x,y))
+ return
+ elif r == 2:
+ for l in self.lines:
+ if not l.on:
+ l.start((x,y))
+ return
+ elif r == 3:
+ for t in self.triangles:
+ if not t.on:
+ t.start((x,y))
+ return
+
+ def update(self):
+ for c in self.circles:
+ c.update()
+ for s in self.squares:
+ s.update()
+ for l in self.lines:
+ l.update()
+ for t in self.triangles:
+ t.update()
+
+def main():
+ psyco.full()
+ screen = gu.init(WIDTH,HEIGHT)
+ pygame.mouse.set_visible(True)
+ writer = Writer()
+ ano = AnoEngine(writer,MIDI_PORT)
+ clock = pygame.time.Clock()
+
+ while True:
+ clock.tick(FPS)
+ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT)
+ glLoadIdentity()
+ ano.on_event(pygame.event.get())
+ writer.update()
+ writer.draw()
+ pygame.display.flip()
+
+if __name__ == "__main__":
+ main()