Posted April 19, 201411 yr Okay, so I have an elephant entity with a custom model that is working quite great (including articulated trunk). My kids of course wanted the elephant to be bigger so I decided to scale it by factor of 2.0F. I did this by putting this in entity constructor // make elephants big scaleFactor = 2.0F ; this.setScale(scaleFactor); And also putting this in the render for the entity: protected void preRenderCallbackHerdAnimal(EntityHerdAnimal entity, float f) { GL11.glScalef(entity.scaleFactor, entity.scaleFactor, entity.scaleFactor); } And it works great. Got a nice big elephant and bounding box seems to be right as it navigates around. However, I had one really weird thing happen. I spawned the elephant right next to a village that had a forge. And suddenly there were giant flames coming out of the building. It seemed that the fire was scaled as well, as it would sort of glitch if I moved around it. It didn't quite seem like the elephant itself was on fire as it wandered off and the fire stayed in the town. But wasn't quite like the town was on fire either. Anyway, it seemed that the fire was being scaled, maybe because the GL scaling persisted into another rendering method. If I'm using a GL Scale function is it a good practice to set it back to 1.0F in some post render method? Check out my tutorials here: http://jabelarminecraft.blogspot.com/
April 19, 201411 yr Hi Easy fix: GL11.glPushMatrix() GL11.glScalef(etc) render your elephant GL11.glPopMatrix() the push and the pop make sure that your scalef doesn't affect anything afterwards -TGG
April 19, 201411 yr Author Thanks. I just came across some other info where it was leading me to the fact that I need to put in extra push and pop of the matrix since mine wasn't inside a pop and push. Okay previously I had the scaling in the preRenderCallback() method but since I need the matrix to include the rendering and since I don't know of a post render method I figure I have to do the push and pop of the matrix right in the render event. I did that, and it does scale but the weird thing is that the elephants now are only halfway above the ground. The hit box (visible with F3+B) is still proper size above ground. And they move around okay so I assume that the bounding box is indeed still okay (and it should be since rendering should be independent). I can translate the matrix in my render, but before I do that I would like to know why this happened. Why would a scaling in the pre-render callback have different result than doing the scaling as first thing in the render? My render method currently with the overall scaling included: public void renderElephant(EntityElephant parEntity, float parTime, float parSwingSuppress, float par4, float parHeadAngleY, float parHeadAngleX, float par7) { setRotationAngles(parTime, parSwingSuppress, par4, parHeadAngleY, parHeadAngleX, par7, parEntity); // scale the whole thing for big or small entities GL11.glPushMatrix(); GL11.glScalef(parEntity.scaleFactor, parEntity.scaleFactor, parEntity.scaleFactor); if (this.isChild) { float f6 = 2.0F; GL11.glPushMatrix(); GL11.glTranslatef(0.0F, this.field_78145_g * par7, this.field_78151_h * par7); childHead.render(par7); GL11.glPopMatrix(); GL11.glPushMatrix(); GL11.glScalef(1.0F / f6, 1.0F / f6, 1.0F / f6); GL11.glTranslatef(0.0F, 24.0F * par7, 0.0F); body.render(par7); leg1.render(par7); leg2.render(par7); leg3.render(par7); leg4.render(par7); GL11.glPopMatrix(); } else { head.render(par7); body.render(par7); leg1.render(par7); leg2.render(par7); leg3.render(par7); leg4.render(par7); } // don't forget to pop the matrix for overall scaling GL11.glPopMatrix(); } Check out my tutorials here: http://jabelarminecraft.blogspot.com/
April 20, 201411 yr Thanks. I just came across some other info where it was leading me to the fact that I need to put in extra push and pop of the matrix since mine wasn't inside a pop and push. Okay previously I had the scaling in the preRenderCallback() method but since I need the matrix to include the rendering and since I don't know of a post render method I figure I have to do the push and pop of the matrix right in the render event. I did that, and it does scale but the weird thing is that the elephants now are only halfway above the ground. The hit box (visible with F3+B) is still proper size above ground. And they move around okay so I assume that the bounding box is indeed still okay (and it should be since rendering should be independent). I can translate the matrix in my render, but before I do that I would like to know why this happened. Why would a scaling in the pre-render callback have different result than doing the scaling as first thing in the render? My render method currently with the overall scaling included: public void renderElephant(EntityElephant parEntity, float parTime, float parSwingSuppress, float par4, float parHeadAngleY, float parHeadAngleX, float par7) { setRotationAngles(parTime, parSwingSuppress, par4, parHeadAngleY, parHeadAngleX, par7, parEntity); // scale the whole thing for big or small entities GL11.glPushMatrix(); GL11.glScalef(parEntity.scaleFactor, parEntity.scaleFactor, parEntity.scaleFactor); if (this.isChild) { float f6 = 2.0F; GL11.glPushMatrix(); GL11.glTranslatef(0.0F, this.field_78145_g * par7, this.field_78151_h * par7); childHead.render(par7); GL11.glPopMatrix(); GL11.glPushMatrix(); GL11.glScalef(1.0F / f6, 1.0F / f6, 1.0F / f6); GL11.glTranslatef(0.0F, 24.0F * par7, 0.0F); body.render(par7); leg1.render(par7); leg2.render(par7); leg3.render(par7); leg4.render(par7); GL11.glPopMatrix(); } else { head.render(par7); body.render(par7); leg1.render(par7); leg2.render(par7); leg3.render(par7); leg4.render(par7); } // don't forget to pop the matrix for overall scaling GL11.glPopMatrix(); } Hi I've found this link for OpenGL very useful as a reference http://www.glprogramming.com/red/ The reason the glScalef is different is almost certainly because of a translate after the preRenderCallback. If you translate the elephant and then scale it, it scales up around a different "centre" point (eg around its head instead of its feet), so its feet will move by a different amount due to the scaling To fix it, GL11.glTranslatef up, scale, then translate back down by the same amount. One other thing - I suspect your bounding box might not be right (it might just look right because of your scalef). You need to make sure Entity.boundingBox is the right size.. -TGG
April 20, 201411 yr Author Hi I've found this link for OpenGL very useful as a reference http://www.glprogramming.com/red/ The reason the glScalef is different is almost certainly because of a translate after the preRenderCallback. Yeah, that was certainly what it looked like. I was just surprised that there would be a translate between the pre-render callback -- it sort of makes that method more difficult to use if you have to anticipate a translation. If you translate the elephant and then scale it, it scales up around a different "centre" point (eg around its head instead of its feet), so its feet will move by a different amount due to the scaling To fix it, GL11.glTranslatef up, scale, then translate back down by the same amount. Thanks. I'm pretty good with spatial transformation, but mainly was surprised by the unexpected translation as mentioned above. I understand that you have to be careful about the center point location before scaling, otherwise you get an effective translation where it will be moved further from the center point. One other thing - I suspect your bounding box might not be right (it might just look right because of your scalef). You need to make sure Entity.boundingBox is the right size. I think it is correct because (a) the entities are happily moving around despite being "submerged" in the ground, (b) if I press F3+B I can see the hitboxes which look correct and are actually the hit box if I try to hit the entity. That should be sufficient to prove that it is correct, right? Also, why do you think that scaling would affect the BB anyway -- isn't the GL scaling purely rendering? Check out my tutorials here: http://jabelarminecraft.blogspot.com/
April 20, 201411 yr One other thing - I suspect your bounding box might not be right (it might just look right because of your scalef). You need to make sure Entity.boundingBox is the right size. I think it is correct because (a) the entities are happily moving around despite being "submerged" in the ground, (b) if I press F3+B I can see the hitboxes which look correct and are actually the hit box if I try to hit the entity. That should be sufficient to prove that it is correct, right? Also, why do you think that scaling would affect the BB anyway -- isn't the GL scaling purely rendering? Keen, sounds like it is right. Yeah you're right, the scaling is purely rendering. What I meant was - the scaling wouldn't affect the BB, but if you draw the BB while scaling is on, it will make the BB look twice as big as it actually is. i.e. if the drawing is affected by scaling and it looks right, that means the BB actually too small. But to be honest I don't remember if the hitbox is drawn at the same time as the entity. Anyway it sounds like it's not a problem. -TGG
April 20, 201411 yr Author But to be honest I don't remember if the hitbox is drawn at the same time as the entity. If I drew my own bounding box, I'd have to be careful about that. But it seems that the built-in key binding (F3+B) draws separately and correctly. By the way, I recommend to anyone playing with their own models to use this feature to see the bounding box to confirm all the positioning is working correctly. Anyway, the issue is solved. The correct translation was 1.5F in Y direction prior to scaling (in same matrix). The main take away is that it seems there is a translation between the pre-render callback and the render so keep that in mind if you use the callback. Check out my tutorials here: http://jabelarminecraft.blogspot.com/
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.