diff options
Diffstat (limited to 'indra/llmath/llvolume.h')
| -rw-r--r-- | indra/llmath/llvolume.h | 233 |
1 files changed, 140 insertions, 93 deletions
diff --git a/indra/llmath/llvolume.h b/indra/llmath/llvolume.h index 9af02d2629..d48a79ee46 100644 --- a/indra/llmath/llvolume.h +++ b/indra/llmath/llvolume.h @@ -2,30 +2,25 @@ * @file llvolume.h * @brief LLVolume base class. * - * $LicenseInfo:firstyear=2002&license=viewergpl$ - * - * Copyright (c) 2002-2007, Linden Research, Inc. - * + * $LicenseInfo:firstyear=2002&license=viewerlgpl$ * Second Life Viewer Source Code - * The source code in this file ("Source Code") is provided by Linden Lab - * to you under the terms of the GNU General Public License, version 2.0 - * ("GPL"), unless you have obtained a separate licensing agreement - * ("Other License"), formally executed by you and Linden Lab. Terms of - * the GPL can be found in doc/GPL-license.txt in this distribution, or - * online at http://secondlife.com/developers/opensource/gplv2 + * Copyright (C) 2010, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. * - * There are special exceptions to the terms and conditions of the GPL as - * it is applied to this Source Code. View the full text of the exception - * in the file doc/FLOSS-exception.txt in this software distribution, or - * online at http://secondlife.com/developers/opensource/flossexception + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. * - * By copying, modifying or distributing this software, you acknowledge - * that you have read and understood your obligations described above, - * and agree to abide by those obligations. + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA * - * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO - * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY, - * COMPLETENESS OR PERFORMANCE. + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA * $/LicenseInfo$ */ @@ -51,7 +46,8 @@ class LLVolume; #include "llquaternion.h" #include "llstrider.h" #include "v4coloru.h" -#include "llmemory.h" +#include "llrefcount.h" +#include "llfile.h" //============================================================================ @@ -72,6 +68,8 @@ const F32 TAPER_QUANTA = 0.01f; const F32 REV_QUANTA = 0.015f; const F32 HOLLOW_QUANTA = 0.00002f; +const S32 MAX_VOLUME_TRIANGLE_INDICES = 10000; + //============================================================================ // useful masks @@ -172,7 +170,7 @@ const LLFaceID LL_FACE_OUTER_SIDE_3 = 0x1 << 8; //============================================================================ -// sculpt types +// sculpt types + flags const U8 LL_SCULPT_TYPE_NONE = 0; const U8 LL_SCULPT_TYPE_SPHERE = 1; @@ -180,21 +178,30 @@ const U8 LL_SCULPT_TYPE_TORUS = 2; const U8 LL_SCULPT_TYPE_PLANE = 3; const U8 LL_SCULPT_TYPE_CYLINDER = 4; +const U8 LL_SCULPT_TYPE_MASK = LL_SCULPT_TYPE_SPHERE | LL_SCULPT_TYPE_TORUS | LL_SCULPT_TYPE_PLANE | LL_SCULPT_TYPE_CYLINDER; + +const U8 LL_SCULPT_FLAG_INVERT = 64; +const U8 LL_SCULPT_FLAG_MIRROR = 128; class LLProfileParams { public: LLProfileParams() + : mCurveType(LL_PCODE_PROFILE_SQUARE), + mBegin(0.f), + mEnd(1.f), + mHollow(0.f), + mCRC(0) { - mBegin = 0; - mEnd = 1; - mHollow = 0; - mCurveType = LL_PCODE_PROFILE_SQUARE; } LLProfileParams(U8 curve, F32 begin, F32 end, F32 hollow) - : mCurveType(curve), mBegin(begin), mEnd(end), mHollow(hollow) + : mCurveType(curve), + mBegin(begin), + mEnd(end), + mHollow(hollow), + mCRC(0) { } @@ -219,6 +226,7 @@ public: temp_f32 = 1.f; } mHollow = temp_f32; + mCRC = 0; } bool operator==(const LLProfileParams ¶ms) const; @@ -227,8 +235,8 @@ public: void copyParams(const LLProfileParams ¶ms); - BOOL importFile(FILE *fp); - BOOL exportFile(FILE *fp) const; + BOOL importFile(LLFILE *fp); + BOOL exportFile(LLFILE *fp) const; BOOL importLegacyStream(std::istream& input_stream); BOOL exportLegacyStream(std::ostream& output_stream) const; @@ -306,27 +314,36 @@ class LLPathParams { public: LLPathParams() + : + mCurveType(LL_PCODE_PATH_LINE), + mBegin(0.f), + mEnd(1.f), + mScale(1.f,1.f), + mShear(0.f,0.f), + mTwistBegin(0.f), + mTwistEnd(0.f), + mRadiusOffset(0.f), + mTaper(0.f,0.f), + mRevolutions(1.f), + mSkew(0.f), + mCRC(0) { - mBegin = 0; - mEnd = 1; - mScale.setVec(1,1); - mShear.setVec(0,0); - mCurveType = LL_PCODE_PATH_LINE; - mTwistBegin = 0; - mTwistEnd = 0; - mRadiusOffset = 0; - mTaper.setVec(0,0); - mRevolutions = 1; - mSkew = 0; } LLPathParams(U8 curve, F32 begin, F32 end, F32 scx, F32 scy, F32 shx, F32 shy, F32 twistend, F32 twistbegin, F32 radiusoffset, F32 tx, F32 ty, F32 revolutions, F32 skew) - : mCurveType(curve), mBegin(begin), mEnd(end), mTwistBegin(twistbegin), mTwistEnd(twistend), - mRadiusOffset(radiusoffset), mRevolutions(revolutions), mSkew(skew) + : mCurveType(curve), + mBegin(begin), + mEnd(end), + mScale(scx,scy), + mShear(shx,shy), + mTwistBegin(twistbegin), + mTwistEnd(twistend), + mRadiusOffset(radiusoffset), + mTaper(tx,ty), + mRevolutions(revolutions), + mSkew(skew), + mCRC(0) { - mScale.setVec(scx,scy); - mShear.setVec(shx,shy); - mTaper.setVec(tx,ty); } LLPathParams(U8 curve, U16 begin, U16 end, U8 scx, U8 scy, U8 shx, U8 shy, U8 twistend, U8 twistbegin, U8 radiusoffset, U8 tx, U8 ty, U8 revolutions, U8 skew) @@ -344,6 +361,8 @@ public: mTaper.setVec(U8_TO_F32(tx) * TAPER_QUANTA,U8_TO_F32(ty) * TAPER_QUANTA); mRevolutions = ((F32)revolutions) * REV_QUANTA + 1.0f; mSkew = U8_TO_F32(skew) * SCALE_QUANTA; + + mCRC = 0; } bool operator==(const LLPathParams ¶ms) const; @@ -352,8 +371,8 @@ public: void copyParams(const LLPathParams ¶ms); - BOOL importFile(FILE *fp); - BOOL exportFile(FILE *fp) const; + BOOL importFile(LLFILE *fp); + BOOL exportFile(LLFILE *fp) const; BOOL importLegacyStream(std::istream& input_stream); BOOL exportLegacyStream(std::ostream& output_stream) const; @@ -522,6 +541,7 @@ class LLVolumeParams { public: LLVolumeParams() + : mSculptType(LL_SCULPT_TYPE_NONE) { } @@ -543,8 +563,8 @@ public: const LLPathParams &getPathParams() const {return mPathParams;} LLPathParams &getPathParams() {return mPathParams;} - BOOL importFile(FILE *fp); - BOOL exportFile(FILE *fp) const; + BOOL importFile(LLFILE *fp); + BOOL exportFile(LLFILE *fp) const; BOOL importLegacyStream(std::istream& input_stream); BOOL exportLegacyStream(std::ostream& output_stream) const; @@ -627,6 +647,9 @@ public: friend std::ostream& operator<<(std::ostream &s, const LLVolumeParams &volume_params); + // debug helper functions + void setCube(); + protected: LLProfileParams mProfileParams; LLPathParams mPathParams; @@ -638,9 +661,8 @@ protected: class LLProfile { public: - LLProfile(const LLProfileParams ¶ms) - : mParams(params), - mOpen(FALSE), + LLProfile() + : mOpen(FALSE), mConcave(FALSE), mDirty(TRUE), mTotalOut(0), @@ -652,15 +674,13 @@ public: S32 getTotal() const { return mTotal; } S32 getTotalOut() const { return mTotalOut; } // Total number of outside points - BOOL isHollow() const { return (mParams.getHollow() > 0); } BOOL isFlat(S32 face) const { return (mFaces[face].mCount == 2); } BOOL isOpen() const { return mOpen; } void setDirty() { mDirty = TRUE; } - BOOL generate(BOOL path_open, F32 detail = 1.0f, S32 split = 0, BOOL is_sculpted = FALSE); + BOOL generate(const LLProfileParams& params, BOOL path_open, F32 detail = 1.0f, S32 split = 0, + BOOL is_sculpted = FALSE, S32 sculpt_size = 0); BOOL isConcave() const { return mConcave; } public: - const LLProfileParams &mParams; - struct Face { S32 mIndex; @@ -676,16 +696,14 @@ public: std::vector<Face> mFaces; std::vector<LLVector3> mEdgeNormals; std::vector<LLVector3> mEdgeCenters; - F32 mMaxX; - F32 mMinX; friend std::ostream& operator<<(std::ostream &s, const LLProfile &profile); protected: - void genNormals(); - void genNGon(S32 sides, F32 offset=0.0f, F32 bevel = 0.0f, F32 ang_scale = 1.f, S32 split = 0); + void genNormals(const LLProfileParams& params); + void genNGon(const LLProfileParams& params, S32 sides, F32 offset=0.0f, F32 bevel = 0.0f, F32 ang_scale = 1.f, S32 split = 0); - Face* addHole(BOOL flat, F32 sides, F32 offset, F32 box_hollow, F32 ang_scale, S32 split = 0); + Face* addHole(const LLProfileParams& params, BOOL flat, F32 sides, F32 offset, F32 box_hollow, F32 ang_scale, S32 split = 0); Face* addCap (S16 faceID); Face* addFace(S32 index, S32 count, F32 scaleU, S16 faceID, BOOL flat); @@ -715,9 +733,8 @@ public: }; public: - LLPath(const LLPathParams ¶ms) - : mParams(params), - mOpen(FALSE), + LLPath() + : mOpen(FALSE), mTotal(0), mDirty(TRUE), mStep(1) @@ -726,8 +743,9 @@ public: virtual ~LLPath(); - void genNGon(S32 sides, F32 offset=0.0f, F32 end_scale = 1.f, F32 twist_scale = 1.f); - virtual BOOL generate(F32 detail=1.0f, S32 split = 0, BOOL is_sculpted = FALSE); + void genNGon(const LLPathParams& params, S32 sides, F32 offset=0.0f, F32 end_scale = 1.f, F32 twist_scale = 1.f); + virtual BOOL generate(const LLPathParams& params, F32 detail=1.0f, S32 split = 0, + BOOL is_sculpted = FALSE, S32 sculpt_size = 0); BOOL isOpen() const { return mOpen; } F32 getStep() const { return mStep; } @@ -740,7 +758,6 @@ public: friend std::ostream& operator<<(std::ostream &s, const LLPath &path); public: - const LLPathParams &mParams; std::vector<PathPt> mPath; protected: @@ -753,18 +770,30 @@ protected: class LLDynamicPath : public LLPath { public: - LLDynamicPath(const LLPathParams ¶ms) : LLPath(params) { } - BOOL generate(F32 detail=1.0f, S32 split = 0, BOOL is_sculpted = FALSE); + LLDynamicPath() : LLPath() { } + /*virtual*/ BOOL generate(const LLPathParams& params, F32 detail=1.0f, S32 split = 0, + BOOL is_sculpted = FALSE, S32 sculpt_size = 0); }; // Yet another "face" class - caches volume-specific, but not instance-specific data for faces) class LLVolumeFace { public: - LLVolumeFace(); - BOOL create(BOOL partial_build = FALSE); - void createBinormals(); + LLVolumeFace() : + mID(0), + mTypeMask(0), + mHasBinormals(FALSE), + mBeginS(0), + mBeginT(0), + mNumS(0), + mNumT(0) + { + } + BOOL create(LLVolume* volume, BOOL partial_build = FALSE); + void createBinormals(); + void makeTriStrip(); + class VertexData { public: @@ -805,17 +834,13 @@ public: std::vector<VertexData> mVertices; std::vector<U16> mIndices; + std::vector<U16> mTriStrip; std::vector<S32> mEdge; - LLVolume *mVolumep; // Deliberately NOT reference counted - djs 11/20/03 - otherwise would make an annoying circular reference - // Shouldn't need num_old and num_new, really - djs - static BOOL updateColors(LLColor4U *old_colors, const S32 num_old, const LLVolumeFace &old_face, - LLStrider<LLColor4U> &new_colors, const S32 num_new, const LLVolumeFace &new_face); - -protected: - BOOL createUnCutCubeCap(BOOL partial_build = FALSE); - BOOL createCap(BOOL partial_build = FALSE); - BOOL createSide(BOOL partial_build = FALSE); +private: + BOOL createUnCutCubeCap(LLVolume* volume, BOOL partial_build = FALSE); + BOOL createCap(LLVolume* volume, BOOL partial_build = FALSE); + BOOL createSide(LLVolume* volume, BOOL partial_build = FALSE); }; class LLVolume : public LLRefCount @@ -843,12 +868,12 @@ public: LLVolume(const LLVolumeParams ¶ms, const F32 detail, const BOOL generate_single_face = FALSE, const BOOL is_unique = FALSE); - U8 getProfileType() const { return mProfilep->mParams.getCurveType(); } - U8 getPathType() const { return mPathp->mParams.getCurveType(); } + U8 getProfileType() const { return mParams.getProfileParams().getCurveType(); } + U8 getPathType() const { return mParams.getPathParams().getCurveType(); } S32 getNumFaces() const { return (S32)mProfilep->mFaces.size(); } - S32 getNumVolumeFaces() const { return mNumVolumeFaces; } - F32 getDetail() const { return mDetail; } - const LLVolumeParams & getParams() const { return mParams; } + S32 getNumVolumeFaces() const { return mVolumeFaces.size(); } + F32 getDetail() const { return mDetail; } + const LLVolumeParams& getParams() const { return mParams; } LLVolumeParams getCopyOfParams() const { return mParams; } const LLProfile& getProfile() const { return *mProfilep; } LLPath& getPath() const { return *mPathp; } @@ -869,14 +894,28 @@ public: S32 getSculptLevel() const { return mSculptLevel; } S32 *getTriangleIndices(U32 &num_indices) const; - void generateSilhouetteVertices(std::vector<LLVector3> &vertices, std::vector<LLVector3> &normals, std::vector<S32> &segments, const LLVector3& view_vec, - const LLMatrix4& mat, - const LLMatrix3& norm_mat); + + // returns number of triangle indeces required for path/profile mesh + S32 getNumTriangleIndices() const; + + void generateSilhouetteVertices(std::vector<LLVector3> &vertices, + std::vector<LLVector3> &normals, + std::vector<S32> &segments, + const LLVector3& view_vec, + const LLMatrix4& mat, + const LLMatrix3& norm_mat, + S32 face_index); //get the face index of the face that intersects with the given line segment at the point //closest to start. Moves end to the point of intersection. Returns -1 if no intersection. //Line segment must be in volume space. - S32 lineSegmentIntersect(const LLVector3& start, LLVector3& end) const; + S32 lineSegmentIntersect(const LLVector3& start, const LLVector3& end, + S32 face = -1, // which face to check, -1 = ALL_SIDES + LLVector3* intersection = NULL, // return the intersection point + LLVector2* tex_coord = NULL, // return the texture coordinates of the intersection point + LLVector3* normal = NULL, // return the surface normal at the intersection point + LLVector3* bi_normal = NULL // return the surface bi-normal at the intersection point + ); // The following cleans up vertices and triangles, // getting rid of degenerate triangles and duplicate vertices, @@ -904,9 +943,11 @@ public: void sculpt(U16 sculpt_width, U16 sculpt_height, S8 sculpt_components, const U8* sculpt_data, S32 sculpt_level); private: - F32 sculptGetSurfaceArea(U16 sculpt_width, U16 sculpt_height, S8 sculpt_components, const U8* sculpt_data); void sculptGenerateMapVertices(U16 sculpt_width, U16 sculpt_height, S8 sculpt_components, const U8* sculpt_data, U8 sculpt_type); + F32 sculptGetSurfaceArea(); void sculptGeneratePlaceholder(); + void sculptCalcMeshResolution(U16 width, U16 height, U8 type, S32& s, S32& t); + protected: BOOL generate(); @@ -923,8 +964,8 @@ protected: std::vector<Point> mMesh; BOOL mGenerateSingleFace; - S32 mNumVolumeFaces; - LLVolumeFace *mVolumeFaces; + typedef std::vector<LLVolumeFace> face_list_t; + face_list_t mVolumeFaces; }; std::ostream& operator<<(std::ostream &s, const LLVolumeParams &volume_params); @@ -937,4 +978,10 @@ LLVector3 calc_binormal_from_triangle( const LLVector3& pos2, const LLVector2& tex2); +BOOL LLLineSegmentBoxIntersect(const LLVector3& start, const LLVector3& end, const LLVector3& center, const LLVector3& size); +BOOL LLTriangleRayIntersect(const LLVector3& vert0, const LLVector3& vert1, const LLVector3& vert2, const LLVector3& orig, const LLVector3& dir, + F32* intersection_a, F32* intersection_b, F32* intersection_t, BOOL two_sided); + + + #endif |
