~yacinechaouche/+junk/BZR

« back to all changes in this revision

Viewing changes to PROG/LETS3D/lets3d/lib/model.py

  • Committer: yacinechaouche at yahoo
  • Date: 2015-01-14 22:23:03 UTC
  • Revision ID: yacinechaouche@yahoo.com-20150114222303-6gbtqqxii717vyka
Ajout de CODE et PROD. Il faudra ensuite ajouter ce qu'il y avait dan TMP

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
## file model.py
 
2
 
 
3
from objloader import *
 
4
from drawing import *
 
5
from OpenGL.GL import *
 
6
 
 
7
class Model:
 
8
 
 
9
    def __init__(self,filename="",groupname = None,model = None,textureFileName = None) :
 
10
        """
 
11
        This holds all informations relative to a 3D (lightwave) model. Developers can use an object of this class to represent immobile 3D models. For mobile models use MobileModel instead. To create a composite model, specify it's filename. For the components, specify the groupname and the model's model (model). model is specified for a construction by copy.
 
12
        """
 
13
        if groupname :
 
14
            if not model :
 
15
                raise 'No model model specified for the group',groupname
 
16
            else :
 
17
                print 'creation of model ',groupname
 
18
                self.copy(model)
 
19
                self.groups = {groupname : model.groups[groupname]}
 
20
                del model.groups[groupname]
 
21
                model.buildModelList()                
 
22
                #print self.groups
 
23
                self.min = self.groups[groupname][MINIMA]
 
24
                self.max = self.groups[groupname][MAXIMA]
 
25
                self.center = self.groups[groupname][CENTER]
 
26
                self.boundingbox = [self.min,self.max]
 
27
                self.modelList = glGenLists(1)
 
28
                self.buildModelList()
 
29
                return 
 
30
 
 
31
        print 'creation of model', filename
 
32
        self.filename          = filename
 
33
        self.materialFileName  = ''
 
34
        self.textureFileName   = textureFileName
 
35
        self.materialFile      = ''
 
36
        self.vertices          = []
 
37
        self.textures          = []
 
38
        self.normals           = []
 
39
        self.nb_vertices       = 0
 
40
        self.nb_textures       = 0
 
41
        self.nb_normals        = 0        
 
42
        self.nb_faces          = 0
 
43
        self.nb_materials      = 0
 
44
        self.nb_groups         = 0
 
45
        self.nb_elements       = 0
 
46
        self.materials         = {}  # dictionary 
 
47
        self.groups            = {}  # dictionary
 
48
        self.center            = [0,0,0]
 
49
        self.min               = [INFINITY,INFINITY,INFINITY]
 
50
        self.max               = [-INFINITY,-INFINITY,-INFINITY]
 
51
        self.loader            = ObjLoader(model=self)
 
52
        self.boundingBox       = [self.min,self.max]
 
53
        self.boundingBoxShowed = False
 
54
        self.drawing           = Drawing()
 
55
        self.modelList         = glGenLists(1)
 
56
 
 
57
        
 
58
        if self.modelList == 0 :
 
59
            print 'Error in MobileModel constructor, self.modelList is', self.modelList, '. returning.'
 
60
           # return 
 
61
            
 
62
        self.buildModelList()
 
63
 
 
64
    def copy(self,model):
 
65
        for i,j in model.__dict__.items() :
 
66
            self.__dict__[i] = j
 
67
 
 
68
    def buildModelList(self):
 
69
        glNewList(self.modelList,GL_COMPILE)
 
70
        if self.textureFileName :
 
71
            glEnable(GL_TEXTURE_2D)
 
72
            self.drawing.useTexture(self.textureFileName)
 
73
        glPushMatrix()
 
74
        for g in self.groups.values():
 
75
            if not self.textureFileName :
 
76
                try:
 
77
                    self.useMaterial(g[MATERIAL])
 
78
                    pass
 
79
                except:
 
80
                    print "Warning : a group has no material in ", self.model.filename,"!"
 
81
                    pass
 
82
            #FACES is an enumeration. It's value is 1
 
83
            for f in g[FACES]:
 
84
                if  len(f) == 3 * self.nb_elements :
 
85
                    glBegin(GL_TRIANGLES)
 
86
                elif len(f) == 4 * self.nb_elements :
 
87
                    glBegin(GL_QUADS)
 
88
                else :
 
89
                    glBegin(GL_POLYGON)
 
90
                for i in range(0,len(f),self.nb_elements): 
 
91
                    #Keep in mind that first line is line 1, not 0
 
92
                    j = i + self.nb_elements - 1
 
93
                    k = i + 1
 
94
                    glNormal(self.normals[f[j]-1][X],
 
95
                             self.normals[f[j]-1][Y],
 
96
                             self.normals[f[j]-1][Z])
 
