Ejemplo n.º 1
0
        public int DrawCostume(VirtScreen vs, int numStrips, Actor actor, bool drawToBackBuf)
        {
            var pixelsNavigator = new PixelNavigator(vs.Surfaces[drawToBackBuf ? 1 : 0]);

            pixelsNavigator.OffsetX(vs.XStart);

            ActorX += (vs.XStart & 7);
            _w      = vs.Width;
            _h      = vs.Height;
            pixelsNavigator.OffsetX(-(vs.XStart & 7));
            startNav = new PixelNavigator(pixelsNavigator);

            if (_vm.Game.Version <= 1)
            {
                _xmove = 0;
                _ymove = 0;
            }
            else if (_vm.Game.IsOldBundle)
            {
                _xmove = -72;
                _ymove = -100;
            }
            else
            {
                _xmove = _ymove = 0;
            }

            int result = 0;

            for (int i = 0; i < 16; i++)
            {
                result |= DrawLimb(actor, i);
            }
            return(result);
        }
Ejemplo n.º 2
0
        public int DrawCostume(VirtScreen vs, int numStrips, Actor actor, bool drawToBackBuf)
        {
            var pixelsNavigator = new PixelNavigator(vs.Surfaces[drawToBackBuf ? 1 : 0]);
            pixelsNavigator.OffsetX(vs.XStart);

            ActorX += (vs.XStart & 7);
            _w = vs.Width;
            _h = vs.Height;
            pixelsNavigator.OffsetX(-(vs.XStart & 7));
            startNav = new PixelNavigator(pixelsNavigator);

            if (_vm.Game.Version <= 1)
            {
                _xmove = 0;
                _ymove = 0;
            }
            else if (_vm.Game.IsOldBundle)
            {
                _xmove = -72;
                _ymove = -100;
            }
            else
            {
                _xmove = _ymove = 0;
            }

            int result = 0;
            for (int i = 0; i < 16; i++)
                result |= DrawLimb(actor, i);
            return result;
        }
Ejemplo n.º 3
0
        protected void FadeOut(int effect)
        {
            _mainVirtScreen.SetDirtyRange(0, 0);

            if (Game.Version < 7)
            {
                Camera.LastPosition.X = Camera.CurrentPosition.X;
            }

            if (Game.Version == 3 && _game.Platform == Platform.FMTowns)
            {
                Gdi.Fill(TextSurface,
                         new Rect(0, MainVirtScreen.TopLine * _textSurfaceMultiplier,
                                  _textSurface.Pitch, (MainVirtScreen.TopLine + MainVirtScreen.Height) * _textSurfaceMultiplier), 0);
            }

            if ((Game.Version == 7 || _screenEffectFlag) && effect != 0)
            {
                // Fill screen 0 with black
                var pixNav = new PixelNavigator(_mainVirtScreen.Surfaces[0]);
                pixNav.OffsetX(_mainVirtScreen.XStart);
                Gdi.Fill(pixNav, 0, _mainVirtScreen.Width, _mainVirtScreen.Height);

                // Fade to black with the specified effect, if any.
                switch (effect)
                {
                case 1:
                case 2:
                case 3:
                case 4:
                case 5:
                case 6:
                    DoTransitionEffect(effect - 1);
                    break;

                case 128:
                    UnkScreenEffect6();
                    break;

                case 129:
                    // Just blit screen 0 to the display (i.e. display will be black)
                    _mainVirtScreen.SetDirtyRange(0, _mainVirtScreen.Height);
                    UpdateDirtyScreen(_mainVirtScreen);
                    if (_townsScreen != null)
                    {
                        _townsScreen.Update();
                    }
                    break;

                default:
                    throw new NotImplementedException(string.Format("fadeOut: case {0}", effect));
                }
            }

            // Update the palette at the end (once we faded to black) to avoid
            // some nasty effects when the palette is changed
            UpdatePalette();

            _screenEffectFlag = false;
        }
