Ticket #8405: thumbnails-v1.patch

File thumbnails-v1.patch, 27.8 KB (added by lordhoto, 20 years ago)
  • common/module.mk

    diff -d -u --rec -N --exclude=CVS scummvm.old/common/module.mk scummvm/common/module.mk
    old new  
    2121        common/scaler/hq3x.o \
    2222        common/scaler/scale2x.o \
    2323        common/scaler/scale3x.o \
    24         common/scaler/scalebit.o
     24        common/scaler/scalebit.o \
     25        common/scaler/thumbnail.o
    2526
    2627ifdef HAVE_NASM
    2728MODULE_OBJS += \
  • common/scaler/thumbnail.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/common/scaler/thumbnail.cpp scummvm/common/scaler/thumbnail.cpp
    old new  
     1/* ScummVM - Scumm Interpreter
     2 * Copyright (C) 2001  Ludvig Strigeus
     3 * Copyright (C) 2001-2005 The ScummVM project
     4 *
     5 * This program is free software; you can redistribute it and/or
     6 * modify it under the terms of the GNU General Public License
     7 * as published by the Free Software Foundation; either version 2
     8 * of the License, or (at your option) any later version.
     9
     10 * This program is distributed in the hope that it will be useful,
     11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
     12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     13 * GNU General Public License for more details.
     14
     15 * You should have received a copy of the GNU General Public License
     16 * along with this program; if not, write to the Free Software
     17 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
     18 *
     19 * $Header: $
     20 *
     21 */
     22
     23#include "stdafx.h"
     24#include "common/scummsys.h"
     25#include "scaler.h"
     26#include "scaler/intern.h"
     27
     28template<int bitFormat>
     29void createThumbnail_4(const uint8* src, uint32 srcPitch, uint8* dstPtr, uint32 dstPitch, int width, int height) {
     30        for (int y = 0; y < height; y += 4) {
     31                for (int x = 0; x < width; x += 4, dstPtr += 2) {
     32                        uint16 colorx1y1 = *(((const uint16*)src) + x);
     33                        uint16 colorx2y1 = *(((const uint16*)src) + x + 1);
     34                        uint16 colorx3y1 = *(((const uint16*)src) + x + 2);
     35                        uint16 colorx4y1 = *(((const uint16*)src) + x + 3);
     36                       
     37                        uint16 colorx1y2 = *(((const uint16*)(src + srcPitch)) + x);
     38                        uint16 colorx2y2 = *(((const uint16*)(src + srcPitch)) + x + 1);
     39                        uint16 colorx3y2 = *(((const uint16*)(src + srcPitch)) + x + 2);
     40                        uint16 colorx4y2 = *(((const uint16*)(src + srcPitch)) + x + 3);
     41                       
     42                        uint16 colorx1y3 = *(((const uint16*)(src + srcPitch * 2)) + x);
     43                        uint16 colorx2y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 1);
     44                        uint16 colorx3y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 2);
     45                        uint16 colorx4y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 3);
     46                       
     47                        uint16 colorx1y4 = *(((const uint16*)(src + srcPitch * 3)) + x);
     48                        uint16 colorx2y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 1);
     49                        uint16 colorx3y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 2);
     50                        uint16 colorx4y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 3);
     51                               
     52                        uint16 upleft = Q_INTERPOLATE<bitFormat>(colorx1y1, colorx2y1, colorx1y2, colorx2y2);
     53                        uint16 upright = Q_INTERPOLATE<bitFormat>(colorx3y1, colorx4y1, colorx3y2, colorx4y2);
     54                        uint16 downleft = Q_INTERPOLATE<bitFormat>(colorx1y3, colorx2y3, colorx1y4, colorx2y4);
     55                        uint16 downright = Q_INTERPOLATE<bitFormat>(colorx3y3, colorx4y3, colorx3y4, colorx4y4);
     56                               
     57                        *((uint16*)dstPtr) = Q_INTERPOLATE<bitFormat>(upleft, upright, downleft, downright);                   
     58                }
     59                dstPtr += (dstPitch - 160);
     60                src += 4 * srcPitch;
     61        }
     62}
     63
     64template<int bitFormat>
     65void createThumbnail_8(const uint8* src, uint32 srcPitch, uint8* dstPtr, uint32 dstPitch, int width, int height) {
     66        for (int y = 0; y < height; y += 8) {
     67                for (int x = 0; x < width; x += 8, dstPtr += 2) {
     68                        uint16 colorx1y1 = *(((const uint16*)src) + x);
     69                        uint16 colorx2y1 = *(((const uint16*)src) + x + 1);
     70                        uint16 colorx3y1 = *(((const uint16*)src) + x + 2);
     71                        uint16 colorx4y1 = *(((const uint16*)src) + x + 3);
     72                       
     73                        uint32 colorx5y1 = *(((const uint16*)src) + x + 4);
     74                        uint16 colorx6y1 = *(((const uint16*)src) + x + 5);
     75                        uint16 colorx7y1 = *(((const uint16*)src) + x + 6);
     76                        uint16 colorx8y1 = *(((const uint16*)src) + x + 7);
     77                       
     78                        uint16 colorx1y2 = *(((const uint16*)(src + srcPitch)) + x);
     79                        uint16 colorx2y2 = *(((const uint16*)(src + srcPitch)) + x + 1);
     80                        uint16 colorx3y2 = *(((const uint16*)(src + srcPitch)) + x + 2);
     81                        uint16 colorx4y2 = *(((const uint16*)(src + srcPitch)) + x + 3);
     82                       
     83                        uint16 colorx5y2 = *(((const uint16*)(src + srcPitch)) + x + 4);
     84                        uint16 colorx6y2 = *(((const uint16*)(src + srcPitch)) + x + 5);
     85                        uint16 colorx7y2 = *(((const uint16*)(src + srcPitch)) + x + 6);
     86                        uint16 colorx8y2 = *(((const uint16*)(src + srcPitch)) + x + 7);
     87                       
     88                        uint16 colorx1y3 = *(((const uint16*)(src + srcPitch * 2)) + x);
     89                        uint16 colorx2y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 1);
     90                        uint16 colorx3y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 2);
     91                        uint16 colorx4y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 3);
     92                       
     93                        uint16 colorx5y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 4);
     94                        uint16 colorx6y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 5);
     95                        uint16 colorx7y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 6);
     96                        uint16 colorx8y3 = *(((const uint16*)(src + srcPitch * 2)) + x + 7);
     97                       
     98                        uint16 colorx1y4 = *(((const uint16*)(src + srcPitch * 3)) + x);
     99                        uint16 colorx2y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 1);
     100                        uint16 colorx3y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 2);
     101                        uint16 colorx4y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 3);
     102                       
     103                        uint16 colorx5y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 4);
     104                        uint16 colorx6y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 5);
     105                        uint16 colorx7y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 6);
     106                        uint16 colorx8y4 = *(((const uint16*)(src + srcPitch * 3)) + x + 7);
     107                       
     108                        uint16 colorx1y5 = *(((const uint16*)(src + srcPitch * 3)) + x);
     109                        uint16 colorx2y5 = *(((const uint16*)(src + srcPitch * 3)) + x + 1);
     110                        uint16 colorx3y5 = *(((const uint16*)(src + srcPitch * 3)) + x + 2);
     111                        uint16 colorx4y5 = *(((const uint16*)(src + srcPitch * 3)) + x + 3);
     112                       
     113                        uint16 colorx5y5 = *(((const uint16*)(src + srcPitch * 4)) + x + 4);
     114                        uint16 colorx6y5 = *(((const uint16*)(src + srcPitch * 4)) + x + 5);
     115                        uint16 colorx7y5 = *(((const uint16*)(src + srcPitch * 4)) + x + 6);
     116                        uint16 colorx8y5 = *(((const uint16*)(src + srcPitch * 4)) + x + 7);
     117                       
     118                        uint16 colorx1y6 = *(((const uint16*)(src + srcPitch * 5)) + x);
     119                        uint16 colorx2y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 1);
     120                        uint16 colorx3y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 2);
     121                        uint16 colorx4y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 3);
     122                       
     123                        uint16 colorx5y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 4);
     124                        uint16 colorx6y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 5);
     125                        uint16 colorx7y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 6);
     126                        uint16 colorx8y6 = *(((const uint16*)(src + srcPitch * 5)) + x + 7);
     127                       
     128                        uint16 colorx1y7 = *(((const uint16*)(src + srcPitch * 6)) + x);
     129                        uint16 colorx2y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 1);
     130                        uint16 colorx3y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 2);
     131                        uint16 colorx4y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 3);
     132                       
     133                        uint16 colorx5y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 4);
     134                        uint16 colorx6y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 5);
     135                        uint16 colorx7y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 6);
     136                        uint16 colorx8y7 = *(((const uint16*)(src + srcPitch * 6)) + x + 7);
     137                       
     138                        uint16 colorx1y8 = *(((const uint16*)(src + srcPitch * 7)) + x);
     139                        uint16 colorx2y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 1);
     140                        uint16 colorx3y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 2);
     141                        uint16 colorx4y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 3);
     142                       
     143                        uint16 colorx5y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 4);
     144                        uint16 colorx6y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 5);
     145                        uint16 colorx7y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 6);
     146                        uint16 colorx8y8 = *(((const uint16*)(src + srcPitch * 7)) + x + 7);
     147                               
     148                        uint16 rectx1y1 = Q_INTERPOLATE<bitFormat>(colorx1y1, colorx2y1, colorx1y2, colorx2y2);
     149                        uint16 rectx2y1 = Q_INTERPOLATE<bitFormat>(colorx3y1, colorx4y1, colorx3y2, colorx4y2);
     150                        uint16 rectx3y1 = Q_INTERPOLATE<bitFormat>(colorx5y1, colorx6y1, colorx5y2, colorx6y2);
     151                        uint16 rectx4y1 = Q_INTERPOLATE<bitFormat>(colorx7y1, colorx8y1, colorx7y2, colorx8y2);
     152                       
     153                        uint16 rectx1y2 = Q_INTERPOLATE<bitFormat>(colorx1y3, colorx2y3, colorx1y4, colorx2y4);
     154                        uint16 rectx2y2 = Q_INTERPOLATE<bitFormat>(colorx3y3, colorx4y3, colorx3y4, colorx4y4);
     155                        uint16 rectx3y2 = Q_INTERPOLATE<bitFormat>(colorx5y3, colorx6y3, colorx5y4, colorx6y4);
     156                        uint16 rectx4y2 = Q_INTERPOLATE<bitFormat>(colorx7y3, colorx8y3, colorx7y4, colorx8y4);
     157                       
     158                        uint16 rectx1y3 = Q_INTERPOLATE<bitFormat>(colorx1y5, colorx2y5, colorx1y6, colorx2y6);
     159                        uint16 rectx2y3 = Q_INTERPOLATE<bitFormat>(colorx3y5, colorx4y5, colorx3y6, colorx4y6);
     160                        uint16 rectx3y3 = Q_INTERPOLATE<bitFormat>(colorx5y5, colorx6y5, colorx5y6, colorx6y6);
     161                        uint16 rectx4y3 = Q_INTERPOLATE<bitFormat>(colorx7y5, colorx8y5, colorx7y6, colorx8y6);
     162                       
     163                        uint16 rectx1y4 = Q_INTERPOLATE<bitFormat>(colorx1y7, colorx2y7, colorx1y8, colorx2y8);
     164                        uint16 rectx2y4 = Q_INTERPOLATE<bitFormat>(colorx3y7, colorx4y7, colorx3y8, colorx4y8);
     165                        uint16 rectx3y4 = Q_INTERPOLATE<bitFormat>(colorx5y7, colorx6y7, colorx5y8, colorx6y8);
     166                        uint16 rectx4y4 = Q_INTERPOLATE<bitFormat>(colorx7y7, colorx8y7, colorx7y8, colorx8y8);                                 
     167                       
     168                        uint16 upleft = Q_INTERPOLATE<bitFormat>(rectx1y1, rectx2y1, rectx1y2, rectx2y2);
     169                        uint16 upright = Q_INTERPOLATE<bitFormat>(rectx3y1, rectx4y1, rectx3y2, rectx4y2);
     170                        uint16 downleft = Q_INTERPOLATE<bitFormat>(rectx1y3, rectx2y3, rectx1y4, rectx2y4);
     171                        uint16 downright = Q_INTERPOLATE<bitFormat>(rectx3y3, rectx4y3, rectx3y4, rectx4y4);
     172                               
     173                        *((uint16*)dstPtr) = Q_INTERPOLATE<bitFormat>(upleft, upright, downleft, downright);                   
     174                }
     175                dstPtr += (dstPitch - 160);
     176                src += 8 * srcPitch;
     177        }
     178}
     179
     180void createThumbnail(const uint8* src, uint32 srcPitch, uint8* dstPtr, uint32 dstPitch, int width, int height) {
     181        // only 1/4 and 1/8 downscale supported
     182        if(width != 320 && width != 640)
     183                return;
     184               
     185        const int downScaleMode = (width == 320) ? 4 : 8;
     186       
     187        if(downScaleMode == 4) {
     188                createThumbnail_4<565>(src, srcPitch, dstPtr, dstPitch, width, height);
     189        } else if(downScaleMode == 8) {
     190                createThumbnail_8<565>(src, srcPitch, dstPtr, dstPitch, width, height);
     191        }
     192}
  • common/scaler.h

    diff -d -u --rec -N --exclude=CVS scummvm.old/common/scaler.h scummvm/common/scaler.h
    old new  
    5959
    6060extern int stretch200To240(uint8 *buf, uint32 pitch, int width, int height, int srcX, int srcY, int origSrcY);
    6161
     62// creates a 80x50 thumbnail for 320x200 games
     63// and 80x60 thumbnail for 320x240 and 640x480 games
     64// only 565 mode
     65extern void createThumbnail(const uint8* src, uint32 srcPitch, uint8* dstPtr, uint32 dstPitch, int width, int height);
     66
    6267enum {
    6368        GFX_NORMAL = 0,
    6469        GFX_DOUBLESIZE = 1,
  • gui/ListWidget.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/ListWidget.cpp scummvm/gui/ListWidget.cpp
    old new  
    380380}
    381381
    382382void ListWidget::endEditMode() {
     383        if(!_editMode)
     384                return;
    383385        // send a message that editing finished with a return/enter key press
    384386        _editMode = false;
    385387        _list[_selectedItem] = _editString;
  • gui/ListWidget.h

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/ListWidget.h scummvm/gui/ListWidget.h
    old new  
    8686
    8787        // Made startEditMode for SCUMM's SaveLoadChooser
    8888        void startEditMode();
     89        void endEditMode();
    8990
    9091protected:
    9192        void drawWidget(bool hilite);
     
    9394        int findItem(int x, int y) const;
    9495        void scrollBarRecalc();
    9596
    96         void endEditMode();
    9797        void abortEditMode();
    9898       
    9999        Common::Rect getEditRect() const;
  • gui/newgui.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/newgui.cpp scummvm/gui/newgui.cpp
    old new  
    2121#include "stdafx.h"
    2222#include "common/system.h"
    2323#include "common/util.h"
     24#include "common/scaler.h"
    2425#include "gui/newgui.h"
    2526#include "gui/dialog.h"
    2627
     
    400401                        if (bitmap[y / _scaleFactor] & mask)
    401402                                        ptr[x] = color;
    402403                }
     404        }
     405}
     406
     407//
     408// Copies a Surface to the Overlay
     409//
     410void NewGui::drawSurface(const OverlayColor* data, int x, int y, int width, int height, int pitch) {
     411        if(_scaleFactor == 1) {
     412                uint8* dst = (uint8*)getBasePtr(x, y); 
     413                for (int y_ = 0; y_ < height; ++y_, dst += _screen.pitch) {
     414                        memcpy(dst, &data[y * pitch], pitch);
     415                }
     416        } else if(_scaleFactor == 2) {
     417                Normal2x((const uint8*)data, pitch, (uint8*)getBasePtr(x * 2, y * 2), _screen.pitch, width, height);
    403418        }
    404419}
    405420
  • gui/newgui.h

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/newgui.h scummvm/gui/newgui.h
    old new  
    146146        int getFontHeight() const;
    147147
    148148        void drawBitmap(uint32 *bitmap, int x, int y, OverlayColor color, int h = 8);
     149        void drawSurface(const OverlayColor* data, int x, int y, int width, int height, int pitch);
    149150
    150151        void addDirtyRect(int x, int y, int w, int h);
    151152};
  • gui/widget.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/widget.cpp scummvm/gui/widget.cpp
    old new  
    2424#include "gui/dialog.h"
    2525#include "gui/newgui.h"
    2626
    27 
    2827namespace GUI {
    2928
    3029Widget::Widget(GuiObject *boss, int x, int y, int w, int h)
     
    258257
    259258int SliderWidget::posToValue(int pos) {
    260259        return (pos) * (_valueMax - _valueMin) / (_w - _labelWidth - 4) + _valueMin;
     260}
     261
     262#pragma mark -
     263
     264GraphicsWidget::GraphicsWidget(GuiObject *boss, int x, int y, int w, int h)
     265        : Widget(boss, x, y, w, h), _gfx(0), _gfxWidth(0), _gfxHeight(0), _bpp(0) {
     266        _flags = WIDGET_ENABLED | WIDGET_CLEARBG;
     267        _type = kGraphicsWidget;
     268}
     269
     270GraphicsWidget::~GraphicsWidget() {
     271        delete [] _gfx;
     272}
     273
     274void GraphicsWidget::setGfx(int width, int height, int bpp, const uint8 *data) {
     275        delete [] _gfx;
     276        _gfx = 0;
     277       
     278        _gfx = new uint8[width * height * bpp];
     279        assert(_gfx);
     280       
     281        _gfxWidth = width;
     282        _gfxHeight = height;
     283        _bpp = bpp;
     284       
     285        memcpy(_gfx, data, width * height * bpp);
     286}
     287
     288void GraphicsWidget::drawWidget(bool hilite) {
     289        if(sizeof(OverlayColor) != _bpp || !_gfx) {
     290                g_gui.drawString("No preview", _x, _y + _h / 2 - g_gui.getFontHeight() / 2, _w, g_gui._textcolor, Graphics::kTextAlignCenter);
     291                return;
     292        }
     293       
     294        uint drawWidth = _gfxWidth, drawHeight = _gfxHeight;
     295       
     296        if(_w < _gfxWidth)
     297                drawWidth = _w;
     298        if(_h < _gfxHeight)
     299                drawHeight = _h;
     300       
     301        g_gui.drawSurface((OverlayColor*)_gfx, _x, _y, drawWidth, drawHeight, drawWidth * _bpp);
     302        g_gui.addDirtyRect(_x, _y, _w, _h);
    261303}
    262304
    263305} // End of namespace GUI
  • gui/widget.h

    diff -d -u --rec -N --exclude=CVS scummvm.old/gui/widget.h scummvm/gui/widget.h
    old new  
    5252        kListWidget                     = 'LIST',
    5353        kScrollBarWidget        = 'SCRB',
    5454        kPopUpWidget            = 'POPU',
    55         kTabWidget                      = 'TABW'
     55        kTabWidget                      = 'TABW',
     56        kGraphicsWidget         = 'GFXW'
    5657};
    5758
    5859enum {
     
    208209
    209210        int valueToPos(int value);
    210211        int posToValue(int pos);
     212};
     213
     214/* GraphicsWidget */
     215class GraphicsWidget : public Widget {
     216public:
     217        GraphicsWidget(GuiObject *boss, int x, int y, int w, int h);
     218        ~GraphicsWidget();
     219       
     220        // bpp = _byte_ per pixel
     221        void setGfx(int width, int height, int bpp, const uint8 *data);
     222protected:
     223        void drawWidget(bool hilite);
     224       
     225        uint8 *_gfx;
     226        int _gfxWidth, _gfxHeight, _bpp;
    211227};
    212228
    213229} // End of namespace GUI
  • scumm/dialogs.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/dialogs.cpp scummvm/scumm/dialogs.cpp
    old new  
    2323#include "common/config-manager.h"
    2424#include "common/system.h"
    2525
    26 #include "gui/chooser.h"
     26#include "gui/dialog.h"
     27#include "gui/widget.h"
    2728#include "gui/newgui.h"
    2829#include "gui/ListWidget.h"
    2930
     
    5455using GUI::WIDGET_ENABLED;
    5556
    5657typedef GUI::OptionsDialog GUI_OptionsDialog;
    57 typedef GUI::ChooserDialog GUI_ChooserDialog;
    5858
    5959namespace Scumm {
    6060
     
    198198        kQuitCmd = 'QUIT'
    199199};
    200200
    201 class SaveLoadChooser : public GUI::ChooserDialog {
     201enum {
     202        kChooseCmd = 'Chos'
     203};
     204
     205class SaveLoadChooser : public GUI::Dialog {
    202206        typedef Common::String String;
    203207        typedef Common::StringList StringList;
    204208protected:
    205209        bool _saveMode;
     210        GUI::ListWidget         *_list;
     211        GUI::ButtonWidget       *_chooseButton;
     212        GUI::GraphicsWidget     *_gfxWidget;
     213        ScummEngine                     *_scumm;
    206214
    207215public:
    208         SaveLoadChooser(const String &title, const String &buttonLabel, bool saveMode);
     216        SaveLoadChooser(const String &title, const String &buttonLabel, bool saveMode, ScummEngine *engine);
    209217       
    210218        virtual void handleCommand(CommandSender *sender, uint32 cmd, uint32 data);
    211         const String &getResultString() const;
     219        const String &getResultString() const; 
     220        void setList(const StringList& list);
    212221};
    213222
    214 SaveLoadChooser::SaveLoadChooser(const String &title, const String &buttonLabel, bool saveMode)
    215         : GUI::ChooserDialog(title, buttonLabel, 182), _saveMode(saveMode) {
    216 
     223SaveLoadChooser::SaveLoadChooser(const String &title, const String &buttonLabel, bool saveMode, ScummEngine *engine)
     224        : Dialog(8, (200 - 182) / 2, 320 - 2 * 8, 182), _saveMode(saveMode), _list(0), _chooseButton(0), _gfxWidget(0), _scumm(engine) {
     225       
     226        new StaticTextWidget(this, 10, 6, _w - 2 * 10, kLineHeight, title, kTextAlignCenter);
     227       
     228        // Add choice list
     229        _list = new GUI::ListWidget(this, 10, 18, _w - 2 * 10 - 100, _h - 14 - 24 - 10);
    217230        _list->setEditable(saveMode);
    218231        _list->setNumberingMode(saveMode ? GUI::kListNumberingOne : GUI::kListNumberingZero);
     232       
     233        // Add the thumbnail displayer
     234        _gfxWidget = new GUI::GraphicsWidget(this, _w - 102, _y + 6, 88, 68);
     235        _gfxWidget->setFlags(GUI::WIDGET_BORDER);
     236       
     237        // Buttons
     238        addButton(_w - 2 * (kButtonWidth + 10), _h - 24, "Cancel", kCloseCmd, 0);
     239        _chooseButton = addButton(_w-(kButtonWidth + 10), _h - 24, buttonLabel, kChooseCmd, 0);
     240        _chooseButton->setEnabled(false);
    219241}
    220242
    221243const Common::String &SaveLoadChooser::getResultString() const {
    222244        return _list->getSelectedString();
    223245}
    224246
     247void SaveLoadChooser::setList(const StringList& list) {
     248        _list->setList(list);
     249}
     250
    225251void SaveLoadChooser::handleCommand(CommandSender *sender, uint32 cmd, uint32 data) {
    226252        int selItem = _list->getSelected();
    227253        switch (cmd) {
     
    229255        case GUI::kListItemDoubleClickedCmd:
    230256                if (selItem >= 0) {
    231257                        if (_saveMode || !getResultString().isEmpty()) {
     258                                _list->endEditMode();
    232259                                setResult(selItem);
    233260                                close();
    234261                        }
    235262                }
    236263                break;
     264        case kChooseCmd:
     265                _list->endEditMode();
     266                setResult(selItem);
     267                close();
     268                break;
    237269        case GUI::kListSelectionChangedCmd:
     270                _scumm->loadThumbnailFromSlot(_saveMode ? selItem + 1 : selItem);
     271                _gfxWidget->setGfx(80, 60, 2, (const uint8*)_scumm->getThumbnail());
     272                _gfxWidget->draw();
    238273                if (_saveMode) {
    239274                        _list->startEditMode();
    240275                }
     
    244279                _chooseButton->setEnabled(selItem >= 0 && (_saveMode || !getResultString().isEmpty()));
    245280                _chooseButton->draw();
    246281                break;
     282        case kCloseCmd:
     283                setResult(-1);
    247284        default:
    248                 GUI_ChooserDialog::handleCommand(sender, cmd, data);
     285                GUI::Dialog::handleCommand(sender, cmd, data);
    249286        }
    250287}
    251288
     289#pragma mark -
     290
    252291Common::StringList generateSavegameList(ScummEngine *scumm, bool saveMode) {
    253292        // Get savegame names
    254293        Common::StringList l;
     
    307346#ifndef DISABLE_HELP
    308347        _helpDialog = new HelpDialog(scumm);
    309348#endif
    310         _saveDialog = new SaveLoadChooser("Save game:", "Save", true);
    311         _loadDialog = new SaveLoadChooser("Load game:", "Load", false);
     349        _saveDialog = new SaveLoadChooser("Save game:", "Save", true, _vm);
     350        _loadDialog = new SaveLoadChooser("Load game:", "Load", false, _vm);
    312351}
    313352
    314353MainMenuDialog::~MainMenuDialog() {
  • scumm/gfx.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/gfx.cpp scummvm/scumm/gfx.cpp
    old new  
    530530                _vm->_system->copyRectToScreen(_herculesBuf + x + y * Common::kHercW,
    531531                        Common::kHercW, x + (Common::kHercW - _vm->_screenWidth * 2) / 2, y, width, height);
    532532        } else {
    533                 // Finally blit the whole thing to the screen
    534                 _vm->_system->copyRectToScreen(_compositeBuf + x + y * _vm->_screenWidth, _vm->_screenWidth, x, y, width, height);
     533                if(_vm->creatingThumbnail()) {
     534                        _vm->copyToThumbnailScreen(_compositeBuf + x + y * _vm->_screenWidth, _vm->_screenWidth, x, y, width, height);
     535                } else {
     536                        // Finally blit the whole thing to the screen
     537                        _vm->_system->copyRectToScreen(_compositeBuf + x + y * _vm->_screenWidth, _vm->_screenWidth, x, y, width, height);
     538                }
    535539        }
    536540}
    537541
  • scumm/module.mk

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/module.mk scummvm/scumm/module.mk
    old new  
    7575        scumm/smush/smush_player.o \
    7676        scumm/smush/saud_channel.o \
    7777        scumm/smush/smush_mixer.o \
    78         scumm/smush/smush_font.o
     78        scumm/smush/smush_font.o \
     79        scumm/thumbnail.o
    7980
    8081MODULE_DIRS += \
    8182        scumm \
  • scumm/saveload.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/saveload.cpp scummvm/scumm/saveload.cpp
    old new  
    8787        Serializer ser(out, true, CURRENT_VER);
    8888        saveOrLoad(&ser, CURRENT_VER);
    8989        delete out;
     90       
     91        // create thumbnail file
     92        makeSavegameName(filename, slot, false);
     93        strcat(filename, ".tmb");       
     94        if (!(out = _saveFileMan->openSavefile(filename, true)))
     95                return false;           
     96        createThumbnail();     
     97        out->write(_thumbnail, sizeof(uint16) * 80*60);
     98        delete out;
     99        // --------------------
     100       
    90101        debug(1, "State saved as '%s'", filename);
    91102        return true;
    92103}
  • scumm/scumm.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/scumm.cpp scummvm/scumm/scumm.cpp
    old new  
    568568          _heversion(gs.heversion),
    569569          _numActors(gs.numActors),
    570570          _features(gs.features),
    571           gdi(this), _pauseDialog(0), _mainMenuDialog(0), _versionDialog(0),
     571          gdi(this), _pauseDialog(0), _mainMenuDialog(0), _versionDialog(0), _createThumbnail(false), _temporaryScreen(0),
    572572          _targetName(detector->_targetName) {
     573         
     574        // fill thumbnail with 0
     575        memset(_thumbnail, 0, 80*60*2);
    573576
    574577        // Copy MD5 checksum
    575578        memcpy(_gameMD5, md5sum, 16);
  • scumm/scumm.h

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/scumm.h scummvm/scumm/scumm.h
    old new  
    536536
    537537        void lock(int type, int i);
    538538        void unlock(int type, int i);
     539       
     540// thumbnail stuff
     541public:
     542        void createThumbnail();
     543        void loadThumbnailFromData(const uint16* data);
     544        void loadThumbnailFromSlot(int slot);
     545        const uint16* getThumbnail() { return _thumbnail; }
     546       
     547        bool creatingThumbnail() { return _createThumbnail; }
     548        void copyToThumbnailScreen(const byte *buf, int pitch, int x, int y, int w, int h);
     549protected:
     550        uint16 _thumbnail[80*60];
     551        byte *_temporaryScreen;
     552        bool _createThumbnail;
     553// ends here
    539554
    540555protected:
    541556        /* Heap and memory management */
  • scumm/thumbnail.cpp

    diff -d -u --rec -N --exclude=CVS scummvm.old/scumm/thumbnail.cpp scummvm/scumm/thumbnail.cpp
    old new  
     1/* ScummVM - Scumm Interpreter
     2 * Copyright (C) 2001  Ludvig Strigeus
     3 * Copyright (C) 2001-2005 The ScummVM project
     4 *
     5 * This program is free software; you can redistribute it and/or
     6 * modify it under the terms of the GNU General Public License
     7 * as published by the Free Software Foundation; either version 2
     8 * of the License, or (at your option) any later version.
     9
     10 * This program is distributed in the hope that it will be useful,
     11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
     12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     13 * GNU General Public License for more details.
     14
     15 * You should have received a copy of the GNU General Public License
     16 * along with this program; if not, write to the Free Software
     17 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
     18 *
     19 * $Header: $
     20 *
     21 */
     22 
     23#include "common/stdafx.h"
     24#include "common/scummsys.h"
     25#include "common/system.h"
     26#include "common/savefile.h"
     27#include "common/scaler.h"
     28#include "scumm.h"
     29
     30namespace Scumm {
     31
     32inline uint16 RGBToColor(const uint8 r, const uint8 g, const uint8 b) {
     33        return ((((r >> 3) & 0x1F) << 11) | (((g >> 2) & 0x3F) << 5) | ((b >> 3) & 0x1F));
     34}
     35
     36inline void colorToRGB(uint16 color, uint8 &r, uint8 &g, uint8 &b) {
     37        r = (((color >> 11) & 0x1F) << 3);
     38        g = (((color >> 5) & 0x3F) << 2);
     39        b = ((color&0x1F) << 3);
     40}
     41
     42void ScummEngine::createThumbnail() {
     43        if(sizeof(OverlayColor) != sizeof(uint16))
     44                return;
     45       
     46        _temporaryScreen = new byte[_system->getWidth() * _system->getHeight()];
     47        assert(_temporaryScreen);
     48       
     49        _createThumbnail = true;       
     50        int pos = 0;
     51        for (VirtScreen *vs = &virtscr[0]; pos < ARRAYSIZE(virtscr); ++pos, vs = &virtscr[pos]) {
     52                markRectAsDirty((VirtScreenNumber)pos, 0, vs->w, 0, vs->h);
     53        }
     54       
     55        drawDirtyScreenParts();
     56       
     57        uint16 *screen = new uint16[_system->getWidth() * _system->getHeight()];
     58        assert(screen);
     59       
     60        const uint8 *palette = _currentPalette;
     61       
     62        for(int y = 0; y < _system->getHeight(); ++y) {
     63                for(int x = 0; x < _system->getWidth(); ++x) {
     64                        uint8 index = _temporaryScreen[y * _system->getWidth() + x];                   
     65                        screen[y * _system->getWidth() + x] = RGBToColor(palette[index * 3], palette[index * 3 + 1], palette[index * 3 + 2]);
     66                }
     67        }
     68       
     69        _createThumbnail = false;
     70        delete [] _temporaryScreen;
     71        _temporaryScreen = 0;
     72       
     73        memset(_thumbnail, 0, 80*60*2);
     74        ::createThumbnail((const uint8*)screen, _system->getWidth() * 2, (uint8*)_thumbnail, 160, _system->getWidth(), _system->getHeight());
     75       
     76        delete [] screen;
     77}
     78
     79void ScummEngine::loadThumbnailFromData(const uint16* data) {
     80        if(sizeof(OverlayColor) != sizeof(uint16))
     81                return;
     82
     83        for (int y = 0; y < 60; ++y) {
     84                for (int x = 0; x < 80; ++x) {
     85                        uint8 r, g, b;
     86                        colorToRGB(data[y * 80 + x], r, g, b);
     87                       
     88                        // converting to current OSystem Color
     89                        _thumbnail[y * 80 + x] = _system->RGBToColor(r, g, b);
     90                }
     91        }
     92}
     93
     94void ScummEngine::copyToThumbnailScreen(const byte *buf, int pitch, int x, int y, int w, int h) {
     95        assert(_temporaryScreen);
     96        uint8* dst = _temporaryScreen + y * _system->getWidth() + x;
     97        while (h--) {
     98                memcpy(dst, buf, w);
     99                buf += pitch;
     100                dst += _system->getWidth();
     101        }
     102}
     103
     104void ScummEngine::loadThumbnailFromSlot(int slot) {
     105        char filename[256];
     106        makeSavegameName(filename, slot, false);
     107        strcat(filename, ".tmb");
     108       
     109        SaveFile *out;
     110        if (!(out = _saveFileMan->openSavefile(filename, false))) {
     111                delete out;
     112                memset(_thumbnail, 0, sizeof(uint16) * 80*60);
     113                return;
     114        }
     115               
     116        out->read(_thumbnail, sizeof(uint16) * 80*60);
     117        loadThumbnailFromData(_thumbnail);
     118        delete out;
     119}
     120
     121} // end of namespace Scumm