97
                    glVertex(self.vertices[f[i]-1][X],
 
98
                             self.vertices[f[i]-1][Y],
 
99
                             self.vertices[f[i]-1][Z])
 
100
                    if self.textureFileName and self.nb_elements == 3 :
 
101
##                         print self.nb_elements
 
102
##                         print k
 
103
##                         print f[k]
 
104
##                         print self.textures[f[k] - 1]
 
105
                        
 
106
                        glTexCoord(self.textures[f[k]-1][X],
 
107
                                   self.textures[f[k]-1][Y])
 
108
                        ##self.textures[f[k]-1][Z])
 
109
 
 
110
                glEnd()
 
111
        glPopMatrix()
 
112
        if self.textureFileName :
 
113
            glDisable(GL_TEXTURE_2D)    
 
114
        glEndList()
 
115
        
 
116
    def useMaterial(self,materialName):
 
117
        for param in [GL_AMBIENT,GL_SPECULAR,GL_DIFFUSE,GL_SHININESS]:
 
118
            try: # sometimes not all values are defined, so put this line in a try block
 
119
                glMaterialfv(GL_FRONT,param,self.materials[materialName][param])
 
120
            except:
 
121
                pass
 
122
 
 
123
    def draw(self):
 
124
        glPushMatrix()
 
125
        glCallList(self.modelList)
 
126
        if(self.boundingBoxShowed):
 
127
            self.drawBoundingBox()
 
128
        glPopMatrix()
 
129
 
 
130
    def buildBoundingBoxList(self):
 
131
        self.boundingBoxList = glGenLists(1)
 
132
        glNewList(self.boundingBoxList,GL_COMPILE)
 
133
        glDisable(GL_LIGHTING)
 
134
        glPushMatrix()
 
135
        glTranslate(self.center[X],self.center[Y],self.center[Z])
 
136
        glScale(self.max[X]-self.min[X],self.max[Y]-self.min[Y],self.max[Z]-self.min[Z])
 
137
        glutWireCube(1.0)
 
138
        glPopMatrix()
 
139
        glEnable(GL_LIGHTING)
 
140
        glEndList()
 
141
 
 
142
    def drawBoundingBox(self):
 
143
        glPushMatrix()
 
144
        glCallList(self.boundingBoxList)
 
145
        glPopMatrix()
 
146
 
 
147
    def showBoundingBox(self,showing):
 
148
        if showing :
 
149
            self.boundingBoxShowed = True
 
150
            self.buildBoundingBoxList()
 
151
        else :
 
152
            self.boundingBoxShowed= False
 
153
            glDeleteLists(self.boundingBoxList,1)
 
154
 
 
155
def loader_test(filename='',groupname='') :
 
156
    if (filename == '' or groupname == ''):
 
157
        print "usage : loader_test (filename,groupname)"
 
158
        return 
 
159
 
 
160
    model = Model(filename)
 
161
    for name,g in model.groups.items() :
 
162
        #print 'group ', name
 
163
        for f in g[FACES] :
 
164
            #print 'faces are', f
 
165
            for i in range(0,len(f),model.nb_elements):
 
166
                #Keep in mind that first line is line 1, not 0
 
167
                #print 'i is',i,' and len(f) is', len(f)
 
168
                #print 'len(normals) is',len(l.normals),'and f[i+1]-1 is ', f[i+1] - 1,'sans le -1',f[i+1]
 
169
                #print 'normals are',l.normals[f[i+2]-1][X],l.normals[f[i+2]-1][Y],l.normals[f[i+2]-1][Z]
 
170
                #print 'vertices are',l.vertices[f[i]-1][X],l.vertices[f[i]-1][Y],l.vertices[f[i]-1][Z]
 
171
                pass
 
172
    if not model.groups.has_key(groupname) :
 
173
        print "error, no group named", groupname, "in model. Returning."
 
174
        return
 
175
    model.computeBoundingBox(groupname)
 
176
    print 'min du ',groupname,' est', model.groups[groupname][MINIMA]
 
177
    print 'max du ',groupname,' est', model.groups[groupname][MAXIMA]
 
178
    print 'centre du ',groupname,' est', model.groups[groupname][CENTER]
 
179
    print 'min du ', filename.split(".")[0],model.min
 
180
    print 'max du ',filename.split(".")[0] ,model.max
 
181
    print 'centre du ',filename.split(".")[0],model.center
 
182
#####################            
 
183
##loader_test("tank.obj",'Canon')
 
184
def testSingleton():
 
185
 
 
186
    model1 = Model(filename = 'jeep.txt')
 
187
    model2 = Model(filename = 'tank.obj')
 
188
    print model1.loader
 
189
    print ObjLoader.singleton
 
190
    print model2.loader
 
191
    
 
192
##testSingleton()