Ejemplo n.º 4
0
        void RestoreCharsetBg()
        {
            _nextLeft = _string[0].Position.X;
            _nextTop  = _string[0].Position.Y + ScreenTop;

            if (_charset.HasMask)
            {
                _charset.HasMask  = false;
                _charset.Str.Left = -1;
                _charset.Left     = -1;

                // Restore background on the whole text area. This code is based on
                // restoreBackground(), but was changed to only restore those parts which are
                // currently covered by the charset mask.

                var vs = _charset.TextScreen;
                if (vs.Height == 0)
                {
                    return;
                }

                MarkRectAsDirty(vs, 0, vs.Width, 0, vs.Height, Gdi.UsageBitRestored);

                if (vs.HasTwoBuffers && _currentRoom != 0 && IsLightOn())
                {
                    if (vs != MainVirtScreen)
                    {
                        // Restore from back buffer
                        var screenBufNav = new PixelNavigator(vs.Surfaces[0]);
                        screenBufNav.OffsetX(vs.XStart);
                        var backNav = new PixelNavigator(vs.Surfaces[1]);
                        backNav.OffsetX(vs.XStart);
                        Gdi.Blit(screenBufNav, backNav, vs.Width, vs.Height);
                    }
                }
                else
                {
                    // Clear area
                    var screenBuf = vs.Surfaces[0].Pixels;
                    Array.Clear(screenBuf, 0, screenBuf.Length);
                }

                if (vs.HasTwoBuffers)
                {
                    // Clean out the charset mask
                    ClearTextSurface();
                }
            }
        }
Ejemplo n.º 5
0
        static byte[] Capture(VirtScreen screen, int x, int y, int w, int h)
        {
            var pixels = new byte[w * h];
            var nav    = new PixelNavigator(screen.Surfaces[0]);

            nav.GoTo(x, y);
            for (int height = 0; height < h; height++)
            {
                for (int width = 0; width < w; width++)
                {
                    pixels[height * w + width] = nav.Read();
                    nav.OffsetX(1);
                }
                nav.Offset(-w, 1);
            }
            return(pixels);
        }
Ejemplo n.º 6
0
        protected void TownsDrawStripToScreen(VirtScreen vs, int dstX, int dstY, int srcX, int srcY, int width, int height)
        {
            if (width <= 0 || height <= 0)
            {
                return;
            }

            int m = _textSurfaceMultiplier;

            var src1 = new PixelNavigator(vs.Surfaces[0]);

            src1.GoTo(vs.XStart + srcX, srcY);
            var src2 = new PixelNavigator(_textSurface);

            src2.GoTo(srcX * m, (srcY + vs.TopLine - ScreenTop) * m);
            var dst1 = new PixelNavigator(_townsScreen.GetLayerPixels(0, dstX, dstY).Value);
            var dst2 = new PixelNavigator(_townsScreen.GetLayerPixels(1, dstX * m, dstY * m).Value);

            int dp1 = _townsScreen.GetLayerPitch(0) - width * _townsScreen.GetLayerBpp(0);
            int dp2 = _townsScreen.GetLayerPitch(1) - width * m * _townsScreen.GetLayerBpp(1);
            int sp1 = vs.Pitch - (width * Surface.GetBytesPerPixel(vs.PixelFormat));
            int sp2 = _textSurface.Pitch - width * m;

            if (vs == MainVirtScreen || Game.GameId == GameId.Indy3 || Game.GameId == GameId.Zak)
            {
                for (int h = 0; h < height; ++h)
                {
                    if (Surface.GetBytesPerPixel(_gfxManager.PixelFormat) == 2)
                    {
                        for (int w = 0; w < width; ++w)
                        {
                            dst1.WriteUInt16(_16BitPalette[src1.Read()]);
                            src1.OffsetX(1);
                            dst1.OffsetX(1);
                        }

                        src1.OffsetX(sp1 / src1.BytesByPixel);
                        dst1.OffsetX(dp1 / dst1.BytesByPixel);
                    }
                    else
                    {
                        for (int i = 0; i < width; i++)
                        {
                            dst1.Write(src1.Read());
                            dst1.OffsetX(1);
                            src1.OffsetX(1);
                        }
                    }

                    for (int sH = 0; sH < m; ++sH)
                    {
                        for (int i = 0; i < width * m; i++)
                        {
                            dst2.Write(src2.Read());
                            src2.OffsetX(1);
                            dst2.OffsetX(1);
                        }
                        src2.OffsetX(_textSurface.Width - (width * m));
                        dst2.OffsetX(dst2.Width - (width * m));
                    }
                }
            }
            else
            {
                dst1 = new PixelNavigator(dst2);
                for (int h = 0; h < height; ++h)
                {
                    for (int w = 0; w < width; ++w)
                    {
                        var t = (src1.Read()) & 0x0f;
                        src1.OffsetX(1);
                        for (int i = 0; i < m; i++)
                        {
                            dst1.Write((byte)((t << 4) | t));
                            dst1.OffsetX(1);
                        }
                    }

                    dst1 = new PixelNavigator(dst2);
                    var src3 = new PixelNavigator(src2);

                    if (m == 2)
                    {
                        dst2.OffsetY(1);
                        src3.OffsetY(1);
                    }

                    for (int w = 0; w < width * m; ++w)
                    {
                        dst2.Write((byte)(src3.Read() | dst1.Read() & _townsLayer2Mask[src3.Read()]));
                        dst2.OffsetX(1);
                        dst1.Write((byte)(src2.Read() | dst1.Read() & _townsLayer2Mask[src2.Read()]));
                        src2.OffsetX(1);
                        src3.OffsetX(1);
                        dst1.OffsetX(1);
                    }

                    src1.OffsetX(sp1 / src1.BytesByPixel);
                    src2 = new PixelNavigator(src3);
                    src2.OffsetX(sp2 / src2.BytesByPixel);
                    dst1 = new PixelNavigator(dst2);
                    dst1.OffsetX(dp2 / dst1.BytesByPixel);
                    dst2.OffsetX(dp2 / dst2.BytesByPixel);
                }
            }

            _townsScreen.AddDirtyRect(dstX * m, dstY * m, width * m, height * m);
        }
