Advertisement
trishLEX

Lab6

May 15th, 2017
482
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 16.99 KB | None | 0 0
  1. import glfw
  2. from OpenGL.GL import *
  3. from OpenGL.GLU import *
  4. import math
  5. import json
  6. import PIL.Image
  7.  
  8. im = "texture.bmp"
  9.  
  10. def background():
  11.     glClearColor(0.8, 0.8, 0.8, 1.0)
  12.     glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT)
  13.     glEnable(GL_DEPTH_TEST)
  14.  
  15.  
  16. def mouseCallback(window, button, action, mods):
  17.     size = 3
  18.     if button == glfw.MOUSE_BUTTON_1 and action and torus.isWire:
  19.         torus.isWire = False
  20.     elif button == glfw.MOUSE_BUTTON_1 and action and not torus.isWire:
  21.         torus.isWire = True
  22.     elif button == glfw.MOUSE_BUTTON_2 and action:
  23.         torus.counter += 1
  24.         print(torus.counter, size)
  25.         torus.currentGL_Pname = torus.GL_Pnames[torus.counter % size]
  26.         print("NOW GLpname is", torus.currentGL_Pname)
  27.  
  28.  
  29. def keyCallback(window, key, scancode, action, mods):
  30.     if key == glfw.KEY_SPACE and action:
  31.         torus.save()
  32.     elif key == glfw.KEY_INSERT and action:
  33.         torus.isOpened = True
  34.         torus.open()
  35.     elif key == glfw.KEY_W and action:
  36.         torus.center[1] += 0.1
  37.     elif key == glfw.KEY_A and action:
  38.         torus.center[0] -= 0.1
  39.     elif key == glfw.KEY_D and action:
  40.         torus.center[0] += 0.1
  41.     elif key == glfw.KEY_S and action:
  42.         torus.center[1] -= 0.1
  43.     elif key == glfw.KEY_UP and action:
  44.         torus.rotate_x += 10.0
  45.     elif key == glfw.KEY_DOWN and action:
  46.         torus.rotate_x -= 10.0
  47.     elif key == glfw.KEY_LEFT and action:
  48.         torus.rotate_y += 10.0
  49.     elif key == glfw.KEY_RIGHT and action:
  50.         torus.rotate_y -= 10.0
  51.     elif key == glfw.KEY_KP_SUBTRACT and action and torus.nsides > 3:
  52.         torus.nsides -= 1
  53.         torus.rings -= 1
  54.         torus.polygonMesh = []
  55.         torus.setMesh()
  56.     elif key == glfw.KEY_KP_ADD and action:
  57.         torus.nsides += 1
  58.         torus.rings += 1
  59.         torus.polygonMesh = []
  60.         torus.setMesh()
  61.     elif key == glfw.KEY_ENTER and action:
  62.         torus.h0 = torus.center
  63.         if not torus.isOpened:
  64.             torus.v0 = [0.2, 0.2, 0.2]
  65.             torus.t = 0
  66.         torus.isOpened = False
  67.         torus.drop = True
  68.     elif key == glfw.KEY_PAUSE and action:
  69.         torus.drop = False
  70.     elif key == glfw.KEY_DELETE and action:
  71.         torus.clear()
  72.     elif key == glfw.KEY_T and action:
  73.         if torus.isTextured:
  74.             torus.isTextured = False
  75.         else:
  76.             torus.isTextured = True
  77.     elif key == glfw.KEY_1 and action:
  78.         if torus.currentGL_Pname == GL_LIGHT_MODEL_AMBIENT:
  79.             if torus.GL_Pnames_dict.get(torus.currentGL_Pname)[0] > -3:
  80.                 value = torus.GL_Pnames_dict.get(torus.currentGL_Pname)
  81.                 for i in range(3):
  82.                     value[i] -= 0.1
  83.                 torus.GL_Pnames_dict.update({torus.currentGL_Pname: value})
  84.         else:
  85.             value = torus.GL_Pnames_dict.get(torus.currentGL_Pname)
  86.             value = not value
  87.             torus.GL_Pnames_dict.update({torus.currentGL_Pname: value})
  88.         print(torus.GL_Pnames_dict)
  89.     elif key == glfw.KEY_2 and action:
  90.         if torus.currentGL_Pname == GL_LIGHT_MODEL_AMBIENT:
  91.             if torus.GL_Pnames_dict.get(torus.currentGL_Pname)[0] < 4:
  92.                 value = torus.GL_Pnames_dict.get(torus.currentGL_Pname)
  93.                 for i in range(3):
  94.                     value[i] += 0.1
  95.                 torus.GL_Pnames_dict.update({torus.currentGL_Pname: value})
  96.         else:
  97.             value = torus.GL_Pnames_dict.get(torus.currentGL_Pname)
  98.             value = not value
  99.             torus.GL_Pnames_dict.update({torus.currentGL_Pname: value})
  100.         print(torus.GL_Pnames_dict)
  101.  
  102.  
  103.  
  104. class Torus:
  105.     def __init__(self):
  106.         self.isTextured = False
  107.         self.polygonMesh = []
  108.         self.normals = []
  109.         self.center = [0, 0, 0]
  110.         self.nsides = 3
  111.         self.rings = 3
  112.         self.r = 0.2
  113.         self.R = 0.4
  114.         self.rotate_x = 0
  115.         self.rotate_y = 0
  116.         self.isWire = False
  117.         self.setMesh()
  118.         self.GL_Pnames_dict = {GL_LIGHT_MODEL_AMBIENT: [0.2, 0.2, 0.2, 1.0], GL_LIGHT_MODEL_LOCAL_VIEWER: GL_FALSE,
  119.                                GL_LIGHT_MODEL_TWO_SIDE: GL_TRUE}
  120.         self.GL_Pnames = (GL_LIGHT_MODEL_AMBIENT, GL_LIGHT_MODEL_LOCAL_VIEWER, GL_LIGHT_MODEL_TWO_SIDE)
  121.         self.currentGL_Pname = GL_LIGHT_MODEL_AMBIENT
  122.         self.drop = False
  123.         self.counter = 0
  124.         self.v0 = [0.2, 0.2, 0.2]
  125.         self.h0 = [0, 0, 0]
  126.         self.t = 0
  127.         self.isOpened = False
  128.  
  129.     def setMesh(self):
  130.         for i in range(self.rings):
  131.             theta = i * 2.0 * math.pi / self.rings
  132.             theta1 = ((i + 1) % self.rings) * 2.0 * math.pi / self.rings
  133.             for j in range(self.nsides):
  134.                 phi = j * 2.0 * math.pi / self.nsides
  135.                 phi1 = ((j + 1) % self.nsides) * 2.0 * math.pi / self.nsides
  136.  
  137.                 p0 = [math.cos(theta) * (self.R + self.r * math.cos(phi)),
  138.                       - math.sin(theta) * (self.R + self.r * math.cos(phi)),
  139.                       self.r * math.sin(phi)]
  140.                 p1 = [math.cos(theta1) * (self.R + self.r * math.cos(phi)),
  141.                       - math.sin(theta1) * (self.R + self.r * math.cos(phi)),
  142.                       self.r * math.sin(phi)]
  143.                 p2 = [math.cos(theta1) * (self.R + self.r * math.cos(phi1)),
  144.                       - math.sin(theta1) * (self.R + self.r * math.cos(phi1)),
  145.                       self.r * math.sin(phi1)]
  146.                 p3 = [math.cos(theta) * (self.R + self.r * math.cos(phi1)),
  147.                       - math.sin(theta) * (self.R + self.r * math.cos(phi1)),
  148.                       self.r * math.sin(phi1)]
  149.  
  150.                 p = [p0, p1, p2, p3]
  151.  
  152.                 n0 = [math.cos(theta) * (math.cos(phi)), -math.sin(theta) * (math.cos(phi)), math.sin(phi)]
  153.                 n1 = [math.cos(theta1) * (math.cos(phi)), -math.sin(theta1) * (math.cos(phi)), math.sin(phi)]
  154.                 n2 = [math.cos(theta1) * (math.cos(phi1)), -math.sin(theta1) * (math.cos(phi1)), math.sin(phi1)]
  155.                 n3 = [math.cos(theta) * (math.cos(phi1)), -math.sin(theta) * (math.cos(phi1)), math.sin(phi1)]
  156.  
  157.                 n = [n0, n1, n2, n3]
  158.  
  159.                 self.polygonMesh.append(p)
  160.                 self.normals.append(n)
  161.  
  162.     def clear(self):
  163.         self.polygonMesh = []
  164.         self.normals = []
  165.         self.center = [0, 0, 0]
  166.         self.nsides = 4
  167.         self.rings = 4
  168.         self.r = 0.2
  169.         self.R = 0.4
  170.         self.rotate_x = 0
  171.         self.rotate_y = 0
  172.         self.isWire = False
  173.         self.setMesh()
  174.         self.GL_Pnames_dict = {GL_LIGHT_MODEL_AMBIENT: [0.2, 0.2, 0.2, 1.0], GL_LIGHT_MODEL_LOCAL_VIEWER: GL_FALSE,
  175.                                GL_LIGHT_MODEL_TWO_SIDE: GL_TRUE}
  176.         self.GL_Pnames = (GL_LIGHT_MODEL_AMBIENT, GL_LIGHT_MODEL_LOCAL_VIEWER, GL_LIGHT_MODEL_TWO_SIDE)
  177.         self.currentGL_Pname = GL_LIGHT_MODEL_AMBIENT
  178.         self.drop = False
  179.         self.counter = 0
  180.         self.v0 = [0.2, 0.2, 0.2]
  181.         self.h0 = [0, 0, 0]
  182.         self.t = 0
  183.         self.isOpened = False
  184.  
  185.     def save(self):
  186.         print("SAVING")
  187.         jsonFile = {'polygonMesh': self.polygonMesh, 'normals': self.normals, 'center': self.center,
  188.                     'nsides': self.nsides, 'rings': self.rings, 'r': self.r, 'R': self.R, 'rotate_x': self.rotate_x,
  189.                     'rotate_y': self.rotate_y, 'isWire': self.isWire, 'GL_Pnames_dict': self.GL_Pnames_dict,
  190.                     'GL_Pnames': self.GL_Pnames, 'currentGL_Pname': self.currentGL_Pname, 'drop': self.drop,
  191.                     'counter': self.counter, 'v0': self.v0, 'h0': self.h0, 't': self.t, 'isOpened': self.isOpened, 'isTextured': self.isTextured}
  192.         file = open("scene.txt", "w")
  193.         file.write(json.dumps(jsonFile))
  194.         file.close()
  195.  
  196.     def open(self):
  197.         print("OPENING")
  198.         file = open("scene.txt")
  199.         jsonf = json.loads(file.read())
  200.         self.polygonMesh = jsonf['polygonMesh']
  201.         self.normals = jsonf['normals']
  202.         self.center = jsonf['center']
  203.         self.nsides = jsonf['nsides']
  204.         self.rings = jsonf['rings']
  205.         self.r = jsonf['r']
  206.         self.R = jsonf['R']
  207.         self.rotate_x = jsonf['rotate_x']
  208.         self.rotate_y = jsonf['rotate_y']
  209.         self.isWire = jsonf['isWire']
  210.         self.GL_Pnames_dict = jsonf['GL_Pnames_dict']
  211.  
  212.         dict = {}
  213.         for i in range(3):
  214.             b = self.GL_Pnames_dict.popitem()
  215.             a = [b[0], b[1]]
  216.             if a[0] == '2898':
  217.                 a[0] = GL_LIGHT_MODEL_TWO_SIDE
  218.             elif a[0] == '2897':
  219.                 a[0] = GL_LIGHT_MODEL_LOCAL_VIEWER
  220.             else:
  221.                 a[0] = GL_LIGHT_MODEL_AMBIENT
  222.             dict.update({a[0]: a[1]})
  223.         self.GL_Pnames_dict = dict
  224.  
  225.         self.GL_Pnames = jsonf['GL_Pnames']
  226.         for i in range(3):
  227.             if self.GL_Pnames[i] == '2898':
  228.                 self.GL_Pnames[i] = GL_LIGHT_MODEL_TWO_SIDE
  229.             elif self.GL_Pnames[i] == '2897':
  230.                 self.GL_Pnames[i] = GL_LIGHT_MODEL_LOCAL_VIEWER
  231.             else:
  232.                 self.GL_Pnames[i] = GL_LIGHT_MODEL_AMBIENT
  233.  
  234.         self.currentGL_Pname = jsonf['currentGL_Pname']
  235.         if self.currentGL_Pname == '2898':
  236.             self.currentGL_Pname = GL_LIGHT_MODEL_TWO_SIDE
  237.         elif self.currentGL_Pname == '2897':
  238.             self.currentGL_Pname = GL_LIGHT_MODEL_LOCAL_VIEWER
  239.         else:
  240.             self.currentGL_Pname = GL_LIGHT_MODEL_AMBIENT
  241.  
  242.         self.drop = jsonf['drop']
  243.         self.counter = jsonf['counter']
  244.         self.v0 = jsonf['v0']
  245.         self.h0 = jsonf['h0']
  246.         self.t = jsonf['t']
  247.         self.isOpened = jsonf['isOpened']
  248.         self.isTextured = jsonf['isTextured']
  249.         file.close()
  250.  
  251.  
  252. def drawTorus():
  253.     glPointSize(1)
  254.     glLineWidth(2)
  255.  
  256.     if torus.isWire:
  257.         glPolygonMode(GL_FRONT_AND_BACK, GL_LINE)
  258.     else:
  259.         glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)
  260.  
  261.     glMatrixMode(GL_PROJECTION)
  262.     glLoadIdentity()
  263.  
  264.     theta = math.asin(0.5 / math.sqrt(2))
  265.     phi = math.asin(0.5 / math.sqrt(2 - 0.25))
  266.  
  267.     a = [1, 0, 0, 0, 0, 1, 0, 0, 0, 0, -1, 0, 0, 0, 0, 1]
  268.     b = [1, 0, 0, 0, 0, math.cos(theta), math.sin(theta), 0, 0, -math.sin(theta), math.cos(theta), 0, 0, 0, 0, 1]
  269.     c = [math.cos(phi), 0, -math.sin(phi), 0, 0, 1, 0, 0, math.sin(phi), 0, math.cos(phi), 0, 0, 0, 0, 1]
  270.  
  271.     glMultMatrixf(a)
  272.     glMultMatrixf(b)
  273.     glMultMatrixf(c)
  274.  
  275.     glMatrixMode(GL_MODELVIEW)
  276.     glLoadIdentity()
  277.  
  278.     glRotatef(torus.rotate_x, 1, 0, 0)
  279.     glRotatef(torus.rotate_y, 0, 1, 0)
  280.  
  281.     glTranslatef(torus.center[0], torus.center[1], torus.center[2])
  282.  
  283.     count = torus.rings * torus.nsides
  284.     global texture
  285.     glBindTexture(GL_TEXTURE_2D, texture)
  286.     k = 1
  287.     for i in range(count):
  288.         glEnable(GL_NORMALIZE)
  289.         glBegin(GL_POLYGON)
  290.         n = torus.rings
  291.         if i % n == 0 and i != 0:
  292.             k -= 1 / n
  293.         if k > 1 or k < 0:
  294.             print("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA")
  295.         #glTexCoord2f(1.0, 1.0)
  296.         #glTexCoord2f((i % n + 1) / n, (i % n + 1) / n)
  297.         #glColor3f(1.0, 0.0, 0.0)
  298.         glTexCoord2f(k, (i % n + 1) / n)
  299.         #print(k, (i % n + 1) / n)
  300.         glVertex3fv(torus.polygonMesh[i][3])
  301.         #print(torus.polygonMesh[i][3])
  302.         #glTexCoord2f(1.0, 0.0)
  303.         #glTexCoord2f((i % n) / n, (i % n + 1) / n)
  304.         #glColor3f(0.0, 1.0, 0.0)
  305.         glTexCoord2f(k - 1/n, (i % n + 1) / n)
  306.         #print(k - 1/n, (i % n + 1) / n)
  307.         glVertex3fv(torus.polygonMesh[i][2])
  308.         #print(torus.polygonMesh[i][2])
  309.         #glTexCoord2f(1.0, 1.0)
  310.         #glTexCoord2f((i % n) / n, (i % n) / n)
  311.         #glColor3f(0.0, 0.0, 1.0)
  312.         glTexCoord2f(k -1/n, (i % n) / n)
  313.         #print(k -1/n, (i % n) / n)
  314.         glVertex3fv(torus.polygonMesh[i][1])
  315.         #print(torus.polygonMesh[i][1])
  316.         #glTexCoord2f(0.0, 1.0)
  317.         #glTexCoord2f((i % n + 1) / n, (i % n) / n)
  318.         #glColor3f(1.0, 1.0, 1.0)
  319.         glTexCoord2f(k, (i % n) / n)
  320.         #print(k, (i % n) / n)
  321.         glVertex3fv(torus.polygonMesh[i][0])
  322.         #print(torus.polygonMesh[i][0])
  323.  
  324.         #print('==================', i % n)
  325.  
  326.         glEnd()
  327.  
  328.  
  329. def makeLighting():
  330.     glEnable(GL_LIGHTING)
  331.     glEnable(GL_LIGHT0)
  332.  
  333.     glLightfv(GL_LIGHT0, GL_AMBIENT | GL_DIFFUSE | GL_SPECULAR, (0.5, 0.5, 0.5, 1))
  334.  
  335.     glLightModelfv(GL_LIGHT_MODEL_AMBIENT, torus.GL_Pnames_dict.get(GL_LIGHT_MODEL_AMBIENT))
  336.     glLightModelfv(GL_LIGHT_MODEL_LOCAL_VIEWER, torus.GL_Pnames_dict.get(GL_LIGHT_MODEL_LOCAL_VIEWER))
  337.     glLightModelfv(GL_LIGHT_MODEL_TWO_SIDE, torus.GL_Pnames_dict.get(GL_LIGHT_MODEL_TWO_SIDE))
  338.  
  339.     # glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, [0.2, 0.2, 0.2, 1])  ###рассеянный свет
  340.     # glMaterialfv(GL_FRONT, GL_SPECULAR, [0.7, 0.7, 0.7, 1])  ###отражаемый свет
  341.     # glMaterialfv(GL_FRONT, GL_EMISSION, [0.5, 0.5, 0.5, 1])  ###излучаемый свет
  342.     # glMaterialfv(GL_FRONT, GL_SHININESS, 1)  # степень блеска
  343.  
  344.  
  345. def h(time):
  346.     x = torus.h0[0] + torus.v0[0] * time
  347.     y = torus.h0[1] + torus.v0[1] * time - 9.8 * time * time / 2
  348.     z = torus.h0[2] + torus.v0[2] * time
  349.     if x + torus.R >= 1 or x - torus.R <= -1:
  350.         torus.v0 = v(time)
  351.         torus.v0 = [-torus.v0[0], torus.v0[1], torus.v0[2]]
  352.         torus.t = 0
  353.         if x + torus.R >= 1:
  354.             torus.h0 = [1 - torus.R, torus.center[1], torus.center[2]]
  355.             return torus.h0
  356.         elif x - torus.R <= -1:
  357.             torus.h0 = [-1 + torus.R, torus.center[1], torus.center[2]]
  358.             return torus.h0
  359.     elif y + torus.R >= 1 or y - torus.R <= -1:
  360.         torus.v0 = v(time)
  361.         torus.v0 = [torus.v0[0], -torus.v0[1], torus.v0[2]]
  362.         torus.t = 0
  363.         if y + torus.R >= 1:
  364.             torus.h0 = [torus.center[0], 1 - torus.R, torus.center[2]]
  365.             return torus.h0
  366.         elif y - torus.R <= -1:
  367.             torus.h0 = [torus.center[0], -1 + torus.R, torus.center[2]]
  368.             return torus.h0
  369.     elif z + torus.R >= 1 or z - torus.R <= -1:
  370.         torus.v0 = v(time)
  371.         torus.v0 = [torus.v0[0], torus.v0[1], -torus.v0[2]]
  372.         torus.t = 0
  373.         if z + torus.R >= 1:
  374.             torus.h0 = [torus.center[0], torus.center[1], 1 - torus.R]
  375.             return torus.h0
  376.         elif z - torus.R <= -1:
  377.             torus.h0 = [torus.center[0], torus.center[1], -1 + torus.R]
  378.             return torus.h0
  379.     else:
  380.         return [x, y, z]
  381.  
  382.  
  383. def v(time):
  384.     vector = [0, 0, 0]
  385.     vector[0] = torus.v0[0]
  386.     vector[1] = torus.v0[1] - 9.8 * time
  387.     vector[2] = torus.v0[2]
  388.     return vector
  389.  
  390.  
  391. def drop(t):
  392.     if 0.6 in [abs(i) for i in h(t + 1 / 60)]:
  393.         print("impact, torus.center =", torus.center)
  394.         return torus.center
  395.     else:
  396.         point = h(t)
  397.         print("point", point)
  398.         return point
  399.  
  400.  
  401. def draw():
  402.     drawTorus()
  403.     makeLighting()
  404.     if torus.drop:
  405.         torus.t += 1 / 60
  406.         # print(t)
  407.         center = drop(torus.t)
  408.         # print("center", center)
  409.         print("v0", torus.v0)
  410.         torus.center = center
  411.     if torus.isTextured:
  412.         init()
  413.     else:
  414.         glDisable(GL_TEXTURE_2D)
  415.  
  416.  
  417. class Drawer:
  418.     window = False
  419.  
  420.     def __init__(self):
  421.         if not glfw.init():
  422.             return
  423.  
  424.         self.window = glfw.create_window(800, 800, "Lab3", None, None)
  425.         if not self.window:
  426.             glfw.terminate()
  427.             return
  428.  
  429.         glfw.make_context_current(self.window)
  430.  
  431.         glfw.set_mouse_button_callback(self.window, mouseCallback)
  432.         glfw.set_key_callback(self.window, keyCallback)
  433.  
  434.         global texture
  435.         texture = loadTexture(im)
  436.  
  437.     def startLoop(self):
  438.         while not glfw.window_should_close(self.window):
  439.             background()
  440.             draw()
  441.  
  442.             glfw.swap_buffers(self.window)
  443.             glfw.poll_events()
  444.  
  445.         glfw.terminate()
  446.  
  447. def init ():
  448.     glClearDepth ( 1.0 )
  449.     glDepthFunc  ( GL_LEQUAL )
  450.     glEnable     ( GL_DEPTH_TEST )
  451.     glEnable     ( GL_TEXTURE_2D )
  452.     glHint       ( GL_POLYGON_SMOOTH_HINT,         GL_NICEST )
  453.     glHint       ( GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST )
  454.     glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE)
  455.  
  456. def loadTexture(fileName):
  457.     image = PIL.Image.open(fileName)
  458.     width = image.size[0]
  459.     height = image.size[1]
  460.     image = image.tobytes("raw", "RGBA", 0, -1)
  461.     texture = glGenTextures(1)
  462.  
  463.     glBindTexture(GL_TEXTURE_2D, texture)
  464.     glPixelStorei(GL_UNPACK_ALIGNMENT, 1)
  465.     glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT)
  466.     glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT)
  467.     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR)
  468.     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR)
  469.     glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE)
  470.     gluBuild2DMipmaps(GL_TEXTURE_2D, 3, width, height, GL_RGBA, GL_UNSIGNED_BYTE, image)
  471.  
  472.     return texture
  473.  
  474.  
  475. drawer = Drawer()
  476. torus = Torus()
  477. drawer.startLoop()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement