001    package net.minecraft.util;
002    
003    import cpw.mods.fml.relauncher.Side;
004    import cpw.mods.fml.relauncher.SideOnly;
005    
006    public class Vec3
007    {
008        public static final Vec3Pool vec3dPool = new Vec3Pool(-1, -1);
009        public final Vec3Pool myVec3LocalPool;
010    
011        /** X coordinate of Vec3D */
012        public double xCoord;
013    
014        /** Y coordinate of Vec3D */
015        public double yCoord;
016    
017        /** Z coordinate of Vec3D */
018        public double zCoord;
019    
020        /**
021         * Static method for creating a new Vec3D given the three x,y,z values. This is only called from the other static
022         * method which creates and places it in the list.
023         */
024        public static Vec3 createVectorHelper(double par0, double par2, double par4)
025        {
026            return new Vec3(vec3dPool, par0, par2, par4);
027        }
028    
029        protected Vec3(Vec3Pool par1Vec3Pool, double par2, double par4, double par6)
030        {
031            if (par2 == -0.0D)
032            {
033                par2 = 0.0D;
034            }
035    
036            if (par4 == -0.0D)
037            {
038                par4 = 0.0D;
039            }
040    
041            if (par6 == -0.0D)
042            {
043                par6 = 0.0D;
044            }
045    
046            this.xCoord = par2;
047            this.yCoord = par4;
048            this.zCoord = par6;
049            this.myVec3LocalPool = par1Vec3Pool;
050        }
051    
052        /**
053         * Sets the x,y,z components of the vector as specified.
054         */
055        protected Vec3 setComponents(double par1, double par3, double par5)
056        {
057            this.xCoord = par1;
058            this.yCoord = par3;
059            this.zCoord = par5;
060            return this;
061        }
062    
063        @SideOnly(Side.CLIENT)
064    
065        /**
066         * Returns a new vector with the result of the specified vector minus this.
067         */
068        public Vec3 subtract(Vec3 par1Vec3)
069        {
070            return this.myVec3LocalPool.getVecFromPool(par1Vec3.xCoord - this.xCoord, par1Vec3.yCoord - this.yCoord, par1Vec3.zCoord - this.zCoord);
071        }
072    
073        /**
074         * Normalizes the vector to a length of 1 (except if it is the zero vector)
075         */
076        public Vec3 normalize()
077        {
078            double var1 = (double)MathHelper.sqrt_double(this.xCoord * this.xCoord + this.yCoord * this.yCoord + this.zCoord * this.zCoord);
079            return var1 < 1.0E-4D ? this.myVec3LocalPool.getVecFromPool(0.0D, 0.0D, 0.0D) : this.myVec3LocalPool.getVecFromPool(this.xCoord / var1, this.yCoord / var1, this.zCoord / var1);
080        }
081    
082        public double dotProduct(Vec3 par1Vec3)
083        {
084            return this.xCoord * par1Vec3.xCoord + this.yCoord * par1Vec3.yCoord + this.zCoord * par1Vec3.zCoord;
085        }
086    
087        @SideOnly(Side.CLIENT)
088    
089        /**
090         * Returns a new vector with the result of this vector x the specified vector.
091         */
092        public Vec3 crossProduct(Vec3 par1Vec3)
093        {
094            return this.myVec3LocalPool.getVecFromPool(this.yCoord * par1Vec3.zCoord - this.zCoord * par1Vec3.yCoord, this.zCoord * par1Vec3.xCoord - this.xCoord * par1Vec3.zCoord, this.xCoord * par1Vec3.yCoord - this.yCoord * par1Vec3.xCoord);
095        }
096    
097        /**
098         * Adds the specified x,y,z vector components to this vector and returns the resulting vector. Does not change this
099         * vector.
100         */
101        public Vec3 addVector(double par1, double par3, double par5)
102        {
103            return this.myVec3LocalPool.getVecFromPool(this.xCoord + par1, this.yCoord + par3, this.zCoord + par5);
104        }
105    
106        /**
107         * Euclidean distance between this and the specified vector, returned as double.
108         */
109        public double distanceTo(Vec3 par1Vec3)
110        {
111            double var2 = par1Vec3.xCoord - this.xCoord;
112            double var4 = par1Vec3.yCoord - this.yCoord;
113            double var6 = par1Vec3.zCoord - this.zCoord;
114            return (double)MathHelper.sqrt_double(var2 * var2 + var4 * var4 + var6 * var6);
115        }
116    
117        /**
118         * The square of the Euclidean distance between this and the specified vector.
119         */
120        public double squareDistanceTo(Vec3 par1Vec3)
121        {
122            double var2 = par1Vec3.xCoord - this.xCoord;
123            double var4 = par1Vec3.yCoord - this.yCoord;
124            double var6 = par1Vec3.zCoord - this.zCoord;
125            return var2 * var2 + var4 * var4 + var6 * var6;
126        }
127    
128        /**
129         * The square of the Euclidean distance between this and the vector of x,y,z components passed in.
130         */
131        public double squareDistanceTo(double par1, double par3, double par5)
132        {
133            double var7 = par1 - this.xCoord;
134            double var9 = par3 - this.yCoord;
135            double var11 = par5 - this.zCoord;
136            return var7 * var7 + var9 * var9 + var11 * var11;
137        }
138    
139        /**
140         * Returns the length of the vector.
141         */
142        public double lengthVector()
143        {
144            return (double)MathHelper.sqrt_double(this.xCoord * this.xCoord + this.yCoord * this.yCoord + this.zCoord * this.zCoord);
145        }
146    
147        /**
148         * Returns a new vector with x value equal to the second parameter, along the line between this vector and the
149         * passed in vector, or null if not possible.
150         */
151        public Vec3 getIntermediateWithXValue(Vec3 par1Vec3, double par2)
152        {
153            double var4 = par1Vec3.xCoord - this.xCoord;
154            double var6 = par1Vec3.yCoord - this.yCoord;
155            double var8 = par1Vec3.zCoord - this.zCoord;
156    
157            if (var4 * var4 < 1.0000000116860974E-7D)
158            {
159                return null;
160            }
161            else
162            {
163                double var10 = (par2 - this.xCoord) / var4;
164                return var10 >= 0.0D && var10 <= 1.0D ? this.myVec3LocalPool.getVecFromPool(this.xCoord + var4 * var10, this.yCoord + var6 * var10, this.zCoord + var8 * var10) : null;
165            }
166        }
167    
168        /**
169         * Returns a new vector with y value equal to the second parameter, along the line between this vector and the
170         * passed in vector, or null if not possible.
171         */
172        public Vec3 getIntermediateWithYValue(Vec3 par1Vec3, double par2)
173        {
174            double var4 = par1Vec3.xCoord - this.xCoord;
175            double var6 = par1Vec3.yCoord - this.yCoord;
176            double var8 = par1Vec3.zCoord - this.zCoord;
177    
178            if (var6 * var6 < 1.0000000116860974E-7D)
179            {
180                return null;
181            }
182            else
183            {
184                double var10 = (par2 - this.yCoord) / var6;
185                return var10 >= 0.0D && var10 <= 1.0D ? this.myVec3LocalPool.getVecFromPool(this.xCoord + var4 * var10, this.yCoord + var6 * var10, this.zCoord + var8 * var10) : null;
186            }
187        }
188    
189        /**
190         * Returns a new vector with z value equal to the second parameter, along the line between this vector and the
191         * passed in vector, or null if not possible.
192         */
193        public Vec3 getIntermediateWithZValue(Vec3 par1Vec3, double par2)
194        {
195            double var4 = par1Vec3.xCoord - this.xCoord;
196            double var6 = par1Vec3.yCoord - this.yCoord;
197            double var8 = par1Vec3.zCoord - this.zCoord;
198    
199            if (var8 * var8 < 1.0000000116860974E-7D)
200            {
201                return null;
202            }
203            else
204            {
205                double var10 = (par2 - this.zCoord) / var8;
206                return var10 >= 0.0D && var10 <= 1.0D ? this.myVec3LocalPool.getVecFromPool(this.xCoord + var4 * var10, this.yCoord + var6 * var10, this.zCoord + var8 * var10) : null;
207            }
208        }
209    
210        public String toString()
211        {
212            return "(" + this.xCoord + ", " + this.yCoord + ", " + this.zCoord + ")";
213        }
214    
215        /**
216         * Rotates the vector around the x axis by the specified angle.
217         */
218        public void rotateAroundX(float par1)
219        {
220            float var2 = MathHelper.cos(par1);
221            float var3 = MathHelper.sin(par1);
222            double var4 = this.xCoord;
223            double var6 = this.yCoord * (double)var2 + this.zCoord * (double)var3;
224            double var8 = this.zCoord * (double)var2 - this.yCoord * (double)var3;
225            this.xCoord = var4;
226            this.yCoord = var6;
227            this.zCoord = var8;
228        }
229    
230        /**
231         * Rotates the vector around the y axis by the specified angle.
232         */
233        public void rotateAroundY(float par1)
234        {
235            float var2 = MathHelper.cos(par1);
236            float var3 = MathHelper.sin(par1);
237            double var4 = this.xCoord * (double)var2 + this.zCoord * (double)var3;
238            double var6 = this.yCoord;
239            double var8 = this.zCoord * (double)var2 - this.xCoord * (double)var3;
240            this.xCoord = var4;
241            this.yCoord = var6;
242            this.zCoord = var8;
243        }
244    
245        @SideOnly(Side.CLIENT)
246    
247        /**
248         * Rotates the vector around the z axis by the specified angle.
249         */
250        public void rotateAroundZ(float par1)
251        {
252            float var2 = MathHelper.cos(par1);
253            float var3 = MathHelper.sin(par1);
254            double var4 = this.xCoord * (double)var2 + this.yCoord * (double)var3;
255            double var6 = this.yCoord * (double)var2 - this.xCoord * (double)var3;
256            double var8 = this.zCoord;
257            this.xCoord = var4;
258            this.yCoord = var6;
259            this.zCoord = var8;
260        }
261    }