SWF_ScriptFunction.h (7087B)
1 /* 2 =========================================================================== 3 4 Doom 3 BFG Edition GPL Source Code 5 Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company. 6 7 This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code"). 8 9 Doom 3 BFG Edition Source Code is free software: you can redistribute it and/or modify 10 it under the terms of the GNU General Public License as published by 11 the Free Software Foundation, either version 3 of the License, or 12 (at your option) any later version. 13 14 Doom 3 BFG Edition Source Code is distributed in the hope that it will be useful, 15 but WITHOUT ANY WARRANTY; without even the implied warranty of 16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 GNU General Public License for more details. 18 19 You should have received a copy of the GNU General Public License 20 along with Doom 3 BFG Edition Source Code. If not, see <http://www.gnu.org/licenses/>. 21 22 In addition, the Doom 3 BFG Edition Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the Doom 3 BFG Edition Source Code. If not, please request a copy in writing from id Software at the address below. 23 24 If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA. 25 26 =========================================================================== 27 */ 28 #ifndef __SWF_SCRIPTFUNCTION_H__ 29 #define __SWF_SCRIPTFUNCTION_H__ 30 31 /* 32 ======================== 33 Interface for calling functions from script 34 ======================== 35 */ 36 class idSWFScriptFunction { 37 public: 38 virtual ~idSWFScriptFunction() {}; 39 40 virtual idSWFScriptVar Call( idSWFScriptObject * thisObject, const idSWFParmList & parms ){ return idSWFScriptVar(); }; // this should never be hit 41 virtual void AddRef(){}; 42 virtual void Release(){}; 43 virtual idSWFScriptObject *GetPrototype() { return NULL; } 44 virtual void SetPrototype( idSWFScriptObject * _object ) { } 45 }; 46 47 /* 48 ======================== 49 Interface for calling functions from script, implemented statically 50 ======================== 51 */ 52 class idSWFScriptFunction_Static : public idSWFScriptFunction { 53 public: 54 idSWFScriptFunction_Static() { } 55 virtual void AddRef() { } 56 virtual void Release() { } 57 }; 58 59 /* 60 ======================== 61 Interface for calling functions from script, implemented natively on a nested class object 62 ======================== 63 */ 64 template< typename T > 65 class idSWFScriptFunction_Nested : public idSWFScriptFunction { 66 protected: 67 T * pThis; 68 public: 69 idSWFScriptFunction_Nested() : pThis( NULL ) { } 70 71 idSWFScriptFunction * Bind( T * _pThis ) { pThis = _pThis; return this; } 72 virtual void AddRef() { } 73 virtual void Release() { } 74 }; 75 76 /* 77 ======================== 78 Interface for calling functions from script, with reference counting 79 NOTE: The ref count starts at 0 here because it assumes you do an AddRef on the allocated 80 object. The proper way is to start it at 1 and force the caller to Release, but that's 81 really kind of a pain in the ass. It was made to be used like this: 82 object->Set( "myFunction", new idSWFScriptFunction_MyFunction() ); 83 ======================== 84 */ 85 class idSWFScriptFunction_RefCounted : public idSWFScriptFunction { 86 public: 87 idSWFScriptFunction_RefCounted() : refCount( 0 ) { } 88 void AddRef() { refCount++; } 89 void Release() { if ( --refCount <= 0 ) { delete this; } } 90 private: 91 int refCount; 92 }; 93 94 /* 95 ======================== 96 Action Scripts can define a pool of constants then push values from that pool 97 The documentation isn't very clear on the scope of these things, but from what 98 I've gathered by testing, pool is per-function and copied into the function 99 whenever that function is declared. 100 ======================== 101 */ 102 class idSWFConstantPool { 103 public: 104 idSWFConstantPool(); 105 ~idSWFConstantPool() { Clear(); } 106 107 void Clear(); 108 void Copy( const idSWFConstantPool & other ); 109 idSWFScriptString * Get( int n ) { return pool[n]; } 110 void Append( idSWFScriptString * s ) { pool.Append( s ); } 111 112 private: 113 idList< idSWFScriptString *, TAG_SWF > pool; 114 }; 115 116 /* 117 ======================== 118 The idSWFStack class is just a helper routine for treating an idList like a stack 119 ======================== 120 */ 121 class idSWFStack : public idList< idSWFScriptVar > { 122 public: 123 idSWFScriptVar & A() { return operator[]( Num() - 1 ); } 124 idSWFScriptVar & B() { return operator[]( Num() - 2 ); } 125 idSWFScriptVar & C() { return operator[]( Num() - 3 ); } 126 idSWFScriptVar & D() { return operator[]( Num() - 4 ); } 127 void Pop( int n ) { SetNum( Num() - n ); } 128 }; 129 130 /* 131 ======================== 132 idSWFScriptFunction_Script is a script function that's implemented in action script 133 ======================== 134 */ 135 class idSWFScriptFunction_Script : public idSWFScriptFunction { 136 public: 137 idSWFScriptFunction_Script() : refCount( 1 ), flags( 0 ), prototype( NULL ), data( NULL ), length( 0 ), defaultSprite( NULL ) { registers.SetNum( 4 ); } 138 virtual ~idSWFScriptFunction_Script(); 139 140 static idSWFScriptFunction_Script * Alloc() { return new (TAG_SWF) idSWFScriptFunction_Script; } 141 void AddRef() { refCount++; } 142 void Release() { if ( --refCount == 0 ) { delete this; } } 143 144 // This could all be passed to Alloc (and was at one time) but in some places it's far more convenient to specify each separately 145 void SetFlags( uint16 _flags ) { flags = _flags; } 146 void SetData( const byte * _data, uint32 _length ) { data = _data; length = _length; } 147 void SetScope( idList<idSWFScriptObject *> & scope ); 148 void SetConstants( const idSWFConstantPool & _constants ) { constants.Copy( _constants ); } 149 void SetDefaultSprite( idSWFSpriteInstance * _sprite ) { defaultSprite = _sprite; } 150 void AllocRegisters( int numRegs ) { registers.SetNum( numRegs ); } 151 void AllocParameters( int numParms ) { parameters.SetNum( numParms ); } 152 void SetParameter( uint8 n, uint8 r, const char * name ) { parameters[n].reg = r; parameters[n].name = name; } 153 154 idSWFScriptObject * GetPrototype() { return prototype; } 155 void SetPrototype( idSWFScriptObject * _prototype ) { _prototype->AddRef(); assert( prototype == NULL ); prototype = _prototype; } 156 157 virtual idSWFScriptVar Call( idSWFScriptObject * thisObject, const idSWFParmList & parms ); 158 159 private: 160 idSWFScriptVar Run( idSWFScriptObject * thisObject, idSWFStack & stack, idSWFBitStream & bitstream ); 161 162 private: 163 int refCount; 164 165 uint16 flags; 166 const byte * data; 167 uint32 length; 168 idSWFScriptObject * prototype; 169 170 idSWFSpriteInstance * defaultSprite; // some actions have an implicit sprite they work off of (e.g. Action_GotoFrame outside of object scope) 171 172 idList< idSWFScriptObject *, TAG_SWF > scope; 173 174 idSWFConstantPool constants; 175 idList< idSWFScriptVar, TAG_SWF > registers; 176 177 struct parmInfo_t { 178 const char * name; 179 uint8 reg; 180 }; 181 idList< parmInfo_t, TAG_SWF > parameters; 182 }; 183 184 #endif // !__SWF_SCRIPTFUNCTION_H__