⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 camera.java

📁 基于java的3d开发库。对坐java3d的朋友有很大的帮助。
💻 JAVA
📖 第 1 页 / 共 4 页
字号:
                    // Warning: Why test with the contrary plane?                    clippingPlane = nearPlane;                }                else {                    // Not possible: non implemented case!                        VSDK.reportMessage(this, VSDK.WARNING,                             "clipLineCohenSutherlandPlanes",                             "Unusal ray case, check code and data");                }                if ( clippingPlane != null ) {                    if ( !clippingPlane.doIntersection(testRay) ) {                        VSDK.reportMessage(this, VSDK.WARNING,                             "clipLineCohenSutherlandPlanes",                             "Unusal ray assembly, check code and data");                    }                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t));                    linePasses = true;                }                //--------------------------------------------------                if ( outcodeout == outcode0 ) {                    clippedPoint0.x = clippingMidPoint.x;                    clippedPoint0.y = clippingMidPoint.y;                    clippedPoint0.z = clippingMidPoint.z;                    outcode0 = calculateOutcodeBits(clippedPoint0,                        rightPlane, leftPlane, upPlane,                         downPlane, nearPlane, farPlane);                  }                  else {                    clippedPoint1.x = clippingMidPoint.x;                    clippedPoint1.y = clippingMidPoint.y;                    clippedPoint1.z = clippingMidPoint.z;                    outcode1 = calculateOutcodeBits(clippedPoint1,                        rightPlane, leftPlane, upPlane,                         downPlane, nearPlane, farPlane);                }            }        } while ( !done );        return linePasses;    }    /**    This method implements the Cohen-Sutherland line clipping algorithm with    respect to the view volume defined by current camera. Recieves the two    line endpoints and return true if any part of this line lies inside the    view volume.  In the case the line crosses the view volume, the new    resulting endpoints are calculated and returned.    This algorithm structure follows the one proposed in [FOLE1992].3.12.3,    generalizing it to the 3D case, as noted in [FOLE1992].6.5.3.    The resulting clipped points are in the canonical volume reference, ready    for projection.  If 3D clipped points are needed, they must be premultiplied    by the inverse of the normalizingTransformation.    */    public boolean clipLineCohenSutherlandCanonicVolume(                             Vector3D point0, Vector3D point1,                             Vector3D clippedPoint0, Vector3D clippedPoint1)    {        //- Local variables definition ------------------------------------        int outcode0;                // 6bit containment code for point0        int outcode1;                // 6bit containment code for point1        int outcodeout;              // Selected endpoint code for iteration        Vector3D clippingMidPoint;   // Selected endpoint clipped for iteration        Ray testRay;                 // Ray use for general line/plane clipping        Vector3D dirFromP0ToP1;      // Temporary for testRay construction        double l;                    // Length of dirFromP0ToP1        int planeId;                 // A number from 1 to 6 identifying which                                     // plane intersection is being tested        //- Algorithm initial state ---------------------------------------        Vector3D pp0, pp1;        pp0 = normalizingTransformation.multiply(point0);        pp1 = normalizingTransformation.multiply(point1);        clippedPoint0.x = pp0.x;        clippedPoint0.y = pp0.y;        clippedPoint0.z = pp0.z;        clippedPoint1.x = pp1.x;        clippedPoint1.y = pp1.y;        clippedPoint1.z = pp1.z;        updateVectors();        clippingMidPoint = new Vector3D();        outcode0 = calculateOutcodeBits(pp0);        outcode1 = calculateOutcodeBits(pp1);        //- Main Cohen-Sutherland iteration cycle (incremental clipping) --        boolean linePasses = false; // Algorithm return value        boolean done = false;       // Iteration exit condition        do {            //- Trivial cases: trivial accept and trivial reject ----------            if ( outcode0 == 0x0 && outcode1 == 0x0 ) {                linePasses = true;                done = true;            }            else if ( (outcode0 & outcode1) != 0x0 ) {                linePasses = false;                done = true;            }            //- Iterative cases: clipping with each of the 6 planes -------            else {                //--------------------------------------------------                dirFromP0ToP1 = clippedPoint1.substract(clippedPoint0);                l = dirFromP0ToP1.length();                if ( l < VSDK.EPSILON ) {                    // continue;                    return false;                }                dirFromP0ToP1.x /= l;                dirFromP0ToP1.y /= l;                dirFromP0ToP1.z /= l;                //--------------------------------------------------                if ( outcode0 != 0 ) {                    outcodeout = outcode0;                  }                  else {                    outcodeout = outcode1;                }                testRay = new Ray(clippedPoint0, dirFromP0ToP1);                //--------------------------------------------------                planeId = 0;                if ( (OPCODE_UP & outcodeout) != 0x0 ) {                    planeId = 1; // up plane;                }                else if ( (OPCODE_DOWN & outcodeout) != 0x0 ) {                    planeId = 2; // down plane;                }                else if ( (OPCODE_LEFT & outcodeout) != 0x0 ) {                    planeId = 3; // left plane;                }                else if ( (OPCODE_RIGHT & outcodeout) != 0x0 ) {                    planeId = 4; // right plane;                }                else if ( (OPCODE_NEAR & outcodeout) != 0x0 ) {                    planeId = 5; // near plane                }                else if ( (OPCODE_FAR & outcodeout) != 0x0 ) {                    planeId = 6; // far plane;                }                else {                    // Not possible: non implemented case!                        VSDK.reportMessage(this, VSDK.WARNING,                             "clipLineCohenSutherlandCanonicVolume",                             "Unusal case, check code and data");                }                double de;                de = (outcodeout == outcode1) ? -VSDK.EPSILON: VSDK.EPSILON;                switch ( planeId ) {                  case 1: // up plane                    testRay.t =                           (l * (1 - clippedPoint0.z - clippedPoint0.y)) /                           (clippedPoint1.z - clippedPoint0.z +                            clippedPoint1.y - clippedPoint0.y);                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                  case 2: // down plane                    testRay.t =                           (l * (clippedPoint0.y - clippedPoint0.z +1)) /                           (clippedPoint1.z - clippedPoint0.z -                            clippedPoint1.y + clippedPoint0.y);                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                  case 3: // left plane                    testRay.t =                           (l * (clippedPoint0.x - clippedPoint0.z +1)) /                           (clippedPoint1.z - clippedPoint0.z -                            clippedPoint1.x + clippedPoint0.x);                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                  case 4: // right plane                    testRay.t =                           (l * (1 - clippedPoint0.z - clippedPoint0.x)) /                           (clippedPoint1.z - clippedPoint0.z +                            clippedPoint1.x - clippedPoint0.x);                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                  case 5: // near plane                    // Warning: near plane clipping                    testRay.t = 			( /*(1-nearPlaneDistance)*/ -clippedPoint0.z * l) /                           (clippedPoint1.z - clippedPoint0.z);                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                  case 6: // far plane                    testRay.t =                         (((-fpd()-                             clippedPoint0.z) * l) /                              (clippedPoint1.z - clippedPoint0.z));                    clippingMidPoint = testRay.origin.add(                        testRay.direction.multiply(testRay.t+de));                    linePasses = true;                    break;                }                //--------------------------------------------------                if ( outcodeout == outcode0 ) {                    clippedPoint0.x = clippingMidPoint.x;                    clippedPoint0.y = clippingMidPoint.y;                    clippedPoint0.z = clippingMidPoint.z;                    outcode0 = calculateOutcodeBits(clippedPoint0);                  }                  else {                    clippedPoint1.x = clippingMidPoint.x;                    clippedPoint1.y = clippingMidPoint.y;                    clippedPoint1.z = clippingMidPoint.z;                    outcode1 = calculateOutcodeBits(clippedPoint1);                }            }        } while ( !done );        return linePasses;    }    /**    Given a point `inPoint` in world coordinates, this method calculates a    pixel's  coordinate in viewport space (in the form <u, v, 0>).    Returns true if the pixel lies inside the viewport, false otherwise.    Note that the integer part of the returned `outProjected` point (in    its x and y coordinates) can be used as an input to a putPixel type    image operation for display, and the same coordinate as double, is    usefull as an input for antialiased versions of line rasterizers.    This method is fundamental for visualization operations, where some    examples includes but are not limited to:    - Given two (previously clipped) line endpoints in world space,       projected positions can be used for 2D line drawing for wireframe      and hidden line rendering algorithms (caligraphic phase prior to      2D rasterizing).    - For interaction techniques, 2D feedback over 2D visualization.    - As part of complex interaction techniques involving a 3D point image      in camera viewport, for example to calculate relative movement in 3D      with respect to aparent current view from camera.    TODO: Current implementation is suspicious. It should use a simple    multiplication of point with projection matrix... but this idea is not    working.    */    public boolean projectPoint(Vector3D inPoint, Vector3D outProjected)    {        // 1. Calculate vectors        Vector3D upCopy = null;        Vector3D rightCopy = null;        double fovFactor = 0.0;        double scaleFactor = 0.0;        fovFactor = viewportXSize/viewportYSize;        updateVectors(); // Should be made a prerequisite for efficiency!        // 2. Calculate projection plane        Vector3D p;        Vector3D center;        InfinitePlane viewPlane;        center = new Vector3D(front);        p = getPosition();        center.normalize();        center.multiply(nearPlaneDistance);        center = center.add(p);        viewPlane = new InfinitePlane(front.multiply(-1), center);        // 3. Calculate projected global coordinates XYZ        Vector3D projected;        if ( projectionMode == PROJECTION_MODE_ORTHOGONAL ) {            projected = (viewPlane.projectPoint(inPoint).substract(center)).multiply(orthogonalZoom);        }        else {            // 3.1. Vector calculation for perspective case            upCopy = new Vector3D(up);            rightCopy = new Vector3D(left.multiply(-1));            scaleFactor = 1.0/Math.tan(Math.toRadians(fov/2));            upCopy.normalize();            upCopy = upCopy.multiply(scaleFactor);            rightCopy.normalize();            rightCopy = rightCopy.multiply(scaleFactor).multiply(1/fovFactor);            // 3.2. Calculate projector for perspective case            Ray r;            r = new Ray(p, inPoint.substract(p));            // 3.3. Project point in view plane from perspective eyepoint            if ( !viewPlane.doIntersection(r) ||                 r.direction.length() < VSDK.EPSILON ) {                return false;            }            projected = r.origin.add(r.direction.multiply(r.t)).substract(center);            // 3.4. Clip projected point in viewport            if ( projected.x < -1 || projected.x > 1 ||                 projected.y < -1 || projected.y > 1 ) {                return false;            }        }        // 4. Scale point to viewport        if ( projectionMode == PROJECTION_MODE_ORTHOGONAL ) {            outProjected.x = viewportXSize/2 + (projected.dotProduct(left.multiply(-1)))/(2*fovFactor)*viewportXSize;            outProjected.y = (((projected.dotProduct(up)*-1)+1)/2)*viewportYSize;        }        else {            outProjected.x = (projected.dotProduct(rightCopy)/2+0.5)*viewportXSize;            outProjected.y = (1-(projected.dotProduct(upCopy)/2+0.5))*viewportYSize;        }        outProjected.z = 0.0;        return true;    }    /**    Return 6 outward pointing planes bounding the view volume / frustum    for current camera.    PRE: updateVectors method should be called before calling this method.    */    public InfinitePlane[] getBoundingPlanes()    {        InfinitePlane planes[];        planes = new InfinitePlane[6];        planes[0] = calculateUPlane(-0.5);        planes[1] = calculateUPlane(0.5);        planes[2] = calculateVPlane(-0.5);        planes[3] = calculateVPlane(0.5);        planes[4] = calculateNearPlane();        planes[5] = calculateFarPlane();        return planes;    }}//===========================================================================//= EOF                                                                     =//===========================================================================

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -