SHERLOCK: 3DO intro: implement fade from white

This commit is contained in:
Martin Kiewitz 2015-06-09 23:22:52 +02:00 committed by Willem Jan Palenstijn
parent 866d7a27d8
commit 6aaee559dc
7 changed files with 109 additions and 32 deletions

View File

@ -140,17 +140,23 @@ bool Animation::play(const Common::String &filename, bool intro, int minDelay, i
return !skipped && !_vm->shouldQuit();
}
bool Animation::play3DO(const Common::String &filename, bool intro, int minDelay, int fade,
bool Animation::play3DO(const Common::String &filename, bool intro, int minDelay, bool fadeFromGrey,
int speed) {
Events &events = *_vm->_events;
Screen &screen = *_vm->_screen;
Sound &sound = *_vm->_sound;
Sound &sound = *_vm->_sound;
int soundNumber = 0;
bool fadeActive = false;
uint16 fadeLimitColor = 0;
uint16 fadeLimitColorRed = 0;
uint16 fadeLimitColorGreen = 0;
uint16 fadeLimitColorBlue = 0;
// Check for any any sound frames for the given animation
const int *soundFrames = checkForSoundFrames(filename, intro);
// Add on the VDX extension
// Add the VDX extension
Common::String indexName = "prologue/" + filename + ".3dx";
// Load the animation
@ -166,13 +172,11 @@ bool Animation::play3DO(const Common::String &filename, bool intro, int minDelay
ImageFile3DO images(graphicsName, true);
events.wait(minDelay);
// if (fade != 0 && fade != 255)
// screen.fadeToBlack();
// if (setPalette) {
// if (fade != 255)
// screen.setPalette(images._palette);
// }
if (fadeFromGrey) {
fadeActive = true;
fadeLimitColor = 0xCE59; // RGB565: 25, 50, 25 -> "grey"
}
int frameNumber = 0;
Common::Point pt;
@ -196,18 +200,36 @@ bool Animation::play3DO(const Common::String &filename, bool intro, int minDelay
// Draw the sprite. Note that we explicitly use the raw frame below, rather than the ImageFrame,
// since we don't want the offsets in the image file to be used, just the explicit position we specify
screen.transBlitFromUnscaled3DO(images[imageFrame]._frame, pt);
//events.wait(1000);
if (!fadeActive) {
screen.transBlitFromUnscaled3DO(images[imageFrame]._frame, pt);
} else {
// Fade active, blit to backbuffer1
screen._backBuffer1.transBlitFromUnscaled3DO(images[imageFrame]._frame, pt);
}
} else {
#if 0
// At this point, either the sprites for the frame has been complete, or there weren't any sprites
// at all to draw for the frame
//if (fade == 255) {
// // Gradual fade in
// if (screen.equalizePalette(images._palette) == 0)
// fade = 0;
//}
#endif
if (fadeActive) {
// process fading
screen.blitFrom3DOcolorLimit(fadeLimitColor);
if (!fadeLimitColor) {
// we are at the end, so stop
fadeActive = false;
} else {
// decrease limit color
fadeLimitColorRed = fadeLimitColor & 0xF800;
fadeLimitColorGreen = fadeLimitColor & 0x07E0;
fadeLimitColorBlue = fadeLimitColor & 0x001F;
if (fadeLimitColorRed)
fadeLimitColor -= 0x0800;
if (fadeLimitColorGreen)
fadeLimitColor -= 0x0040; // -2 because we are using RGB565, sherlock uses RGB555
if (fadeLimitColorBlue)
fadeLimitColor -= 0x0001;
}
}
// Check if we've reached a frame with sound
if (frameNumber++ == *soundFrames) {

View File

@ -78,7 +78,7 @@ public:
*/
bool play(const Common::String &filename, bool intro, int minDelay, int fade, bool setPalette, int speed);
bool play3DO(const Common::String &filename, bool intro, int minDelay, int fade, int speed);
bool play3DO(const Common::String &filename, bool intro, int minDelay, bool fadeFromGrey, int speed);
};
} // End of namespace Sherlock

View File

@ -540,9 +540,10 @@ bool ScalpelEngine::show3DOSplash() {
if (finished) {
// EA logo movie
Scalpel3DOMoviePlay("EAlogo.stream", Common::Point(20, 0));
_screen->clear();
}
// Always clear screen
_screen->clear();
return finished;
}
@ -552,13 +553,17 @@ bool ScalpelEngine::showCityCutscene3DO() {
// Play intro music
_music->playMusic("prolog");
// Fade screen to grey
_screen->_backBuffer1.fill(0xCE59); // RGB565: 25, 50, 25 (grey)
_screen->fadeIntoScreen3DO(2);
// rain.aiff seems to be playing in an endless loop until
// sherlock logo fades away TODO
bool finished = _music->waitUntilMSec(3400, 0, 0, 3400);
if (finished)
finished = _animation->play3DO("26open1", true, 1, 255, 2);
finished = _animation->play3DO("26open1", true, 1, true, 2);
if (finished) {
_screen->_backBuffer1.blitFrom(*_screen); // save into backbuffer 1, used for fade
@ -587,7 +592,7 @@ bool ScalpelEngine::showCityCutscene3DO() {
}
if (finished)
finished = _animation->play3DO("26open2", true, 1, 0, 2);
finished = _animation->play3DO("26open2", true, 1, false, 2);
if (finished) {
_screen->_backBuffer1.blitFrom(*_screen); // save into backbuffer 1, used for fade
@ -638,7 +643,7 @@ bool ScalpelEngine::showAlleyCutscene3DO() {
bool finished = _music->waitUntilMSec(43500, 0, 0, 1000);
if (finished)
finished = _animation->play3DO("27PRO1", true, 1, 3, 2);
finished = _animation->play3DO("27PRO1", true, 1, false, 2);
if (finished) {
// Fade out...
@ -649,7 +654,7 @@ bool ScalpelEngine::showAlleyCutscene3DO() {
}
if (finished)
finished = _animation->play3DO("27PRO2", true, 1, 0, 2);
finished = _animation->play3DO("27PRO2", true, 1, false, 2);
if (finished)
finished = _music->waitUntilMSec(76000, 0, 0, 1000);
@ -677,7 +682,7 @@ bool ScalpelEngine::showAlleyCutscene3DO() {
}
if (finished)
finished = _animation->play3DO("27PRO3", true, 1, 0, 2);
finished = _animation->play3DO("27PRO3", true, 1, false, 2);
if (finished) {
// Fade out
@ -710,10 +715,10 @@ bool ScalpelEngine::showStreetCutscene3DO() {
finished = _music->waitUntilMSec(100300, 0, 0, 1000);
}
finished = _animation->play3DO("14KICK", true, 1, 3, 2);
finished = _animation->play3DO("14KICK", true, 1, false, 2);
if (finished)
finished = _animation->play3DO("14NOTE", true, 1, 0, 3);
finished = _animation->play3DO("14NOTE", true, 1, false, 3);
if (finished) {
// Fade out
@ -730,10 +735,10 @@ bool ScalpelEngine::showOfficeCutscene3DO() {
finished = _music->waitUntilMSec(151000, 0, 0, 1000);
if (finished)
_animation->play3DO("COFF1", true, 1, 3, 3);
_animation->play3DO("COFF1", true, 1, false, 3);
if (finished)
finished = _animation->play3DO("COFF2", true, 1, 0, 3);
finished = _animation->play3DO("COFF2", true, 1, false, 3);
if (finished)
finished = _music->waitUntilMSec(182400, 0, 0, 1000);
@ -761,10 +766,10 @@ bool ScalpelEngine::showOfficeCutscene3DO() {
finished = _music->waitUntilMSec(222200, 0, 0, 1000);
if (finished)
finished = _animation->play3DO("COFF3", true, 1, 0, 3);
finished = _animation->play3DO("COFF3", true, 1, false, 3);
if (finished)
finished = _animation->play3DO("COFF4", true, 1, 0, 3);
finished = _animation->play3DO("COFF4", true, 1, false, 3);
return finished;
}

View File

@ -233,7 +233,6 @@ void Screen::verticalTransition() {
void Screen::fadeIntoScreen3DO(int speed) {
Events &events = *_vm->_events;
Common::Rect changedRect;
uint16 *currentScreenBasePtr = (uint16 *)getPixels();
uint16 *targetScreenBasePtr = (uint16 *)_backBuffer->getPixels();
uint16 *currentScreenPtr = NULL;
@ -315,6 +314,49 @@ void Screen::fadeIntoScreen3DO(int speed) {
} while ((pixelsChanged) && (!_vm->shouldQuit()));
}
void Screen::blitFrom3DOcolorLimit(uint16 limitColor) {
uint16 *currentScreenPtr = (uint16 *)getPixels();
uint16 *targetScreenPtr = (uint16 *)_backBuffer->getPixels();
uint16 currentScreenPixel = 0;
uint16 screenWidth = this->w();
uint16 screenHeight = this->h();
uint16 screenX = 0;
uint16 screenY = 0;
uint16 currentScreenPixelRed = 0;
uint16 currentScreenPixelGreen = 0;
uint16 currentScreenPixelBlue = 0;
uint16 limitPixelRed = limitColor & 0xF800;
uint16 limitPixelGreen = limitColor & 0x07E0;
uint16 limitPixelBlue = limitColor & 0x001F;
for (screenY = 0; screenY < screenHeight; screenY++) {
for (screenX = 0; screenX < screenWidth; screenX++) {
currentScreenPixel = *targetScreenPtr;
currentScreenPixelRed = currentScreenPixel & 0xF800;
currentScreenPixelGreen = currentScreenPixel & 0x07E0;
currentScreenPixelBlue = currentScreenPixel & 0x001F;
if (currentScreenPixelRed < limitPixelRed)
currentScreenPixelRed = limitPixelRed;
if (currentScreenPixelGreen < limitPixelGreen)
currentScreenPixelGreen = limitPixelGreen;
if (currentScreenPixelBlue < limitPixelBlue)
currentScreenPixelBlue = limitPixelBlue;
*currentScreenPtr = currentScreenPixelRed | currentScreenPixelGreen | currentScreenPixelBlue;
currentScreenPtr++;
targetScreenPtr++;
}
}
// Too much considered dirty at the moment
addDirtyRect(Common::Rect(0, 0, screenWidth, screenHeight));
}
void Screen::restoreBackground(const Common::Rect &r) {
if (r.width() > 0 && r.height() > 0) {
Common::Rect tempRect = r;

View File

@ -153,6 +153,8 @@ public:
*/
void fadeIntoScreen3DO(int speed);
void blitFrom3DOcolorLimit(uint16 color);
/**
* Prints the text passed onto the back buffer at the given position and color.
* The string is then blitted to the screen

View File

@ -226,6 +226,10 @@ void Surface::fillRect(const Common::Rect &r, byte color) {
addDirtyRect(r);
}
void Surface::fill(uint16 color) {
_surface.fillRect(Common::Rect(_surface.w, _surface.h), color);
}
bool Surface::clip(Common::Rect &srcBounds, Common::Rect &destBounds) {
if (destBounds.left >= _surface.w || destBounds.top >= _surface.h ||
destBounds.right <= 0 || destBounds.bottom <= 0)

View File

@ -139,6 +139,8 @@ public:
*/
void fillRect(const Common::Rect &r, byte color);
void fill(uint16 color);
void maskArea(const ImageFrame &src, const Common::Point &pt, int scrollX);
/**