001    package net.minecraft.src;
002    
003    import cpw.mods.fml.common.Side;
004    import cpw.mods.fml.common.asm.SideOnly;
005    import java.util.ArrayList;
006    import java.util.Iterator;
007    import java.util.List;
008    import org.lwjgl.opengl.GL11;
009    
010    public class ModelRenderer
011    {
012        /** The size of the texture file's width in pixels. */
013        public float textureWidth;
014    
015        /** The size of the texture file's height in pixels. */
016        public float textureHeight;
017    
018        /** The X offset into the texture used for displaying this model */
019        private int textureOffsetX;
020    
021        /** The Y offset into the texture used for displaying this model */
022        private int textureOffsetY;
023        public float rotationPointX;
024        public float rotationPointY;
025        public float rotationPointZ;
026        public float rotateAngleX;
027        public float rotateAngleY;
028        public float rotateAngleZ;
029        private boolean compiled;
030    
031        /** The GL display list rendered by the Tessellator for this model */
032        private int displayList;
033        public boolean mirror;
034        public boolean showModel;
035    
036        /** Hides the model. */
037        public boolean isHidden;
038        public List cubeList;
039        public List childModels;
040        public final String boxName;
041        private ModelBase baseModel;
042        public float field_82906_o;
043        public float field_82908_p;
044        public float field_82907_q;
045    
046        public ModelRenderer(ModelBase par1ModelBase, String par2Str)
047        {
048            this.textureWidth = 64.0F;
049            this.textureHeight = 32.0F;
050            this.compiled = false;
051            this.displayList = 0;
052            this.mirror = false;
053            this.showModel = true;
054            this.isHidden = false;
055            this.cubeList = new ArrayList();
056            this.baseModel = par1ModelBase;
057            par1ModelBase.boxList.add(this);
058            this.boxName = par2Str;
059            this.setTextureSize(par1ModelBase.textureWidth, par1ModelBase.textureHeight);
060        }
061    
062        public ModelRenderer(ModelBase par1ModelBase)
063        {
064            this(par1ModelBase, (String)null);
065        }
066    
067        public ModelRenderer(ModelBase par1ModelBase, int par2, int par3)
068        {
069            this(par1ModelBase);
070            this.setTextureOffset(par2, par3);
071        }
072    
073        /**
074         * Sets the current box's rotation points and rotation angles to another box.
075         */
076        public void addChild(ModelRenderer par1ModelRenderer)
077        {
078            if (this.childModels == null)
079            {
080                this.childModels = new ArrayList();
081            }
082    
083            this.childModels.add(par1ModelRenderer);
084        }
085    
086        public ModelRenderer setTextureOffset(int par1, int par2)
087        {
088            this.textureOffsetX = par1;
089            this.textureOffsetY = par2;
090            return this;
091        }
092    
093        public ModelRenderer addBox(String par1Str, float par2, float par3, float par4, int par5, int par6, int par7)
094        {
095            par1Str = this.boxName + "." + par1Str;
096            TextureOffset var8 = this.baseModel.getTextureOffset(par1Str);
097            this.setTextureOffset(var8.textureOffsetX, var8.textureOffsetY);
098            this.cubeList.add((new ModelBox(this, this.textureOffsetX, this.textureOffsetY, par2, par3, par4, par5, par6, par7, 0.0F)).func_78244_a(par1Str));
099            return this;
100        }
101    
102        public ModelRenderer addBox(float par1, float par2, float par3, int par4, int par5, int par6)
103        {
104            this.cubeList.add(new ModelBox(this, this.textureOffsetX, this.textureOffsetY, par1, par2, par3, par4, par5, par6, 0.0F));
105            return this;
106        }
107    
108        /**
109         * Creates a textured box. Args: originX, originY, originZ, width, height, depth, scaleFactor.
110         */
111        public void addBox(float par1, float par2, float par3, int par4, int par5, int par6, float par7)
112        {
113            this.cubeList.add(new ModelBox(this, this.textureOffsetX, this.textureOffsetY, par1, par2, par3, par4, par5, par6, par7));
114        }
115    
116        public void setRotationPoint(float par1, float par2, float par3)
117        {
118            this.rotationPointX = par1;
119            this.rotationPointY = par2;
120            this.rotationPointZ = par3;
121        }
122        
123        @SideOnly(Side.CLIENT)
124        public void render(float par1)
125        {
126            if (!this.isHidden)
127            {
128                if (this.showModel)
129                {
130                    if (!this.compiled)
131                    {
132                        this.compileDisplayList(par1);
133                    }
134    
135                    GL11.glTranslatef(this.field_82906_o, this.field_82908_p, this.field_82907_q);
136                    Iterator var2;
137                    ModelRenderer var3;
138    
139                    if (this.rotateAngleX == 0.0F && this.rotateAngleY == 0.0F && this.rotateAngleZ == 0.0F)
140                    {
141                        if (this.rotationPointX == 0.0F && this.rotationPointY == 0.0F && this.rotationPointZ == 0.0F)
142                        {
143                            GL11.glCallList(this.displayList);
144    
145                            if (this.childModels != null)
146                            {
147                                var2 = this.childModels.iterator();
148    
149                                while (var2.hasNext())
150                                {
151                                    var3 = (ModelRenderer)var2.next();
152                                    var3.render(par1);
153                                }
154                            }
155                        }
156                        else
157                        {
158                            GL11.glTranslatef(this.rotationPointX * par1, this.rotationPointY * par1, this.rotationPointZ * par1);
159                            GL11.glCallList(this.displayList);
160    
161                            if (this.childModels != null)
162                            {
163                                var2 = this.childModels.iterator();
164    
165                                while (var2.hasNext())
166                                {
167                                    var3 = (ModelRenderer)var2.next();
168                                    var3.render(par1);
169                                }
170                            }
171    
172                            GL11.glTranslatef(-this.rotationPointX * par1, -this.rotationPointY * par1, -this.rotationPointZ * par1);
173                        }
174                    }
175                    else
176                    {
177                        GL11.glPushMatrix();
178                        GL11.glTranslatef(this.rotationPointX * par1, this.rotationPointY * par1, this.rotationPointZ * par1);
179    
180                        if (this.rotateAngleZ != 0.0F)
181                        {
182                            GL11.glRotatef(this.rotateAngleZ * (180F / (float)Math.PI), 0.0F, 0.0F, 1.0F);
183                        }
184    
185                        if (this.rotateAngleY != 0.0F)
186                        {
187                            GL11.glRotatef(this.rotateAngleY * (180F / (float)Math.PI), 0.0F, 1.0F, 0.0F);
188                        }
189    
190                        if (this.rotateAngleX != 0.0F)
191                        {
192                            GL11.glRotatef(this.rotateAngleX * (180F / (float)Math.PI), 1.0F, 0.0F, 0.0F);
193                        }
194    
195                        GL11.glCallList(this.displayList);
196    
197                        if (this.childModels != null)
198                        {
199                            var2 = this.childModels.iterator();
200    
201                            while (var2.hasNext())
202                            {
203                                var3 = (ModelRenderer)var2.next();
204                                var3.render(par1);
205                            }
206                        }
207    
208                        GL11.glPopMatrix();
209                    }
210    
211                    GL11.glTranslatef(-this.field_82906_o, -this.field_82908_p, -this.field_82907_q);
212                }
213            }
214        }
215    
216        @SideOnly(Side.CLIENT)
217        public void renderWithRotation(float par1)
218        {
219            if (!this.isHidden)
220            {
221                if (this.showModel)
222                {
223                    if (!this.compiled)
224                    {
225                        this.compileDisplayList(par1);
226                    }
227    
228                    GL11.glPushMatrix();
229                    GL11.glTranslatef(this.rotationPointX * par1, this.rotationPointY * par1, this.rotationPointZ * par1);
230    
231                    if (this.rotateAngleY != 0.0F)
232                    {
233                        GL11.glRotatef(this.rotateAngleY * (180F / (float)Math.PI), 0.0F, 1.0F, 0.0F);
234                    }
235    
236                    if (this.rotateAngleX != 0.0F)
237                    {
238                        GL11.glRotatef(this.rotateAngleX * (180F / (float)Math.PI), 1.0F, 0.0F, 0.0F);
239                    }
240    
241                    if (this.rotateAngleZ != 0.0F)
242                    {
243                        GL11.glRotatef(this.rotateAngleZ * (180F / (float)Math.PI), 0.0F, 0.0F, 1.0F);
244                    }
245    
246                    GL11.glCallList(this.displayList);
247                    GL11.glPopMatrix();
248                }
249            }
250        }
251    
252        /**
253         * Allows the changing of Angles after a box has been rendered
254         */
255        @SideOnly(Side.CLIENT)
256        public void postRender(float par1)
257        {
258            if (!this.isHidden)
259            {
260                if (this.showModel)
261                {
262                    if (!this.compiled)
263                    {
264                        this.compileDisplayList(par1);
265                    }
266    
267                    if (this.rotateAngleX == 0.0F && this.rotateAngleY == 0.0F && this.rotateAngleZ == 0.0F)
268                    {
269                        if (this.rotationPointX != 0.0F || this.rotationPointY != 0.0F || this.rotationPointZ != 0.0F)
270                        {
271                            GL11.glTranslatef(this.rotationPointX * par1, this.rotationPointY * par1, this.rotationPointZ * par1);
272                        }
273                    }
274                    else
275                    {
276                        GL11.glTranslatef(this.rotationPointX * par1, this.rotationPointY * par1, this.rotationPointZ * par1);
277    
278                        if (this.rotateAngleZ != 0.0F)
279                        {
280                            GL11.glRotatef(this.rotateAngleZ * (180F / (float)Math.PI), 0.0F, 0.0F, 1.0F);
281                        }
282    
283                        if (this.rotateAngleY != 0.0F)
284                        {
285                            GL11.glRotatef(this.rotateAngleY * (180F / (float)Math.PI), 0.0F, 1.0F, 0.0F);
286                        }
287    
288                        if (this.rotateAngleX != 0.0F)
289                        {
290                            GL11.glRotatef(this.rotateAngleX * (180F / (float)Math.PI), 1.0F, 0.0F, 0.0F);
291                        }
292                    }
293                }
294            }
295        }
296    
297        /**
298         * Compiles a GL display list for this model
299         */
300        @SideOnly(Side.CLIENT)
301        private void compileDisplayList(float par1)
302        {
303            this.displayList = GLAllocation.generateDisplayLists(1);
304            GL11.glNewList(this.displayList, GL11.GL_COMPILE);
305            Tessellator var2 = Tessellator.instance;
306            Iterator var3 = this.cubeList.iterator();
307    
308            while (var3.hasNext())
309            {
310                ModelBox var4 = (ModelBox)var3.next();
311                var4.render(var2, par1);
312            }
313    
314            GL11.glEndList();
315            this.compiled = true;
316        }
317    
318        /**
319         * Returns the model renderer with the new texture parameters.
320         */
321        public ModelRenderer setTextureSize(int par1, int par2)
322        {
323            this.textureWidth = (float)par1;
324            this.textureHeight = (float)par2;
325            return this;
326        }
327    }