[Scummvm-cvs-logs] SF.net SVN: scummvm: [22588] scummvm/trunk
aquadran at users.sourceforge.net
aquadran at users.sourceforge.net
Tue May 23 16:46:13 CEST 2006
Revision: 22588
Author: aquadran
Date: 2006-05-23 16:43:52 -0700 (Tue, 23 May 2006)
ViewCVS: http://svn.sourceforge.net/scummvm/?rev=22588&view=rev
Log Message:
-----------
imported AGI engine
Modified Paths:
--------------
scummvm/trunk/AUTHORS
scummvm/trunk/base/plugins.cpp
scummvm/trunk/dists/msvc8/gob.vcproj
scummvm/trunk/dists/msvc8/kyra.vcproj
scummvm/trunk/dists/msvc8/scummvm.sln
scummvm/trunk/dists/msvc8/scummvm.vcproj
scummvm/trunk/doc/credits.tex
scummvm/trunk/gui/credits.h
scummvm/trunk/tools/credits.pl
Added Paths:
-----------
scummvm/trunk/dists/msvc8/agi.vcproj
scummvm/trunk/engines/agi/
scummvm/trunk/engines/agi/agi.cpp
scummvm/trunk/engines/agi/agi.h
scummvm/trunk/engines/agi/agi_v2.cpp
scummvm/trunk/engines/agi/agi_v3.cpp
scummvm/trunk/engines/agi/checks.cpp
scummvm/trunk/engines/agi/console.cpp
scummvm/trunk/engines/agi/console.h
scummvm/trunk/engines/agi/cycle.cpp
scummvm/trunk/engines/agi/font.cpp
scummvm/trunk/engines/agi/global.cpp
scummvm/trunk/engines/agi/graphics.cpp
scummvm/trunk/engines/agi/graphics.h
scummvm/trunk/engines/agi/id.cpp
scummvm/trunk/engines/agi/inv.cpp
scummvm/trunk/engines/agi/keyboard.cpp
scummvm/trunk/engines/agi/keyboard.h
scummvm/trunk/engines/agi/list.h
scummvm/trunk/engines/agi/logic.cpp
scummvm/trunk/engines/agi/logic.h
scummvm/trunk/engines/agi/lzw.cpp
scummvm/trunk/engines/agi/lzw.h
scummvm/trunk/engines/agi/menu.cpp
scummvm/trunk/engines/agi/menu.h
scummvm/trunk/engines/agi/module.mk
scummvm/trunk/engines/agi/motion.cpp
scummvm/trunk/engines/agi/objects.cpp
scummvm/trunk/engines/agi/op_cmd.cpp
scummvm/trunk/engines/agi/op_dbg.cpp
scummvm/trunk/engines/agi/op_test.cpp
scummvm/trunk/engines/agi/opcodes.h
scummvm/trunk/engines/agi/patches.cpp
scummvm/trunk/engines/agi/picture.cpp
scummvm/trunk/engines/agi/picture.h
scummvm/trunk/engines/agi/savegame.cpp
scummvm/trunk/engines/agi/savegame.h
scummvm/trunk/engines/agi/sound.cpp
scummvm/trunk/engines/agi/sound.h
scummvm/trunk/engines/agi/sprite.cpp
scummvm/trunk/engines/agi/sprite.h
scummvm/trunk/engines/agi/text.cpp
scummvm/trunk/engines/agi/text.h
scummvm/trunk/engines/agi/view.cpp
scummvm/trunk/engines/agi/view.h
scummvm/trunk/engines/agi/words.cpp
Modified: scummvm/trunk/AUTHORS
===================================================================
--- scummvm/trunk/AUTHORS 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/AUTHORS 2006-05-23 23:43:52 UTC (rev 22588)
@@ -24,6 +24,10 @@
Gregory Montoir
Eugene Sandulenko
+ AGI:
+ Pawel Kolodziejski
+ Eugene Sandulenko
+
BASS:
Robert Goeffringmann
Oliver Kiehl
@@ -193,6 +197,7 @@
Jezar - For his freeverb filter implementation
Jim Leiterman - Various info on his FM-TOWNS/Marty SCUMM ports
lloyd - For deep tech details about C64 Zak & MM
+ Sarien Team - Original AGI engine code
Jimmi Thogersen - For ScummRev, and much obscure code/documentation
Tristan - For additional work on the original MT-32 emulator
Modified: scummvm/trunk/base/plugins.cpp
===================================================================
--- scummvm/trunk/base/plugins.cpp 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/base/plugins.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -368,6 +368,9 @@
#ifndef DISABLE_CINE
LINK_PLUGIN(CINE)
#endif
+ #ifndef DISABLE_CINE
+ LINK_PLUGIN(AGI)
+ #endif
#endif
}
Added: scummvm/trunk/dists/msvc8/agi.vcproj
===================================================================
--- scummvm/trunk/dists/msvc8/agi.vcproj (rev 0)
+++ scummvm/trunk/dists/msvc8/agi.vcproj 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,338 @@
+<?xml version="1.0" encoding="windows-1250"?>
+<VisualStudioProject
+ ProjectType="Visual C++"
+ Version="8,00"
+ Name="agi"
+ ProjectGUID="{F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}"
+ RootNamespace="agi"
+ Keyword="Win32Proj"
+ >
+ <Platforms>
+ <Platform
+ Name="Win32"
+ />
+ </Platforms>
+ <ToolFiles>
+ </ToolFiles>
+ <Configurations>
+ <Configuration
+ Name="Debug|Win32"
+ OutputDirectory="agi_Debug"
+ IntermediateDirectory="agi_Debug"
+ ConfigurationType="4"
+ CharacterSet="2"
+ >
+ <Tool
+ Name="VCPreBuildEventTool"
+ />
+ <Tool
+ Name="VCCustomBuildTool"
+ />
+ <Tool
+ Name="VCXMLDataGeneratorTool"
+ />
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"
+ />
+ <Tool
+ Name="VCMIDLTool"
+ />
+ <Tool
+ Name="VCCLCompilerTool"
+ AdditionalOptions="/wd4201 /wd4512 /wd4511 /wd4100 /wd4121 /wd4310 /wd4706 /wd4127 /wd4189 /wd4702 /wd4996"
+ Optimization="0"
+ AdditionalIncludeDirectories="../..;../../engines"
+ PreprocessorDefinitions="WIN32;_DEBUG;USE_ZLIB;USE_MAD;USE_VORBIS"
+ MinimalRebuild="true"
+ ExceptionHandling="1"
+ BasicRuntimeChecks="3"
+ RuntimeLibrary="1"
+ BufferSecurityCheck="true"
+ EnableFunctionLevelLinking="true"
+ ForceConformanceInForLoopScope="true"
+ UsePrecompiledHeader="0"
+ WarningLevel="4"
+ WarnAsError="false"
+ SuppressStartupBanner="false"
+ DebugInformationFormat="4"
+ />
+ <Tool
+ Name="VCManagedResourceCompilerTool"
+ />
+ <Tool
+ Name="VCResourceCompilerTool"
+ />
+ <Tool
+ Name="VCPreLinkEventTool"
+ />
+ <Tool
+ Name="VCLibrarianTool"
+ OutputFile="$(OutDir)/agi.lib"
+ />
+ <Tool
+ Name="VCALinkTool"
+ />
+ <Tool
+ Name="VCXDCMakeTool"
+ />
+ <Tool
+ Name="VCBscMakeTool"
+ />
+ <Tool
+ Name="VCFxCopTool"
+ />
+ <Tool
+ Name="VCPostBuildEventTool"
+ />
+ </Configuration>
+ <Configuration
+ Name="Release|Win32"
+ OutputDirectory="agi_Release"
+ IntermediateDirectory="agi_Release"
+ ConfigurationType="4"
+ CharacterSet="2"
+ WholeProgramOptimization="1"
+ >
+ <Tool
+ Name="VCPreBuildEventTool"
+ />
+ <Tool
+ Name="VCCustomBuildTool"
+ />
+ <Tool
+ Name="VCXMLDataGeneratorTool"
+ />
+ <Tool
+ Name="VCWebServiceProxyGeneratorTool"
+ />
+ <Tool
+ Name="VCMIDLTool"
+ />
+ <Tool
+ Name="VCCLCompilerTool"
+ AdditionalOptions="/wd4201 /wd4512 /wd4511 /wd4100 /wd4121 /wd4310 /wd4706 /wd4127 /wd4189 /wd4702 /wd4996"
+ Optimization="3"
+ InlineFunctionExpansion="2"
+ OmitFramePointers="true"
+ AdditionalIncludeDirectories="../../;../../common"
+ PreprocessorDefinitions="WIN32;NDEBUG;USE_ZLIB;USE_MAD;USE_VORBIS"
+ StringPooling="true"
+ ExceptionHandling="1"
+ RuntimeLibrary="0"
+ BufferSecurityCheck="false"
+ EnableFunctionLevelLinking="false"
+ ForceConformanceInForLoopScope="true"
+ UsePrecompiledHeader="0"
+ WarningLevel="4"
+ WarnAsError="true"
+ DebugInformationFormat="0"
+ />
+ <Tool
+ Name="VCManagedResourceCompilerTool"
+ />
+ <Tool
+ Name="VCResourceCompilerTool"
+ />
+ <Tool
+ Name="VCPreLinkEventTool"
+ />
+ <Tool
+ Name="VCLibrarianTool"
+ OutputFile="$(OutDir)/agi.lib"
+ />
+ <Tool
+ Name="VCALinkTool"
+ />
+ <Tool
+ Name="VCXDCMakeTool"
+ />
+ <Tool
+ Name="VCBscMakeTool"
+ />
+ <Tool
+ Name="VCFxCopTool"
+ />
+ <Tool
+ Name="VCPostBuildEventTool"
+ />
+ </Configuration>
+ </Configurations>
+ <References>
+ </References>
+ <Files>
+ <File
+ RelativePath="..\..\engines\agi\agi.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\agi.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\agi_v2.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\agi_v3.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\checks.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\console.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\console.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\cycle.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\font.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\global.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\graphics.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\graphics.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\id.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\inv.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\keyboard.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\keyboard.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\list.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\logic.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\logic.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\lzw.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\lzw.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\menu.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\menu.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\motion.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\objects.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\op_cmd.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\op_dbg.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\op_test.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\opcodes.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\patches.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\picture.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\picture.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\savegame.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\savegame.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\sound.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\sound.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\sprite.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\sprite.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\text.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\text.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\view.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\view.h"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\agi\words.cpp"
+ >
+ </File>
+ </Files>
+ <Globals>
+ </Globals>
+</VisualStudioProject>
Property changes on: scummvm/trunk/dists/msvc8/agi.vcproj
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:eol-style
+ native
Modified: scummvm/trunk/dists/msvc8/gob.vcproj
===================================================================
--- scummvm/trunk/dists/msvc8/gob.vcproj 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/dists/msvc8/gob.vcproj 2006-05-23 23:43:52 UTC (rev 22588)
@@ -4,6 +4,7 @@
Version="8,00"
Name="gob"
ProjectGUID="{976D947A-A45F-4437-991E-412F695C64C7}"
+ RootNamespace="gob"
Keyword="Win32Proj"
>
<Platforms>
@@ -247,6 +248,14 @@
>
</File>
<File
+ RelativePath="..\..\engines\gob\goblin_v1.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\gob\goblin_v2.cpp"
+ >
+ </File>
+ <File
RelativePath="..\..\engines\gob\init.cpp"
>
</File>
@@ -287,6 +296,14 @@
>
</File>
<File
+ RelativePath="..\..\engines\gob\map_v1.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\gob\map_v2.cpp"
+ >
+ </File>
+ <File
RelativePath="..\..\engines\gob\mult.cpp"
>
</File>
Modified: scummvm/trunk/dists/msvc8/kyra.vcproj
===================================================================
--- scummvm/trunk/dists/msvc8/kyra.vcproj 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/dists/msvc8/kyra.vcproj 2006-05-23 23:43:52 UTC (rev 22588)
@@ -4,6 +4,7 @@
Version="8,00"
Name="kyra"
ProjectGUID="{9D9A98A0-F88F-4CA2-B8FF-462470EBE3EC}"
+ RootNamespace="kyra"
Keyword="Win32Proj"
>
<Platforms>
@@ -191,6 +192,10 @@
>
</File>
<File
+ RelativePath="..\..\engines\kyra\kyra3.cpp"
+ >
+ </File>
+ <File
RelativePath="..\..\engines\kyra\plugin.cpp"
>
</File>
@@ -255,6 +260,10 @@
>
</File>
<File
+ RelativePath="..\..\engines\kyra\sound_digital.cpp"
+ >
+ </File>
+ <File
RelativePath="..\..\engines\kyra\sprites.cpp"
>
</File>
@@ -279,6 +288,14 @@
>
</File>
<File
+ RelativePath="..\..\engines\kyra\vqa.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\engines\kyra\vqa.h"
+ >
+ </File>
+ <File
RelativePath="..\..\engines\kyra\wsamovie.cpp"
>
</File>
Modified: scummvm/trunk/dists/msvc8/scummvm.sln
===================================================================
--- scummvm/trunk/dists/msvc8/scummvm.sln 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/dists/msvc8/scummvm.sln 2006-05-23 23:43:52 UTC (rev 22588)
@@ -1,15 +1,16 @@
Microsoft Visual Studio Solution File, Format Version 9.00
-# Visual C++ Express 2005
+# Visual Studio 2005
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "scummvm", "scummvm.vcproj", "{8434CB15-D08F-427D-9E6D-581AE5B28440}"
ProjectSection(ProjectDependencies) = postProject
{6CC3E421-779D-4E80-8100-520886A0F9FF} = {6CC3E421-779D-4E80-8100-520886A0F9FF}
- {1CA4AC50-5426-433A-8B5E-FFE39568098E} = {1CA4AC50-5426-433A-8B5E-FFE39568098E}
+ {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E} = {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}
{676DB4C5-9A3E-4EE1-8483-EBB79DC0700E} = {676DB4C5-9A3E-4EE1-8483-EBB79DC0700E}
{9D9A98A0-F88F-4CA2-B8FF-462470EBE3EC} = {9D9A98A0-F88F-4CA2-B8FF-462470EBE3EC}
{976D947A-A45F-4437-991E-412F695C64C7} = {976D947A-A45F-4437-991E-412F695C64C7}
{E0EC9C72-A33E-49DA-B1DC-BB44B9799BFA} = {E0EC9C72-A33E-49DA-B1DC-BB44B9799BFA}
{6A55AF61-7CA1-49E0-9385-59C1FE9D4DB7} = {6A55AF61-7CA1-49E0-9385-59C1FE9D4DB7}
{B5527758-2F51-4CCD-AAE1-B0E28654BD6A} = {B5527758-2F51-4CCD-AAE1-B0E28654BD6A}
+ {1CA4AC50-5426-433A-8B5E-FFE39568098E} = {1CA4AC50-5426-433A-8B5E-FFE39568098E}
{B6AFD548-63D2-40CD-A652-E87095AFCBAF} = {B6AFD548-63D2-40CD-A652-E87095AFCBAF}
{C8AAE83E-198B-4ECA-A877-166827953979} = {C8AAE83E-198B-4ECA-A877-166827953979}
{1A1CA028-61B5-4A6C-A918-F5D8721AB1AC} = {1A1CA028-61B5-4A6C-A918-F5D8721AB1AC}
@@ -37,6 +38,8 @@
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "cine", "cine.vcproj", "{1CA4AC50-5426-433A-8B5E-FFE39568098E}"
EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "agi", "agi.vcproj", "{F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Win32 = Debug|Win32
@@ -91,6 +94,10 @@
{1CA4AC50-5426-433A-8B5E-FFE39568098E}.Debug|Win32.Build.0 = Debug|Win32
{1CA4AC50-5426-433A-8B5E-FFE39568098E}.Release|Win32.ActiveCfg = Release|Win32
{1CA4AC50-5426-433A-8B5E-FFE39568098E}.Release|Win32.Build.0 = Release|Win32
+ {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}.Debug|Win32.ActiveCfg = Debug|Win32
+ {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}.Debug|Win32.Build.0 = Debug|Win32
+ {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}.Release|Win32.ActiveCfg = Release|Win32
+ {F5F57066-CDF4-4F80-B9E7-7F4D21850D6E}.Release|Win32.Build.0 = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Modified: scummvm/trunk/dists/msvc8/scummvm.vcproj
===================================================================
--- scummvm/trunk/dists/msvc8/scummvm.vcproj 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/dists/msvc8/scummvm.vcproj 2006-05-23 23:43:52 UTC (rev 22588)
@@ -4,6 +4,7 @@
Version="8,00"
Name="scummvm"
ProjectGUID="{8434CB15-D08F-427D-9E6D-581AE5B28440}"
+ RootNamespace="scummvm"
Keyword="Win32Proj"
>
<Platforms>
@@ -67,7 +68,7 @@
/>
<Tool
Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib sdl.lib zdll.lib libmad.lib vorbisfile_static.lib vorbis_static.lib ogg_static.lib libmpeg2.lib sword1_debug/sword1.lib sword2_debug/sword2.lib lure_debug/lure.lib cine_debug/cine.lib kyra_debug/kyra.lib gob_debug/gob.lib queen_debug/queen.lib saga_debug/saga.lib scumm_debug/scumm.lib simon_debug/simon.lib sky_debug/sky.lib"
+ AdditionalDependencies="winmm.lib sdl.lib zlib.lib libmad.lib vorbisfile_static.lib vorbis_static.lib ogg_static.lib libmpeg2.lib sword1_debug/sword1.lib sword2_debug/sword2.lib lure_debug/lure.lib cine_debug/cine.lib kyra_debug/kyra.lib gob_debug/gob.lib queen_debug/queen.lib saga_debug/saga.lib agi_debug/agi.lib scumm_debug/scumm.lib simon_debug/simon.lib sky_debug/sky.lib"
OutputFile="$(OutDir)/scummvm.exe"
LinkIncremental="2"
IgnoreDefaultLibraryNames="libc.lib;libcmt.lib"
@@ -155,7 +156,7 @@
/>
<Tool
Name="VCLinkerTool"
- AdditionalDependencies="winmm.lib sdl.lib zdll.lib libmad.lib vorbisfile_static.lib vorbis_static.lib ogg_static.lib libmpeg2.lib saga_release/saga.lib sword1_release/sword1.lib sword2_release/sword2.lib lure_release/lure.lib cine_release/cine.lib kyra_release/kyra.lib gob_release/gob.lib queen_release/queen.lib scumm_release/scumm.lib simon_release/simon.lib sky_release/sky.lib"
+ AdditionalDependencies="winmm.lib sdl.lib zlib.lib libmad.lib vorbisfile_static.lib vorbis_static.lib ogg_static.lib libmpeg2.lib saga_release/saga.lib agi_release/agi.lib sword1_release/sword1.lib sword2_release/sword2.lib lure_release/lure.lib cine_release/cine.lib kyra_release/kyra.lib gob_release/gob.lib queen_release/queen.lib scumm_release/scumm.lib simon_release/simon.lib sky_release/sky.lib"
OutputFile="$(OutDir)/scummvm.exe"
LinkIncremental="1"
SuppressStartupBanner="true"
@@ -998,6 +999,14 @@
>
</File>
<File
+ RelativePath="..\..\graphics\paletteman.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\graphics\paletteman.h"
+ >
+ </File>
+ <File
RelativePath="..\..\graphics\primitives.cpp"
>
</File>
Modified: scummvm/trunk/doc/credits.tex
===================================================================
--- scummvm/trunk/doc/credits.tex 2006-05-23 20:10:01 UTC (rev 22587)
+++ scummvm/trunk/doc/credits.tex 2006-05-23 23:43:52 UTC (rev 22588)
@@ -34,6 +34,13 @@
Eugene Sandulenko & \textit{}\\
\end{tabular}
\end{list}
+\item \textbf{ AGI}
+\begin{list}{}{\setlength{\leftmargin}{0.2cm}}
+\item \begin{tabular}[h]{p{0.3\linewidth}p{0.6\linewidth}}
+ Pawe{\l} Ko{\l}odziejski & \textit{}\\
+ Eugene Sandulenko & \textit{}\\
+ \end{tabular}
+\end{list}
\item \textbf{ BASS}
\begin{list}{}{\setlength{\leftmargin}{0.2cm}}
\item \begin{tabular}[h]{p{0.3\linewidth}p{0.6\linewidth}}
@@ -293,6 +300,7 @@
Jezar & \textit{For his freeverb filter implementation}\\
Jim Leiterman & \textit{Various info on his FM-TOWNS/Marty SCUMM ports}\\
lloyd & \textit{For deep tech details about C64 Zak \& MM}\\
+ Sarien Team & \textit{Original AGI engine code}\\
Jimmi Th{\o}gersen & \textit{For ScummRev, and much obscure code/documentation}\\
Tristan & \textit{For additional work on the original MT-32 emulator}\\
\end{tabular}
Added: scummvm/trunk/engines/agi/agi.cpp
===================================================================
--- scummvm/trunk/engines/agi/agi.cpp (rev 0)
+++ scummvm/trunk/engines/agi/agi.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,627 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2003 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+#include "common/file.h"
+#include "common/savefile.h"
+#include "common/config-manager.h"
+
+#include "base/plugins.h"
+
+#include "backends/fs/fs.h"
+
+#include "sound/mididrv.h"
+#include "sound/mixer.h"
+
+#include "agi/agi.h"
+#include "agi/text.h"
+#include "agi/graphics.h"
+#include "agi/sprite.h"
+#include "agi/opcodes.h"
+#include "agi/keyboard.h"
+#include "agi/menu.h"
+#include "agi/savegame.h"
+
+namespace Agi {
+
+void gfx_set_palette();
+
+extern int optind;
+
+struct agi_options opt;
+struct game_id_list game_info;
+struct agi_game game;
+
+static struct agi_loader *loader; /* loader */
+
+extern struct agi_loader agi_v2;
+extern struct agi_loader agi_v3;
+
+static volatile uint32 tick_timer = 0;
+
+#define TICK_SECONDS 20
+
+static int key_control = 0;
+static int key_alt = 0;
+
+#define KEY_QUEUE_SIZE 16
+
+static int key_queue[KEY_QUEUE_SIZE];
+static int key_queue_start = 0;
+static int key_queue_end = 0;
+
+#define key_enqueue(k) do { key_queue[key_queue_end++] = (k); \
+ key_queue_end %= KEY_QUEUE_SIZE; } while (0)
+#define key_dequeue(k) do { (k) = key_queue[key_queue_start++]; \
+ key_queue_start %= KEY_QUEUE_SIZE; } while (0)
+
+static void process_events() {
+ OSystem::Event event;
+ int key = 0;
+
+ while (g_system->pollEvent(event)) {
+ switch (event.type) {
+ case OSystem::EVENT_QUIT:
+ deinit_video();
+ deinit_machine();
+ g_system->quit();
+ break;
+ case OSystem::EVENT_LBUTTONDOWN:
+ key = BUTTON_LEFT;
+ mouse.button = 1;
+ key_enqueue(key);
+ mouse.x = event.mouse.x;
+ mouse.y = event.mouse.y;
+ break;
+ case OSystem::EVENT_RBUTTONDOWN:
+ key = BUTTON_RIGHT;
+ mouse.button = 2;
+ key_enqueue(key);
+ mouse.x = event.mouse.x;
+ mouse.y = event.mouse.y;
+ break;
+ case OSystem::EVENT_MOUSEMOVE:
+ mouse.x = event.mouse.x;
+ mouse.y = event.mouse.y;
+ break;
+ case OSystem::EVENT_LBUTTONUP:
+ case OSystem::EVENT_RBUTTONUP:
+ mouse.button = 0;
+ break;
+ case OSystem::EVENT_KEYDOWN:
+ if (event.kbd.flags == OSystem::KBD_CTRL) {
+ key_control |= 1;
+ key = 0;
+ break;
+ } else if (event.kbd.flags == OSystem::KBD_ALT) {
+ key_alt |= 1;
+ key = 0;
+ break;
+ } else if (event.kbd.flags == OSystem::KBD_SHIFT) {
+ key = 0;
+ break;
+ }
+
+ switch (key = event.kbd.keycode) {
+ case 256 + 20: // left arrow
+ key = KEY_LEFT;
+ break;
+ case 256 + 19: // right arrow
+ key = KEY_RIGHT;
+ break;
+ case 256 + 17: // up arrow
+ key = KEY_UP;
+ break;
+ case 256 + 18: // down arrow
+ key = KEY_DOWN;
+ break;
+ case 256 + 24: // page up
+ key = KEY_UP_RIGHT;
+ break;
+ case 256 + 25: // page down
+ key = KEY_DOWN_RIGHT;
+ break;
+ case 256 + 22: // home
+ key = KEY_UP_LEFT;
+ break;
+ case 256 + 23: // end
+ key = KEY_DOWN_LEFT;
+ break;
+ case '+':
+ key = '+';
+ break;
+ case '-':
+ key = '-';
+ break;
+ case 9:
+ key = 0x0009;
+ break;
+ case 282:
+ key = 0x3b00;
+ break;
+ case 283:
+ key = 0x3c00;
+ break;
+ case 284:
+ key = 0x3d00;
+ break;
+ case 285:
+ key = 0x3e00;
+ break;
+ case 286:
+ key = 0x3f00;
+ break;
+ case 287:
+ key = 0x4000;
+ break;
+ case 288:
+ key = 0x4100;
+ break;
+ case 289:
+ key = 0x4200;
+ break;
+ case 290:
+ key = 0x4300;
+ break;
+ case 291:
+ key = 0x4400;
+ break;
+ case 292:
+ key = KEY_STATUSLN;
+ break;
+ case 293:
+ key = KEY_PRIORITY;
+ break;
+ case 27:
+ key = 0x1b;
+ break;
+ case '\n':
+ case '\r':
+ key = KEY_ENTER;
+ break;
+ default:
+ if (!isalpha(key))
+ break;
+ if (key_control)
+ key = (key & ~0x20) - 0x40;
+ else if (key_alt)
+ key = scancode_table[(key & ~0x20) - 0x41] << 8;
+ break;
+ }
+ if (key)
+ key_enqueue(key);
+ break;
+ case OSystem::EVENT_KEYUP:
+ if (event.kbd.flags == OSystem::KBD_CTRL) {
+ key_control &= ~1;
+ key = 0;
+ break;
+ } else if (event.kbd.flags == OSystem::KBD_ALT) {
+ key_alt &= ~1;
+ key = 0;
+ break;
+ } else if (event.kbd.flags == OSystem::KBD_SHIFT) {
+ key = 0;
+ break;
+ }
+ break;
+ default:
+ break;
+ }
+ }
+}
+
+int agi_is_keypress_low() {
+ process_events();
+ return key_queue_start != key_queue_end;
+}
+
+void agi_timer_low() {
+ static uint32 m = 0;
+ uint32 dm;
+
+ if (tick_timer < m)
+ m = 0;
+
+ while ((dm = tick_timer - m) < 5) {
+ process_events();
+ g_system->delayMillis(10);
+ g_system->updateScreen();
+ }
+ m = tick_timer;
+}
+
+int agi_get_keypress_low() {
+ int k;
+
+ while (key_queue_start == key_queue_end) /* block */
+ agi_timer_low();
+ key_dequeue(k);
+
+ return k;
+}
+
+static uint32 agi_timer_function_low(uint32 i) {
+ tick_timer++;
+ return i;
+}
+
+static void init_pri_table() {
+ int i, p, y = 0;
+
+ for (p = 1; p < 15; p++) {
+ for (i = 0; i < 12; i++) {
+ game.pri_table[y++] = p < 4 ? 4 : p;
+ }
+ }
+}
+
+int agi_init() {
+ int ec, i;
+
+ debug(2, "initializing");
+ debug(2, "game.ver = 0x%x", game.ver);
+
+ /* reset all flags to false and all variables to 0 */
+ for (i = 0; i < MAX_FLAGS; i++)
+ game.flags[i] = 0;
+ for (i = 0; i < MAX_VARS; i++)
+ game.vars[i] = 0;
+
+ /* clear all resources and events */
+ for (i = 0; i < MAX_DIRS; i++) {
+ memset(&game.views[i], 0, sizeof(struct agi_view));
+ memset(&game.pictures[i], 0, sizeof(struct agi_picture));
+ memset(&game.logics[i], 0, sizeof(struct agi_logic));
+ memset(&game.sounds[i], 0, sizeof(struct agi_sound));
+ }
+
+ /* clear view table */
+ for (i = 0; i < MAX_VIEWTABLE; i++)
+ memset(&game.view_table[i], 0, sizeof(struct vt_entry));
+
+ init_words();
+
+ menu_init();
+ init_pri_table();
+
+ /* clear string buffer */
+ for (i = 0; i < MAX_STRINGS; i++)
+ game.strings[i][0] = 0;
+
+ /* setup emulation */
+
+ switch (loader->int_version >> 12) {
+ case 2:
+ report("Emulating Sierra AGI v%x.%03x\n",
+ (int)(loader->int_version >> 12) & 0xF,
+ (int)(loader->int_version) & 0xFFF);
+ break;
+ case 3:
+ report("Emulating Sierra AGI v%x.002.%03x\n",
+ (int)(loader->int_version >> 12) & 0xF,
+ (int)(loader->int_version) & 0xFFF);
+ break;
+ }
+
+ game.game_flags |= opt.amiga ? ID_AMIGA : 0;
+ game.game_flags |= opt.agds ? ID_AGDS : 0;
+
+ if (game.game_flags & ID_AMIGA)
+ report("Amiga padded game detected.\n");
+
+ if (game.game_flags & ID_AGDS)
+ report("AGDS mode enabled.\n");
+
+ ec = loader->init(); /* load vol files, etc */
+
+ if (ec == err_OK)
+ ec = loader->load_objects(OBJECTS);
+
+ /* note: demogs has no words.tok */
+ if (ec == err_OK)
+ ec = loader->load_words(WORDS);
+
+ /* FIXME: load IIgs instruments and samples */
+ /* load_instruments("kq.sys16"); */
+
+ /* Load logic 0 into memory */
+ if (ec == err_OK)
+ ec = loader->load_resource(rLOGIC, 0);
+
+ return ec;
+}
+
+/*
+ * Public functions
+ */
+
+void agi_unload_resources() {
+ int i;
+
+ /* Make sure logic 0 is always loaded */
+ for (i = 1; i < MAX_DIRS; i++) {
+ loader->unload_resource(rLOGIC, i);
+ }
+ for (i = 0; i < MAX_DIRS; i++) {
+ loader->unload_resource(rVIEW, i);
+ loader->unload_resource(rPICTURE, i);
+ loader->unload_resource(rSOUND, i);
+ }
+}
+
+int agi_deinit() {
+ int ec;
+
+ clean_input(); /* remove all words from memory */
+ agi_unload_resources(); /* unload resources in memory */
+ loader->unload_resource(rLOGIC, 0);
+ ec = loader->deinit();
+ unload_objects();
+ unload_words();
+
+ clear_image_stack();
+
+ return ec;
+}
+
+int agi_detect_game() {
+ int ec = err_OK;
+
+ loader = &agi_v2;
+ ec = loader->detect_game();
+
+ if (ec != err_OK) {
+ loader = &agi_v3;
+ ec = loader->detect_game();
+ }
+
+ return ec;
+}
+
+int agi_version() {
+ return loader->version;
+}
+
+int agi_get_release() {
+ return loader->int_version;
+}
+
+void agi_set_release(int n) {
+ loader->int_version = n;
+}
+
+int agi_load_resource(int r, int n) {
+ int i;
+
+ i = loader->load_resource(r, n);
+#ifdef PATCH_LOGIC
+ if (r == rLOGIC)
+ patch_logic(n);
+#endif
+
+ return i;
+}
+
+int agi_unload_resource(int r, int n) {
+ return loader->unload_resource(r, n);
+}
+
+const char *_savePath;
+extern AGIMusic *g_agi_music;
+
+struct GameSettings {
+ const char *gameid;
+ const char *description;
+ byte id;
+ uint32 features;
+ const char *detectname;
+};
+
+static const GameSettings agi_settings[] = {
+ {"agi", "AGI game", GID_AGI, MDT_ADLIB, "VIEWDIR"},
+ {NULL, NULL, 0, 0, NULL}
+};
+
+Common::RandomSource * rnd;
+
+AgiEngine::AgiEngine(OSystem * syst) : Engine(syst) {
+
+ // Setup mixer
+ if (!_mixer->isReady()) {
+ warning("Sound initialization failed.");
+ }
+
+ _mixer->setVolumeForSoundType(Audio::Mixer::kSFXSoundType, ConfMan.getInt("sfx_volume"));
+ _mixer->setVolumeForSoundType(Audio::Mixer::kMusicSoundType, ConfMan.getInt("music_volume"));
+
+ _savePath = _saveFileMan->getSavePath();
+
+ const GameSettings *g;
+
+ const char *gameid = ConfMan.get("gameid").c_str();
+ for (g = agi_settings; g->gameid; ++g)
+ if (!scumm_stricmp(g->gameid, gameid))
+ _gameId = g->id;
+
+ rnd = new Common::RandomSource();
+
+ game.clock_enabled = false;
+ game.state = STATE_INIT;
+}
+
+void AgiEngine::initialize() {
+ memset(&opt, 0, sizeof(struct agi_options));
+ opt.gamerun = GAMERUN_RUNGAME;
+#ifdef USE_HIRES
+ opt.hires = true;
+#endif
+ opt.soundemu = SOUND_EMU_NONE;
+
+ init_machine();
+
+ game.color_fg = 15;
+ game.color_bg = 0;
+
+ *game.name = 0;
+
+ game.sbuf = (uint8 *) calloc(_WIDTH, _HEIGHT);
+#ifdef USE_HIRES
+ game.hires = (uint8 *) calloc(_WIDTH * 2, _HEIGHT);
+#endif
+
+ init_sprites();
+ init_video();
+
+ tick_timer = 0;
+ Common::g_timer->installTimerProc((Common::Timer::TimerProc) agi_timer_function_low, 10 * 1000, NULL);
+
+ console_init();
+
+ game.ver = -1; /* Don't display the conf file warning */
+
+ debugC(2, kDebugLevelMain, "Detect game");
+ if (agi_detect_game() == err_OK) {
+ game.state = STATE_LOADED;
+ debugC(2, kDebugLevelMain, "game loaded");
+ } else {
+ report("Could not open AGI game");
+ }
+
+ debugC(2, kDebugLevelMain, "Init sound");
+ init_sound();
+ g_agi_music = new AGIMusic(_mixer);
+}
+
+AgiEngine::~AgiEngine() {
+ agi_deinit();
+ delete g_agi_music;
+ deinit_sound();
+ deinit_video();
+ deinit_sprites();
+#ifdef USE_HIRES
+ free(game.hires);
+#endif
+ free(game.sbuf);
+ deinit_machine();
+ delete rnd;
+}
+
+void AgiEngine::errorString(const char *buf1, char *buf2) {
+ strcpy(buf2, buf1);
+}
+
+int AgiEngine::init() {
+ // Initialize backend
+ _system->beginGFXTransaction();
+ initCommonGFX(false);
+ _system->initSize(320, 200);
+ _system->endGFXTransaction();
+
+ Common::addSpecialDebugLevel(kDebugLevelMain, "Main", "Generic debug level");
+ Common::addSpecialDebugLevel(kDebugLevelResources, "Resources", "Resources debugging");
+ Common::addSpecialDebugLevel(kDebugLevelSprites, "Sprites", "Sprites debugging");
+ Common::addSpecialDebugLevel(kDebugLevelInventory, "Inventory", "Inventory debugging");
+ Common::addSpecialDebugLevel(kDebugLevelInput, "Input", "Input events debugging");
+ Common::addSpecialDebugLevel(kDebugLevelMenu, "Menu", "Menu debugging");
+ Common::addSpecialDebugLevel(kDebugLevelScripts, "Scrpits", "Scripts debugging");
+ Common::addSpecialDebugLevel(kDebugLevelSound, "Sound", "Sound debugging");
+ Common::addSpecialDebugLevel(kDebugLevelText, "Text", "Text output debugging");
+
+ initialize();
+
+ gfx_set_palette();
+
+ return 0;
+}
+
+int AgiEngine::go() {
+ _system->showMouse(true);
+
+ report(" \nAGI engine " VERSION " is ready.\n");
+ if (game.state < STATE_LOADED) {
+ console_prompt();
+ do {
+ main_cycle();
+ } while (game.state < STATE_RUNNING);
+ if (game.ver < 0)
+ game.ver = 0; /* Enable conf file warning */
+ }
+
+ run_game();
+
+ return 0;
+}
+
+} // End of namespace Agi
+
+GameList Engine_AGI_gameIDList() {
+ GameList games;
+ const Agi::GameSettings *g = Agi::agi_settings;
+
+ while (g->gameid) {
+ games.push_back(*g);
+ g++;
+ }
+
+ return games;
+}
+
+GameDescriptor Engine_AGI_findGameID(const char *gameid) {
+ const Agi::GameSettings *g = Agi::agi_settings;
+ while (g->gameid) {
+ if (0 == scumm_stricmp(gameid, g->gameid))
+ break;
+ g++;
+ }
+ return *g;
+}
+
+DetectedGameList Engine_AGI_detectGames(const FSList &fslist) {
+ DetectedGameList detectedGames;
+ const Agi::GameSettings * g;
+
+ for (g = Agi::agi_settings; g->gameid; ++g) {
+ // Iterate over all files in the given directory
+ for (FSList::const_iterator file = fslist.begin();
+ file != fslist.end(); ++file) {
+ const char *gameName = file->displayName().c_str();
+
+ if (0 == scumm_stricmp(g->detectname, gameName)) {
+ // Match found, add to list of candidates, then abort inner loop.
+ detectedGames.push_back(*g);
+ break;
+ }
+ }
+ }
+ return detectedGames;
+}
+
+PluginError Engine_AGI_create(OSystem *syst, Engine **engine) {
+ assert(engine);
+ *engine = new Agi::AgiEngine(syst);
+ return kNoError;
+}
+
+REGISTER_PLUGIN(AGI, "AGI Engine");
Property changes on: scummvm/trunk/engines/agi/agi.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/agi.h
===================================================================
--- scummvm/trunk/engines/agi/agi.h (rev 0)
+++ scummvm/trunk/engines/agi/agi.h 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,545 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2001 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef __AGI_H
+#define __AGI_H
+
+#include "common/stdafx.h"
+#include "common/scummsys.h"
+#include "common/endian.h"
+#include "common/util.h"
+#include "common/file.h"
+#include "common/savefile.h"
+#include "common/system.h"
+
+#include "base/engine.h"
+
+namespace Agi {
+
+typedef signed int Err;
+
+/*
+ * Version and other definitions
+ */
+#define INLINE __inline
+#define VERSION __DATE__ " " __TIME__
+
+/* Default features -- can be overriden in portdefs.h */
+#define USE_CONSOLE
+#define USE_PCM_SOUND
+#define USE_IIGS_SOUND
+#define USE_HIRES
+#define USE_MOUSE
+#define AGDS_SUPPORT
+
+#define TITLE "AGI engine"
+
+#define DIR_ "dir"
+#define LOGDIR "logdir"
+#define PICDIR "picdir"
+#define VIEWDIR "viewdir"
+#define SNDDIR "snddir"
+#define OBJECTS "object"
+#define WORDS "words.tok"
+
+#define MAX_DIRS 256
+#define MAX_VARS 256
+#define MAX_FLAGS (256 >> 3)
+#define MAX_VIEWTABLE 255 /* KQ3 uses o255! */
+#define MAX_WORDS 20
+#define MAX_STRINGS 24 /* MAX_STRINGS + 1 used for get.num */
+#define MAX_STRINGLEN 40
+#ifndef MAX_PATH
+#define MAX_PATH 260
+#endif
+
+#define _EMPTY 0xfffff
+#define EGO_OWNED 0xff
+
+#define CRYPT_KEY_SIERRA "Avis Durgan"
+#define CRYPT_KEY_AGDS "Alex Simkin"
+
+#ifndef INLINE
+#define INLINE
+#endif
+
+#ifndef USE_PCM_SOUND
+#undef USE_IIGS_SOUND
+#endif
+
+#define MSG_BOX_COLOUR 0x0f /* White */
+#define MSG_BOX_TEXT 0x00 /* Black */
+#define MSG_BOX_LINE 0x04 /* Red */
+#define STATUS_FG 0x00 /* Black */
+#define STATUS_BG 0x0f /* White */
+#define PATCH_LOGIC /* disable copy protection on some games */
+
+} // End of namespace Agi
+
+/* AGI resources */
+#include "agi/console.h"
+#include "agi/view.h"
+#include "agi/picture.h"
+#include "agi/logic.h"
+#include "agi/sound.h"
+
+namespace Agi {
+
+int getflag(int);
+void setflag(int, int);
+void flipflag(int);
+int getvar(int);
+void setvar(int, int);
+void decrypt(uint8 * mem, int len);
+void release_sprites(void);
+int main_cycle(void);
+int view_pictures(void);
+int parse_cli(int, char **);
+int run_game(void);
+int init_machine(void);
+int deinit_machine(void);
+int get_direction(int x, int y, int x0, int y0, int s);
+void inventory(void);
+void list_games(void);
+uint32 match_crc(uint32, char *, int);
+int v2id_game(void);
+int v3id_game(void);
+int v4id_game(uint32 ver);
+void update_timer(void);
+int get_app_dir(char *app_dir, unsigned int size);
+
+enum {
+ NO_GAMEDIR = 0,
+ GAMEDIR
+};
+
+enum AGIErrors {
+ err_OK = 0,
+ err_DoNothing,
+ err_BadCLISwitch,
+ err_InvalidAGIFile,
+ err_BadFileOpen,
+ err_NotEnoughMemory,
+ err_BadResource,
+ err_UnknownAGIVersion,
+ err_RestartGame,
+ err_NoLoopsInView,
+ err_ViewDataError,
+ err_NoGameList,
+
+ err_Unk = 127
+};
+
+enum kDebugLevels {
+ kDebugLevelMain = 1 << 0,
+ kDebugLevelResources = 1 << 1,
+ kDebugLevelSprites = 1 << 2,
+ kDebugLevelInventory = 1 << 3,
+ kDebugLevelInput = 1 << 4,
+ kDebugLevelMenu = 1 << 5,
+ kDebugLevelScripts = 1 << 6,
+ kDebugLevelSound = 1 << 7,
+ kDebugLevelText = 1 << 8
+};
+
+/**
+ * AGI resources.
+ */
+enum {
+ rLOGIC = 1,
+ rSOUND,
+ rVIEW,
+ rPICTURE
+};
+
+enum {
+ RES_LOADED = 1,
+ RES_COMPRESSED = 0x40
+};
+
+enum {
+ lCOMMAND_MODE = 1,
+ lTEST_MODE
+};
+
+struct game_id_list {
+ struct game_id_list *next;
+ uint32 version;
+ uint32 crc;
+ char *gName;
+ char *switches;
+};
+
+#ifdef USE_MOUSE
+struct mouse {
+ int button;
+ unsigned int x;
+ unsigned int y;
+};
+#endif
+
+/**
+ * Command-line options.
+ */
+struct agi_options {
+#define GAMERUN_RUNGAME 0
+#define GAMERUN_PICVIEW 1
+#define GAMERUN_WORDS 2
+#define GAMERUN_OBJECTS 3
+#define GAMERUN_GAMES 4
+#define GAMERUN_CRC 5
+ int gamerun; /**< game run mode*/
+ int emuversion; /**< AGI version to emulate */
+ int agds; /**< enable AGDS mode */
+ int amiga; /**< enable Amiga mode */
+ int fullscreen; /**< use full screen mode if available */
+ int nosound; /**< disable sound */
+ int egapal; /**< use PC EGA palette */
+ int cgaemu; /**< use PC CGA emulation */
+#ifdef USE_HIRES
+ int hires; /**< use hi-res pictures */
+#endif
+ int soundemu; /**< sound emulation mode */
+#ifdef USE_MOUSE
+ int agimouse; /**< AGI Mouse 1.0 emulation */
+#endif
+};
+
+extern struct agi_options opt;
+extern uint8 *exec_name;
+
+extern volatile uint32 clock_ticks;
+extern volatile uint32 clock_count;
+extern volatile uint32 msg_box_secs2;
+
+#ifdef USE_CONSOLE
+extern struct agi_debug debug_;
+#endif
+
+#ifdef USE_MOUSE
+extern struct mouse mouse;
+#endif
+
+int console_keyhandler(int);
+int console_init(void);
+void console_cycle(void);
+void console_lock(void);
+void console_prompt(void);
+#define report printf
+
+enum GameId {
+ GID_AGI = 1
+};
+
+extern Common::RandomSource * rnd;
+extern const char *_savePath;
+
+class AgiEngine:public::Engine {
+ int _gameId;
+
+ void errorString(const char *buf_input, char *buf_output);
+
+protected:
+ int init();
+ int go();
+ void shutdown();
+ void initialize();
+
+
+public:
+ AgiEngine(OSystem * syst);
+ virtual ~ AgiEngine();
+ int getGameId() {
+ return _gameId;
+}};
+
+#define WIN_TO_PIC_X(x) ((x) / 2)
+#define WIN_TO_PIC_Y(y) ((y) < 8 ? 999 : (y) >= (8 + _HEIGHT) ? 999 : (y) - 8)
+
+/**
+ * AGI variables.
+ */
+enum {
+ V_cur_room = 0, /* 0 */
+ V_prev_room,
+ V_border_touch_ego,
+ V_score,
+ V_border_code,
+ V_border_touch_obj, /* 5 */
+ V_ego_dir,
+ V_max_score,
+ V_free_pages,
+ V_word_not_found,
+ V_time_delay, /* 10 */
+ V_seconds,
+ V_minutes,
+ V_hours,
+ V_days,
+ V_joystick_sensitivity, /* 15 */
+ V_ego_view_resource,
+ V_agi_err_code,
+ V_agi_err_code_info,
+ V_key,
+ V_computer, /* 20 */
+ V_window_reset,
+ V_soundgen,
+ V_volume,
+ V_max_input_chars,
+ V_sel_item, /* 25 */
+ V_monitor
+};
+
+/**
+ * AGI flags
+ */
+enum {
+ F_ego_water = 0, /* 0 */
+ F_ego_invisible,
+ F_entered_cli,
+ F_ego_touched_p2,
+ F_said_accepted_input,
+ F_new_room_exec, /* 5 */
+ F_restart_game,
+ F_script_blocked,
+ F_joy_sensitivity,
+ F_sound_on,
+ F_debugger_on, /* 10 */
+ F_logic_zero_firsttime,
+ F_restore_just_ran,
+ F_status_selects_items,
+ F_menus_work,
+ F_output_mode, /* 15 */
+ F_auto_restart
+};
+
+struct agi_event {
+ uint16 data;
+ uint8 occured;
+};
+
+struct agi_object {
+ int location;
+ char *name;
+};
+
+struct agi_word {
+ int id;
+ char *word;
+};
+
+struct agi_dir {
+ uint8 volume;
+ uint32 offset;
+ uint32 len;
+ uint32 clen;
+ uint8 flags;
+ /* 0 = not in mem, can be freed
+ * 1 = in mem, can be released
+ * 2 = not in mem, cant be released
+ * 3 = in mem, cant be released
+ * 0x40 = was compressed
+ */
+};
+
+struct agi_block {
+ int active;
+ int x1, y1;
+ int x2, y2;
+ uint8 *buffer; /* used for window background */
+};
+
+#define EGO_VIEW_TABLE 0
+#define HORIZON 36
+#define _WIDTH 160
+#define _HEIGHT 168
+
+/**
+ * AGI game structure.
+ * This structure contains all global data of an AGI game executed
+ * by the interpreter.
+ */
+struct agi_game {
+#define STATE_INIT 0x00
+#define STATE_LOADED 0x01
+#define STATE_RUNNING 0x02
+ int state; /**< state of the interpreter */
+
+ char name[8]; /**< lead in id (e.g. `GR' for goldrush) */
+ char id[8]; /**< game id */
+ uint32 crc; /**< game CRC */
+
+ /* game flags and variables */
+ uint8 flags[MAX_FLAGS];
+ /**< 256 1-bit flags */
+ uint8 vars[MAX_VARS];
+ /**< 256 variables */
+
+ /* internal variables */
+ int horizon; /**< horizon y coordinate */
+ int line_status; /**< line number to put status on */
+ int line_user_input;
+ /**< line to put user input on */
+ int line_min_print;
+ /**< num lines to print on */
+ int cursor_pos; /**< column where the input cursor is */
+ uint8 input_buffer[40];
+ /**< buffer for user input */
+ uint8 echo_buffer[40];
+ /**< buffer for echo.line */
+ int keypress;
+#define INPUT_NORMAL 0x01
+#define INPUT_GETSTRING 0x02
+#define INPUT_MENU 0x03
+#define INPUT_NONE 0x04
+ int input_mode; /**< keyboard input mode */
+ int input_enabled;
+ /**< keyboard input enabled */
+ int lognum; /**< current logic number */
+
+ /* internal flags */
+ int player_control;
+ /**< player is in control */
+ int quit_prog_now;
+ /**< quit now */
+ int status_line; /**< status line on/off */
+ int clock_enabled;
+ /**< clock is on/off */
+ int exit_all_logics;
+ /**< break cycle after new.room */
+ int picture_shown;
+ /**< show.pic has been issued */
+ int has_prompt; /**< input prompt has been printed */
+#define ID_AGDS 0x00000001
+#define ID_AMIGA 0x00000002
+ int game_flags; /**< agi options flags */
+
+ uint8 pri_table[_HEIGHT];
+ /**< priority table */
+
+ /* windows */
+ uint32 msg_box_ticks;
+ /**< timed message box tick counter */
+ struct agi_block block;
+ struct agi_block window;
+ int has_window;
+
+ /* graphics & text */
+ int gfx_mode;
+ char cursor_char;
+ unsigned int color_fg;
+ unsigned int color_bg;
+ uint8 *sbuf; /**< 160x168 AGI screen buffer */
+#ifdef USE_HIRES
+ uint8 *hires; /**< 320x168 hi-res buffer */
+#endif
+
+ /* player command line */
+ struct agi_word ego_words[MAX_WORDS];
+ int num_ego_words;
+
+ unsigned int num_objects;
+
+ struct agi_event ev_keyp[MAX_DIRS];
+ /**< keyboard keypress events */
+ char strings[MAX_STRINGS + 1][MAX_STRINGLEN];
+ /**< strings */
+
+ /* directory entries for resources */
+ struct agi_dir dir_logic[MAX_DIRS];
+ struct agi_dir dir_pic[MAX_DIRS];
+ struct agi_dir dir_view[MAX_DIRS];
+ struct agi_dir dir_sound[MAX_DIRS];
+
+ /* resources */
+ struct agi_picture pictures[MAX_DIRS];
+ /**< AGI picture resources */
+ struct agi_logic logics[MAX_DIRS];
+ /**< AGI logic resources */
+ struct agi_view views[MAX_DIRS]; /**< AGI view resources */
+ struct agi_sound sounds[MAX_DIRS];
+ /**< AGI sound resources */
+
+ /* view table */
+ struct vt_entry view_table[MAX_VIEWTABLE];
+
+ int32 ver; /**< detected game version */
+
+ int simple_save; /**< select simple savegames */
+};
+
+/**
+ *
+ */
+struct agi_loader {
+ int version;
+ int int_version;
+ int (*init) (void);
+ int (*deinit) (void);
+ int (*detect_game) ();
+ int (*load_resource) (int, int);
+ int (*unload_resource) (int, int);
+ int (*load_objects) (char *);
+ int (*load_words) (char *);
+};
+
+extern struct agi_game game;
+
+int agi_init(void);
+int agi_deinit(void);
+int agi_version(void);
+int agi_get_release(void);
+void agi_set_release(int);
+int agi_detect_game();
+int agi_load_resource(int, int);
+int agi_unload_resource(int, int);
+void agi_unload_resources(void);
+
+/* words */
+int show_words(void);
+int load_words(char *);
+void unload_words(void);
+int find_word(char *word, int *flen);
+void dictionary_words(char *);
+
+/* objects */
+int show_objects(void);
+int load_objects(char *fname);
+int alloc_objects(int);
+void unload_objects(void);
+char *object_name(unsigned int);
+int object_get_location(unsigned int);
+void object_set_location(unsigned int, int);
+
+void new_input_mode(int);
+void old_input_mode(void);
+
+int run_logic(int);
+
+void agi_timer_low();
+int agi_get_keypress_low();
+int agi_is_keypress_low();
+
+} // End of namespace Agi
+
+#endif /* __AGI_H */
Property changes on: scummvm/trunk/engines/agi/agi.h
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/agi_v2.cpp
===================================================================
--- scummvm/trunk/engines/agi/agi_v2.cpp (rev 0)
+++ scummvm/trunk/engines/agi/agi_v2.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,309 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2001 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+#include "common/file.h"
+
+#include "agi/agi.h"
+
+namespace Agi {
+
+static int agi_v2_init(void);
+static int agi_v2_deinit(void);
+static int agi_v2_detect_game();
+static int agi_v2_load_resource(int, int);
+static int agi_v2_unload_resource(int, int);
+static int agi_v2_load_objects(char *);
+static int agi_v2_load_words(char *);
+
+struct agi_loader agi_v2 = {
+ 2,
+ 0,
+ agi_v2_init,
+ agi_v2_deinit,
+ agi_v2_detect_game,
+ agi_v2_load_resource,
+ agi_v2_unload_resource,
+ agi_v2_load_objects,
+ agi_v2_load_words
+};
+
+static int agi_v2_detect_game() {
+ if (!Common::File::exists(LOGDIR) ||
+ !Common::File::exists(PICDIR) ||
+ !Common::File::exists(SNDDIR) ||
+ !Common::File::exists(VIEWDIR))
+ return err_InvalidAGIFile;
+
+ agi_v2.int_version = 0x2917; /* setup for 2.917 */
+ return v2id_game();
+}
+
+static int agi_v2_load_dir(struct agi_dir *agid, char *fname) {
+ Common::File fp;
+ uint8 *mem;
+ uint32 flen;
+ unsigned int i;
+ char *path;
+
+ path = fname;
+ report("Loading directory: %s\n", path);
+
+ if ((!fp.open(path))) {
+ return err_BadFileOpen;
+ }
+
+ fp.seek(0, SEEK_END);
+ flen = fp.pos();
+ fp.seek(0, SEEK_SET);
+
+ if ((mem = (uint8 *) malloc(flen + 32)) == NULL) {
+ fp.close();
+ return err_NotEnoughMemory;
+ }
+
+ fp.read(mem, flen);
+
+ /* set all directory resources to gone */
+ for (i = 0; i < MAX_DIRS; i++) {
+ agid[i].volume = 0xff;
+ agid[i].offset = _EMPTY;
+ }
+
+ /* build directory entries */
+ for (i = 0; i < flen; i += 3) {
+ agid[i / 3].volume = *(mem + i) >> 4;
+ agid[i / 3].offset = READ_BE_UINT24(mem + i) & (uint32) _EMPTY;
+ debugC(3, kDebugLevelResources, "%d: volume %d, offset 0x%05x", i / 3, agid[i / 3].volume, agid[i / 3].offset);
+ }
+
+ free(mem);
+ fp.close();
+
+ return err_OK;
+}
+
+static int agi_v2_init() {
+ int ec = err_OK;
+
+ /* load directory files */
+ ec = agi_v2_load_dir(game.dir_logic, LOGDIR);
+ if (ec == err_OK)
+ ec = agi_v2_load_dir(game.dir_pic, PICDIR);
+ if (ec == err_OK)
+ ec = agi_v2_load_dir(game.dir_view, VIEWDIR);
+ if (ec == err_OK)
+ ec = agi_v2_load_dir(game.dir_sound, SNDDIR);
+
+ return ec;
+}
+
+static int agi_v2_deinit() {
+ int ec = err_OK;
+
+#if 0
+ /* unload words */
+ agi_v2_unload_words();
+
+ /* unload objects */
+ agi_v2_unload_objects();
+#endif
+
+ return ec;
+}
+
+static int agi_v2_unload_resource(int t, int n) {
+ debugC(3, kDebugLevelResources, "unload resource");
+
+ switch (t) {
+ case rLOGIC:
+ unload_logic(n);
+ break;
+ case rPICTURE:
+ unload_picture(n);
+ break;
+ case rVIEW:
+ unload_view(n);
+ break;
+ case rSOUND:
+ unload_sound(n);
+ break;
+ }
+
+ return err_OK;
+}
+
+/*
+ * This function does noting but load a raw resource into memory,
+ * if further decoding is required, it must be done by another
+ * routine. NULL is returned if unsucsessfull.
+ */
+static uint8 *agi_v2_load_vol_res(struct agi_dir *agid) {
+ uint8 *data = NULL;
+ char x[MAX_PATH], *path;
+ Common::File fp;
+ unsigned int sig;
+
+ sprintf(x, "vol.%i", agid->volume);
+ path = x;
+ debugC(3, kDebugLevelResources, "Vol res: path = %s", path);
+
+ if (agid->offset != _EMPTY && fp.open(path)) {
+ debugC(3, kDebugLevelResources, "loading resource at offset %d", agid->offset);
+ fp.seek(agid->offset, SEEK_SET);
+ fp.read(&x, 5);
+ if ((sig = READ_BE_UINT16((uint8 *) x)) == 0x1234) {
+ agid->len = READ_LE_UINT16((uint8 *) x + 3);
+ data = (uint8 *) calloc(1, agid->len + 32);
+ if (data != NULL) {
+ fp.read(data, agid->len);
+ } else {
+ abort();
+ }
+ } else {
+#if 0
+ /* FIXME: call some panic handler instead of
+ * deiniting directly
+ */
+ deinit_video_mode();
+#endif
+ report("Error: bad signature %04x\n", sig);
+ // fprintf (stderr, "ACK! BAD RESOURCE!!!\n");
+ return 0;
+ }
+ fp.close();
+ } else {
+ /* we have a bad volume resource */
+ /* set that resource to NA */
+ agid->offset = _EMPTY;
+ }
+
+ return data;
+}
+
+/*
+ * Loads a resource into memory, a raw resource is loaded in
+ * with above routine, then further decoded here.
+ */
+int agi_v2_load_resource(int t, int n) {
+ int ec = err_OK;
+ uint8 *data = NULL;
+
+ debugC(3, kDebugLevelResources, "(t = %d, n = %d)", t, n);
+ if (n > MAX_DIRS)
+ return err_BadResource;
+
+ switch (t) {
+ case rLOGIC:
+ if (~game.dir_logic[n].flags & RES_LOADED) {
+ debugC(3, kDebugLevelResources, "loading logic resource %d", n);
+ agi_v2.unload_resource(rLOGIC, n);
+
+ /* load raw resource into data */
+ data = agi_v2_load_vol_res(&game.dir_logic[n]);
+
+ game.logics[n].data = data;
+ ec = data ? decode_logic(n) : err_BadResource;
+
+ game.logics[n].sIP = 2;
+ }
+
+ /* if logic was cached, we get here */
+ /* reset code pointers incase it was cached */
+
+ game.logics[n].cIP = game.logics[n].sIP;
+ break;
+ case rPICTURE:
+ /* if picture is currently NOT loaded *OR* cacheing is off,
+ * unload the resource (caching == off) and reload it
+ */
+
+ debugC(3, kDebugLevelResources, "loading picture resource %d", n);
+ if (game.dir_pic[n].flags & RES_LOADED)
+ break;
+
+ /* if loaded but not cached, unload it */
+ /* if cached but not loaded, etc */
+ agi_v2.unload_resource(rPICTURE, n);
+ data = agi_v2_load_vol_res(&game.dir_pic[n]);
+
+ if (data != NULL) {
+ game.pictures[n].rdata = data;
+ game.dir_pic[n].flags |= RES_LOADED;
+ } else {
+ ec = err_BadResource;
+ }
+ break;
+ case rSOUND:
+ debugC(3, kDebugLevelResources, "loading sound resource %d", n);
+ if (game.dir_sound[n].flags & RES_LOADED)
+ break;
+
+ data = agi_v2_load_vol_res(&game.dir_sound[n]);
+
+ if (data != NULL) {
+ game.sounds[n].rdata = data;
+ game.dir_sound[n].flags |= RES_LOADED;
+ decode_sound(n);
+ } else {
+ ec = err_BadResource;
+ }
+ break;
+ case rVIEW:
+ /* Load a VIEW resource into memory...
+ * Since VIEWS alter the view table ALL the time
+ * can we cache the view? or must we reload it all
+ * the time?
+ */
+ if (game.dir_view[n].flags & RES_LOADED)
+ break;
+
+ debugC(3, kDebugLevelResources, "loading view resource %d", n);
+ agi_v2.unload_resource(rVIEW, n);
+ data = agi_v2_load_vol_res(&game.dir_view[n]);
+ if (data) {
+ game.views[n].rdata = data;
+ game.dir_view[n].flags |= RES_LOADED;
+ ec = decode_view(n);
+ } else {
+ ec = err_BadResource;
+ }
+ break;
+ default:
+ ec = err_BadResource;
+ break;
+ }
+
+ return ec;
+}
+
+static int agi_v2_load_objects(char *fname) {
+ return load_objects(fname);
+}
+
+static int agi_v2_load_words(char *fname) {
+ return load_words(fname);
+}
+
+} // End of namespace Agi
Property changes on: scummvm/trunk/engines/agi/agi_v2.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/agi_v3.cpp
===================================================================
--- scummvm/trunk/engines/agi/agi_v3.cpp (rev 0)
+++ scummvm/trunk/engines/agi/agi_v3.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,389 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2003 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+
+#include "agi/agi.h"
+#include "agi/lzw.h"
+
+#include "backends/fs/fs.h"
+
+#include "common/config-manager.h"
+
+namespace Agi {
+
+static int agi_v3_init(void);
+static int agi_v3_deinit(void);
+static int agi_v3_detect_game();
+static int agi_v3_load_resource(int, int);
+static int agi_v3_unload_resource(int, int);
+static int agi_v3_load_objects(char *);
+static int agi_v3_load_words(char *);
+
+struct agi_loader agi_v3 = {
+ 3,
+ 0,
+ agi_v3_init,
+ agi_v3_deinit,
+ agi_v3_detect_game,
+ agi_v3_load_resource,
+ agi_v3_unload_resource,
+ agi_v3_load_objects,
+ agi_v3_load_words
+};
+
+int agi_v3_detect_game() {
+ int ec = err_Unk;
+ bool found = false;
+
+ FSList fslist;
+ FilesystemNode dir(ConfMan.get("path"));
+
+ if (!dir.listDir(fslist, FilesystemNode::kListFilesOnly)) {
+ warning("AgiEngine: invalid game path '%s'",
+ dir.path().c_str());
+ return err_InvalidAGIFile;
+ }
+
+ for (FSList::const_iterator file = fslist.begin();
+ file != fslist.end() && !found; ++file) {
+ Common::String f = file->displayName();
+ f.toLowercase();
+
+ if (f.hasSuffix("vol.0")) {
+ strncpy(game.name, f.c_str(), f.size() > 5 ? f.size() - 5 : f.size());
+ debugC(3, kDebugLevelMain, "game.name = %s", game.name);
+ agi_v3.int_version = 0x3149; // setup for 3.002.149
+ ec = v3id_game();
+
+ found = true;
+ }
+ }
+
+ if (!found) {
+ debugC(3, kDebugLevelMain, "not found");
+ ec = err_InvalidAGIFile;
+ }
+
+ return ec;
+}
+
+static int agi_v3_load_dir(struct agi_dir *agid, Common::File *fp,
+ uint32 offs, uint32 len) {
+ int ec = err_OK;
+ uint8 *mem;
+ unsigned int i;
+
+ fp->seek(offs, SEEK_SET);
+ if ((mem = (uint8 *) malloc(len + 32)) != NULL) {
+ fp->read(mem, len);
+
+ /* set all directory resources to gone */
+ for (i = 0; i < MAX_DIRS; i++) {
+ agid[i].volume = 0xff;
+ agid[i].offset = _EMPTY;
+ }
+
+ /* build directory entries */
+ for (i = 0; i < len; i += 3) {
+ agid[i / 3].volume = *(mem + i) >> 4;
+ agid[i / 3].offset = READ_BE_UINT24(mem + i) & (uint32) _EMPTY;
+ }
+
+ free(mem);
+ } else {
+ ec = err_NotEnoughMemory;
+ }
+
+ return ec;
+}
+
+struct agi3vol {
+ uint32 sddr;
+ uint32 len;
+};
+
+int agi_v3_init(void) {
+ int ec = err_OK;
+ struct agi3vol agi_vol3[4];
+ int i;
+ uint16 xd[4];
+ Common::File fp;
+ Common::String path;
+
+ path = Common::String(game.name) + DIR_;
+
+ if (!fp.open(path)) {
+ printf("Failed to open \"%s\"\n", path.c_str());
+ return err_BadFileOpen;
+ }
+ /* build offset table for v3 directory format */
+ fp.read(&xd, 8);
+ fp.seek(0, SEEK_END);
+
+ for (i = 0; i < 4; i++)
+ agi_vol3[i].sddr = READ_LE_UINT16((uint8 *) & xd[i]);
+
+ agi_vol3[0].len = agi_vol3[1].sddr - agi_vol3[0].sddr;
+ agi_vol3[1].len = agi_vol3[2].sddr - agi_vol3[1].sddr;
+ agi_vol3[2].len = agi_vol3[3].sddr - agi_vol3[2].sddr;
+ agi_vol3[3].len = fp.pos() - agi_vol3[3].sddr;
+
+ if (agi_vol3[3].len > 256 * 3)
+ agi_vol3[3].len = 256 * 3;
+
+ fp.seek(0, SEEK_SET);
+
+ /* read in directory files */
+ ec = agi_v3_load_dir(game.dir_logic, &fp, agi_vol3[0].sddr,
+ agi_vol3[0].len);
+
+ if (ec == err_OK) {
+ ec = agi_v3_load_dir(game.dir_pic, &fp, agi_vol3[1].sddr, agi_vol3[1].len);
+ }
+
+ if (ec == err_OK) {
+ ec = agi_v3_load_dir(game.dir_view, &fp, agi_vol3[2].sddr, agi_vol3[2].len);
+ }
+
+ if (ec == err_OK) {
+ ec = agi_v3_load_dir(game.dir_sound, &fp, agi_vol3[3].sddr, agi_vol3[3].len);
+ }
+
+ return ec;
+}
+
+int agi_v3_deinit() {
+ int ec = err_OK;
+
+#if 0
+ /* unload words */
+ agi_v3_unload_words();
+
+ /* unload objects */
+ agi_v3_unload_objects();
+#endif
+
+ return ec;
+}
+
+int agi_v3_unload_resource(int t, int n) {
+ switch (t) {
+ case rLOGIC:
+ unload_logic(n);
+ break;
+ case rPICTURE:
+ unload_picture(n);
+ break;
+ case rVIEW:
+ unload_view(n);
+ break;
+ case rSOUND:
+ unload_sound(n);
+ break;
+ }
+
+ return err_OK;
+}
+
+/*
+ * This function does noting but load a raw resource into memory.
+ * If further decoding is required, it must be done by another
+ * routine.
+ *
+ * NULL is returned if unsucsessful.
+ */
+uint8 *agi_v3_load_vol_res(struct agi_dir *agid) {
+ char x[MAX_PATH];
+ uint8 *data = NULL, *comp_buffer;
+ Common::File fp;
+ Common::String path;
+
+ debugC(3, kDebugLevelResources, "(%p)", agid);
+ sprintf(x, "vol.%i", agid->volume);
+ path = Common::String(game.name) + x;
+
+ if (agid->offset != _EMPTY && fp.open(path)) {
+ fp.seek(agid->offset, SEEK_SET);
+ fp.read(&x, 7);
+
+ if (READ_BE_UINT16((uint8 *) x) != 0x1234) {
+#if 0
+ /* FIXME */
+ deinit_video_mode();
+#endif
+ debugC(3, kDebugLevelResources, "path = %s", path.c_str());
+ debugC(3, kDebugLevelResources, "offset = %d", agid->offset);
+ debugC(3, kDebugLevelResources, "x = %x %x", x[0], x[1]);
+ error("ACK! BAD RESOURCE");
+
+ g_system->quit();
+ }
+
+ agid->len = READ_LE_UINT16((uint8 *) x + 3); /* uncompressed size */
+ agid->clen = READ_LE_UINT16((uint8 *) x + 5); /* compressed len */
+
+ comp_buffer = (uint8 *)calloc(1, agid->clen + 32);
+ fp.read(comp_buffer, agid->clen);
+
+ if (x[2] & 0x80 || agid->len == agid->clen) {
+ /* do not decompress */
+ data = comp_buffer;
+
+#if 0
+ /* CM: added to avoid problems in
+ * convert_v2_v3_pic() when clen > len
+ * e.g. Sierra demo 4, first picture
+ * (Tue Mar 16 13:13:43 EST 1999)
+ */
+ agid->len = agid->clen;
+
+ /* Now removed to fix Gold Rush! in demo4 */
+#endif
+ } else {
+ /* it is compressed */
+ data = (uint8 *)calloc(1, agid->len + 32);
+ LZW_expand(comp_buffer, data, agid->len);
+ free(comp_buffer);
+ agid->flags |= RES_COMPRESSED;
+ }
+
+ fp.close();
+ } else {
+ /* we have a bad volume resource */
+ /* set that resource to NA */
+ agid->offset = _EMPTY;
+ }
+
+ return data;
+}
+
+/*
+ * Loads a resource into memory, a raw resource is loaded in
+ * with above routine, then further decoded here.
+ */
+int agi_v3_load_resource(int t, int n) {
+ int ec = err_OK;
+ uint8 *data = NULL;
+
+ if (n > MAX_DIRS)
+ return err_BadResource;
+
+ switch (t) {
+ case rLOGIC:
+ /* load resource into memory, decrypt messages at the end
+ * and build the message list (if logic is in memory)
+ */
+ if (~game.dir_logic[n].flags & RES_LOADED) {
+ /* if logic is already in memory, unload it */
+ agi_v3.unload_resource(rLOGIC, n);
+
+ /* load raw resource into data */
+ data = agi_v3_load_vol_res(&game.dir_logic[n]);
+ game.logics[n].data = data;
+
+ /* uncompressed logic files need to be decrypted */
+ if (data != NULL) {
+ /* resloaded flag gets set by decode logic */
+ /* needed to build string table */
+ ec = decode_logic(n);
+ game.logics[n].sIP = 2;
+ } else {
+ ec = err_BadResource;
+ }
+
+ /*logics[n].sIP=2; *//* saved IP = 2 */
+ /*logics[n].cIP=2; *//* current IP = 2 */
+
+ game.logics[n].cIP = game.logics[n].sIP;
+ }
+
+ /* if logic was cached, we get here */
+ /* reset code pointers incase it was cached */
+
+ game.logics[n].cIP = game.logics[n].sIP;
+ break;
+ case rPICTURE:
+ /* if picture is currently NOT loaded *OR* cacheing is off,
+ * unload the resource (caching==off) and reload it
+ */
+ if (~game.dir_pic[n].flags & RES_LOADED) {
+ agi_v3.unload_resource(rPICTURE, n);
+ data = agi_v3_load_vol_res(&game.dir_pic[n]);
+ if (data != NULL) {
+ data = convert_v3_pic(data, game.dir_pic[n].len);
+ game.pictures[n].rdata = data;
+ game.dir_pic[n].flags |= RES_LOADED;
+ } else {
+ ec = err_BadResource;
+ }
+ }
+ break;
+ case rSOUND:
+ if (game.dir_sound[n].flags & RES_LOADED)
+ break;
+
+ if ((data = agi_v3_load_vol_res(&game.dir_sound[n])) != NULL) {
+ game.sounds[n].rdata = data;
+ game.dir_sound[n].flags |= RES_LOADED;
+ decode_sound(n);
+ } else {
+ ec = err_BadResource;
+ }
+ break;
+ case rVIEW:
+ /* Load a VIEW resource into memory...
+ * Since VIEWS alter the view table ALL the time can we
+ * cache the view? or must we reload it all the time?
+ */
+ /* load a raw view from a VOL file into data */
+ if (game.dir_view[n].flags & RES_LOADED)
+ break;
+
+ agi_v3.unload_resource(rVIEW, n);
+ if ((data = agi_v3_load_vol_res(&game.dir_view[n])) != NULL) {
+ game.views[n].rdata = data;
+ game.dir_view[n].flags |= RES_LOADED;
+ ec = decode_view(n);
+ } else {
+ ec = err_BadResource;
+ }
+ break;
+ default:
+ ec = err_BadResource;
+ break;
+ }
+
+ return ec;
+}
+
+static int agi_v3_load_objects(char *fname) {
+ return load_objects(fname);
+}
+
+static int agi_v3_load_words(char *fname) {
+ return load_words(fname);
+}
+
+} // End of namespace Agi
Property changes on: scummvm/trunk/engines/agi/agi_v3.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/checks.cpp
===================================================================
--- scummvm/trunk/engines/agi/checks.cpp (rev 0)
+++ scummvm/trunk/engines/agi/checks.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,320 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2001 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+#include "agi/agi.h"
+
+namespace Agi {
+
+static int check_position(struct vt_entry *v) {
+ debugC(4, kDebugLevelSprites, "check position @ %d, %d", v->x_pos, v->y_pos);
+
+ if (v->x_pos < 0 ||
+ v->x_pos + v->x_size > _WIDTH ||
+ v->y_pos - v->y_size + 1 < 0 ||
+ v->y_pos >= _HEIGHT ||
+ ((~v->flags & IGNORE_HORIZON) && v->y_pos <= game.horizon)) {
+ debugC(4, kDebugLevelSprites, "check position failed: x=%d, y=%d, h=%d, w=%d",
+ v->x_pos, v->y_pos, v->x_size, v->y_size);
+ return 0;
+ }
+
+ /* MH1 needs this, but it breaks LSL1 */
+ if (agi_get_release() >= 0x3000) {
+ if (v->y_pos < v->y_size)
+ return 0;
+ }
+
+ return 1;
+}
+
+/**
+ * Check if there's another object on the way
+ */
+static int check_collision(struct vt_entry *v) {
+ struct vt_entry *u;
+
+ if (v->flags & IGNORE_OBJECTS)
+ return 0;
+
+ for (u = game.view_table; u < &game.view_table[MAX_VIEWTABLE]; u++) {
+ if ((u->flags & (ANIMATED | DRAWN)) != (ANIMATED | DRAWN))
+ continue;
+
+ if (u->flags & IGNORE_OBJECTS)
+ continue;
+
+ /* Same object, check next */
+ if (v->entry == u->entry)
+ continue;
+
+ /* No horizontal overlap, check next */
+ if (v->x_pos + v->x_size < u->x_pos ||
+ v->x_pos > u->x_pos + u->x_size)
+ continue;
+
+ /* Same y, return error! */
+ if (v->y_pos == u->y_pos)
+ goto return_1;
+
+ /* Crossed the baseline, return error! */
+ if ((v->y_pos > u->y_pos && v->y_pos2 < u->y_pos2) ||
+ (v->y_pos < u->y_pos && v->y_pos2 > u->y_pos2)) {
+ goto return_1;
+ }
+ }
+
+ return 0;
+
+ return_1:
+ debugC(4, kDebugLevelSprites, "check returns 1 (object %d)", v->entry);
+ return 1;
+}
+
+static int check_priority(struct vt_entry *v) {
+ int i, trigger, water, pass, pri;
+ uint8 *p0;
+
+ if (~v->flags & FIXED_PRIORITY) {
+ /* Priority bands */
+ v->priority = game.pri_table[v->y_pos];
+ }
+
+ trigger = 0;
+ water = 0;
+ pass = 1;
+
+ if (v->priority == 0x0f)
+ goto _check_ego;
+
+ water = 1;
+
+ p0 = &game.sbuf[v->x_pos + v->y_pos * _WIDTH];
+
+ for (i = 0; i < v->x_size; i++, p0++) {
+ pri = *p0 >> 4;
+
+ if (pri == 0) { /* unconditional black. no go at all! */
+ pass = 0;
+ break;
+ }
+
+ if (pri == 3) /* water surface */
+ continue;
+
+ water = 0;
+
+ if (pri == 1) { /* conditional blue */
+ if (v->flags & IGNORE_BLOCKS)
+ continue;
+
+ debugC(4, kDebugLevelSprites, "Blocks observed!");
+ pass = 0;
+ break;
+ }
+
+ if (pri == 2) { /* trigger */
+ debugC(4, kDebugLevelSprites, "stepped on trigger");
+#ifdef USE_CONSOLE
+ if (!debug_.ignoretriggers)
+#endif
+ trigger = 1;
+ }
+ }
+
+ if (pass) {
+ if (!water && v->flags & ON_WATER)
+ pass = 0;
+ if (water && v->flags & ON_LAND)
+ pass = 0;
+ }
+
+ _check_ego:
+ if (v->entry == 0) {
+ setflag(F_ego_touched_p2, trigger ? true : false);
+ setflag(F_ego_water, water ? true : false);
+ }
+
+ return pass;
+}
+
+/*
+ * Public functions
+ */
+
+/**
+ * Update position of objects
+ * This function updates the position of all animated, updating view
+ * table entries according to its motion type, step size, etc. The
+ * new position must be valid according to the sprite positioning
+ * rules, otherwise the previous position will be kept.
+ */
+void update_position() {
+ struct vt_entry *v;
+ int x, y, old_x, old_y, border;
+
+ game.vars[V_border_code] = 0;
+ game.vars[V_border_touch_ego] = 0;
+ game.vars[V_border_touch_obj] = 0;
+
+ for (v = game.view_table; v < &game.view_table[MAX_VIEWTABLE]; v++) {
+ if ((v->flags & (ANIMATED | UPDATE | DRAWN)) != (ANIMATED | UPDATE | DRAWN)) {
+ continue;
+ }
+
+ if (v->step_time_count != 0) {
+ if (--v->step_time_count != 0)
+ continue;
+ }
+
+ v->step_time_count = v->step_time;
+
+ x = old_x = v->x_pos;
+ y = old_y = v->y_pos;
+
+ /* If object has moved, update its position */
+ if (~v->flags & UPDATE_POS) {
+ int dx[9] = { 0, 0, 1, 1, 1, 0, -1, -1, -1 };
+ int dy[9] = { 0, -1, -1, 0, 1, 1, 1, 0, -1 };
+ x += v->step_size * dx[v->direction];
+ y += v->step_size * dy[v->direction];
+ }
+
+ /* Now check if it touched the borders */
+ border = 0;
+
+ /* Check left/right borders */
+ if (x < 0) {
+ x = 0;
+ border = 4;
+ } else if (x <= 0 && agi_get_release() == 0x3086) { /* KQ4 */
+ x = 0; /* See bug #590462 */
+ border = 4;
+ } else if (v->entry == 0 && x == 0 && v->flags & ADJ_EGO_XY) {
+ /* Extra test to walk west clicking the mouse */
+ x = 0;
+ border = 4;
+ } else if (x + v->x_size > _WIDTH) {
+ x = _WIDTH - v->x_size;
+ border = 2;
+ }
+
+ /* Check top/bottom borders. */
+ if (y - v->y_size + 1 < 0) {
+ y = v->y_size - 1;
+ border = 1;
+ } else if (y > _HEIGHT - 1) {
+ y = _HEIGHT - 1;
+ border = 3;
+ } else if ((~v->flags & IGNORE_HORIZON) && y <= game.horizon) {
+ debugC(4, kDebugLevelSprites, "y = %d, horizon = %d", y, game.horizon);
+ y = game.horizon + 1;
+ border = 1;
+ }
+
+ /* Test new position. rollback if test fails */
+ v->x_pos = x;
+ v->y_pos = y;
+ if (check_collision(v) || !check_priority(v)) {
+ v->x_pos = old_x;
+ v->y_pos = old_y;
+ border = 0;
+ fix_position(v->entry);
+ }
+
+ if (border != 0) {
+ if (v == game.view_table) {
+ game.vars[V_border_touch_ego] = border;
+ } else {
+ game.vars[V_border_code] = v->entry;
+ game.vars[V_border_touch_obj] = border;
+ }
+ if (v->motion == MOTION_MOVE_OBJ) {
+ in_destination(v);
+ }
+ }
+
+ v->flags &= ~UPDATE_POS;
+ }
+}
+
+/**
+ * Adjust position of a sprite
+ * This function adjusts the position of a sprite moving it until
+ * certain criteria is matched. According to priority and control line
+ * data, a sprite may not always appear at the location we specified.
+ * This behaviour is also known as the "Budin-Sonneveld effect".
+ *
+ * @param n view table entry number
+ */
+void fix_position(int n) {
+ struct vt_entry *v = &game.view_table[n];
+ int count, dir, size;
+
+ debugC(4, kDebugLevelSprites, "adjusting view table entry #%d (%d,%d)", n, v->x_pos, v->y_pos);
+
+ /* test horizon */
+ if ((~v->flags & IGNORE_HORIZON) && v->y_pos <= game.horizon)
+ v->y_pos = game.horizon + 1;
+
+ dir = 0;
+ count = size = 1;
+
+ while (!check_position(v) || check_collision(v) || !check_priority(v)) {
+ switch (dir) {
+ case 0: /* west */
+ v->x_pos--;
+ if (--count)
+ continue;
+ dir = 1;
+ break;
+ case 1: /* south */
+ v->y_pos++;
+ if (--count)
+ continue;
+ dir = 2;
+ size++;
+ break;
+ case 2: /* east */
+ v->x_pos++;
+ if (--count)
+ continue;
+ dir = 3;
+ break;
+ case 3: /* north */
+ v->y_pos--;
+ if (--count)
+ continue;
+ dir = 0;
+ size++;
+ break;
+ }
+
+ count = size;
+ }
+
+ debugC(4, kDebugLevelSprites, "view table entry #%d position adjusted to (%d,%d)", n, v->x_pos, v->y_pos);
+}
+
+} // End of namespace Agi
Property changes on: scummvm/trunk/engines/agi/checks.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/console.cpp
===================================================================
--- scummvm/trunk/engines/agi/console.cpp (rev 0)
+++ scummvm/trunk/engines/agi/console.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,873 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2002 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+
+#include "agi/agi.h"
+#include "agi/graphics.h"
+#include "agi/sprite.h"
+#include "agi/text.h"
+#include "agi/keyboard.h"
+#include "agi/opcodes.h"
+#include "agi/console.h"
+
+namespace Agi {
+
+#ifdef USE_CONSOLE
+
+/*
+ * The main interpreter engine has not been designed to have a console, and a few
+ * kludges were needed to make the console work. First of all, the main
+ * interpreter loop works at cycle level, not instruction level. To keep
+ * the illusion that the console is threaded, a console updating function
+ * is called from loops inside instructions such as get.string().
+ */
+
+#define CONSOLE_LINES_ONSCREEN 20
+#define CONSOLE_PROMPT "$"
+#define CONSOLE_CURSOR_HOLLOW 1
+#define CONSOLE_CURSOR_SOLID 2
+#define CONSOLE_CURSOR_EMPTY 3
+#define CONSOLE_COLOR 14
+#define CONSOLE_SCROLLUP_KEY KEY_PGUP
+#define CONSOLE_SCROLLDN_KEY KEY_PGDN
+#define CONSOLE_START_KEY KEY_HOME
+#define CONSOLE_END_KEY KEY_END
+#define CONSOLE_INPUT_SIZE 39
+
+struct console_command {
+ char cmd[8];
+ char dsc[40];
+ void (*handler) (void);
+};
+
+struct agi_console console;
+struct agi_debug debug_;
+
+/* This used to be a linked list, but we reduce total memory footprint
+ * by implementing it as a statically allocated array.
+ */
+#define MAX_CCMD 16
+static struct console_command ccmd_list[MAX_CCMD];
+static int num_ccmd = 0;
+
+static uint8 has_console = 0;
+static uint8 console_input = 0;
+
+static char *_p0, *_p1, *_p2, *_p3, *_p4, *_p5; /* FIXME: array */
+static char _p[80];
+static int _pn;
+
+/*
+ * Console line management
+ */
+
+static int first_line = 0;
+
+static void add_console_line(char *s) {
+ int last_line;
+
+ last_line = (CONSOLE_LINES_BUFFER - 1 + first_line) % CONSOLE_LINES_BUFFER;
+
+ strncpy(console.line[last_line], s, CONSOLE_LINE_SIZE);
+ first_line %= CONSOLE_LINES_BUFFER;
+}
+
+static char *get_console_line(int n) {
+ return console.line[(n + first_line) % CONSOLE_LINES_BUFFER];
+}
+
+static char *get_last_console_line() {
+ int last_line = (CONSOLE_LINES_BUFFER - 1 + first_line) % CONSOLE_LINES_BUFFER;
+
+ return console.line[last_line];
+}
+
+/*
+ * Console command parsing
+ * 'o' commands added by Shaun Jackman <sjackman at shaw.ca>, 11 Apr 2002
+ */
+
+static int console_parse(char *b) {
+ struct console_command *d;
+ int i;
+
+ for (; *b && *b == ' '; b++) {
+ } /* eat spaces */
+ for (; *b && b[strlen(b) - 1] == ' '; b[strlen(b) - 1] = 0) {
+ }
+ if (!*b)
+ return 0;
+
+ /* get or set flag/var/obj values */
+ if ((b[0] == 'f' || b[0] == 'v' || b[0] == 'o') && isdigit(b[1])) {
+ char *e;
+ int f = (int)strtoul(&b[1], &e, 10);
+ if (*e == 0) {
+ if (f >= 0 && f <= 255) {
+ switch (b[0]) {
+ case 'f':
+ report(getflag(f) ? "true\n" : "false\n");
+ break;
+ case 'v':
+ report("%3d\n", getvar(f));
+ break;
+ case 'o':
+ report("%3d]%-24s(%3d)\n", f, object_name(f), object_get_location(f));
+ break;
+ }
+ return 0;
+ }
+ return -1;
+ } else if (*e == '=') {
+ int n = (int)strtoul(e + 1, NULL, 0);
+ switch (b[0]) {
+ case 'f':
+ setflag(f, !!n);
+ break;
+ case 'v':
+ setvar(f, n);
+ break;
+ case 'o':
+ object_set_location(f, n);
+ break;
+ }
+ return 0;
+ }
+ }
+
+ /* tokenize the input line */
+ if (strchr(b, ' '))
+ strcpy(_p, strchr(b, ' ') + 1);
+ _p0 = strtok(b, " ");
+ _p1 = strtok(NULL, " ");
+ _p2 = strtok(NULL, " ");
+ _p3 = strtok(NULL, " ");
+ _p4 = strtok(NULL, " ");
+ _p5 = strtok(NULL, " ");
+
+ /* set number of parameters. ugh, must rewrite this later */
+ _pn = 5;
+ if (!_p5)
+ _pn = 4;
+ if (!_p4)
+ _pn = 3;
+ if (!_p3)
+ _pn = 2;
+ if (!_p2)
+ _pn = 1;
+ if (!_p1)
+ _pn = 0;
+
+ debugC(5, kDebugLevelMain, "number of parameters: %d", _pn);
+
+ for (i = 0; i < num_ccmd; i++) {
+ d = &ccmd_list[i];
+ if (!strcmp(_p0, d->cmd) && d->handler) {
+ d->handler();
+ return 0;
+ }
+ }
+
+ for (i = 0; logic_names_cmd[i].name; i++) {
+ if (!strcmp(_p0, logic_names_cmd[i].name)) {
+ uint8 p[16];
+ if (_pn != logic_names_cmd[i].num_args) {
+ report("AGI command wants %d arguments\n", logic_names_cmd[i].num_args);
+ return 0;
+ }
+ p[0] = _p1 ? (char)strtoul(_p1, NULL, 0) : 0;
+ p[1] = _p2 ? (char)strtoul(_p2, NULL, 0) : 0;
+ p[2] = _p3 ? (char)strtoul(_p3, NULL, 0) : 0;
+ p[3] = _p4 ? (char)strtoul(_p4, NULL, 0) : 0;
+ p[4] = _p5 ? (char)strtoul(_p5, NULL, 0) : 0;
+
+ debugC(5, kDebugLevelMain, "ccmd: %s %d %d %d", logic_names_cmd[i].name, p[0], p[1], p[2]);
+
+ execute_agi_command(i, p);
+
+ return 0;
+ }
+ }
+
+ return -1;
+}
+
+/*
+ * Console commands
+ */
+
+static void ccmd_help() {
+ int i;
+
+ if (!_p1) {
+ report("Command Description\n");
+ report("------- --------------------------------\n");
+ for (i = 0; i < num_ccmd; i++)
+ report("%-8s%s\n", ccmd_list[i].cmd, ccmd_list[i].dsc);
+ return;
+ }
+
+ for (i = 0; i < num_ccmd; i++) {
+ if (!strcmp(ccmd_list[i].cmd, _p1) && ccmd_list[i].handler) {
+ report("%s\n", ccmd_list[i].dsc);
+ return;
+ }
+ }
+
+ report("Unknown command or no help available\n");
+
+ return;
+}
+
+static void ccmd_ver() {
+ report(VERSION "\n");
+ return;
+}
+
+static void ccmd_crc() {
+ char name[80];
+ report("0x%05x\n", game.crc);
+ if (match_crc(game.crc, name, 80))
+ report("%s\n", name);
+ else
+ report("Unknown game\n");
+ return;
+}
+
+static void ccmd_quit() {
+ deinit_video();
+ /* deinit_machine (); */
+ exit(0);
+}
+
+#if 0
+static void ccmd_exec() {
+ if (game.state < STATE_LOADED) {
+ report("No game loaded.\n");
+ return;
+ }
+
+ if (game.state >= STATE_RUNNING) {
+ report("Game already running.\n");
+ return;
+ }
+
+ report("Executing AGI game.\n");
+ game.state = STATE_RUNNING;
+}
+#endif
+
+#ifdef USE_HIRES
+
+static void ccmd_hires() {
+ if (_pn != 1 || (strcmp(_p1, "on") && strcmp(_p1, "off"))) {
+ report("Usage: hires on|off\n");
+ return;
+ }
+
+ opt.hires = !strcmp(_p1, "on");
+ erase_both();
+ show_pic();
+ blit_both();
+ return;
+}
+
+#endif
+
+static void ccmd_agiver() {
+ int ver, maj, min;
+
+ ver = agi_get_release();
+ maj = (ver >> 12) & 0xf;
+ min = ver & 0xfff;
+
+ report(maj <= 2 ? "%x.%03x\n" : "%x.002.%03x\n", maj, min);
+ return;
+}
+
+static void ccmd_flags() {
+ int i, j;
+
+ report(" ");
+ for (j = 0; j < 10; j++)
+ report("%d ", j);
+ report("\n");
+
+ for (i = 0; i < 255;) {
+ report("%3d ", i);
+ for (j = 0; j < 10; j++, i++) {
+ report("%c ", getflag(i) ? 'T' : 'F');
+ }
+ report("\n");
+ }
+ return;
+}
+
+static void ccmd_vars() {
+ int i, j;
+
+ for (i = 0; i < 255;) {
+ for (j = 0; j < 5; j++, i++) {
+ report("%03d:%3d ", i, getvar(i));
+ }
+ report("\n");
+ }
+ return;
+}
+
+#if 0
+
+static void ccmd_say() {
+ setflag(F_entered_cli, true);
+ dictionary_words(_p);
+}
+
+static void ccmd_inv() {
+ unsigned int i, j;
+
+ for (j = i = 0; i < game.num_objects; i++) {
+ if (object_get_location(i) == EGO_OWNED) {
+ report("%3d]%-16.16s", i, object_name(i));
+ if (j % 2)
+ report("\n");
+ j++;
+ }
+ }
+ if (j == 0) {
+ report("none\n");
+ return;
+ }
+ if (j % 2)
+ report("\n");
+}
+
+#endif
+
+static void ccmd_objs() {
+ unsigned int i;
+
+ for (i = 0; i < game.num_objects; i++) {
+ report("%3d]%-24s(%3d)\n", i, object_name(i), object_get_location(i));
+ }
+ return;
+}
+
+static void ccmd_opcode() {
+ if (_pn != 1 || (strcmp(_p1, "on") && strcmp(_p1, "off"))) {
+ report("Usage: opcode on|off\n");
+ return;
+ }
+
+ debug_.opcodes = !strcmp(_p1, "on");
+ return;
+}
+
+static void ccmd_logic0() {
+ if (_pn != 1 || (strcmp(_p1, "on") && strcmp(_p1, "off"))) {
+ report("Usage: logic0 on|off\n");
+ return;
+ }
+
+ debug_.logic0 = !strcmp(_p1, "on");
+ return;
+}
+
+static void ccmd_trigger() {
+ if (_pn != 1 || (strcmp(_p1, "on") && strcmp(_p1, "off"))) {
+ report("Usage: trigger on|off\n");
+ return;
+ }
+
+ debug_.ignoretriggers = strcmp(_p1, "on");
+ return;
+}
+
+static void ccmd_step() {
+ debug_.enabled = 1;
+
+ if (_pn == 0) {
+ debug_.steps = 1;
+ return;
+ }
+
+ debug_.steps = strtoul(_p1, NULL, 0);
+ return;
+}
+
+static void ccmd_debug() {
+ debug_.enabled = 1;
+ debug_.steps = 0;
+ return;
+}
+
+static void ccmd_cont() {
+ debug_.enabled = 0;
+ debug_.steps = 0;
+ return;
+}
+
+/*
+ * Register console commands
+ */
+static void console_cmd(char *cmd, char *dsc, void (*handler) (void)) {
+ assert(num_ccmd < MAX_CCMD);
+
+ strcpy(ccmd_list[num_ccmd].cmd, cmd);
+ strcpy(ccmd_list[num_ccmd].dsc, dsc);
+ ccmd_list[num_ccmd].handler = handler;
+
+ num_ccmd++;
+}
+
+/* Console reporting */
+
+/* A slightly modified strtok() for report() */
+static char *get_token(char *s, char d) {
+ static char *x;
+ char *n, *m;
+
+ if (s)
+ x = s;
+
+ m = x;
+ n = strchr(x, d);
+
+ if (n) {
+ *n = 0;
+ x = n + 1;
+ } else {
+ x = strchr(x, 0);
+ }
+
+ return m;
+}
+
+static void build_console_lines(int n) {
+ int j, y1;
+ char *line;
+
+ clear_console_screen(GFX_HEIGHT - n * 10);
+
+ for (j = CONSOLE_LINES_ONSCREEN - n; j < CONSOLE_LINES_ONSCREEN; j++) {
+ line = get_console_line(console.first_line + j);
+ print_text_console(line, 0, j, strlen(line) + 1, CONSOLE_COLOR, 0);
+ }
+
+ y1 = console.y - n * 10;
+ if (y1 < 0)
+ y1 = 0;
+
+ /* CM:
+ * This will cause blinking when using menus+console, but this
+ * function is called by report() which can be called from any
+ * point with or without sprites placed. If we protect the
+ * flush_block() call with redraw/release sprites cloning will
+ * happen when activating the console. This could be fixed by
+ * keeping a control flag in redraw/release to not do the
+ * actions twice, but I don't want to do that -- not yet.
+ */
+ flush_block(0, y1, GFX_WIDTH - 1, console.y);
+}
+
+/*
+ * Public functions
+ */
+
+int console_init() {
+ console_cmd("agiver", "Show emulated Sierra AGI version", ccmd_agiver);
+ console_cmd("cont", "Resume interpreter execution", ccmd_cont);
+ console_cmd("debug", "Stop interpreter execution", ccmd_debug);
+ console_cmd("crc", "Show AGI game CRC", ccmd_crc);
+#if 0
+ console_cmd("exec", "Execute loaded AGI game", ccmd_exec);
+#endif
+ console_cmd("flags", "Dump all AGI flags", ccmd_flags);
+ console_cmd("help", "List available commands", ccmd_help);
+#ifdef USE_HIRES
+ console_cmd("hires", "Turn hi-res mode on/off", ccmd_hires);
+#endif
+ console_cmd("logic0", "Turn logic 0 debugging on/off", ccmd_logic0);
+ console_cmd("objs", "List all objects and locations", ccmd_objs);
+ console_cmd("opcode", "Turn opcodes on/off in debug", ccmd_opcode);
+ console_cmd("quit", "Quit the interpreter", ccmd_quit);
+#if 0
+ console_cmd("inv", "List current inventory", ccmd_inv);
+ console_cmd("say", "Pass argument to the AGI parser", ccmd_say);
+#endif
+ console_cmd("step", "Execute the next AGI instruction", ccmd_step);
+ console_cmd("trigger", "Turn trigger lines on/off", ccmd_trigger);
+ console_cmd("vars", "Dump all AGI variables", ccmd_vars);
+ console_cmd("ver", "Show interpreter version", ccmd_ver);
+
+ console.active = 1;
+ console.input_active = 1;
+ console.index = 0;
+ console.max_y = 150;
+ console.y = console.max_y;
+ console.first_line = CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN;
+
+ debug_.enabled = 0;
+ debug_.opcodes = 0;
+ debug_.logic0 = 1;
+ debug_.priority = 0;
+
+ has_console = 1;
+ clear_screen(0);
+
+ return err_OK;
+}
+
+static void build_console_layer() {
+ build_console_lines(console.max_y / 10);
+}
+
+void report(char *message, ...) {
+ char x[512], y[512], z[64], *msg, *n;
+ va_list args;
+ int i, s, len;
+
+ if (!has_console)
+ return;
+
+ va_start(args, message);
+#ifdef HAVE_VSNPRINTF
+ vsnprintf(y, 510, (char *)message, args);
+#else
+ vsprintf(y, (char *)message, args);
+#endif
+ va_end(args);
+
+ if (console_input) {
+ strcpy(z, get_last_console_line());
+ strcpy(x, ">");
+ } else {
+ strcpy(x, get_last_console_line());
+ }
+
+ strcat(x, y);
+
+ len = 40;
+ msg = n = word_wrap_string(x, &len);
+
+ for (s = 1; *n; n++)
+ if (*n == '\n')
+ s++;
+
+ add_console_line(get_token(msg, '\n'));
+ for (i = 1; i < s; i++) {
+ first_line++;
+ n = get_token(NULL, '\n');
+ add_console_line(n);
+ }
+
+ console.first_line = CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN;
+
+ if (console_input) {
+ add_console_line(z);
+ }
+
+ /* Build layer */
+ if (console.y) {
+ if (s > 1)
+ build_console_layer();
+ else
+ build_console_lines(1);
+ }
+
+ free(msg);
+
+ do_update();
+}
+
+void console_cycle() {
+ static int old_y = 0;
+ static int blink = 0;
+ static char cursor[] = " ";
+
+ /* If no game has been loaded, keep the console visible! */
+ if (game.state < STATE_RUNNING) {
+ console.active = 1;
+ console.count = 10;
+ }
+
+ /* Initial console auto-hide timer */
+ if (console.count > 0)
+ console.count--;
+ if (console.count == 0) {
+ console.active = 0;
+ console.count = -1;
+ }
+
+ if (console.active) {
+ if (console.y < console.max_y)
+ console.y += 15;
+ else
+ console.y = console.max_y;
+ } else {
+ console.count = -1;
+
+ if (console.y > 0)
+ console.y -= 15;
+ else
+ console.y = 0;
+ }
+
+ /* console shading animation */
+ if (old_y != console.y) {
+ int y = console.y;
+ if (old_y > console.y) {
+ /* going up */
+ y = old_y;
+ }
+ flush_block(0, 0, GFX_WIDTH - 1, y);
+ old_y = console.y;
+ }
+
+ blink++;
+ blink %= 16;
+ if (console.input_active) {
+ *cursor = blink < 8 ?
+ CONSOLE_CURSOR_SOLID : CONSOLE_CURSOR_EMPTY;
+ } else {
+ *cursor = CONSOLE_CURSOR_HOLLOW;
+ }
+ if (console.y > 0
+ && console.first_line ==
+ CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN) {
+ int16 y1 = console.y - 10, y2 = console.y - 1;
+ if (y1 < 0)
+ y1 = 0;
+ if (y2 < 0)
+ y2 = 0;
+ print_text_console(cursor, (1 + console.index), 19, 2, CONSOLE_COLOR, 0);
+ flush_block((1 + console.index) * 8, y1, (1 + console.index) * 8 + 7, y2 - 1);
+ }
+
+ do_update();
+}
+
+/* Return true if key was handled */
+int console_keyhandler(int k) {
+ static char buffer[CONSOLE_INPUT_SIZE];
+ int16 y1, y2;
+ char m[2];
+
+#ifdef USE_MOUSE
+ /* Right button switches console on/off */
+ if (!opt.agimouse) /* AGI Mouse uses right button */
+ if (k == BUTTON_RIGHT)
+ k = CONSOLE_ACTIVATE_KEY;
+#endif
+
+ if (!console.active) {
+ if (k == CONSOLE_ACTIVATE_KEY) {
+ console.active = 1;
+ return true;
+ }
+ return false;
+ }
+
+ if (!console.input_active) {
+ if (k == CONSOLE_SWITCH_KEY) {
+ console.input_active = 1;
+ return true;
+ }
+ if (k == CONSOLE_ACTIVATE_KEY) {
+ console.active = 0;
+ return true;
+ }
+ return false;
+ }
+
+ y1 = console.y - 10;
+ y2 = console.y - 1;
+
+ if (y1 < 0)
+ y1 = 0;
+ if (y2 < 0)
+ y2 = 0;
+
+#ifdef USE_MOUSE
+ /* Ignore left button in console */
+ if (k == BUTTON_LEFT)
+ return true;
+#endif
+
+ /* this code breaks scrolling up, maybe it shoud only be executed
+ * in the default case?
+ */
+ if (k) {
+ /* make sure it's not enter or a scroll key */
+ if ((k != KEY_ENTER) && (k != CONSOLE_SCROLLUP_KEY) && (k != CONSOLE_SCROLLDN_KEY)
+ && (k != CONSOLE_START_KEY)) {
+ /* on any other input reset the console to the bottom */
+ if (console.first_line != CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN) {
+ console.first_line = CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN;
+ build_console_layer();
+ }
+ console.count = -1;
+ }
+ }
+
+ switch (k) {
+ case KEY_ENTER:
+ console_lock();
+ console.index = 0;
+ report("\n");
+
+ if (console_parse(buffer) != 0)
+ report("What? Where?\n");
+
+ buffer[0] = 0;
+ console_prompt();
+ break;
+ case KEY_BACKSPACE:{
+ char *x;
+ if (!console.index)
+ break;
+ x = get_last_console_line();
+ x[console.index] = 0;
+ *m = CONSOLE_CURSOR_EMPTY;
+ print_text_console(m, (console.index + 1), 19, 2, CONSOLE_COLOR, 0);
+ flush_block((console.index + 1) * CHAR_COLS, y1, (console.index + 1 + 1) * CHAR_COLS - 1, y2);
+ console.index--;
+ buffer[console.index] = 0;
+ }
+ break;
+ case CONSOLE_ACTIVATE_KEY:
+ console.active = !console.active;
+ if (console.active)
+ build_console_layer();
+ break;
+ case CONSOLE_SWITCH_KEY:
+ console.count = -1;
+ if (console.y)
+ console.input_active = !console.input_active;
+ break;
+ case CONSOLE_SCROLLUP_KEY:
+ console.count = -1;
+ if (!console.y)
+ break;
+ if (console.first_line > (CONSOLE_LINES_ONSCREEN / 2))
+ console.first_line -= CONSOLE_LINES_ONSCREEN / 2;
+ else
+ console.first_line = 0;
+ build_console_layer();
+ break;
+ case CONSOLE_SCROLLDN_KEY:
+ console.count = -1;
+ if (!console.y)
+ break;
+ if (console.first_line < (CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN - CONSOLE_LINES_ONSCREEN / 2))
+ console.first_line += CONSOLE_LINES_ONSCREEN / 2;
+ else
+ console.first_line = CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN;
+ build_console_layer();
+ break;
+ case CONSOLE_START_KEY:
+ console.count = -1;
+ if (console.y)
+ console.first_line = 0;
+ break;
+ case CONSOLE_END_KEY:
+ console.count = -1;
+ if (console.y)
+ console.first_line = CONSOLE_LINES_BUFFER - CONSOLE_LINES_ONSCREEN;
+ break;
+ default:
+ if (k >= 0x20 && k <= 0x7f && (console.index < CONSOLE_INPUT_SIZE - 2)) {
+ char l[42];
+ buffer[console.index] = k;
+ *m = k;
+ m[1] = 0;
+ console.index++;
+
+ sprintf(l, "%s%c", get_last_console_line(), k);
+ strncpy(get_last_console_line(), l, CONSOLE_LINE_SIZE);
+
+ buffer[console.index] = 0;
+ print_text_console(m, console.index, 19, 2, CONSOLE_COLOR, 0);
+ flush_block(console.index * 8, y1, console.index * 8 + 7, y2);
+ }
+ break;
+ }
+
+ do_update();
+
+ return true;
+}
+
+void console_prompt() {
+ report(CONSOLE_PROMPT);
+ console_input = 1;
+}
+
+void console_lock() {
+ console_input = 0;
+}
+
+#else
+
+void *debug;
+
+void report(char *message, ...) {
+ /* dummy */
+}
+
+int console_init() {
+ return 0;
+}
+
+/* Date: Sun, 14 Oct 2001 23:02:02 -0700
+ * From: Vasyl Tsvirkunov <vasyl at pacbell.net>
+ *
+ * This one was rather harmless and affected only builds without console.
+ * In SQ1&2 (and likely some others) name entry screen did not update
+ * properly. The bug caused by implicit assumption in cycle.c that
+ * console_cycle() updates the screen. Well, it does, if console is enabled.
+ * The fix is simple. In the second version of console_cycle() in console.c
+ * (the "dummy" one) add call to do_update(). The thing raises some
+ * questions about overall architecture of main cycle, but otherwise the fix
+ * works just fine.
+ */
+void console_cycle() {
+ do_update();
+}
+
+void console_lock() {
+ /* dummy */
+}
+
+void console_prompt() {
+ /* dummy */
+}
+
+int console_keyhandler(int i) {
+ return false;
+}
+
+#endif /* USE_CONSOLE */
+
+} // End of namespace Agi
Property changes on: scummvm/trunk/engines/agi/console.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/console.h
===================================================================
--- scummvm/trunk/engines/agi/console.h (rev 0)
+++ scummvm/trunk/engines/agi/console.h 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,71 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2001 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#ifndef __AGI_CONSOLE_H
+#define __AGI_CONSOLE_H
+
+namespace Agi {
+
+#ifdef USE_CONSOLE
+
+#define CONSOLE_LINES_BUFFER 80
+#define CONSOLE_LINE_SIZE (GFX_WIDTH / 8)
+#define CONSOLE_ACTIVATE_KEY '`'
+#define CONSOLE_SWITCH_KEY '~'
+
+struct agi_console {
+ int active;
+ int input_active;
+ int index;
+ int y;
+ int max_y;
+ int first_line;
+ int count;
+ char *line[CONSOLE_LINES_BUFFER];
+};
+
+struct agi_debug {
+ int enabled;
+ int opcodes;
+ int logic0;
+ int steps;
+ int priority;
+ int statusline;
+ int ignoretriggers;
+};
+
+extern struct agi_console console;
+
+#endif /* USE_CONSOLE */
+
+int console_keyhandler(int);
+int console_init(void);
+void console_cycle(void);
+void console_lock(void);
+void console_prompt(void);
+void report(char *, ...);
+
+} // End of namespace Agi
+
+#endif /* __AGI_CONSOLE_H */
Property changes on: scummvm/trunk/engines/agi/console.h
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/cycle.cpp
===================================================================
--- scummvm/trunk/engines/agi/cycle.cpp (rev 0)
+++ scummvm/trunk/engines/agi/cycle.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,423 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2003 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+
+#include "agi/agi.h"
+#include "agi/text.h"
+#include "agi/sprite.h"
+#include "agi/graphics.h"
+#include "agi/keyboard.h"
+#include "agi/menu.h"
+#include "agi/savegame.h"
+
+namespace Agi {
+
+#define TICK_SECONDS 20
+
+#ifdef USE_MOUSE
+struct mouse mouse;
+#endif
+
+volatile uint32 clock_ticks;
+volatile uint32 clock_count;
+
+/**
+ * Set up new room.
+ * This function is called when ego enters a new room.
+ * @param n room number
+ */
+void new_room(int n) {
+ struct vt_entry *v;
+ int i;
+
+ debugC(4, kDebugLevelMain, "*** room %d ***", n);
+ stop_sound();
+
+ i = 0;
+ for (v = game.view_table; v < &game.view_table[MAX_VIEWTABLE]; v++) {
+ v->entry = i++;
+ v->flags &= ~(ANIMATED | DRAWN);
+ v->flags |= UPDATE;
+ v->step_time = 1;
+ v->step_time_count = 1;
+ v->cycle_time = 1;
+ v->cycle_time_count = 1;
+ v->step_size = 1;
+ }
+ agi_unload_resources();
+
+ game.player_control = true;
+ game.block.active = false;
+ game.horizon = 36;
+ game.vars[V_prev_room] = game.vars[V_cur_room];
+ game.vars[V_cur_room] = n;
+ game.vars[V_border_touch_obj] = 0;
+ game.vars[V_border_code] = 0;
+ game.vars[V_ego_view_resource] = game.view_table[0].current_view;
+
+ agi_load_resource(rLOGIC, n);
+
+ /* Reposition ego in the new room */
+ switch (game.vars[V_border_touch_ego]) {
+ case 1:
+ game.view_table[0].y_pos = _HEIGHT - 1;
+ break;
+ case 2:
+ game.view_table[0].x_pos = 0;
+ break;
+ case 3:
+ game.view_table[0].y_pos = HORIZON + 1;
+ break;
+ case 4:
+ game.view_table[0].x_pos = _WIDTH - game.view_table[0].x_size;
+ break;
+ }
+
+ game.vars[V_border_touch_ego] = 0;
+ setflag(F_new_room_exec, true);
+
+ game.exit_all_logics = true;
+
+ write_status();
+ write_prompt();
+}
+
+static void reset_controllers() {
+ int i;
+
+ for (i = 0; i < MAX_DIRS; i++) {
+ game.ev_keyp[i].occured = false;
+ }
+}
+
+static void interpret_cycle() {
+ int old_sound, old_score;
+
+ if (game.player_control)
+ game.vars[V_ego_dir] = game.view_table[0].direction;
+ else
+ game.view_table[0].direction = game.vars[V_ego_dir];
+
+ check_all_motions();
+
+ old_score = game.vars[V_score];
+ old_sound = getflag(F_sound_on);
+
+ game.exit_all_logics = false;
+ while (run_logic(0) == 0 && !game.quit_prog_now) {
+ game.vars[V_word_not_found] = 0;
+ game.vars[V_border_touch_obj] = 0;
+ game.vars[V_border_code] = 0;
+ old_score = game.vars[V_score];
+ setflag(F_entered_cli, false);
+ game.exit_all_logics = false;
+ reset_controllers();
+ }
+ reset_controllers();
+
+ game.view_table[0].direction = game.vars[V_ego_dir];
+
+ if (game.vars[V_score] != old_score || getflag(F_sound_on) != old_sound)
+ write_status();
+
+ game.vars[V_border_touch_obj] = 0;
+ game.vars[V_border_code] = 0;
+ setflag(F_new_room_exec, false);
+ setflag(F_restart_game, false);
+ setflag(F_restore_just_ran, false);
+
+ if (game.gfx_mode) {
+ update_viewtable();
+ do_update();
+ }
+}
+
+/**
+ * Update AGI interpreter timer.
+ */
+void update_timer() {
+ clock_count++;
+ if (clock_count <= TICK_SECONDS)
+ return;
+
+ clock_count -= TICK_SECONDS;
+
+ if (!game.clock_enabled)
+ return;
+
+ setvar(V_seconds, getvar(V_seconds) + 1);
+ if (getvar(V_seconds) < 60)
+ return;
+
+ setvar(V_seconds, 0);
+ setvar(V_minutes, getvar(V_minutes) + 1);
+ if (getvar(V_minutes) < 60)
+ return;
+
+ setvar(V_minutes, 0);
+ setvar(V_hours, getvar(V_hours) + 1);
+ if (getvar(V_hours) < 24)
+ return;
+
+ setvar(V_hours, 0);
+ setvar(V_days, getvar(V_days) + 1);
+}
+
+static int old_mode = -1;
+
+void new_input_mode(int i) {
+ old_mode = game.input_mode;
+ game.input_mode = i;
+}
+
+void old_input_mode() {
+ game.input_mode = old_mode;
+}
+
+/* If main_cycle returns false, don't process more events! */
+int main_cycle() {
+ unsigned int key, kascii;
+ struct vt_entry *v = &game.view_table[0];
+
+ poll_timer(); /* msdos driver -> does nothing */
+ update_timer();
+
+ if (game.ver == 0) {
+ message_box("Warning: game CRC not listed, assuming AGI version 2.917.");
+ game.ver = -1;
+ }
+
+ key = do_poll_keyboard();
+
+#ifdef USE_MOUSE
+ /* In AGI Mouse emulation mode we must update the mouse-related
+ * vars in every interpreter cycle.
+ */
+ if (opt.agimouse) {
+ game.vars[28] = mouse.x / 2;
+ game.vars[29] = mouse.y;
+ }
+#endif
+
+#ifdef USE_CONSOLE
+ if (key == KEY_PRIORITY) {
+ erase_both();
+ debug_.priority = !debug_.priority;
+ show_pic();
+ blit_both();
+ commit_both();
+ key = 0;
+ }
+
+ if (key == KEY_STATUSLN) {
+ debug_.statusline = !debug_.statusline;
+ write_status();
+ key = 0;
+ }
+#endif
+
+ /* Click-to-walk mouse interface */
+ if (game.player_control && v->flags & ADJ_EGO_XY) {
+ v->direction = get_direction(v->x_pos, v->y_pos, v->parm1, v->parm2, v->step_size);
+
+ if (v->direction == 0)
+ in_destination(v);
+ }
+
+ kascii = KEY_ASCII(key);
+
+ if (!console_keyhandler(key)) {
+ if (kascii)
+ setvar(V_key, kascii);
+ process_key:
+ switch (game.input_mode) {
+ case INPUT_NORMAL:
+ if (!handle_controller(key)) {
+ if (key == 0 || !game.input_enabled)
+ break;
+ handle_keys(key);
+
+ /* if ESC pressed, activate menu before
+ * accept.input from the interpreter cycle
+ * sets the input mode to normal again
+ * (closes: #540856)
+ */
+ if (key == KEY_ESCAPE) {
+ key = 0;
+ goto process_key;
+ }
+
+ /* commented out to close bug #438872
+ * if (key) game.keypress = key;
+ */
+ }
+ break;
+ case INPUT_GETSTRING:
+ handle_controller(key);
+ handle_getstring(key);
+ setvar(V_key, 0); /* clear ENTER key */
+ break;
+ case INPUT_MENU:
+ menu_keyhandler(key);
+ console_cycle();
+ return false;
+ case INPUT_NONE:
+ handle_controller(key);
+ if (key)
+ game.keypress = key;
+ break;
+ }
+ } else {
+ if (game.input_mode == INPUT_MENU) {
+ console_cycle();
+ return false;
+ }
+ }
+
+ console_cycle();
+
+ if (game.msg_box_ticks > 0)
+ game.msg_box_ticks--;
+
+ return true;
+}
+
+static int play_game() {
+ int ec = err_OK;
+
+ debugC(2, kDebugLevelMain, "initializing...");
+ debugC(2, kDebugLevelMain, "game.ver = 0x%x", game.ver);
+
+ stop_sound();
+ clear_screen(0);
+
+ game.horizon = HORIZON;
+ game.player_control = false;
+
+ setflag(F_logic_zero_firsttime, true); /* not in 2.917 */
+ setflag(F_new_room_exec, true); /* needed for MUMG and SQ2! */
+ setflag(F_sound_on, true); /* enable sound */
+ setvar(V_time_delay, 2); /* "normal" speed */
+
+ game.gfx_mode = true;
+ game.quit_prog_now = false;
+ game.clock_enabled = true;
+ game.line_user_input = 22;
+
+#ifdef USE_MOUSE
+ if (opt.agimouse)
+ report("Using AGI Mouse 1.0 protocol\n");
+#endif
+
+ report("Running AGI script.\n");
+
+#ifdef USE_CONSOLE
+ console.count = 5;
+ console_prompt();
+#endif
+
+ setflag(F_entered_cli, false);
+ setflag(F_said_accepted_input, false);
+ game.vars[V_word_not_found] = 0;
+ game.vars[V_key] = 0;
+
+ debugC(2, kDebugLevelMain, "Entering main loop");
+ do {
+
+ if (!main_cycle())
+ continue;
+
+ if (getvar(V_time_delay) == 0 ||
+ (1 + clock_count) % getvar(V_time_delay) == 0) {
+ if (!game.has_prompt && game.input_mode == INPUT_NORMAL) {
+ write_prompt();
+ game.has_prompt = 1;
+ } else
+ if (game.has_prompt && game.input_mode == INPUT_NONE) {
+ write_prompt();
+ game.has_prompt = 0;
+ }
+
+ interpret_cycle();
+
+ setflag(F_entered_cli, false);
+ setflag(F_said_accepted_input, false);
+ game.vars[V_word_not_found] = 0;
+ game.vars[V_key] = 0;
+ }
+
+ if (game.quit_prog_now == 0xff)
+ ec = err_RestartGame;
+
+ } while (game.quit_prog_now == 0);
+
+ stop_sound();
+
+ return ec;
+}
+
+int run_game() {
+ int i, ec = err_OK;
+
+#ifdef USE_HIRES
+ if (opt.cgaemu)
+ opt.hires = 0;
+#endif
+
+ for (i = 0; i < MAX_DIRS; i++)
+ memset(&game.ev_keyp[i], 0, sizeof(struct agi_event));
+
+ /* Execute the game */
+ do {
+ debugC(2, kDebugLevelMain, "game loop");
+ debugC(2, kDebugLevelMain, "game.ver = 0x%x", game.ver);
+
+ if (agi_init() != err_OK)
+ break;
+ if (ec == err_RestartGame)
+ setflag(F_restart_game, true);
+
+ setvar(V_computer, 0); /* IBM PC (4 = Atari ST) */
+ setvar(V_soundgen, 1); /* IBM PC SOUND */
+ setvar(V_monitor, 0x3); /* EGA monitor */
+ setvar(V_max_input_chars, 38);
+ game.input_mode = INPUT_NONE;
+ game.input_enabled = 0;
+ game.has_prompt = 0;
+
+ game.state = STATE_RUNNING;
+ ec = play_game();
+ game.state = STATE_LOADED;
+ agi_deinit();
+ } while (ec == err_RestartGame);
+
+ menu_deinit();
+
+ release_image_stack();
+
+ return ec;
+}
+
+} // End of namespace Agi
Property changes on: scummvm/trunk/engines/agi/cycle.cpp
___________________________________________________________________
Name: svn:mime-type
+ text/plain
Name: svn:keywords
+ Date Rev Author URL Id
Name: svn:eol-style
+ native
Added: scummvm/trunk/engines/agi/font.cpp
===================================================================
--- scummvm/trunk/engines/agi/font.cpp (rev 0)
+++ scummvm/trunk/engines/agi/font.cpp 2006-05-23 23:43:52 UTC (rev 22588)
@@ -0,0 +1,295 @@
+/* ScummVM - Scumm Interpreter
+ * Copyright (C) 2006 The ScummVM project
+ *
+ * Copyright (C) 1999-2001 Sarien Team
+ *
+ * This program 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; either version 2
+ * of the License, or (at your option) any later version.
+
+ * This program 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. See the
+ * GNU General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * $URL$
+ * $Id$
+ *
+ */
+
+#include "common/stdafx.h"
+
+#include "agi/agi.h"
+
+namespace Agi {
+
+/* 8x8 font patterns */
+uint8 cur_font[] = {
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x7E, 0x42, 0x42, 0x42, 0x42, 0x42, 0x42, 0x7E, /* cursor hollow */
+ 0x7E, 0x7E, 0x7E, 0x7E, 0x7E, 0x7E, 0x7E, 0x7E, /* cursor solid */
@@ Diff output truncated at 100000 characters. @@
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
More information about the Scummvm-git-logs
mailing list