Example #1
0
        public override int clamp(cRealBox3 border)
        { /* We don't change _pskeleton as it has the geometric info.  We
           *    just change _position. */
            if (_baseAccessControl == 1)
            {
                return(base.clamp(border));
            }
            cRealBox3 effectivebox = border;
            cVector3  oldcorner;
            cVector3  newcorner    = new cVector3();
            int       outcode      = 0;
            int       totaloutcode = 0;

            for (int i = 0; i < 8; i++) //Step through the wall's corners
            {
                oldcorner = _pskeleton.corner(i) + _position;
                newcorner.copy(oldcorner);
                outcode = effectivebox.clamp(newcorner);
                if (outcode != cRealBox3.BOX_INSIDE) //corner was moved
                {
                    _position += newcorner - oldcorner;

                    /* As long at the wall is small enough to
                     * fit inside the border, the successive
                     * corrections won't cancel each other out. */
                    totaloutcode |= outcode;
                }
            }
            _wrapposition1.copy(_position);
            _wrapposition2.copy(_position);
            _wrapposition3.copy(_position);
            /* So it won't think it wrapped. */
            return(outcode);
        }
Example #2
0
        /* Uses _foveaproportion which lies between 0.0 and 1.0. We say something is visible if it
         *  appears on the inner _foveaproportion central box of the viewer's image screen,
         *  which is what you see in the view window. */
        //overloads

        //Use _pownerview to get the CpopDoc and get the cGame from that.

        public override void update(ACView pactiveview, float dt)
        {
            base.update(pactiveview, dt);
            ZClipPlanes = Game.Border.outerBox(cSprite.MAXPRISMDZ);
            if (_trackplayer &&
                !((Listener != null) && Listener.RuntimeClass == "cListenerViewerRide"))

            /* The meaning of the visibleplayer() condition is that it doesn't make sense
             * to track the player if it's not an onscreen player. The reason for the
             * listener condition is that you don't want to stare at the player when
             * riding it. */
            /*  I should  explain that the goal here is to not bother turning when the player
             * is  moving around in the middle of the veiw area, and only to turn when he's near
             * the edge, but to have the turning when he's near the edge be smoooth.
             * The use of the 0.85 foveaproportion parameter means that you react before the player
             * gets right up to the edge.  The reactproportion factor in lookAtProportional and
             * moveToProportional is delicate and should probably be adjusted according to the
             * current player speed relative to the visible window.  The issue is that (a) if I make
             * reactproportion too small, like 0.01, then the viewer doesn't turn (or move) fast
             * enough to catch up with the player and keep it in view, but (b) if I make reactpropotion
             * too big, like 0.5, then the turning or moving is such an abrupt jump that the visual
             * effect is jerky.  The goal is to do turns that are just big enough to not look jerky,
             * but to have the turns be big enough so you aren't turning more often than you really
             * have to.  Another downside of a toosmall reactproportion, by the way, is that it can be
             * computationally expensive to react.
             * The way we finally solved this is to do a while loop to turn just
             * far enough, moving just a little at a time so as to not overshoot. */
            {
                if (isVisible(Game.Player.Position)) // Uses _foveaproportion
                {
                    _lastgoodplayeroffset = Position - Game.Player.Position;
                }

                /*I'm not sure about constantly changing _lastgoodplayeroffset.  On the
                 * one hand, the offset I set in setViewpoint was a standard good one, so why
                 * not keep it.  On the other, if I want to move my viewpoint around then I
                 * do want to be able to get a new value here. It seems ok for now.*/
                else //not visible, so do somehting about it.
                {
                    int loopcount      = 0; /* Never have a while loop without a loopcount
                                             * to make sure you don't spin inside the while forever under some
                                             * unexpected situation like at startup. */
                    cVector3 lookat    = Game.Player.Position;
                    cVector3 viewerpos = lookat + _lastgoodplayeroffset;
                    if (Game.worldShape() == cGame.SHAPE_XSCROLLER)
                    {
                        lookat = new cVector3(Game.Player.Position.X,
                                              Game.Border.Midy, Game.Player.Position.Z);
                        viewerpos = new cVector3(lookat.X, Position.Y, Position.Z);
                    }
                    if (Game.worldShape() == cGame.SHAPE_YSCROLLER)
                    {
                        lookat = new cVector3(Game.Border.Midx,
                                              Game.Player.Position.Y, Game.Player.Position.Z);
                        viewerpos = new cVector3(Position.X, lookat.Y, Position.Z);
                    }
                    if (_perspective)
                    {
                        while (!isVisible(lookat) && loopcount < 100) // Uses _foveaproportion
                        {
                            moveToProportional(viewerpos, cCritterViewer.TURNPROPORTION);
                            loopcount++;
                        }
                    }
                    else //ortho case
                    {
                        while (!isVisible(lookat) && loopcount < 100) // Uses _foveaproportion
                        {
                            moveToProportional(lookat + Game.Player.Binormal * 10.0f,
                                               cCritterViewer.TURNPROPORTION);
                            loopcount++;
                        }
                    }
                }
            }
            //Possibly ride the player.
            if (Listener is cListenerViewerRide)
            {
                cCritter pplayer = Game.Player;
                cVector3 offset  = ((cListenerViewerRide)Listener).Offset;
                moveTo(pplayer.Position +
                       pplayer.AttitudeTangent * offset.X +
                       pplayer.AttitudeNormal * offset.Y +
                       pplayer.AttitudeBinormal * offset.Z);
                cRealBox3 skeleton = pplayer.MoveBox;
                if (skeleton.ZSize < 0.5f)
                {
                    skeleton.setZRange(0.0f, offset.Z);
                }
                if (skeleton.YSize < 0.5f)
                {
                    skeleton.setYRange(0.0f, offset.Z);
                }
                skeleton.clamp(_position);
                for (int i = 0; i < Game.Biota.count(); i++)
                {
                    cCritter pother = Game.Biota.GetAt(i);
                    if (pother is cCritterWall)
                    {
                        pother.collide(this);
                    }
                }

                /* colliding with the wall may have twisted the viwer's orientation,
                 * so align it once again. */
                Attitude = pplayer.Attitude; /* Before we call lookAt,
                                              * make sure your attitude matches the player.  For one thing,
                                              * you may have gotten twisted around in the COLLIDEVIEWER code. */
                lookAt(pplayer.Position +
                       pplayer.AttitudeTangent * cListenerViewerRide.PLAYERLOOKAHEAD * pplayer.Radius);

                /* This has the effect that as offset gets large you change your
                 * looking direction see right in front of the player. The multiplier
                 * cCritterViewer.PLAYERLOOKAHEAD is tweaked to work well
                 * with the default cCritterViewer.OFFSET. */
            }
        }