Ejemplo n.º 7
0
        /// <summary>
        /// Blit the specified rectangle from the given virtual screen to the display.
        /// Note: t and b are in *virtual screen* coordinates, while x is relative to
        /// the *real screen*. This is due to the way tdirty/vdirty work: they are
        /// arrays which map 'strips' (sections of the real screen) to dirty areas as
        /// specified by top/bottom coordinate in the virtual screen.
        /// </summary>
        /// <param name="vs"></param>
        /// <param name="x"></param>
        /// <param name="width"></param>
        /// <param name="top"></param>
        /// <param name="bottom"></param>
        void DrawStripToScreen(VirtScreen vs, int x, int width, int top, int bottom)
        {
            // Short-circuit if nothing has to be drawn
            if (bottom <= top || top >= vs.Height)
            {
                return;
            }

            // Perform some clipping
            if (width > vs.Width - x)
            {
                width = vs.Width - x;
            }
            if (top < ScreenTop)
            {
                top = ScreenTop;
            }
            if (bottom > ScreenTop + ScreenHeight)
            {
                bottom = ScreenTop + ScreenHeight;
            }

            // Convert the vertical coordinates to real screen coords
            int y      = vs.TopLine + top - ScreenTop;
            int height = bottom - top;

            if (width <= 0 || height <= 0)
            {
                return;
            }

            byte[] src;
            if (Game.Version < 7)
            {
                if (Game.Platform == Platform.FMTowns)
                {
                    TownsDrawStripToScreen(vs, x, y, x, top, width, height);
                    return;
                }

                var srcNav = new PixelNavigator(vs.Surfaces[0]);
                srcNav.GoTo(vs.XStart + x, top);

                var compNav = new PixelNavigator(_composite);
                var txtNav  = new PixelNavigator(_textSurface);
                int m       = _textSurfaceMultiplier;
                txtNav.GoTo(x * m, y * m);

                var vsPitch   = vs.Pitch - width * vs.BytesPerPixel;
                var textPitch = _textSurface.Pitch - width * m;

                for (int h = height * m; h > 0; --h)
                {
                    for (int w = width * m; w > 0; w--)
                    {
                        var temp = txtNav.Read();
                        int mask = temp ^ CharsetMaskTransparency;
                        mask = (((mask & 0x7f) + 0x7f) | mask) & 0x80;
                        mask = ((mask >> 7) + 0x7f) ^ 0x80;

                        var dst = ((temp ^ srcNav.Read()) & mask) ^ temp;
                        compNav.Write((byte)dst);

                        srcNav.OffsetX(1);
                        txtNav.OffsetX(1);
                        compNav.OffsetX(1);
                    }

                    srcNav.OffsetX(vsPitch);
                    txtNav.OffsetX(textPitch);
                }

                src = _composite.Pixels;
            }
            else
            {
                src = new byte[width * height * vs.BytesPerPixel];
                var srcNav = new PixelNavigator(vs.Surfaces[0]);
                srcNav.GoTo(vs.XStart + x, top);
                for (int h = 0; h < height; h++)
                {
                    for (int w = 0; w < width; w++)
                    {
                        src[h * width + w] = srcNav.Read();
                        srcNav.OffsetX(1);
                    }
                    srcNav.Offset(-width, 1);
                }
            }

            // Finally blit the whole thing to the screen
            _gfxManager.CopyRectToScreen(src, width * vs.BytesPerPixel, x, y, width, height);
        }