Graphics::Surface BladeRunnerEngine::generateThumbnail() const { Graphics::Surface thumbnail; thumbnail.create(640 / 8, 480 / 8, createRGB555()); for (int y = 0; y < thumbnail.h; ++y) { for (int x = 0; x < thumbnail.w; ++x) { uint16 *dstPixel = (uint16 *)thumbnail.getBasePtr(x, y); const uint16 *srcPixel = (const uint16 *)_surfaceFront.getBasePtr(x * 8, y * 8); *dstPixel = *srcPixel; } } return thumbnail; }
SliceRenderer::SliceRenderer(BladeRunnerEngine *vm) { _vm = vm; _pixelFormat = createRGB555(); for (int i = 0; i < 942; i++) { // yes, its going just to 942 and not 997 _animationsShadowEnabled[i] = true; } _animation = -1; _frame = -1; _facing = 0.0f; _scale = 0.0f; _screenEffects = nullptr; _view = nullptr; _lights = nullptr; _setEffects = nullptr; _sliceFramePtr = nullptr; _frameBottomZ = 0.0f; _frameSliceHeight = 0.0f; _framePaletteIndex = 0; _frameSliceCount = 0; _startSlice = 0.0f; _endSlice = 0.0f; _m13 = 0; _m23 = 0; _shadowPolygonDefault[ 0] = Vector3( 16.0f, 96.0f, 0.0f); _shadowPolygonDefault[ 1] = Vector3( 16.0f, 160.0f, 0.0f); _shadowPolygonDefault[ 2] = Vector3( 64.0f, 192.0f, 0.0f); _shadowPolygonDefault[ 3] = Vector3( 80.0f, 240.0f, 0.0f); _shadowPolygonDefault[ 4] = Vector3(160.0f, 240.0f, 0.0f); _shadowPolygonDefault[ 5] = Vector3(192.0f, 192.0f, 0.0f); _shadowPolygonDefault[ 6] = Vector3(240.0f, 160.0f, 0.0f); _shadowPolygonDefault[ 7] = Vector3(240.0f, 96.0f, 0.0f); _shadowPolygonDefault[ 8] = Vector3(192.0f, 64.0f, 0.0f); _shadowPolygonDefault[ 9] = Vector3(160.0f, 16.0f, 0.0f); _shadowPolygonDefault[10] = Vector3( 96.0f, 16.0f, 0.0f); _shadowPolygonDefault[11] = Vector3( 64.0f, 64.0f, 0.0f); for (int i = 0; i < 12; ++i) { _shadowPolygonCurrent[i] = Vector3(0.0f, 0.0f, 0.0f); } }
Common::Error BladeRunnerEngine::run() { Graphics::PixelFormat format = createRGB555(); initGraphics(640, 480, &format); _system->showMouse(true); bool hasSavegames = !SaveFileManager::list(_targetName).empty(); if (!startup(hasSavegames)) { shutdown(); return Common::Error(Common::kUnknownError, "Failed to initialize resources"); } #if BLADERUNNER_DEBUG_GAME { #else if (warnUserAboutUnsupportedGame()) { #endif if (hasSavegames) { _kia->_forceOpen = true; _kia->open(kKIASectionLoad); } // TODO: why is game starting new game here when everything is done in startup? // else { // newGame(1); // } gameLoop(); _mouse->disable(); if (_gameOver) { // autoSaveGame(4, 1); // TODO _endCredits->show(); } } shutdown(); return Common::kNoError; } bool BladeRunnerEngine::startup(bool hasSavegames) { // These are static objects in original game _screenEffects = new ScreenEffects(this, 0x8000); _endCredits = new EndCredits(this); _actorDialogueQueue = new ActorDialogueQueue(this); _settings = new Settings(this); _itemPickup = new ItemPickup(this); _lights = new Lights(this); // TODO: outtake player - but this is done bit differently _policeMaze = new PoliceMaze(this); _obstacles = new Obstacles(this); _sceneScript = new SceneScript(this); _debugger = new Debugger(this); // This is the original startup in the game bool r; _surfaceFront.create(640, 480, createRGB555()); _surfaceBack.create(640, 480, createRGB555()); _surface4.create(640, 480, createRGB555()); _gameTime = new Time(this); r = openArchive("STARTUP.MIX"); if (!r) return false; _gameInfo = new GameInfo(this); if (!_gameInfo) return false; r = _gameInfo->open("GAMEINFO.DAT"); if (!r) { return false; } // TODO: Create datetime - not used // TODO: Create graphics surfaces 1-4 // TODO: Allocate audio cache if (hasSavegames) { if (!loadSplash()) { return false; } } _waypoints = new Waypoints(this, _gameInfo->getWaypointCount()); _combat = new Combat(this); _gameVars = new int[_gameInfo->getGlobalVarCount()](); // TODO: Init Actor AI Update counter // Seed rand // TODO: Sine and cosine lookup tables for intervals of 1.0, 4.0, and 12.0 _cosTable1024 = new Common::CosineTable(1024); // 10-bits = 1024 points for 2*PI; _sinTable1024 = new Common::SineTable(1024); _view = new View(); _sceneObjects = new SceneObjects(this, _view); _gameFlags = new GameFlags(); _gameFlags->setFlagCount(_gameInfo->getFlagCount()); _items = new Items(this); _audioMixer = new AudioMixer(this); _audioPlayer = new AudioPlayer(this); _music = new Music(this); _audioSpeech = new AudioSpeech(this); _ambientSounds = new AmbientSounds(this); // TODO: Read BLADE.INI _chapters = new Chapters(this); if (!_chapters) return false; if (!openArchive("MUSIC.MIX")) return false; if (!openArchive("SFX.MIX")) return false; if (!openArchive("SPCHSFX.TLK")) return false; _overlays = new Overlays(this); _overlays->init(); _zbuffer = new ZBuffer(); _zbuffer->init(640, 480); int actorCount = (int)_gameInfo->getActorCount(); assert(actorCount < kActorCount); for (int i = 0; i != actorCount; ++i) { _actors[i] = new Actor(this, i); _actors[i]->setup(i); } _actors[kActorVoiceOver] = new Actor(this, kActorVoiceOver); _playerActor = _actors[_gameInfo->getPlayerId()]; _playerActor->setFPS(15); _playerActor->timerStart(6, 200); // TODO: Set actor ids (redundant?) _policeMaze = new PoliceMaze(this); _textActorNames = new TextResource(this); if (!_textActorNames->open("ACTORS")) return false; _textCrimes = new TextResource(this); if (!_textCrimes->open("CRIMES")) return false; _textClueTypes = new TextResource(this); if (!_textClueTypes->open("CLUETYPE")) return false; _textKIA = new TextResource(this); if (!_textKIA->open("KIA")) return false; _textSpinnerDestinations = new TextResource(this); if (!_textSpinnerDestinations->open("SPINDEST")) return false; _textVK = new TextResource(this); if (!_textVK->open("VK")) return false; _textOptions = new TextResource(this); if (!_textOptions->open("OPTIONS")) return false; _dialogueMenu = new DialogueMenu(this); if (!_dialogueMenu->loadText("DLGMENU")) return false; _suspectsDatabase = new SuspectsDatabase(this, _gameInfo->getSuspectCount()); _kia = new KIA(this); _spinner = new Spinner(this); _elevator = new Elevator(this); _scores = new Scores(this); _mainFont = new Font(this); _mainFont->open("KIA6PT.FON", 640, 480, -1, 0, 0x252D); _mainFont->setSpacing(1, 0); for (int i = 0; i != 43; ++i) { Shape *shape = new Shape(this); shape->open("SHAPES.SHP", i); _shapes.push_back(shape); } _esper = new ESPER(this); _vk = new VK(this); _mouse = new Mouse(this); // _mouse->setCursorPosition(320, 240); _mouse->setCursor(0); _sliceAnimations = new SliceAnimations(this); r = _sliceAnimations->open("INDEX.DAT"); if (!r) return false; r = _sliceAnimations->openCoreAnim(); if (!r) { return false; } _sliceRenderer = new SliceRenderer(this); _sliceRenderer->setScreenEffects(_screenEffects); _crimesDatabase = new CrimesDatabase(this, "CLUES", _gameInfo->getClueCount()); // TODO: Scene _scene = new Scene(this); // Load INIT.DLL InitScript initScript(this); initScript.SCRIPT_Initialize_Game(); // TODO: Load AI-ACT1.DLL _aiScripts = new AIScripts(this, actorCount); initChapterAndScene(); return true; }