8bpp_base.cpp

Go to the documentation of this file.
00001 /* $Id: 8bpp_base.cpp 17248 2009-08-21 20:21:05Z rubidium $ */
00002 
00003 /*
00004  * This file is part of OpenTTD.
00005  * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2.
00006  * OpenTTD 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.
00007  * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see <http://www.gnu.org/licenses/>.
00008  */
00009 
00012 #include "../stdafx.h"
00013 #include "../gfx_func.h"
00014 #include "8bpp_base.hpp"
00015 
00016 void Blitter_8bppBase::DrawColourMappingRect(void *dst, int width, int height, int pal)
00017 {
00018   const uint8 *ctab = GetNonSprite(pal, ST_RECOLOUR) + 1;
00019 
00020   do {
00021     for (int i = 0; i != width; i++) *((uint8 *)dst + i) = ctab[((uint8 *)dst)[i]];
00022     dst = (uint8 *)dst + _screen.pitch;
00023   } while (--height);
00024 }
00025 
00026 void *Blitter_8bppBase::MoveTo(const void *video, int x, int y)
00027 {
00028   return (uint8 *)video + x + y * _screen.pitch;
00029 }
00030 
00031 void Blitter_8bppBase::SetPixel(void *video, int x, int y, uint8 colour)
00032 {
00033   *((uint8 *)video + x + y * _screen.pitch) = colour;
00034 }
00035 
00036 void Blitter_8bppBase::SetPixelIfEmpty(void *video, int x, int y, uint8 colour)
00037 {
00038   uint8 *dst = (uint8 *)video + x + y * _screen.pitch;
00039   if (*dst == 0) *dst = colour;
00040 }
00041 
00042 void Blitter_8bppBase::DrawRect(void *video, int width, int height, uint8 colour)
00043 {
00044   do {
00045     memset(video, colour, width);
00046     video = (uint8 *)video + _screen.pitch;
00047   } while (--height);
00048 }
00049 
00050 void Blitter_8bppBase::DrawLine(void *video, int x, int y, int x2, int y2, int screen_width, int screen_height, uint8 colour)
00051 {
00052   int dy;
00053   int dx;
00054   int stepx;
00055   int stepy;
00056   int frac;
00057 
00058   dy = (y2 - y) * 2;
00059   if (dy < 0) {
00060     dy = -dy;
00061     stepy = -1;
00062   } else {
00063     stepy = 1;
00064   }
00065 
00066   dx = (x2 - x) * 2;
00067   if (dx < 0) {
00068     dx = -dx;
00069     stepx = -1;
00070   } else {
00071     stepx = 1;
00072   }
00073 
00074   if (x >= 0 && y >= 0 && x < screen_width && y < screen_height) this->SetPixel(video, x, y, colour);
00075   if (dx > dy) {
00076     frac = dy - (dx / 2);
00077     while (x != x2) {
00078       if (frac >= 0) {
00079         y += stepy;
00080         frac -= dx;
00081       }
00082       x += stepx;
00083       frac += dy;
00084       if (x >= 0 && y >= 0 && x < screen_width && y < screen_height) this->SetPixel(video, x, y, colour);
00085     }
00086   } else {
00087     frac = dx - (dy / 2);
00088     while (y != y2) {
00089       if (frac >= 0) {
00090         x += stepx;
00091         frac -= dy;
00092       }
00093       y += stepy;
00094       frac += dx;
00095       if (x >= 0 && y >= 0 && x < screen_width && y < screen_height) this->SetPixel(video, x, y, colour);
00096     }
00097   }
00098 }
00099 
00100 void Blitter_8bppBase::CopyFromBuffer(void *video, const void *src, int width, int height)
00101 {
00102   uint8 *dst = (uint8 *)video;
00103   uint8 *usrc = (uint8 *)src;
00104 
00105   for (; height > 0; height--) {
00106     memcpy(dst, usrc, width * sizeof(uint8));
00107     usrc += width;
00108     dst += _screen.pitch;
00109   }
00110 }
00111 
00112 void Blitter_8bppBase::CopyToBuffer(const void *video, void *dst, int width, int height)
00113 {
00114   uint8 *udst = (uint8 *)dst;
00115   uint8 *src = (uint8 *)video;
00116 
00117   for (; height > 0; height--) {
00118     memcpy(udst, src, width * sizeof(uint8));
00119     src += _screen.pitch;
00120     udst += width;
00121   }
00122 }
00123 
00124 void Blitter_8bppBase::CopyImageToBuffer(const void *video, void *dst, int width, int height, int dst_pitch)
00125 {
00126   uint8 *udst = (uint8 *)dst;
00127   uint8 *src = (uint8 *)video;
00128 
00129   for (; height > 0; height--) {
00130     memcpy(udst, src, width * sizeof(uint8));
00131     src += _screen.pitch;
00132     udst += dst_pitch;
00133   }
00134 }
00135 
00136 void Blitter_8bppBase::ScrollBuffer(void *video, int &left, int &top, int &width, int &height, int scroll_x, int scroll_y)
00137 {
00138   const uint8 *src;
00139   uint8 *dst;
00140 
00141   if (scroll_y > 0) {
00142     /* Calculate pointers */
00143     dst = (uint8 *)video + left + (top + height - 1) * _screen.pitch;
00144     src = dst - scroll_y * _screen.pitch;
00145 
00146     /* Decrease height and increase top */
00147     top += scroll_y;
00148     height -= scroll_y;
00149     assert(height > 0);
00150 
00151     /* Adjust left & width */
00152     if (scroll_x >= 0) {
00153       dst += scroll_x;
00154       left += scroll_x;
00155       width -= scroll_x;
00156     } else {
00157       src -= scroll_x;
00158       width += scroll_x;
00159     }
00160 
00161     for (int h = height; h > 0; h--) {
00162       memcpy(dst, src, width * sizeof(uint8));
00163       src -= _screen.pitch;
00164       dst -= _screen.pitch;
00165     }
00166   } else {
00167     /* Calculate pointers */
00168     dst = (uint8 *)video + left + top * _screen.pitch;
00169     src = dst - scroll_y * _screen.pitch;
00170 
00171     /* Decrese height. (scroll_y is <=0). */
00172     height += scroll_y;
00173     assert(height > 0);
00174 
00175     /* Adjust left & width */
00176     if (scroll_x >= 0) {
00177       dst += scroll_x;
00178       left += scroll_x;
00179       width -= scroll_x;
00180     } else {
00181       src -= scroll_x;
00182       width += scroll_x;
00183     }
00184 
00185     /* the y-displacement may be 0 therefore we have to use memmove,
00186      * because source and destination may overlap */
00187     for (int h = height; h > 0; h--) {
00188       memmove(dst, src, width * sizeof(uint8));
00189       src += _screen.pitch;
00190       dst += _screen.pitch;
00191     }
00192   }
00193 }
00194 
00195 int Blitter_8bppBase::BufferSize(int width, int height)
00196 {
00197   return width * height;
00198 }
00199 
00200 void Blitter_8bppBase::PaletteAnimate(uint start, uint count)
00201 {
00202   /* Video backend takes care of the palette animation */
00203 }
00204 
00205 Blitter::PaletteAnimation Blitter_8bppBase::UsePaletteAnimation()
00206 {
00207   return Blitter::PALETTE_ANIMATION_VIDEO_BACKEND;
00208 }

Generated on Wed Jan 20 23:38:34 2010 for OpenTTD by  doxygen 1.5.6