Initial commit: Complete open-source Decal rebuild

All 5 phases of the open-source Decal rebuild:

Phase 1: 14 decompiled .NET projects (Interop.*, Adapter, FileService, DecalUtil)
Phase 2: 10 native DLLs rewritten as C# COM servers with matching GUIDs
  - DecalDat, DHS, SpellFilter, DecalInput, DecalNet, DecalFilters
  - Decal.Core, DecalControls, DecalRender, D3DService
Phase 3: C++ shims for Inject.DLL (D3D9 hooking) and LauncherHook.DLL
Phase 4: DenAgent WinForms tray application
Phase 5: WiX installer and build script

25 C# projects building with 0 errors.
Native C++ projects require VS 2022 + Windows SDK (x86).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
erik 2026-02-08 18:27:56 +01:00
commit d1442e3747
1382 changed files with 170725 additions and 0 deletions

24
.gitignore vendored Normal file
View file

@ -0,0 +1,24 @@
# Build outputs
bin/
obj/
Debug/
Release/
x86/
x64/
build/
# IDE
.vs/
*.user
*.suo
*.sln.docstates
# NuGet
packages/
# OS
Thumbs.db
.DS_Store
# Native old source (reference only, not part of the build)
# Keep Native/InjectModern/ and Native/LauncherHookModern/

View file

@ -0,0 +1,11 @@
Microsoft Visual Studio Solution File, Format Version 1.00
Project("{73393D18-DAC4-11D1-88FC-0000F8064EBB}") = "Decal 2", "Decal 2.wip", "{3606BE98-3576-4296-9CF6-23746B25EA4E}"
EndProject
Global
GlobalSection(LocalDeployment) = postSolution
StartupProject = {00000000-0000-0000-0000-000000000000}
EndGlobalSection
GlobalSection(BuildOrder) = postSolution
0 = {3606BE98-3576-4296-9CF6-23746B25EA4E}
EndGlobalSection
EndGlobal

BIN
Installer/Attic/Decal 2.wip Normal file

Binary file not shown.

View file

@ -0,0 +1,6 @@
<Project Sdk="WixToolset.Sdk/5.0.0">
<PropertyGroup>
<OutputType>Package</OutputType>
<InstallerPlatform>x86</InstallerPlatform>
</PropertyGroup>
</Project>

View file

@ -0,0 +1,13 @@
Microsoft Visual Studio Solution File, Format Version 1.00
Project("{73393D18-DAC4-11D1-88FC-0000F8064EBB}") = "Decal", "DecalInstaller.wip", "{3606BE98-3576-4296-9CF6-23746B25EA4E}"
EndProject
Global
GlobalSection(LocalDeployment) = postSolution
StartupProject = {00000000-0000-0000-0000-000000000000}
EndGlobalSection
GlobalSection(BuildOrder) = postSolution
0 = {3606BE98-3576-4296-9CF6-23746B25EA4E}
EndGlobalSection
GlobalSection(DeploymentRoot) = postSolution
EndGlobalSection
EndGlobal

File diff suppressed because it is too large Load diff

Binary file not shown.

View file

@ -0,0 +1,13 @@
Microsoft Visual Studio Solution File, Format Version 1.00
Project("{73393D18-DAC4-11D1-88FC-0000F8064EBB}") = "Decal", "DecalInstallerVC7.wip", "{3606BE98-3576-4296-9CF6-23746B25EA4E}"
EndProject
Global
GlobalSection(LocalDeployment) = postSolution
StartupProject = {00000000-0000-0000-0000-000000000000}
EndGlobalSection
GlobalSection(BuildOrder) = postSolution
0 = {3606BE98-3576-4296-9CF6-23746B25EA4E}
EndGlobalSection
GlobalSection(DeploymentRoot) = postSolution
EndGlobalSection
EndGlobal

Binary file not shown.

161
Installer/Installer.nsi Normal file
View file

@ -0,0 +1,161 @@
; Script generated with the Venis Install Wizard
; Define your application name
!define APPNAME "Decal"
!define APPNAMEANDVERSION "Decal 2.6.1.0"
; Main Install settings
Name "${APPNAMEANDVERSION}"
InstallDir "$PROGRAMFILES\Decal"
InstallDirRegKey HKLM "Software\${APPNAME}" ""
OutFile "Decal2610.exe"
; Use compression
SetCompressor LZMA
; Modern interface settings
!include "MUI.nsh"
!define MUI_ABORTWARNING
!insertmacro MUI_PAGE_WELCOME
!insertmacro MUI_PAGE_COMPONENTS
!insertmacro MUI_PAGE_DIRECTORY
!insertmacro MUI_PAGE_INSTFILES
!insertmacro MUI_PAGE_FINISH
!insertmacro MUI_UNPAGE_CONFIRM
!insertmacro MUI_UNPAGE_INSTFILES
; Set languages (first is default language)
!insertmacro MUI_LANGUAGE "English"
!insertmacro MUI_RESERVEFILE_LANGDLL
Section "" DecalCoreSection
; Set Section properties
SetOverwrite on
; Set Section Files and Shortcuts
SetOutPath "$INSTDIR\"
File "Release\Switch-Active.bmp"
File "Release\Switch-Inactive.bmp"
File "Release\Switchbar Disabled.bmp"
File "Release\Switchbar Template.bmp"
File "Release\Tab-Active.bmp"
File "Release\Tab-Inactive.bmp"
File "Release\Decal.dll"
File "Release\DecalControls.dll"
File "Release\DecalDat.dll"
File "Release\DecalFilters.dll"
File "Release\DecalInput.dll"
File "Release\DecalNet.dll"
File "Release\DenAgent.exe"
File "Release\ForceLibrary.dll"
File "Release\Inject.dll"
File "Release\LobbyHook.dll"
File "Release\MapObject.bmp"
File "Release\PlainText.dll"
SetOutPath "$SYSDIR\"
File "Release\LobbyHook.dll"
RegDLL "$INSTDIR\Decal.dll"
RegDLL "$INSTDIR\Inject.dll"
RegDLL "$INSTDIR\DecalControls.dll"
RegDLL "$INSTDIR\DecalDat.dll"
RegDLL "$INSTDIR\DecalNet.dll"
RegDLL "$INSTDIR\DecalFilters.dll"
RegDLL "$INSTDIR\DecalInput.dll"
RegDLL "$INSTDIR\PlainText.dll"
SectionEnd
Section "Desktop Shortcut" DesktopSection
CreateShortCut "$DESKTOP\Decal Agent.lnk" "$INSTDIR\DenAgent.exe"
SectionEnd
Section "Start Menu Entry" SMSection
CreateDirectory "$SMPROGRAMS\Decal"
CreateShortCut "$SMPROGRAMS\Decal\Decal Agent.lnk" "$INSTDIR\DenAgent.exe"
CreateShortCut "$SMPROGRAMS\Decal\Uninstall.lnk" "$INSTDIR\uninstall.exe"
SectionEnd
Section "Quick Launch Shortcut" QLSection
CreateShortCut "$QUICKLAUNCH\Decal Agent.lnk" "$INSTDIR\DenAgent.exe"
SectionEnd
Section -FinishSection
WriteRegStr HKLM "Software\${APPNAME}" "" "$INSTDIR"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "DisplayName" "${APPNAME}"
WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}" "UninstallString" "$INSTDIR\uninstall.exe"
WriteUninstaller "$INSTDIR\uninstall.exe"
SectionEnd
; Modern install component descriptions
!insertmacro MUI_FUNCTION_DESCRIPTION_BEGIN
!insertmacro MUI_DESCRIPTION_TEXT ${Section1} ""
!insertmacro MUI_FUNCTION_DESCRIPTION_END
;Uninstall section
Section Uninstall
;Remove from registry...
DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${APPNAME}"
DeleteRegKey HKLM "SOFTWARE\${APPNAME}"
; Delete self
Delete "$INSTDIR\uninstall.exe"
; Delete Shortcuts
Delete "$DESKTOP\Decal.lnk"
Delete "$SMPROGRAMS\Decal\Decal.lnk"
Delete "$SMPROGRAMS\Decal\Uninstall.lnk"
; Unregister DLLS
UnRegDLL "$INSTDIR\Decal.dll"
UnRegDLL "$INSTDIR\Inject.dll"
UnRegDLL "$INSTDIR\DecalControls.dll"
UnRegDLL "$INSTDIR\DecalDat.dll"
UnRegDLL "$INSTDIR\DecalNet.dll"
UnRegDLL "$INSTDIR\DecalFilters.dll"
UnRegDLL "$INSTDIR\DecalInput.dll"
UnRegDLL "$INSTDIR\PlainText.dll"
; Clean up Decal
Delete "$INSTDIR\Decal.dll"
Delete "$INSTDIR\DecalControls.dll"
Delete "$INSTDIR\DecalDat.dll"
Delete "$INSTDIR\DecalFilters.dll"
Delete "$INSTDIR\DecalInput.dll"
Delete "$INSTDIR\DecalNet.dll"
Delete "$INSTDIR\DenAgent.exe"
Delete "$INSTDIR\ForceLibrary.dll"
Delete "$INSTDIR\Inject.dll"
Delete "$INSTDIR\LobbyHook.dll"
Delete "$INSTDIR\MapObject.bmp"
Delete "$INSTDIR\PlainText.dll"
Delete "$INSTDIR\Switch-Active.bmp"
Delete "$INSTDIR\Switch-Inactive.bmp"
Delete "$INSTDIR\Switchbar Disabled.bmp"
Delete "$INSTDIR\Switchbar Template.bmp"
Delete "$INSTDIR\Tab-Active.bmp"
Delete "$INSTDIR\Tab-Inactive.bmp"
; Remove remaining directories
RMDir "$SMPROGRAMS\Decal"
RMDir "$INSTDIR\"
SectionEnd
; eof

198
Installer/Package.wxs Normal file
View file

@ -0,0 +1,198 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Decal Installer - WiX v4/5 MSI package
Installs all Decal components to Program Files\Decal\
Registers COM servers, creates registry entries, and sets up shortcuts.
-->
<Wix xmlns="http://wixtoolset.org/schemas/v4/wxs">
<Package
Name="Decal"
Version="2.9.9.0"
Manufacturer="Decal Open Source Project"
UpgradeCode="A1B2C3D4-E5F6-7890-ABCD-EF1234567890"
Scope="perMachine"
InstallerVersion="200">
<MajorUpgrade
DowngradeErrorMessage="A newer version of Decal is already installed."
AllowSameVersionUpgrades="yes" />
<MediaTemplate EmbedCab="yes" />
<!-- Installation directory structure -->
<StandardDirectory Id="ProgramFilesFolder">
<Directory Id="INSTALLFOLDER" Name="Decal" />
</StandardDirectory>
<!-- Start Menu -->
<StandardDirectory Id="ProgramMenuFolder">
<Directory Id="DecalMenuFolder" Name="Decal" />
</StandardDirectory>
<!-- Feature: Core (always installed) -->
<Feature Id="CoreFeature" Title="Decal Core" Level="1" Absent="disallow">
<ComponentGroupRef Id="ManagedAssemblies" />
<ComponentGroupRef Id="COMServers" />
<ComponentGroupRef Id="NativeDLLs" />
<ComponentGroupRef Id="Executables" />
<ComponentGroupRef Id="RegistryEntries" />
<ComponentGroupRef Id="Shortcuts" />
</Feature>
</Package>
<!-- ================================================================ -->
<!-- Component Groups -->
<!-- ================================================================ -->
<!-- Managed (.NET) Interop Assemblies -->
<Fragment>
<ComponentGroup Id="ManagedAssemblies" Directory="INSTALLFOLDER">
<!-- Interop assemblies (COM interface definitions) -->
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Core.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Inject.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Controls.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.D3DService.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.DHS.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Dat.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Filters.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Input.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Net.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.Render.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.Interop.SpellFilter.dll" />
</Component>
<!-- Adapter and FileService -->
<Component>
<File Source="$(var.BuildOutput)\Decal.Adapter.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.FileService.dll" />
</Component>
</ComponentGroup>
</Fragment>
<!-- COM Server DLLs (C# implementations of native DLLs) -->
<Fragment>
<ComponentGroup Id="COMServers" Directory="INSTALLFOLDER">
<Component>
<File Source="$(var.BuildOutput)\Decal.Core.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalDat.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DHS.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.SpellFilter.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalInput.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalNet.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalFilters.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalControls.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.DecalRender.dll" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\Decal.D3DService.dll" />
</Component>
</ComponentGroup>
</Fragment>
<!-- Native C++ DLLs -->
<Fragment>
<ComponentGroup Id="NativeDLLs" Directory="INSTALLFOLDER">
<Component>
<File Source="$(var.NativeOutput)\Inject.DLL" />
</Component>
<Component>
<File Source="$(var.NativeOutput)\LauncherHook.DLL" />
</Component>
</ComponentGroup>
</Fragment>
<!-- Executables -->
<Fragment>
<ComponentGroup Id="Executables" Directory="INSTALLFOLDER">
<Component>
<File Id="DenAgentEXE" Source="$(var.BuildOutput)\Decal.DenAgent.exe" Name="DenAgent.EXE" />
</Component>
<Component>
<File Source="$(var.BuildOutput)\DecalUtil.exe" />
</Component>
</ComponentGroup>
</Fragment>
<!-- Registry entries -->
<Fragment>
<ComponentGroup Id="RegistryEntries" Directory="INSTALLFOLDER">
<Component Id="DecalRegistryBase">
<RegistryKey Root="HKLM" Key="SOFTWARE\Decal">
<RegistryValue Name="Version" Type="string" Value="2.9.9.0" />
</RegistryKey>
<RegistryKey Root="HKLM" Key="SOFTWARE\Decal\Agent">
<RegistryValue Name="AgentPath" Type="string" Value="[INSTALLFOLDER]" />
</RegistryKey>
</Component>
<!-- Service registrations -->
<Component Id="DecalServices">
<RegistryKey Root="HKLM" Key="SOFTWARE\Decal\Services">
<!-- Services are registered by their CLSIDs -->
</RegistryKey>
</Component>
<!-- Plugin registrations -->
<Component Id="DecalPlugins">
<RegistryKey Root="HKLM" Key="SOFTWARE\Decal\Plugins">
<!-- Plugins register themselves at install time -->
</RegistryKey>
</Component>
</ComponentGroup>
</Fragment>
<!-- Shortcuts -->
<Fragment>
<ComponentGroup Id="Shortcuts" Directory="DecalMenuFolder">
<Component Id="DenAgentShortcut">
<Shortcut Id="DenAgentStartMenu"
Name="Decal Agent"
Target="[INSTALLFOLDER]DenAgent.EXE"
WorkingDirectory="INSTALLFOLDER" />
<RemoveFolder Id="RemoveDecalMenu" On="uninstall" />
<RegistryValue Root="HKCU" Key="SOFTWARE\Decal" Name="Installed" Type="integer" Value="1" KeyPath="yes" />
</Component>
</ComponentGroup>
</Fragment>
</Wix>

Binary file not shown.

View file

@ -0,0 +1,44 @@
@echo off
title Decal Installer
del %systemdrive%\DecalInstaller.log > nul 2>&1
echo.
echo.
echo.
echo.
echo.
echo.
echo Removing Decal 1.0.1.0
msiexec /x {4AFA7857-D10F-4A74-A504-9C10320A6DB9} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 1.0.2.0
msiexec /x {840FA8EC-CA4D-46BE-94E6-2C85F4E29EDD} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 1.0.2.2
msiexec /x {DBBE8C7F-F27D-48D7-BBC1-5BFA30485980} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 1.1.0.0
msiexec /x {DFB254B2-F9B4-42F1-8B16-C045B18C8DBE} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 2.0.0.0 RC1
msiexec /x {3CFF0D79-376D-4557-8376-A9B48E50F775} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 2.0.0.0 RC2
msiexec /x {701F72C7-421E-4DBE-B8C7-0A8B5258D539} /q /lem+! %systemdrive%\DecalInstaller.log
echo Removing Decal 2.0.0.0 RC3
msiexec /x {D6E309A7-290D-48E0-9992-0DAB18EA4CE4} /q /lem+! %systemdrive%\DecalInstaller.log
echo.
echo.
echo -------Previous Decal Versions Removed-------
echo.
echo.
echo Installing Decal 2.0.0.0 RC3
start msiexec /i Decal.msi /lem+! %systemdrive%\DecalInstaller.log

Binary file not shown.

View file

@ -0,0 +1,4 @@
[DEFAULT]
BASEURL=http://decaldev.sourceforge.net/
[InternetShortcut]
URL=http://decaldev.sourceforge.net/

BIN
Installer/Res/Decal.ico Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.6 KiB

338
Installer/Res/Install.vbs Normal file
View file

@ -0,0 +1,338 @@
'>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> Decal Installer Library <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
Option Explicit
'FSO Constants
Private Const WindowsFolder = 0
Private Const SystemFolder = 1
Private Const TemporaryFolder = 2
'WindowsInstaller Constants
Private Const msiInstallStateUnknown = -1
Private Const msiInstallStateAbsent = 2
Private Const msiUILevelFull = 5
'Minimum versions
Private Const MIN_WSH_VERSION = "5.1"
Private Const MIN_WI_VERSION = "1.11.2405.0"
'Global Objects
Private WshShell, WI, FSO, AllProducts
'prevent premature errors if objects don't exist
On Error Resume Next
Set WshShell = WScript.CreateObject("WScript.Shell") 'needed for reg access and file execution
Set WI = CreateObject("WindowsInstaller.Installer") 'the MSI related functions need this object
Set FSO = CreateObject("Scripting.FileSystemObject") 'can never have too many of these around
Set AllProducts = CreateObject("Scripting.Dictionary") 'All of the product IDs that this should remove before installing
On Error GoTo 0
'Now make sure we got them all
'There is some error checking deeper in, but I've seen a lot of errors so I'm not removing any of it :)
If Not IsObject(WshShell) Then
MsgBox "Internal error creating Windows Scripting Host object (WshShell). Please make sure you have IE6+ installed", _
vbOKOnly, _
"Decal Installer Library"
WScript.Quit
End If
If Not IsObject(FSO) Then
MsgBox "Internal error creating Windows Scripting Host object (FSO). Please make sure you have IE6+ installed", _
vbOKOnly, _
"Decal Installer Library"
WScript.Quit
End If
If Not IsObject(AllProducts) Then
MsgBox "Internal error creating Windows Scripting Host object (Dictionary). Please make sure you have IE6+ installed", _
vbOKOnly, _
"Decal Installer Library"
WScript.Quit
End If
If Not IsObject(WI) Then
MsgBox "Internal error creating Windows Installer object. Please make sure you have Windows Installer installed", _
vbOKOnly, _
"Decal Installer Library"
WScript.Quit
End If
'YOU MUST EDIT THESE FOR YOUR PARTICULAR INSTALLER!!!!!!
'All of these -must- be specified
Private Const ThisProduct = "Decal" ' The name of your product, used it dialogs and such
Private Const ThisVersion = "2.6.0.1" ' The version of your product, used in dialogs and such
Private Const MSIFileName = "Decal.msi" ' The name of the MSI file that will be excuted
'Add all of your previous product IDs to the dictionary for removal by the installer
AllProducts.Add "1.0.1.0", "{4AFA7857-D10F-4A74-A504-9C10320A6DB9}"
AllProducts.Add "1.0.2.0", "{840FA8EC-CA4D-46BE-94E6-2C85F4E29EDD}"
AllProducts.Add "1.0.2.2", "{DBBE8C7F-F27D-48D7-BBC1-5BFA30485980}"
AllProducts.Add "1.1.0.0", "{DFB254B2-F9B4-42F1-8B16-C045B18C8DBE}"
AllProducts.Add "2.0.0.0 RC1", "{3CFF0D79-376D-4557-8376-A9B48E50F775}"
AllProducts.Add "2.0.0.0 RC2", "{701F72C7-421E-4DBE-B8C7-0A8B5258D539}"
AllProducts.Add "2.0.0.0 RC3 ", "{D6E309A7-290D-48E0-9992-0DAB18EA4CE4}"
AllProducts.Add "2.0.0.0 RC4", "{3C2F8BE2-2B35-402F-9BAE-F9FDCA9C22A9}"
AllProducts.Add "2.0.0.0", "{F7DC5688-E3A0-432B-A5DF-F7CB4B02DE03}"
AllProducts.Add "2.1.0.2", "{6C6B886C-66E0-41C9-AF1A-1B02372D5E77}"
AllProducts.Add "2.1.0.4", "{83CE1E0E-E441-4764-A3CC-DBF1A53C40F0}"
AllProducts.Add "2.1.0.5", "{B388C87C-F59D-457F-A839-B6F3A2642CE7}"
AllProducts.Add "2.2.0.0", "{9FB34BE5-A2A3-4509-8A21-133FC27387F7}"
AllProducts.Add "2.2.0.1", "{BE7BB776-FE47-41B7-AACE-1F958A7CE214}"
AllProducts.Add "2.2.2.0", "{92A0F954-9A9D-4FCC-B874-F0A8DBD8BF1B}"
AllProducts.Add "2.2.3.0", "{775AB855-075F-462B-A482-D555569E2C03}"
AllProducts.Add "2.2.4.0", "{0C844C18-2021-4660-AD25-7922653E1A16}"
AllProducts.Add "2.3.0.0", "{DE512CE7-2417-41E5-9C7F-5C091F171785}"
AllProducts.Add "2.3.1.0", "{660E1D69-140D-437E-9D23-9137DA6F0162}"
AllProducts.Add "2.3.1.1", "{A0ACDD8E-3730-4007-926A-55D7B1A5A7B7}"
AllProducts.Add "2.3.1.2", "{E6E77F45-0B35-4F92-9CD3-4B70A821158D}"
AllProducts.Add "2.3.1.3", "{92872CC7-2722-4534-81BE-E99B4D472A95}"
AllProducts.Add "2.3.1.4", "{8186889F-BF27-4F79-9D94-4DD7CB9956F2}"
AllProducts.Add "2.3.1.5", "{09A9F4AE-C043-43CF-85D1-6F14BCAAEB11}"
AllProducts.Add "2.3.1.6", "{A6749A61-B1E5-4FFB-BA4D-AE93E5443EC8}"
AllProducts.Add "2.3.1.7", "{C667B179-E270-4BE5-9C73-0533C1D2B758}"
AllProducts.Add "2.3.1.8", "{88947320-85FC-4327-908D-7801365AD4D9}"
AllProducts.Add "2.3.1.9", "{1CF52690-D209-47C7-97EF-F38D64463AD5}"
AllProducts.Add "2.4.0.0", "{4D7BE8B5-6B0A-4135-8C75-BE8E4BB2E351}"
AllProducts.Add "2.4.1.0", "{E6E9AB9D-812C-40D7-A57C-ED298B48557F}"
AllProducts.Add "2.4.1.2", "{09C6E670-D686-11D6-BFDA-009027B6A4F1}"
AllProducts.Add "2.4.1.3", "{E62F700A-E214-11D6-B2DA-009027B6A4F1}"
AllProducts.Add "2.5.0.0 RC1", "{940240A5-39C7-496A-B2FB-21D87220FCFE}"
AllProducts.Add "2.5.0.0 RC2", "{F685D7CA-12EB-11D7-B2DA-009027B6A4F1}"
AllProducts.Add "2.5.0.0 RC3", "{F15D5960-13C9-11D7-B2DA-009027B6A4F1}"
AllProducts.Add "2.5.0.1 RC1", "{B5B0E8D6-FE22-467C-B09E-1AB5CC837942}"
AllProducts.Add "2.5.0.1", "{CE4276BF-04AE-41C9-B7C2-3DD65B4DAEDD}"
AllProducts.Add "2.5.0.2", "{F794642A-63D5-11D7-B2DA-009027B6A4F1}"
AllProducts.Add "2.5.0.4", "{29E8FB17-4C4E-4F5D-8C5D-F3826ECE2CF6}"
AllProducts.Add "2.5.0.5", "{35012CC1-DC9F-49C3-9593-2B246AE68D3A}"
AllProducts.Add "2.5.2.0 RC1", "{ED4744B7-3F12-453B-9908-D192E0F5477A}"
AllProducts.Add "2.5.2.0 RC2", "{3EA7A26F-9112-45D4-BDE0-9BE451D42A9F}"
AllProducts.Add "2.5.2.0 RC3", "{B04617E3-2AFF-4650-84AF-10BE73B22A15}"
AllProducts.Add "2.6.0.0 RC1", "{6E766A51-09A9-4571-B55A-EE2E4E74B8BC}"
AllProducts.Add "2.6.0.0 RC2", "{4C22590F-22B8-4413-B91D-0403B2F84979}"
AllProducts.Add "2.6.0.0 RC3", "{E86FBB39-9061-475A-B575-F8F9AC12DB74}"
AllProducts.Add "2.6.0.0 RC4", "{16673809-CA94-4E31-9E0B-B2FCA0CBDFAB}"
AllProducts.Add "2.6.0.0 RC5", "{67E0D07C-8A6A-4357-B44F-CCA1A513DFE7}"
AllProducts.Add "2.6.0.0", "{B0DC3DCD-44BD-47C7-AB9D-CC68FB63F4C3}"
AllProducts.Add "2.6.0.1", "{32767F66-7F62-4C0B-81F7-C42B4C7C0148}"
' These are optional
' The features they provide will be ignored if they are left as empty strings
Private Const PathRegValue = "HKLM\SOFTWARE\Decal\Agent\AgentPath" ' Path to a registry key containing the install location of your product
Private Const FavoriteName = "Decal Homepage" ' Name of the Favorite to add at the end of the install
Private Const FavoriteURL = "http://decaldev.sourceforge.net/" ' URL for the Favorite to point to
Private Const FavoriteIconFile = "Denagent.exe" ' File to get the icon for the favorite from (default IE icon if blank)
Private Const FavoriteIconID = "0" ' Icon ID to use from the above file (default IE icon if blank)
' END OF EDITABLE OPTIONS
Private Function IsVersionAgreeable(pActualVersion, pMinumumVersion)
Dim actual, expected, i
IsVersionAgreeable = True
'msgbox "pActualVersion: " & pActualVersion & vbCRLF & "pMinumumVersion: " & pMinumumVersion
actual = split (pActualVersion, ".")
expected = split (pMinumumVersion, ".")
For i = 0 To UBound(expected)
'msgbox cstr(i & " : " & actual(i) & " : " & expected(i))
If CInt(actual(i)) > CInt(expected(i)) Then
'msgbox("greater")
Exit For
ElseIf CInt(actual(i)) < CInt(expected(i)) Then
'msgbox("less")
IsVersionAgreeable = False
Exit For
End If
Next
End Function
Private Sub WSHVersionCheck()
'Function: Check the Windows Scripting Host version, give URL for updating if not good enough,
' then kill the script.
'Args: N/A
'Returns: N/A
'
'Requirements: WshShell = WScript.Shell
'
Dim actualVersion, rc
On Error Resume Next
actualVersion = WScript.Version
On Error GoTo 0
'Bail here if things are ok
If IsVersionAgreeable(actualVersion, MIN_WSH_VERSION) Then Exit Sub
'Didn't bail, so need to prompt for an upgrade
rc = MsgBox ("The " & ThisProduct & " Installer has determined that you do not have a new enough version of Windows Scripting Host to use this installer." & _
String(2, vbCRLF) & _
"The newest version is available with Windows Scripting Host 5.6 which you can download at: " & _
String(2, vbCRLF) & _
"http://download.microsoft.com/download/winscript56/Install/5.6/W9XNT4Me/EN-US/scr56en.exe" & _
String(2, vbCRLF) & _
"Would you like to go there now?", _
vbYesNo + vbQuestion, _
ThisProduct & " Installer")
If rc = vbYes Then WshShell.Run "http://download.microsoft.com/download/winscript56/Install/5.6/W9XNT4Me/EN-US/scr56en.exe"
WScript.Quit
End Sub
Private Sub WIVersionCheck()
'Function: Check the windows installer version, give URL for updating if not good enough,
' then kill the script.
'Args: N/A
'Returns: N/A
'
'Requirements: WI = WindowsInstaller.Installer
' WshShell = WScript.Shell
Dim actualVersion, rc, fileInSysFolder, fileInWinFolder, windowsVersion, strURL, strFailMsg
On Error Resume Next
actualVersion = WI.Version
On Error GoTo 0
'Bail here if things are ok
If IsVersionAgreeable(actualVersion, MIN_WI_VERSION) Then Exit Sub
'Didn't bail, so need to prompt for an upgrade
With FSO
fileInSysFolder = .BuildPath(.GetSpecialFolder(SystemFolder), "winver.exe")
fileInWinFolder = .BuildPath(.GetSpecialFolder(WindowsFolder), "winver.exe")
If .FileExists(fileInSysFolder) Then
windowsVersion = split(.GetFileVersion(fileInSysFolder),".")
ElseIf .FileExists(fileInWinFolder) Then
windowsVersion = split(.GetFileVersion(fileInWinFolder),".")
Else
rc = MsgBox("The Decal Installer was unable to determine your Windows version. Are you using Windows 2000 or Windows XP?", _
vbYesNo + vbQuestion, _
ThisProduct & " Installer")
If rc = vbYes Then
windowsVersion = split("5.0.0.0", ".")
ElseIf rc = vbNo Then
windowsVersion = split("4.0.0.0", ".")
Else
MsgBox "An unknown error occured in Windows Version detection. Please make sure you have Windows Installer properly installed and try again.", _
vbOKOnly, _
ThisProduct & " Installer"
WScript.Quit
End If
End If
End With 'With FSO
If CInt(windowsVersion(1)) < 5 Then
strURL = "http://www.microsoft.com/downloads/release.asp?releaseid=32831"
strFailMsg = "Windows 98/ME users can upgrade at: " & strURL
Else 'If work(0) < 5 Then
strURL = "http://www.microsoft.com/downloads/release.asp?releaseid=32832"
strFailMsg = "Windows 2000 users can upgrade at: " & strURL
End If 'If work(0) < 5 Then
rc = MsgBox ("The " & ThisProduct & " Installer has determined that you do not have a new enough version of Windows Installer to use this installer. " & _
String(2,vbCRLF) & _
strFailMsg & _
String(2,vbCRLF) & _
"Would you like to go there now?", _
vbYesNo + vbQuestion, _
ThisProduct & " Installer")
If rc = vbYes Then
'open the browser and exit
WshShell.Run strURL
End If
WScript.Quit
End Sub
Private Sub WipeProduct(pProdID)
'Function: Check for the product ID. If it exists, silently and forcefully uninstall.
'
'Args: pProdID = a string of the MSI Product ID to be wiped
'Returns: N/A
'
'Requirements: WI = WindowsInstaller.Installer
Dim rc
rc = WI.ProductState(pProdID)
'FIXME
'something about this check is not as precise as it should be. Need to find info
'about different install states and find ways to handle them all
'TEMP FIX ONLY
On Error Resume Next
'END OF TEMP FIX
If rc <> msiInstallStateUnknown Then
'remove it
WI.ConfigureProduct pProdID, 0, msiInstallStateAbsent 'second param is ignored
End If
End Sub
' VERSION CHECKING
WSHVersionCheck
WIVersionCheck
'>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> End of Decal Installer Library <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
'>>>>>>>>>>>>>>>>>>>>>>>>>>>START SCRIPT<<<<<<<<<<<<<<<<<<<<<<<<
'variables
Dim retval, strProductFolder, strProp, strUninstaller, strPathToFavIcon, TXT, i, ProductsToRemove
'make sure they really want to do this
retval = MsgBox("You are about to remove all old " & ThisProduct & " versions and install " & ThisProduct & " v" & ThisVersion & " ", _
vbOkCancel + vbQuestion, _
ThisProduct &" Installer")
If retval = vbCancel Then WScript.Quit
'Before starting, lookup and store the Decal path if it exists
On Error Resume Next 'will fail if not found, leaving an empty string
strDecalFolder = WshShell.RegRead(PathRegValue)
On Error GoTo 0
'>>>>>>>>>>>>>>>UNINSTALLING OLD VERSIONS<<<<<<<<<<<<<<<<<
'Remove MSIs by product code
ProductsToRemove = AllProducts.Items
For i = 0 To UBound(ProductsToRemove)
WipeProduct ProductsToRemove(i)
Next
'>>>>>>>>>>>>>>>>>>>>INSTALLING PDODUCT<<<<<<<<<<<<<<<<<<<<<<<<<<
'install .msi with remembered install path if it exists
strProp = "DISABLEADVTSHORTCUTS=True"
If Len(strProductFolder) > 0 Then strProp = strProp & " TARGETDIR=""" & strProductFolder & """"
WI.UILevel = msiUILevelFull
On Error Resume Next
WI.InstallProduct MSIFileName, strProp
On Error GoTo 0
If Err.Number <> 0 Then WScript.Quit
'The old command line:
'WshShell.Run "msiexec /i Decal.msi " & strProp
'Favorites icon?
If Len(FavoriteName) > 0 And Len(FavoriteURL) > 0 Then
strPathToFavIcon = FSO.BuildPath(WshShell.SpecialFolders("Favorites"), FavoriteName & ".url")
'is is there already?
If Not FSO.FileExists(strPathToFavIcon) Then
retval = MsgBox("Would you like a shortcut to the " & ThisProduct & " Homepage placed in your Favorites menu?", _
vbYesNo + vbQuestion, _
ThisProduct & " Installer")
If retval = vbYes Then
Set TXT = FSO.CreateTextFile(strPathToFavIcon)
TXT.WriteLine "[InternetShortcut]"
TXT.WriteLine "URL=" & FavoriteURL
On Error Resume Next
strProductFolder = WshShell.RegRead(PathRegValue)
On Error GoTo 0
If Len(FavoriteIconFile) > 0 And Len(FavoriteIconID) > 0 And Len(strProductFolder) > 0 Then
TXT.WriteLine "IconFile=" & FSO.BuildPath(strProductFolder, FavoriteIconFile)
TXT.WriteLine "IconIndex=" & FavoriteIconID
End If
TXT.Close
End If
End If
End If
MsgBox ThisProduct & " Installation Completed", _
vbOkOnly + vbInformation, _
ThisProduct & " Installer"

BIN
Installer/Res/decalbar.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.9 KiB

BIN
Installer/Res/gdiplus.dll Normal file

Binary file not shown.

78
Installer/Res/howto.txt Normal file
View file

@ -0,0 +1,78 @@
How to make a new Decal installer:
Update from CVS (or make sure you have the version of the code you want to release)
Update readme.rtf to reflect the current state of Decal
Open the provided VSI project files (DecalInstaller.sln and DecalInstaller.wip)
Change the Product Name, Product Code, Version, Version string in the registry, and whatever else needs to be changed in the installer (but NOT the filename)
Build a new installer
Open Install.vbs
Add a new uninstall entry for the current Product code using the others as an example (AllProducts.Add "<version>", "<GUID>")
Change the ThisVersion constant to reflect the new version number
Save and Close Install.vbs and VSI
Open EnZip 3.00 ( freeware: http://www.cpam.freeserve.co.uk/ )
Choose File, New Archive... (or hit Ctrl-N)
Give a filename such as "Decal_2000.zip" for Decal 2.0.0.0
Add Decal.msi and Install.vbs to the files, using maximum compression (available on the Options tab)
Choose Tools, Create Self-Extractor... (or hit Shift-X)
Click Next to customize the extractor
Click Next to NOT have a message box
Click Next to have it extract to the TEMP folder
Change the Tile Caption to "Decal Installer" and Click Next
Type "Install.vbs" in the Command box, leave the Parameters box empty, then hit Next
Click the Change Icon... button and select the Decal.ico from the source/Installer/Res folder
Select the first icon and Click Ok, then Click Next
Uncheck Display Run Command Checkbox
Check Unzip Automaticly
Make sure Default to overwrite files without prompting is selected
Click Next, then Click Yes to bypass the warning
Verify your options in the displayed listbox and then hit Create (this may look like it's not doing anything, but it is)
When it completes, hit Test Self-Extracting ZIP file now
If everything went ok, it should display a command prompt window while previous Decal versions are uninstalled, then close and start the Decal installer MSI
Click Close, then close EnZip
VERIFY!!!!!!!!
Make sure there is only ONE add/remove entry for Decal
Make sure there is only ONE Decal group in the Start Menu
Make sure there is only ONE Decal icon on the Desktop
Make sure ALL the file versions are correct
Load up Decal and make sure it runs properly (to verify things such as registry values)
Attempt to delete all of the shortcuts, then open IE. If the installer starts and repairs the shortcuts something is wrong.
Test the FavIcon creation
Generally kick it around and attempt to break it
COMMIT!!!!
Commit your new changes with a tag (so that the installer can be rebuilt in it's current state at any time)
If this is a release version (not BETA), create a branch for bugfixes
Upload the binary to SourceForge (see sf.net instructions)
Test the download and verify you get the same file you uploaded
Change the homepage of decaldev.sf.net to point to the new download

132
Installer/Res/readme.rtf Normal file
View file

@ -0,0 +1,132 @@
{\rtf1\ansi\ansicpg1252\uc1\deff0\stshfdbch0\stshfloch0\stshfhich0\stshfbi0\deflang1033\deflangfe1033{\fonttbl{\f0\froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
{\f2\fmodern\fcharset0\fprq1{\*\panose 02070309020205020404}Courier New;}{\f3\froman\fcharset2\fprq2{\*\panose 05050102010706020507}Symbol;}{\f37\froman\fcharset0\fprq2{\*\panose 00000000000000000000}Georgia;}
{\f38\froman\fcharset238\fprq2 Times New Roman CE;}{\f39\froman\fcharset204\fprq2 Times New Roman Cyr;}{\f41\froman\fcharset161\fprq2 Times New Roman Greek;}{\f42\froman\fcharset162\fprq2 Times New Roman Tur;}
{\f43\froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\f44\froman\fcharset178\fprq2 Times New Roman (Arabic);}{\f45\froman\fcharset186\fprq2 Times New Roman Baltic;}{\f46\froman\fcharset163\fprq2 Times New Roman (Vietnamese);}
{\f58\fmodern\fcharset238\fprq1 Courier New CE;}{\f59\fmodern\fcharset204\fprq1 Courier New Cyr;}{\f61\fmodern\fcharset161\fprq1 Courier New Greek;}{\f62\fmodern\fcharset162\fprq1 Courier New Tur;}{\f63\fmodern\fcharset177\fprq1 Courier New (Hebrew);}
{\f64\fmodern\fcharset178\fprq1 Courier New (Arabic);}{\f65\fmodern\fcharset186\fprq1 Courier New Baltic;}{\f66\fmodern\fcharset163\fprq1 Courier New (Vietnamese);}{\f408\froman\fcharset238\fprq2 Georgia CE;}{\f409\froman\fcharset204\fprq2 Georgia Cyr;}
{\f411\froman\fcharset161\fprq2 Georgia Greek;}{\f412\froman\fcharset162\fprq2 Georgia Tur;}{\f415\froman\fcharset186\fprq2 Georgia Baltic;}}{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;\red0\green255\blue0;
\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;\red255\green255\blue255;\red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;
\red192\green192\blue192;}{\stylesheet{\ql \li0\ri0\widctlpar\faauto\rin0\lin0\itap0 \fs24\lang1033\langfe1033\cgrid\langnp1033\langfenp1033 \snext0 Normal;}{\*\cs10 \additive \ssemihidden Default Paragraph Font;}{\*
\ts11\tsrowd\trftsWidthB3\trpaddl108\trpaddr108\trpaddfl3\trpaddft3\trpaddfb3\trpaddfr3\trcbpat1\trcfpat1\tscellwidthfts0\tsvertalt\tsbrdrt\tsbrdrl\tsbrdrb\tsbrdrr\tsbrdrdgl\tsbrdrdgr\tsbrdrh\tsbrdrv
\ql \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \fs20\lang1024\langfe1024\cgrid\langnp1024\langfenp1024 \snext11 \ssemihidden Normal Table;}{\*\cs15 \additive \ul\cf2 \sbasedon10 \styrsid13959554 Hyperlink;}}{\*\listtable
{\list\listtemplateid409371626\listsimple{\listlevel\levelnfc0\levelnfcn0\leveljc0\leveljcn0\levelfollow0\levelstartat0\levelspace0\levelindent0{\leveltext\'01*;}{\levelnumbers;}}{\listname ;}\listid-2}{\list\listtemplateid1512880686\listsimple{\listlevel
\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid190145115}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255
\levelnfcn255\leveljc0\leveljcn0\levelfollow0\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid204221188}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255
\leveljc0\leveljcn0\levelfollow0\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid399254398}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0
\leveljcn0\levelfollow0\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid462045303}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0
\levelfollow0\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid543324763}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid561211173}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid583338098}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid590091954}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid771126764}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid855463441}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1214316582}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1300184623}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1403941801}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1538081160}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1551961698}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1734812107}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1813057095}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid1889994174}{\list\listtemplateid1512880686\listsimple{\listlevel\levelnfc255\levelnfcn255\leveljc0\leveljcn0\levelfollow0
\levelstartat0\levelold\levelspace0\levelindent0{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 }{\listname ;}\listid2028016505}}{\*\listoverridetable{\listoverride\listid-2\listoverridecount1{\lfolevel\listoverrideformat{\listlevel\levelnfc23
\levelnfcn23\leveljc0\leveljcn0\levelfollow0\levelstartat1\levelold\levelspace0\levelindent283{\leveltext\'01\u-3913 ?;}{\levelnumbers;}\f3\fbias0 \fi-283\li283\lin283 }}\ls1}{\listoverride\listid543324763\listoverridecount0\ls2}
{\listoverride\listid2028016505\listoverridecount0\ls3}{\listoverride\listid190145115\listoverridecount0\ls4}{\listoverride\listid1403941801\listoverridecount0\ls5}{\listoverride\listid1889994174\listoverridecount0\ls6}{\listoverride\listid204221188
\listoverridecount0\ls7}{\listoverride\listid583338098\listoverridecount0\ls8}{\listoverride\listid561211173\listoverridecount0\ls9}{\listoverride\listid1214316582\listoverridecount0\ls10}{\listoverride\listid771126764\listoverridecount0\ls11}
{\listoverride\listid462045303\listoverridecount0\ls12}{\listoverride\listid1538081160\listoverridecount0\ls13}{\listoverride\listid590091954\listoverridecount0\ls14}{\listoverride\listid1734812107\listoverridecount0\ls15}{\listoverride\listid1300184623
\listoverridecount0\ls16}{\listoverride\listid855463441\listoverridecount0\ls17}{\listoverride\listid399254398\listoverridecount0\ls18}{\listoverride\listid1551961698\listoverridecount0\ls19}{\listoverride\listid1813057095\listoverridecount0\ls20}}
{\*\rsidtbl \rsid1721752\rsid1909948\rsid11889854\rsid13959554}{\*\generator Microsoft Word 10.0.2627;}{\info{\title Decal README}{\author Adam Wright}{\operator Jeffrey Dodge}{\creatim\yr2002\mo10\dy3\hr3\min43}{\revtim\yr2003\mo6\dy23\hr3\min4}
{\version4}{\edmins9}{\nofpages2}{\nofwords407}{\nofchars2321}{\*\company The Anarchs}{\nofcharsws2723}{\vern16437}}\widowctrl\ftnbj\aenddoc\noxlattoyen\expshrtn\noultrlspc\dntblnsbdb\nospaceforul\hyphcaps0\horzdoc\dghspace120\dgvspace120\dghorigin1701
\dgvorigin1984\dghshow0\dgvshow3\jcompress\viewkind4\viewscale100\nolnhtadjtbl\rsidroot13959554 \fet0\sectd \linex0\headery709\footery709\colsx709\sectdefaultcl\sftnbj {\*\pnseclvl1\pnucrm\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl2
\pnucltr\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl3\pndec\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl4\pnlcltr\pnstart1\pnindent720\pnhang {\pntxta )}}{\*\pnseclvl5\pndec\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl6
\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl7\pnlcrm\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl8\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl9\pnlcrm\pnstart1\pnindent720\pnhang
{\pntxtb (}{\pntxta )}}\pard\plain \qc \li0\ri0\nowidctlpar\faauto\rin0\lin0\itap0 \fs24\lang1033\langfe1033\cgrid\langnp1033\langfenp1033 {\b\f37\fs28\cf1\insrsid13959554 Decal README
\par }{\f2\fs20\cf1\insrsid13959554
\par }{\fs20\cf1\insrsid11889854 This is the 2}{\fs20\cf1\super\insrsid11889854\charrsid11889854 nd}{\fs20\cf1\insrsid11889854 release candidate of Decal version 2.5.2.0}{\fs20\cf1\insrsid13959554 .
\par
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\rin0\lin0\itap0 {\fs22\cf1\insrsid11889854 This is Decal 2.5.2.0 Release Candidate 2 -- a }{\fs22\cf1\insrsid13959554 supported release. We hope that our release}{\fs22\cf1\insrsid11889854 candidates}{
\fs22\cf1\insrsid13959554 are bug free, but if you run into problems, please report them at }{\field{\*\fldinst {\fs22\cf1\insrsid13959554 HYPERLINK "http://forums.acdev.org/phpBB2/viewforum.php" }{\fs22\cf1\insrsid1909948\charrsid1721752 {\*\datafield
00d0c9ea79f9bace118c8200aa004ba90b02000000170000002d00000068007400740070003a002f002f0066006f00720075006d0073002e00610063006400650076002e006f00720067002f007000680070004200420032002f00760069006500770066006f00720075006d002e007000680070000000e0c9ea79f9bace11
8c8200aa004ba90b5a00000068007400740070003a002f002f0066006f00720075006d0073002e00610063006400650076002e006f00720067002f007000680070004200420032002f00760069006500770066006f00720075006d002e00700068007000000000}}}{\fldrslt {
\cs15\fs22\ul\cf2\insrsid13959554\charrsid1721752 http://forums.acdev.org/phpBB2/viewforum.php}}}{\fs22\cf1\insrsid13959554 .
\par This way we can keep track of what the current issues are and work to fix them for the }{\fs22\cf1\insrsid11889854 final release of Decal 2.5.2.0.}{\fs22\cf1\insrsid13959554
\par
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\rin0\lin0\itap0\pararsid11889854 {\b\fs22\cf1\insrsid11889854 Changes since Release 2.5.2.0 RC1
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid11889854 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid11889854
{\fs22\cf1\insrsid11889854 Fixed DenAgent inject dependency. Inject.dll may now reside anywhere on your system.}{\b\fs22\cf1\insrsid11889854\charrsid11889854
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid11889854 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid11889854
{\fs22\cf1\insrsid11889854 Fixed several DenAgent crashes.}{\b\fs22\cf1\insrsid11889854\charrsid11889854
\par }\pard \ql \li0\ri0\nowidctlpar{\*\pn \pnlvlcont\ilvl0\ls0\pnrnot0\pndec }\faauto\rin0\lin0\itap0\pararsid11889854 {\fs22\cf1\insrsid11889854
\par }{\b\fs22\cf1\insrsid11889854 Changes since Beta 2.5.0.5
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid11889854 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid11889854
{\fs22\cf1\insrsid11889854 Lots of bugfixes}{\b\fs22\cf1\insrsid11889854\charrsid11889854
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid11889854 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid11889854
{\fs22\cf1\insrsid11889854 The identify queue no longer fights with the client over whether or not the id panel is closed or open.}{\b\fs22\cf1\insrsid11889854\charrsid11889854
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid11889854 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid11889854
{\fs22\cf1\insrsid11889854 Manually identifying an item sends it to the top of the identify queue \endash you should notice that it is far easier to identify items manually now if a plugin is requesting several items to be identified.}{
\b\fs22\cf1\insrsid11889854
\par }\pard \ql \li0\ri0\nowidctlpar{\*\pn \pnlvlcont\ilvl0\ls0\pnrnot0\pndec }\faauto\rin0\lin0\itap0 {\fs22\cf1\insrsid11889854
\par }\pard \ql \li0\ri0\nowidctlpar{\*\pn \pnlvlcont\ilvl0\ls0\pnrnot0\pndec }\faauto\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554 Changes since Release 2.5.0.1 RC1
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid13959554
{\fs22\cf1\insrsid13959554 Far too many to list \endash most signifigant is the id queue}{\b\fs22\cf1\insrsid13959554
\par }\pard \ql \li0\ri0\nowidctlpar{\*\pn \pnlvlcont\ilvl0\ls0\pnrnot0\pndec }\faauto\rin0\lin0\itap0 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.5.0.1 RC1
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid13959554
{\fs22\cf1\insrsid13959554 Install now enters correct version into the registry}{\b\fs22\cf1\insrsid13959554
\par }\pard \ql \li0\ri0\nowidctlpar{\*\pn \pnlvlcont\ilvl0\ls0\pnrnot0\pndec }\faauto\rin0\lin0\itap0 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.5.0.0 RC3
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid13959554
{\fs22\cf1\insrsid13959554 .Net plugins will now show their version in the agent, rather than the version of the .Net COM proxy.}{\b\fs22\cf1\insrsid13959554
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-283\li283\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls1\pnrnot0\pnf3\pnstart1\pnindent283\pnhang {\pntxtb \'b7}}\faauto\ls1\rin0\lin283\itap0\pararsid13959554
{\fs22\cf1\insrsid13959554 ACHooks slightly cleaned up, should now behave as it did in 2.5.0.0 RC1.}{\b\fs22\cf1\insrsid13959554
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\rin0\lin0\itap0 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.5.0.0 RC1
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls2\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls2\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
CharStats will no longer crash if you switch characters too quickly
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls3\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls3\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
IPluginSink fix \endash if Decal never accepted your command line input, it should now
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls4\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls4\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
Much ACHooks cleanup and many fixes as well as new hooks for developers to use
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\ilvl12\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.4.1.4
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls5\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls5\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554 ?
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\ilvl12\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.4.1.3
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls6\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls6\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
CharStats fixes (enchantments should be far more reliable now)
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls7\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls7\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
Changes to the way controls track focus events
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls8\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls8\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
DenAgent no longer deletes XML files if there were problems updating
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls9\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls9\rin0\lin360\itap0\pararsid13959554 {\fs22\cf1\insrsid13959554
Add 'mask' option for vectors to handle animation packet
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\ilvl12\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.4.1.2
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls10\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls10\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 Compiled in VC6 (works on windows 9x again)
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls11\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls11\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 CharacterStats fixes
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls12\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls12\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 WorldFilter fixes
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\ilvl12\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554
\par Changes since Release 2.4.1.0
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls13\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls13\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks: QueryMemLoc added to the IDL (it should have always been there).
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls14\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls14\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks->QueryMemLoc now returns NULL if there is a client and memlocs.xml version mismatch.
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls15\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls15\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks is created by the Decal object rather than IPluginSite. As a result Services can obtain a reference to it now.
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls16\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls16\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks: SendTellEx Hook
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls17\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls17\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 DecalNet: Uses client hooks for a quicker and more stable parsing method. If the memory locations are not there, it falls back to the previous parser.
\par }\pard \ql \li0\ri0\nowidctlpar\faauto\ilvl12\rin0\lin0\itap0\pararsid13959554 {\b\fs22\cf1\insrsid13959554
\par
\par Changes since Release 2.4
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls18\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls18\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks: Added hook for SetAutoRun
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls19\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls19\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 ACHooks: Added hood for SendTell
\par {\pntext\pard\plain\f3\fs22\cf1\insrsid13959554 \loch\af3\dbch\af0\hich\f3 \'b7\tab}}\pard \ql \fi-360\li360\ri0\nowidctlpar{\*\pn \pnlvlbody\ilvl0\ls20\pnrnot0\pnf3 {\pntxtb \'b7}}\faauto\ls20\rin0\lin360\itap0\pararsid13959554 {
\fs22\cf1\insrsid13959554 WorldFilter: Now uses DestroyedObject hook, this should result in less lag and better memory usage
\par }}

View file

@ -0,0 +1,334 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Collections.ObjectModel;
namespace CustomCollections;
internal class HashedList<T> : IList<T>, ICollection<T>, IEnumerable<T>, IEnumerable
{
private class ListNode
{
public ListNode Previous;
public ListNode Next;
public T Value;
public ListNode(T v, ListNode prev, ListNode nxt)
{
Previous = prev;
Next = nxt;
Value = v;
}
}
private ListNode Head;
private ListNode Tail;
private Dictionary<T, ListNode> HashIndex = new Dictionary<T, ListNode>();
private int ChangeMarker;
private bool IndexCacheValid;
private int IndexCache_Index;
private ListNode IndexCache_Value;
public T this[int index]
{
get
{
if (index >= HashIndex.Count || index < 0)
{
throw new ArgumentOutOfRangeException();
}
return RunToIndex(index).Value;
}
set
{
if (index >= HashIndex.Count || index < 0)
{
throw new ArgumentOutOfRangeException();
}
if (HashIndex.ContainsKey(value))
{
throw new ArgumentException("Duplicate value");
}
ListNode listNode = RunToIndex(index);
HashIndex.Remove(listNode.Value);
listNode.Value = value;
HashIndex.Add(value, listNode);
ChangeMarker++;
}
}
public int Count => HashIndex.Count;
public bool IsReadOnly => false;
public HashedList()
{
}
public HashedList(T[] arr)
{
foreach (T item in arr)
{
Add(item);
}
}
private ListNode RunToIndex(int ind)
{
int num = HashIndex.Count / 2;
if (IndexCacheValid)
{
if (ind > IndexCache_Index)
{
if (ind - IndexCache_Index < num)
{
ListNode listNode = IndexCache_Value;
for (int i = IndexCache_Index; i < ind; i++)
{
listNode = listNode.Next;
}
IndexCache_Index = ind;
IndexCache_Value = listNode;
IndexCacheValid = true;
return listNode;
}
}
else if (IndexCache_Index - ind < num)
{
ListNode listNode2 = IndexCache_Value;
for (int num2 = IndexCache_Index; num2 > ind; num2--)
{
listNode2 = listNode2.Previous;
}
IndexCache_Index = ind;
IndexCache_Value = listNode2;
IndexCacheValid = true;
return listNode2;
}
}
if (ind < num)
{
ListNode listNode3 = Head;
for (int j = 0; j < ind; j++)
{
listNode3 = listNode3.Next;
}
if (listNode3 == null)
{
throw new Exception();
}
IndexCache_Index = ind;
IndexCache_Value = listNode3;
IndexCacheValid = true;
return listNode3;
}
ListNode listNode4 = Tail;
for (int num3 = HashIndex.Count - 1; num3 > ind; num3--)
{
listNode4 = listNode4.Previous;
}
if (listNode4 == null)
{
throw new Exception();
}
IndexCache_Index = ind;
IndexCache_Value = listNode4;
IndexCacheValid = true;
return listNode4;
}
private void RemoveNode(ListNode n)
{
if (n.Previous == null)
{
Head = n.Next;
}
else
{
n.Previous.Next = n.Next;
}
if (n.Next == null)
{
Tail = n.Previous;
}
else
{
n.Next.Previous = n.Previous;
}
HashIndex.Remove(n.Value);
}
public ReadOnlyCollection<T> AsReadOnly()
{
return new ReadOnlyCollection<T>(this);
}
public bool GetIfContains(T matchval, ref T outval)
{
if (HashIndex.ContainsKey(matchval))
{
outval = HashIndex[matchval].Value;
return true;
}
return false;
}
public int IndexOf(T item)
{
if (HashIndex.ContainsKey(item))
{
ListNode listNode = HashIndex[item];
ListNode listNode2 = Head;
for (int i = 0; i < HashIndex.Count; i++)
{
if (listNode2 == listNode)
{
return i;
}
listNode2 = listNode2.Next;
}
return -1;
}
return -1;
}
public void Insert(int index, T item)
{
if (index > HashIndex.Count || index < 0)
{
throw new ArgumentOutOfRangeException();
}
if (HashIndex.ContainsKey(item))
{
throw new ArgumentException("Duplicate value");
}
ListNode listNode;
if (index == HashIndex.Count)
{
Add(item);
listNode = HashIndex[item];
}
else if (index == 0)
{
listNode = new ListNode(item, null, Head);
Head.Previous = listNode;
Head = listNode;
HashIndex.Add(item, listNode);
}
else
{
ListNode listNode2 = RunToIndex(index - 1);
listNode = (listNode2.Next = new ListNode(item, listNode2, listNode2.Next));
listNode.Next.Previous = listNode;
HashIndex.Add(item, listNode);
}
ChangeMarker++;
IndexCache_Index = index;
IndexCache_Value = listNode;
IndexCacheValid = true;
}
public void RemoveAt(int index)
{
if (index >= HashIndex.Count || index < 0)
{
throw new ArgumentOutOfRangeException();
}
ListNode n = RunToIndex(index);
RemoveNode(n);
ChangeMarker++;
IndexCacheValid = false;
}
public void Add(T item)
{
ListNode listNode;
if (HashIndex.Count == 0)
{
listNode = (Tail = (Head = new ListNode(item, null, null)));
}
else
{
if (HashIndex.ContainsKey(item))
{
throw new ArgumentException("Duplicate value");
}
listNode = new ListNode(item, Tail, null);
Tail.Next = listNode;
Tail = listNode;
}
HashIndex.Add(item, listNode);
ChangeMarker++;
IndexCacheValid = false;
}
public void Clear()
{
Head = null;
Tail = null;
HashIndex.Clear();
ChangeMarker++;
IndexCacheValid = false;
}
public bool Contains(T item)
{
return HashIndex.ContainsKey(item);
}
public bool Remove(T item)
{
if (!HashIndex.ContainsKey(item))
{
return false;
}
RemoveNode(HashIndex[item]);
ChangeMarker++;
IndexCacheValid = false;
return true;
}
public void CopyTo(T[] array, int arrayIndex)
{
int num = arrayIndex + HashIndex.Count;
IEnumerator<T> enumerator = GetEnumerator();
for (int i = arrayIndex; i < num; i++)
{
enumerator.MoveNext();
array[i] = enumerator.Current;
}
}
public T[] ToArray()
{
T[] array = new T[HashIndex.Count];
CopyTo(array, 0);
return array;
}
public IEnumerator<T> GetEnumerator()
{
int startchangemarker = ChangeMarker;
for (ListNode cur = Head; cur != null; cur = cur.Next)
{
yield return cur.Value;
if (ChangeMarker != startchangemarker)
{
throw new Exception("Collection modified during enumeration");
}
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}

View file

@ -0,0 +1,213 @@
using System;
using System.ComponentModel;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Windows.Forms;
using Decal.Adapter.Support;
using Decal.Adapter.Wrappers;
using Decal.Interop.Core;
namespace Decal.Adapter.IDQueue;
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComDefaultInterface(typeof(IIdentifyFilter))]
[ProgId("DecalAdapter.FairIDQueue")]
[Guid("5CD85A12-3DED-48E7-B440-B41E2A1452D9")]
[CLSCompliant(true)]
public class FairIDQueue : FairRoundRobinScheduleQueue<Assembly, int>, IIdentifyFilter
{
private static int iVal = 1126270821;
private const int REQUEST_INTERVAL = 600;
private const int MAX_TRY_COUNT = 3;
private const int NULL_ACTION_ID = -1;
private Timer FireTimer = new Timer();
private DateTime LastFireTime = DateTime.MinValue;
private uint CurrentTimerFrame;
private uint LastTimerFireFrame;
private int UserRequestedID = -1;
private int UserRequestedAttempts;
private EventHandler<UserIDRequestProcessedEventArgs> mUserIDRequestProcessed;
[CLSCompliant(false)]
public event EventHandler<UserIDRequestProcessedEventArgs> UserIDRequestProcessed
{
add
{
mUserIDRequestProcessed = (EventHandler<UserIDRequestProcessedEventArgs>)Delegate.Combine(mUserIDRequestProcessed, value);
}
remove
{
mUserIDRequestProcessed = (EventHandler<UserIDRequestProcessedEventArgs>)Delegate.Remove(mUserIDRequestProcessed, value);
}
}
internal FairIDQueue()
: base(3, -1)
{
//IL_0001: Unknown result type (might be due to invalid IL or missing references)
//IL_000b: Expected O, but got Unknown
FireTimer.Interval = 600;
FireTimer.Tick += FireTimer_Tick;
CoreManager.Current.Actions.Underlying.SetIDFilter(this);
CoreManager.Current.MessageProcessed += Current_MessageProcessed;
CoreManager.Current.RenderFrame += Current_RenderFrame;
}
private void Current_RenderFrame(object sender, EventArgs e)
{
CurrentTimerFrame++;
}
private void Current_MessageProcessed(object sender, MessageProcessedEventArgs e)
{
if (e.Message.Type == 63408 && e.Message.Value<int>("event") == 201)
{
int num = e.Message.Value<int>("object");
DeleteAction(num);
if (UserRequestedID == num)
{
UserRequestedID = -1;
Util.SafeFireEvent(this, mUserIDRequestProcessed, new UserIDRequestProcessedEventArgs(num));
}
}
}
internal void Start()
{
LastFireTime = DateTime.MinValue;
FireTimer.Enabled = true;
}
internal void Stop()
{
FireTimer.Enabled = false;
ClearAll();
UserRequestedID = -1;
}
private void FireTimer_Tick(object sender, EventArgs e)
{
if (FireTimer.Interval != 600)
{
FireTimer.Enabled = false;
FireTimer.Interval = 600;
FireTimer.Enabled = true;
}
if (CurrentTimerFrame != LastTimerFireFrame)
{
LastTimerFireFrame = CurrentTimerFrame;
FireNow();
}
}
private void FireNow()
{
Assembly requester = null;
int num = -1;
if (UserRequestedID != -1)
{
num = UserRequestedID;
UserRequestedAttempts++;
if (UserRequestedAttempts > 3)
{
UserRequestedID = -1;
}
}
if (num == -1)
{
num = GetNextAction(ref requester);
}
if (num != -1)
{
LastFireTime = DateTime.Now;
int num2 = num ^ iVal;
CoreManager.Current.Actions.Underlying.CallerRefInstanceInternal = num2;
iVal = (num2 << 5) ^ (num2 >> 13) ^ iVal;
}
}
protected override bool IsActionValidNow(int action)
{
WorldObject worldObject = CoreManager.Current.WorldFilter[action];
if (worldObject == null)
{
return true;
}
if (worldObject.Container == 0)
{
WorldObject worldObject2 = CoreManager.Current.WorldFilter[CoreManager.Current.CharacterFilter.Id];
if (worldObject2 != null && worldObject.Coordinates().DistanceToCoords(worldObject2.Coordinates()) > 0.375)
{
return false;
}
}
return true;
}
protected override bool IsActionPermanentlyInvalid(int action)
{
return !CoreManager.Current.Actions.IsValidObject(action);
}
public void AddToQueue(int lObjectID)
{
AddToQueue(lObjectID, DateTime.MaxValue);
}
public void AddToQueue(int lObjectID, DateTime pTimeout)
{
Assembly assembly = Assembly.GetCallingAssembly();
if (assembly == null)
{
assembly = Assembly.GetExecutingAssembly();
}
AddToQueueForCaller(lObjectID, assembly, pTimeout);
}
internal void AddToQueueForCaller(int lObjectID, Assembly pCaller, DateTime pTimeout)
{
try
{
if (FireTimer.Enabled && lObjectID != -1)
{
Enqueue(pCaller, lObjectID, DateTime.MaxValue);
if ((DateTime.Now - LastFireTime).TotalMilliseconds > 700.0)
{
FireTimer.Enabled = false;
FireTimer.Interval = 1;
FireTimer.Enabled = true;
}
}
}
catch (Exception ex)
{
Util.WriteLine("Queue exception in addtoqueue: " + ex.ToString());
}
}
[CLSCompliant(false)]
[EditorBrowsable(EditorBrowsableState.Never)]
public void ShortcircuitID(int lObjectID)
{
if (FireTimer.Enabled && lObjectID != -1)
{
UserRequestedID = lObjectID;
UserRequestedAttempts = 0;
if ((DateTime.Now - LastFireTime).TotalMilliseconds > 700.0)
{
LastFireTime = DateTime.Now;
}
}
}
}

View file

@ -0,0 +1,281 @@
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Runtime.InteropServices;
using CustomCollections;
namespace Decal.Adapter.IDQueue;
[CLSCompliant(true)]
[ClassInterface(ClassInterfaceType.None)]
public abstract class FairRoundRobinScheduleQueue<CALLERTYPE, ACTIONTYPE>
{
public class ActionRemovedEventArgs : EventArgs
{
private ACTIONTYPE mAction;
public ACTIONTYPE Action => mAction;
internal ActionRemovedEventArgs(ACTIONTYPE pAction)
{
mAction = pAction;
}
}
private class ActionInfo : IEquatable<ActionInfo>
{
public ACTIONTYPE Action;
public DateTime Expires;
public int TryCount;
public ActionInfo(ACTIONTYPE pAction, DateTime pExpires)
{
Action = pAction;
Expires = pExpires;
}
public bool IsExpired()
{
return Expires < DateTime.Now;
}
public bool Equals(ActionInfo other)
{
ref ACTIONTYPE action = ref Action;
object obj = other.Action;
return action.Equals(obj);
}
public override bool Equals(object obj)
{
return Equals(obj as ActionInfo);
}
public override int GetHashCode()
{
return Action.GetHashCode();
}
}
private HashedList<CALLERTYPE> Callers = new HashedList<CALLERTYPE>();
private Dictionary<ACTIONTYPE, ActionInfo> ActInfos = new Dictionary<ACTIONTYPE, ActionInfo>();
private Dictionary<CALLERTYPE, HashedList<ActionInfo>> CallerActions = new Dictionary<CALLERTYPE, HashedList<ActionInfo>>();
private Dictionary<ACTIONTYPE, HashedList<CALLERTYPE>> ActionCallers = new Dictionary<ACTIONTYPE, HashedList<CALLERTYPE>>();
private int MaximumTryCount;
private ACTIONTYPE NullAction;
public int CallerCount => Callers.Count;
public int ActionCount => ActInfos.Count;
public event EventHandler<ActionRemovedEventArgs> OnActionRemoved;
protected FairRoundRobinScheduleQueue(int pMaximumTryCount, ACTIONTYPE pNullAction)
{
MaximumTryCount = pMaximumTryCount;
NullAction = pNullAction;
}
protected abstract bool IsActionValidNow(ACTIONTYPE action);
protected abstract bool IsActionPermanentlyInvalid(ACTIONTYPE action);
private void RotateQueue<T>(HashedList<T> q)
{
if (q.Count > 0)
{
T item = q[0];
q.RemoveAt(0);
q.Add(item);
}
}
public void ClearAll()
{
Callers.Clear();
ActInfos.Clear();
CallerActions.Clear();
ActionCallers.Clear();
}
public void DeleteAction(ACTIONTYPE action)
{
if (!ActionCallers.ContainsKey(action) || !ActInfos.ContainsKey(action))
{
return;
}
ActionInfo item = ActInfos[action];
ActInfos.Remove(action);
HashedList<CALLERTYPE> hashedList = ActionCallers[action];
ActionCallers.Remove(action);
foreach (CALLERTYPE item2 in hashedList)
{
CallerActions[item2].Remove(item);
if (CallerActions[item2].Count == 0)
{
CallerActions.Remove(item2);
Callers.Remove(item2);
}
}
if (this.OnActionRemoved != null)
{
this.OnActionRemoved(this, new ActionRemovedEventArgs(action));
}
}
public void DeleteCaller(CALLERTYPE caller)
{
Callers.Remove(caller);
if (!CallerActions.ContainsKey(caller))
{
return;
}
HashedList<ActionInfo> hashedList = CallerActions[caller];
CallerActions.Remove(caller);
HashedList<ActionInfo> hashedList2 = new HashedList<ActionInfo>();
foreach (ActionInfo item in hashedList)
{
if (ActionCallers.ContainsKey(item.Action))
{
ActionCallers[item.Action].Remove(caller);
if (ActionCallers[item.Action].Count == 0)
{
ActionCallers.Remove(item.Action);
ActInfos.Remove(item.Action);
hashedList2.Add(item);
}
}
}
if (this.OnActionRemoved == null)
{
return;
}
foreach (ActionInfo item2 in hashedList2)
{
this.OnActionRemoved(this, new ActionRemovedEventArgs(item2.Action));
}
}
public ReadOnlyCollection<ACTIONTYPE> GetActionsForCaller(CALLERTYPE caller)
{
List<ACTIONTYPE> list = new List<ACTIONTYPE>();
if (CallerActions.ContainsKey(caller))
{
foreach (ActionInfo item in CallerActions[caller])
{
list.Add(item.Action);
}
}
return list.AsReadOnly();
}
public ReadOnlyCollection<CALLERTYPE> GetCallersForAction(ACTIONTYPE action)
{
if (ActionCallers.ContainsKey(action))
{
return ActionCallers[action].AsReadOnly();
}
return new List<CALLERTYPE>().AsReadOnly();
}
public void Enqueue(CALLERTYPE caller, ACTIONTYPE action, DateTime expiration)
{
ActionInfo actionInfo;
if (ActInfos.ContainsKey(action))
{
actionInfo = ActInfos[action];
if (actionInfo.Expires < expiration)
{
actionInfo.Expires = expiration;
}
actionInfo.TryCount = 0;
}
else
{
actionInfo = new ActionInfo(action, expiration);
ActInfos[action] = actionInfo;
}
if (!CallerActions.ContainsKey(caller) || !CallerActions[caller].Contains(actionInfo))
{
if (!Callers.Contains(caller))
{
Callers.Insert(0, caller);
}
if (!CallerActions.ContainsKey(caller))
{
CallerActions.Add(caller, new HashedList<ActionInfo>());
}
CallerActions[caller].Add(actionInfo);
if (!ActionCallers.ContainsKey(action))
{
ActionCallers.Add(action, new HashedList<CALLERTYPE>());
}
ActionCallers[action].Add(caller);
}
}
public ACTIONTYPE GetNextAction(ref CALLERTYPE requester)
{
HashedList<ActionInfo> hashedList = new HashedList<ActionInfo>();
ACTIONTYPE result = NullAction;
for (int i = 0; i < Callers.Count; i++)
{
CALLERTYPE val = Callers[0];
HashedList<ActionInfo> hashedList2 = CallerActions[val];
bool flag = false;
for (int j = 0; j < hashedList2.Count; j++)
{
ActionInfo actionInfo = hashedList2[0];
if (hashedList.Contains(actionInfo))
{
RotateQueue(hashedList2);
continue;
}
if (actionInfo.IsExpired())
{
hashedList.Add(actionInfo);
RotateQueue(hashedList2);
continue;
}
if (IsActionPermanentlyInvalid(actionInfo.Action))
{
hashedList.Add(actionInfo);
RotateQueue(hashedList2);
continue;
}
if (!IsActionValidNow(actionInfo.Action))
{
RotateQueue(hashedList2);
continue;
}
flag = true;
result = actionInfo.Action;
requester = val;
RotateQueue(hashedList2);
actionInfo.TryCount++;
if (actionInfo.TryCount > MaximumTryCount)
{
hashedList.Add(actionInfo);
}
break;
}
RotateQueue(Callers);
if (flag)
{
break;
}
}
foreach (ActionInfo item in hashedList)
{
DeleteAction(item.Action);
}
return result;
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.IDQueue;
public class UserIDRequestProcessedEventArgs : EventArgs
{
private int mObjectId;
public int ObjectId => mObjectId;
internal UserIDRequestProcessedEventArgs(int ObjectId)
{
mObjectId = ObjectId;
}
}

View file

@ -0,0 +1,68 @@
using System;
using System.Collections.Generic;
namespace Decal.Adapter.Messages;
[CLSCompliant(true)]
public class AdapterMessageEventArgs : EventArgs
{
private EventHandler<AdapterMessageResponseEventArgs> responder;
private List<object> handlers;
private bool canAddHandlers;
internal bool CanAddHandlers
{
get
{
return canAddHandlers;
}
set
{
canAddHandlers = value;
}
}
public event EventHandler<AdapterMessageResponseEventArgs> MessageComplete
{
add
{
responder = (EventHandler<AdapterMessageResponseEventArgs>)Delegate.Combine(responder, value);
}
remove
{
responder = (EventHandler<AdapterMessageResponseEventArgs>)Delegate.Remove(responder, value);
}
}
internal AdapterMessageEventArgs()
{
handlers = new List<object>();
}
public void AddHandler(object obj)
{
if (!CanAddHandlers)
{
throw new InvalidOperationException("Unable to add handlers at this time");
}
if (obj != null)
{
handlers.Add(obj);
}
}
public void SetComplete(object handler, AdapterMessageResponseEventArgs e)
{
handlers.Remove(handler);
if (handlers.Count == 0)
{
e.Complete = true;
}
if (responder != null)
{
responder(this, e);
}
}
}

View file

@ -0,0 +1,30 @@
using System;
namespace Decal.Adapter.Messages;
[CLSCompliant(true)]
public class AdapterMessageResponseEventArgs : EventArgs
{
private bool success;
private bool complete;
public bool Succeeded => success;
public bool Complete
{
get
{
return complete;
}
internal set
{
complete = value;
}
}
protected AdapterMessageResponseEventArgs(bool success)
{
this.success = success;
}
}

View file

@ -0,0 +1,56 @@
using System;
namespace Decal.Adapter.NetParser;
internal class MemberParser : MarshalByRefObject
{
public MemberParser Next;
public MemberParser Child;
public MemberParserType MemberType;
public string MemberName;
public MemberParserCondition Condition;
public string ConditionField;
public long ConditionXor;
public long ConditionAnd;
public long ConditionResult;
public string LengthField;
public long LengthMask;
public int LengthDelta;
public int PreAlignment;
public int PostAlignment;
public MemberParser()
{
}
public MemberParser(MemberParser Source)
{
Next = Source.Next;
Child = Source.Child;
MemberType = Source.MemberType;
MemberName = Source.MemberName;
Condition = Source.Condition;
ConditionField = Source.ConditionField;
ConditionXor = Source.ConditionXor;
ConditionAnd = Source.ConditionAnd;
ConditionResult = Source.ConditionResult;
LengthField = Source.LengthField;
LengthMask = Source.LengthMask;
LengthDelta = Source.LengthDelta;
PreAlignment = Source.PreAlignment;
PostAlignment = Source.PostAlignment;
}
}

View file

@ -0,0 +1,12 @@
namespace Decal.Adapter.NetParser;
internal enum MemberParserCondition
{
None,
EQ,
NE,
GE,
GT,
LE,
LT
}

View file

@ -0,0 +1,18 @@
namespace Decal.Adapter.NetParser;
internal enum MemberParserType
{
BYTE,
WORD,
PackedWORD,
DWORD,
PackedDWORD,
QWORD,
@float,
@double,
String,
WString,
Struct,
Vector,
Case
}

View file

@ -0,0 +1,24 @@
using System;
using System.Runtime.InteropServices;
using Decal.Interop.Net;
namespace Decal.Adapter.NetParser;
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComDefaultInterface(typeof(IMessageFactory))]
[ProgId("DecalAdapter.MessageFactory")]
[Guid("59D7815E-6716-4bd7-B264-69B6A9382701")]
public class MessageFactory : IMessageFactory
{
IMessage2 IMessageFactory.CreateMessage(int pData, int size, bool outgoing)
{
if (pData != 0 && size != 0)
{
byte[] array = (byte[])Array.CreateInstance(typeof(byte), size);
Marshal.Copy(new IntPtr(pData), array, 0, size);
return new MessageWrapper(new Message(array, Message.GetParser(BitConverter.ToInt32(array, 0), outgoing ? MessageDirection.Outbound : MessageDirection.Inbound)));
}
return null;
}
}

View file

@ -0,0 +1,62 @@
using System.Runtime.InteropServices;
using Decal.Interop.Net;
namespace Decal.Adapter.NetParser;
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComDefaultInterface(typeof(IMessageMember))]
[ProgId("DecalAdapter.MessageMemberWrapper")]
[Guid("BD22CFC5-0950-4ab3-9752-5053EE934BE6")]
public class MessageMemberWrapper : MessageRootImpl, IMessageMember
{
public int BeginOffset => Data.mOffset;
public int Count => Data.Count;
public int EndOffset => Data.mOffset + Data.mLength;
// IMessageMember properties - parameterless accessors for the COM interface
object IMessageMember.Value => get_Value(0);
byte[] IMessageMember.RawValue => get_RawValue(0);
IMessageMember IMessageMember.Struct => get_Struct(0);
public MessageMemberWrapper()
{
}
internal MessageMemberWrapper(MessageStruct msg, MessageWrapper wrapper)
: base(msg, wrapper)
{
}
public string get_FieldName(int Index)
{
return Data.Name(Index);
}
public byte[] get_RawValue(object vIndex)
{
return Data.RawValue(Data.ObjectToIndex(vIndex));
}
public IMessageMember get_Struct(object vIndex)
{
int num = Data.ObjectToIndex(vIndex);
if (num < 0)
{
throw new COMHResultException((HResults)(-2147352571));
}
return new MessageMemberWrapper(Data.Struct(num), Wrapped);
}
public object get_Value(object vIndex)
{
int num = Data.ObjectToIndex(vIndex);
if (num >= 0)
{
return Data.Value<object>(num);
}
throw new COMHResultException((HResults)(-2147352571));
}
}

View file

@ -0,0 +1,130 @@
using System.Diagnostics;
using Decal.Interop.Net;
namespace Decal.Adapter.NetParser;
public class MessageRootImpl : MessageRoot, IMessageIterator
{
protected MessageWrapper Wrapped;
protected MessageStruct Data;
protected int FieldIndex;
protected const int Error = -1;
public object Current => Data.Value<object>(FieldIndex);
public string FieldName => Data.Name(FieldIndex);
public int Index => FieldIndex;
public IMessage Message => Wrapped;
public MessageRoot NextObjectIndex
{
[DebuggerNonUserCode]
get
{
if (FieldIndex < Data.mCount)
{
MessageMemberWrapper result = new MessageMemberWrapper(Data.Struct(FieldIndex), Wrapped);
FieldIndex++;
return result;
}
throw new COMHResultException(HResults.E_FAIL);
}
}
// IMessageIterator properties - parameterless accessors for the COM interface.
// The parameterized get_Next/get_NextString etc. below are the COM parameterized property accessors.
object IMessageIterator.Next => throw new COMHResultException(HResults.E_FAIL);
string IMessageIterator.NextString => throw new COMHResultException(HResults.E_FAIL);
int IMessageIterator.NextInt => throw new COMHResultException(HResults.E_FAIL);
double IMessageIterator.NextFloat => throw new COMHResultException(HResults.E_FAIL);
MessageRoot IMessageIterator.NextObject => throw new COMHResultException(HResults.E_FAIL);
ulong IMessageIterator.NextQWord => throw new COMHResultException(HResults.E_FAIL);
protected MessageRootImpl()
{
}
protected MessageRootImpl(MessageStruct data, MessageWrapper wrapper)
: this()
{
Wrapped = wrapper;
Data = data;
if (!Data.mParsed)
{
Data.Parse();
}
}
public void Reset()
{
FieldIndex = 0;
}
[DebuggerNonUserCode]
private T GetNext<T>(string name)
{
FieldIndex = Data.IndexFromName(name);
if (FieldIndex != -1)
{
return Data.Value<T>(FieldIndex);
}
throw new COMHResultException(HResults.E_FAIL);
}
[DebuggerNonUserCode]
private T GetNext<T>(int index)
{
if (index >= 0 && index < Data.mCount)
{
FieldIndex = index;
return Data.Value<T>(FieldIndex);
}
throw new COMHResultException(HResults.E_FAIL);
}
[DebuggerNonUserCode]
public object get_Next(object vIndex)
{
return GetNext<object>(Data.ObjectToIndex(vIndex));
}
[DebuggerNonUserCode]
public double get_NextFloat(string Name)
{
return GetNext<double>(Name);
}
[DebuggerNonUserCode]
public int get_NextInt(string Name)
{
return GetNext<int>(Name);
}
[DebuggerNonUserCode]
public MessageRoot get_NextObject(string Name)
{
FieldIndex = Data.IndexFromName(Name);
if (FieldIndex != -1)
{
return new MessageMemberWrapper(Data.Struct(FieldIndex), Wrapped);
}
throw new COMHResultException(HResults.E_FAIL);
}
[DebuggerNonUserCode]
public ulong get_NextQWord(string Name)
{
return GetNext<ulong>(Name);
}
[DebuggerNonUserCode]
public string get_NextString(string Name)
{
return GetNext<string>(Name);
}
}

View file

@ -0,0 +1,21 @@
using System.Runtime.InteropServices;
using Decal.Interop.Net;
namespace Decal.Adapter.NetParser;
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComDefaultInterface(typeof(MessageRoot))]
[ProgId("DecalAdapter.MessageRootWrapper")]
[Guid("E33FBF17-B6C5-471e-9ED6-A394DEDEBFE5")]
public class MessageRootWrapper : MessageRootImpl
{
public MessageRootWrapper()
{
}
internal MessageRootWrapper(MessageWrapper msg)
: base(msg.Wrapped.mStruct, msg)
{
}
}

View file

@ -0,0 +1,77 @@
using System.Runtime.InteropServices;
using Decal.Interop.Net;
namespace Decal.Adapter.NetParser;
[ComVisible(true)]
[ClassInterface(ClassInterfaceType.None)]
[ComDefaultInterface(typeof(IMessage2))]
[ProgId("DecalAdapter.MessageWrapper")]
[Guid("76142307-98E3-494d-8320-3C801010221D")]
public class MessageWrapper : IMessage2, IMessage
{
private Message msg;
internal Message Wrapped => msg;
public MessageRoot Begin => new MessageRootWrapper(this);
public int Count => msg.Count;
public byte[] RawData => msg.RawData;
public int Type => msg.Type;
// IMessage/IMessage2 properties - parameterless accessors for the COM interface
object IMessage.Value => get_Value(0);
IMessageMember IMessage.Struct => get_Struct(0);
byte[] IMessage.RawValue => get_RawValue(0);
string IMessage.FieldName => get_FieldName(0);
object IMessage2.Value => get_Value(0);
IMessageMember IMessage2.Struct => get_Struct(0);
byte[] IMessage2.RawValue => get_RawValue(0);
string IMessage2.FieldName => get_FieldName(0);
public MessageWrapper()
{
}
internal MessageWrapper(Message msg)
{
this.msg = msg;
if (!this.msg.mStruct.mParsed)
{
this.msg.mStruct.Parse();
}
}
public string get_FieldName(int Index)
{
return msg.Name(Index);
}
public byte[] get_RawValue(object vElement)
{
return msg.RawValue(msg.mStruct.ObjectToIndex(vElement));
}
public IMessageMember get_Struct(object vElement)
{
int num = msg.mStruct.ObjectToIndex(vElement);
if (num < 0)
{
throw new COMHResultException((HResults)1);
}
return new MessageMemberWrapper(msg.Struct(num), this);
}
public object get_Value(object vElement)
{
int num = msg.mStruct.ObjectToIndex(vElement);
if (num >= 0)
{
return msg.Value<object>(num);
}
return null;
}
}

View file

@ -0,0 +1,176 @@
#define TRACE
using System;
using System.CodeDom.Compiler;
using System.ComponentModel;
using System.Diagnostics;
using System.Drawing;
using Decal.Interop.Core;
using Microsoft.CSharp;
using Microsoft.Win32;
namespace Decal.Adapter.Support;
internal static class Util
{
private static int mTrace;
internal static int TraceLevel
{
get
{
return mTrace;
}
set
{
mTrace = value;
}
}
internal static Color ColorFromBGR(int color)
{
return Color.FromArgb(color & 0xFF, (color & 0xFF00) >> 8, (color & 0xFF0000) >> 16);
}
internal static int ColorToBGR(Color color)
{
return (color.B << 16) | (color.G << 8) | color.R;
}
internal static Rectangle toRectangle(tagRECT tr)
{
return new Rectangle(tr.left, tr.top, tr.right - tr.left, tr.bottom - tr.top);
}
internal static tagRECT toTagRECT(Rectangle r)
{
tagRECT result = default(tagRECT);
result.top = r.Top;
result.left = r.Left;
result.bottom = r.Bottom;
result.right = r.Right;
return result;
}
internal static T UnboxTo<T>(object obj)
{
//IL_000a: Unknown result type (might be due to invalid IL or missing references)
try
{
return (T)obj;
}
catch (InvalidCastException)
{
TypeConverter converter = ((CodeDomProvider)new CSharpCodeProvider()).GetConverter(obj.GetType());
if (converter.CanConvertTo(typeof(T)))
{
return (T)converter.ConvertTo(obj, typeof(T));
}
WriteLine("Error Converting object type {0} to {1}", obj.GetType(), typeof(T));
throw;
}
}
internal static void InitializeTracing(string key, string value, int defaultValue)
{
try
{
TraceLevel = (int)Registry.GetValue(key, value, defaultValue);
}
catch
{
TraceLevel = 0;
}
}
public static void WriteLine(string fmt, params object[] args)
{
WriteLine(1, fmt, args);
}
public static void WriteLine(int traceLevel, string fmt, params object[] args)
{
WriteLine(traceLevel, string.Format(fmt, args));
}
public static void WriteLine(int traceLevel, string msg)
{
Trace.WriteLineIf(mTrace >= traceLevel, msg);
}
public static void Write(string fmt, params object[] args)
{
Write(1, string.Format(fmt, args));
}
public static void Write(int traceLevel, string msg)
{
Trace.WriteIf(mTrace >= traceLevel, msg);
}
public static void SafeFireEvent(object sender, EventHandler eventHandler, EventArgs args)
{
if (eventHandler == null)
{
return;
}
Delegate[] invocationList = eventHandler.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
EventHandler eventHandler2 = (EventHandler)invocationList[i];
try
{
eventHandler2(sender, args);
}
catch (Exception ex)
{
WriteLine("SafeFire exception: {0}", ex.ToString());
}
}
}
public static void SafeFireEvent<T>(object sender, EventHandler<T> eventHandler, T args) where T : EventArgs
{
if (eventHandler == null)
{
return;
}
Delegate[] invocationList = eventHandler.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
EventHandler<T> eventHandler2 = (EventHandler<T>)invocationList[i];
try
{
eventHandler2(sender, args);
}
catch (Exception ex)
{
WriteLine("SafeFire exception: {0}", ex.ToString());
}
}
}
public static void SafeFireEvent<T>(object sender, EventHandler<T> eventHandler, T args, ref bool eaten) where T : EatableEventArgs
{
if (eventHandler == null)
{
return;
}
Delegate[] invocationList = eventHandler.GetInvocationList();
for (int i = 0; i < invocationList.Length; i++)
{
EventHandler<T> eventHandler2 = (EventHandler<T>)invocationList[i];
try
{
eventHandler2(sender, args);
if (args.Eat)
{
eaten = true;
}
}
catch (Exception ex)
{
WriteLine("SafeFire exception: {0}", ex.ToString());
}
}
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class AcceptTradeEventArgs : EventArgs
{
private int mTargetId;
public int TargetId => mTargetId;
internal AcceptTradeEventArgs(int TargetId)
{
mTargetId = TargetId;
}
}

View file

@ -0,0 +1,22 @@
using System;
namespace Decal.Adapter.Wrappers;
public class AccountCharInfo : MarshalByRefObject
{
private int myIndex;
private CharacterFilter myFilter;
public string Name => myFilter.get_AccountCharName(myIndex);
public int Id => myFilter.get_AccountCharID(myIndex);
public int Index => myIndex;
internal AccountCharInfo(CharacterFilter filter, int index)
{
myFilter = filter;
myIndex = index;
}
}

View file

@ -0,0 +1,10 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum AddRemoveEventType
{
Add,
Delete
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class AddTradeItemEventArgs : EventArgs
{
private int mItemId;
private int mSideId;
public int ItemId => mItemId;
public int SideId => mSideId;
internal AddTradeItemEventArgs(int ItemId, int SideId)
{
mItemId = ItemId;
mSideId = SideId;
}
}

View file

@ -0,0 +1,71 @@
using System;
using System.Runtime.InteropServices;
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public class AllegianceInfoWrapper : MarshalByRefObject, IDisposable
{
private AllegianceInfo myAllegianceInfo;
private bool isDisposed;
public int Id => myAllegianceInfo.GUID;
public int Gender => myAllegianceInfo.Gender;
public int Leadership => myAllegianceInfo.Leadership;
public int Loyalty => myAllegianceInfo.Loyalty;
public string Name => myAllegianceInfo.Name;
public int Race => myAllegianceInfo.Race;
public int Rank => myAllegianceInfo.Rank;
public int ParentId => myAllegianceInfo.TreeParent;
public int Type => myAllegianceInfo.Type;
public double Unknown => myAllegianceInfo.Unknown;
public long XP => myAllegianceInfo.XP_64;
internal AllegianceInfoWrapper(AllegianceInfo info)
{
myAllegianceInfo = info;
}
~AllegianceInfoWrapper()
{
Dispose(disposing: false);
}
public void Dispose()
{
Dispose(disposing: true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (!isDisposed)
{
}
if (myAllegianceInfo != null)
{
Marshal.ReleaseComObject(myAllegianceInfo);
}
isDisposed = true;
}
protected void EnforceDisposedOnce()
{
if (isDisposed)
{
throw new ObjectDisposedException("AllegianceInfoWrapper");
}
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ApproachVendorEventArgs : EventArgs
{
private int mMerchantId;
private Vendor vendor;
public int MerchantId => mMerchantId;
public Vendor Vendor => vendor;
internal ApproachVendorEventArgs(int MerchantId, Vendor ven)
{
mMerchantId = MerchantId;
vendor = ven;
}
}

View file

@ -0,0 +1,59 @@
using System;
using System.Runtime.InteropServices;
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public class AttributeInfoWrapper : MarshalByRefObject, IDisposable
{
private AttributeInfo myAttribInfo;
private bool isDisposed;
public int Base => myAttribInfo.Base;
public int Buffed => myAttribInfo.Buffed;
public int Creation => myAttribInfo.Creation;
public int Exp => myAttribInfo.Exp;
public string Name => myAttribInfo.Name;
internal AttributeInfoWrapper(AttributeInfo info)
{
myAttribInfo = info;
}
~AttributeInfoWrapper()
{
Dispose(disposing: false);
}
public void Dispose()
{
Dispose(disposing: true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (!isDisposed)
{
}
if (myAttribInfo != null)
{
Marshal.ReleaseComObject(myAttribInfo);
}
isDisposed = true;
}
protected void EnforceDisposedOnce()
{
if (isDisposed)
{
throw new ObjectDisposedException("AttributeInfoWrapper");
}
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum AttributeType
{
CurrentStrength = 1,
CurrentEndurance,
CurrentQuickness,
CurrentCoordination,
CurrentFocus,
CurrentSelf,
BaseStrength,
BaseEndurance,
BaseQuickness,
BaseCoordination,
BaseFocus,
BaseSelf
}

View file

@ -0,0 +1,78 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum Augmentations
{
ReinforcementLugians = 218,
BleearghFortitude = 219,
OswaldEnchancement = 220,
SiraluunBlessing = 221,
EnduringCalm = 222,
SteadfastWill = 223,
CiandraEssence = 224,
YoshiEssence = 225,
JibrilEssence = 226,
CeldisethEssence = 227,
KogaEssence = 228,
ShadowSeventhMule = 229,
MightSeventhMule = 230,
ClutchMiser = 231,
EnduringEnchantment = 232,
CriticalProtection = 233,
QuickLearner = 234,
CiandraFortune = 235,
CharmedSmith = 236,
InnateRenewal = 237,
ArchmageEndurance = 238,
BladeTurner = 240,
ArrowTurner = 241,
MaceTurner = 242,
CausticEnhancement = 243,
FieryEnchancment = 244,
IcyEnchancement = 245,
LightningEnhancement = 246,
InfusedCreature = 294,
InfusedItem = 295,
InfusedLife = 296,
InfusedWar = 297,
EyeRemorseless = 298,
HandRemorseless = 299,
MasterSteelCircle = 300,
MasterFocusedEyed = 301,
MasterFiveFoldPath = 302,
FrenzySlayer = 309,
IronSkinInvincible = 310,
JackOfAllTrades = 326,
InfusedVoid = 328,
[Obsolete("Use InfusedVoid")]
UnknownAug1 = 328,
[Obsolete("Not an aug")]
UnknownAug2 = 329,
[Obsolete("Not an aug")]
UnknownAug3 = 330,
[Obsolete("Not an aug")]
UnknownAug4 = 331,
[Obsolete("Not an aug")]
UnknownAug5 = 332,
AuraValor = 333,
AuraProtection = 334,
AuraGlory = 335,
AuraTemperance = 336,
AuraSurge = 337,
[Obsolete("Not an aug")]
UnknownAug6 = 337,
AuraAethericVision = 338,
AuraManaFlow = 339,
AuraManaInfusion = 340,
[Obsolete("Use AuraManaInfusion")]
UnknownAug7 = 340,
AuraVitality = 341,
[Obsolete("Use AuraVitality")]
UnknownAug8 = 341,
AuraPurity = 342,
AuraCraftsman = 343,
AuraSpecialization = 344,
AuraWorld = 365
}

View file

@ -0,0 +1,29 @@
using System;
using Decal.Interop.Render;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public class Background : HudRenderTarget
{
private HUDBackground internalBackground;
internal HUDBackground Underlying => internalBackground;
internal Background(HUDBackground background)
: base(background)
{
internalBackground = background;
}
public Background Clone()
{
return new Background(internalBackground.Clone());
}
protected override void Dispose(bool disposing)
{
internalBackground = null;
base.Dispose(disposing);
}
}

View file

@ -0,0 +1,16 @@
namespace Decal.Adapter.Wrappers;
public enum BoolValueKey
{
Lockable = 201326592,
Inscribable = 201326593,
Open = 2,
Locked = 3,
HookVisibility = 24,
UnlimitedUses = 63,
CanBeSold = 69,
Retained = 91,
Ivoryable = 99,
Dyeable = 100,
AwayFromKeyboard = 110
}

View file

@ -0,0 +1,229 @@
using System;
using System.Drawing;
using Decal.Adapter.Support;
using Decal.Interop.Inject;
namespace Decal.Adapter.Wrappers;
public class ButtonWrapper : ControlWrapperBase<ButtonClass>
{
private EventHandler<ControlEventArgs> evtClick;
private EventHandler<ControlEventArgs> evtCancel;
private EventHandler<ControlEventArgs> evtDestroy;
private EventHandler<ControlEventArgs> evtHit;
private EventHandler<ControlEventArgs> evtUnhit;
private int myBackground;
public Color Matte
{
get
{
return Util.ColorFromBGR(base.Control.Matte);
}
set
{
base.Control.Matte = Util.ColorToBGR(value);
}
}
public int Background
{
get
{
return myBackground;
}
set
{
myBackground = value;
base.Control.SetBackground(myBackground);
}
}
public event EventHandler<ControlEventArgs> Click
{
add
{
if (evtClick == null)
{
base.Control.Accepted += ClickEvent;
}
evtClick = (EventHandler<ControlEventArgs>)Delegate.Combine(evtClick, value);
}
remove
{
evtClick = (EventHandler<ControlEventArgs>)Delegate.Remove(evtClick, value);
if (evtClick == null)
{
base.Control.Accepted -= ClickEvent;
}
}
}
public event EventHandler<ControlEventArgs> Canceled
{
add
{
if (evtCancel == null)
{
base.Control.Canceled += CanceledEvent;
}
evtCancel = (EventHandler<ControlEventArgs>)Delegate.Combine(evtCancel, value);
}
remove
{
evtCancel = (EventHandler<ControlEventArgs>)Delegate.Remove(evtCancel, value);
if (evtCancel == null)
{
base.Control.Canceled -= CanceledEvent;
}
}
}
public event EventHandler<ControlEventArgs> Destroy
{
add
{
if (evtDestroy == null)
{
base.Control.Destroy += DestroyEvent;
}
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Combine(evtDestroy, value);
}
remove
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, value);
if (evtDestroy == null)
{
base.Control.Destroy -= DestroyEvent;
}
}
}
public event EventHandler<ControlEventArgs> Hit
{
add
{
if (evtHit == null)
{
base.Control.Hit += HitEvent;
}
evtHit = (EventHandler<ControlEventArgs>)Delegate.Combine(evtHit, value);
}
remove
{
evtHit = (EventHandler<ControlEventArgs>)Delegate.Remove(evtHit, value);
if (evtHit == null)
{
base.Control.Hit -= HitEvent;
}
}
}
public event EventHandler<ControlEventArgs> Unhit
{
add
{
if (evtUnhit == null)
{
base.Control.Unhit += UnhitEvent;
}
evtUnhit = (EventHandler<ControlEventArgs>)Delegate.Combine(evtUnhit, value);
}
remove
{
evtUnhit = (EventHandler<ControlEventArgs>)Delegate.Remove(evtUnhit, value);
if (evtUnhit == null)
{
base.Control.Unhit -= UnhitEvent;
}
}
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
if (evtClick != null)
{
evtClick = (EventHandler<ControlEventArgs>)Delegate.Remove(evtClick, evtClick);
base.Control.Accepted -= ClickEvent;
}
if (evtCancel != null)
{
evtCancel = (EventHandler<ControlEventArgs>)Delegate.Remove(evtCancel, evtCancel);
base.Control.Canceled -= CanceledEvent;
}
if (evtDestroy != null)
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, evtDestroy);
base.Control.Destroy -= DestroyEvent;
}
if (evtHit != null)
{
evtHit = (EventHandler<ControlEventArgs>)Delegate.Remove(evtHit, evtHit);
base.Control.Hit -= HitEvent;
}
if (evtUnhit != null)
{
evtUnhit = (EventHandler<ControlEventArgs>)Delegate.Remove(evtUnhit, evtUnhit);
base.Control.Unhit -= UnhitEvent;
}
}
base.Dispose(disposing);
}
public void SetImages(int released, int pressed)
{
SetImages(0, released, pressed);
}
public void SetImages(int module, int released, int pressed)
{
base.Control.SetImages(module, released, pressed);
}
private void ClickEvent(int ID)
{
if (evtClick != null)
{
evtClick(this, new ControlEventArgs(ID));
}
}
private void UnhitEvent(int ID)
{
if (evtUnhit != null)
{
evtUnhit(this, new ControlEventArgs(ID));
}
}
private void HitEvent(int ID)
{
if (evtHit != null)
{
evtHit(this, new ControlEventArgs(ID));
}
}
private void DestroyEvent(int ID)
{
if (evtDestroy != null)
{
evtDestroy(this, new ControlEventArgs(ID));
}
}
private void CanceledEvent(int ID)
{
if (evtCancel != null)
{
evtCancel(this, new ControlEventArgs(ID));
}
}
}

View file

@ -0,0 +1,16 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByAllFilter : WorldObjectCollectionFilter
{
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByAll();
}
internal override void ApplyFilter(Decal.Interop.Filters.Vendor ven)
{
ven.ByAll();
}
}

View file

@ -0,0 +1,39 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByCategoryFilter : WorldObjectCollectionFilter
{
private int category;
public int Category
{
get
{
return category;
}
set
{
category = value;
}
}
public ByCategoryFilter()
{
}
public ByCategoryFilter(int category)
{
this.category = category;
}
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByCategory(category);
}
internal override void ApplyFilter(Decal.Interop.Filters.Vendor ven)
{
ven.ByCategory(category);
}
}

View file

@ -0,0 +1,34 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByContainerFilter : WorldObjectCollectionFilter
{
private int container;
public int Container
{
get
{
return container;
}
set
{
container = value;
}
}
public ByContainerFilter()
{
}
public ByContainerFilter(int container)
{
this.container = container;
}
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByContainer(container);
}
}

View file

@ -0,0 +1,11 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByInventoryFilter : WorldObjectCollectionFilter
{
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByInventory();
}
}

View file

@ -0,0 +1,11 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByLandscapeFilter : WorldObjectCollectionFilter
{
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByLandscape();
}
}

View file

@ -0,0 +1,39 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByNameFilter : WorldObjectCollectionFilter
{
private string name;
public string Name
{
get
{
return name;
}
set
{
name = value;
}
}
public ByNameFilter()
{
}
public ByNameFilter(string name)
{
this.name = name;
}
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByName(name);
}
internal override void ApplyFilter(Decal.Interop.Filters.Vendor ven)
{
ven.ByName(name);
}
}

View file

@ -0,0 +1,16 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByNameSubStringFilter : ByNameFilter
{
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByNameSubstring(base.Name);
}
internal override void ApplyFilter(Decal.Interop.Filters.Vendor ven)
{
ven.ByNameSubstring(base.Name);
}
}

View file

@ -0,0 +1,39 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByObjectClassFilter : WorldObjectCollectionFilter
{
private ObjectClass objClass;
public ObjectClass ObjectClass
{
get
{
return objClass;
}
set
{
objClass = value;
}
}
public ByObjectClassFilter()
{
}
public ByObjectClassFilter(ObjectClass objClass)
{
this.objClass = objClass;
}
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByObjectClass((eObjectClass)objClass);
}
internal override void ApplyFilter(Decal.Interop.Filters.Vendor ven)
{
ven.ByObjectClass((eObjectClass)objClass);
}
}

View file

@ -0,0 +1,34 @@
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ByOwnerFilter : WorldObjectCollectionFilter
{
private int owner;
public int Owner
{
get
{
return owner;
}
set
{
owner = value;
}
}
public ByOwnerFilter()
{
}
public ByOwnerFilter(int owner)
{
this.owner = owner;
}
internal override void ApplyFilter(WorldIterator wi)
{
wi.ByOwner(owner);
}
}

View file

@ -0,0 +1,10 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum CastEventType
{
Untargetted,
Targetted
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeEnchantmentsEventArgs : EventArgs
{
private AddRemoveEventType myType;
private EnchantmentWrapper myEnchantment;
public AddRemoveEventType Type => myType;
public EnchantmentWrapper Enchantment => myEnchantment;
internal ChangeEnchantmentsEventArgs(AddRemoveEventType type, EnchantmentWrapper enchantment)
{
myType = type;
myEnchantment = enchantment;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeExperienceEventArgs : EventArgs
{
private PlayerXPEventType myType;
private int myAmount;
public PlayerXPEventType Type => myType;
public int Amount => myAmount;
internal ChangeExperienceEventArgs(PlayerXPEventType type, int amount)
{
myType = type;
myAmount = amount;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeFellowshipEventArgs : EventArgs
{
private FellowshipEventType myType;
private int myId;
public FellowshipEventType Type => myType;
public int Id => myId;
internal ChangeFellowshipEventArgs(FellowshipEventType type, int Id)
{
myType = type;
myId = Id;
}
}

View file

@ -0,0 +1,21 @@
using System;
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class ChangeObjectEventArgs : EventArgs
{
private WorldObject myChangedObject;
private WorldChangeType myChangeType;
public WorldObject Changed => myChangedObject;
public WorldChangeType Change => myChangeType;
internal ChangeObjectEventArgs(WorldObject changedObject, Decal.Interop.Filters.WorldChangeType changeType)
{
myChangedObject = changedObject;
myChangeType = (WorldChangeType)changeType;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeOptionEventArgs : EventArgs
{
private int myOption;
private int myValue;
public int Option => myOption;
public int Value => myValue;
internal ChangeOptionEventArgs(int option, int value)
{
myOption = option;
myValue = value;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangePlayerEventArgs : EventArgs
{
private PlayerModifyEventType myType;
private int myStat;
public PlayerModifyEventType Type => myType;
public int Stat => myStat;
internal ChangePlayerEventArgs(PlayerModifyEventType type, int Stat)
{
myType = type;
myStat = Stat;
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangePortalModeEventArgs : EventArgs
{
private PortalEventType myType;
public PortalEventType Type => myType;
internal ChangePortalModeEventArgs(PortalEventType type)
{
myType = type;
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeSettingsFlagsEventArgs : EventArgs
{
private int mySettings;
public int Settings => mySettings;
internal ChangeSettingsFlagsEventArgs(int settings)
{
mySettings = settings;
}
}

View file

@ -0,0 +1,25 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeShortcutEventArgs : EventArgs
{
private AddRemoveEventType myType;
private int mySlot;
private int myObjectId;
public AddRemoveEventType Type => myType;
public int Slot => mySlot;
public int ObjectId => myObjectId;
internal ChangeShortcutEventArgs(AddRemoveEventType type, int Slot, int ObjectId)
{
myType = type;
mySlot = Slot;
myObjectId = ObjectId;
}
}

View file

@ -0,0 +1,30 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeSpellbarEventArgs : EventArgs
{
private AddRemoveEventType myType;
private int myTab;
private int mySlot;
private int mySpellId;
public AddRemoveEventType Type => myType;
public int Tab => myTab;
public int Slot => mySlot;
public int SpellId => mySpellId;
internal ChangeSpellbarEventArgs(AddRemoveEventType type, int Tab, int Slot, int SpellId)
{
myType = type;
myTab = Tab;
mySlot = Slot;
mySpellId = SpellId;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class ChangeVitalEventArgs : EventArgs
{
private CharFilterVitalType myType;
private int myAmount;
public CharFilterVitalType Type => myType;
public int Amount => myAmount;
internal ChangeVitalEventArgs(CharFilterVitalType type, int amount)
{
myType = type;
myAmount = amount;
}
}

View file

@ -0,0 +1,14 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum CharFilterAttributeType
{
Strength = 1,
Endurance,
Quickness,
Coordination,
Focus,
Self
}

View file

@ -0,0 +1,16 @@
namespace Decal.Adapter.Wrappers;
public enum CharFilterIndex
{
Vassals,
Enchantments,
Vitals,
Attributes,
Skills,
Characters,
Spells,
Augmentations,
EffectiveAttributes,
EffectiveVitals,
EffectiveSkills
}

View file

@ -0,0 +1,57 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum CharFilterSkillType
{
Axe = 1,
Bow = 2,
Crossbow = 3,
Dagger = 4,
Mace = 5,
MeleeDefense = 6,
MissileDefense = 7,
Spear = 9,
Staff = 10,
Sword = 11,
ThrownWeapons = 12,
Unarmed = 13,
ArcaneLore = 14,
MagicDefense = 15,
ManaConversion = 16,
ItemTinkering = 18,
AssessPerson = 19,
Deception = 20,
Healing = 21,
Jump = 22,
Lockpick = 23,
Run = 24,
AssessCreature = 27,
WeaponTinkering = 28,
ArmorTinkering = 29,
MagicItemTinkering = 30,
CreatureEnchantment = 31,
ItemEnchantment = 32,
LifeMagic = 33,
WarMagic = 34,
Leadership = 35,
Loyalty = 36,
Fletching = 37,
Alchemy = 38,
Cooking = 39,
Salvaging = 40,
TwoHandedCombat = 41,
Gearcraft = 42,
VoidMagic = 43,
HeavyWeapons = 44,
LightWeapons = 45,
FinesseWeapons = 46,
MissileWeapons = 47,
Shield = 48,
DualWield = 49,
Recklessness = 50,
SneakAttack = 51,
DirtyFighting = 52,
Summoning = 54
}

View file

@ -0,0 +1,11 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum CharFilterVitalType
{
Health = 2,
Stamina = 4,
Mana = 6
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,135 @@
using System;
using System.Drawing;
using Decal.Adapter.Support;
using Decal.Interop.Controls;
namespace Decal.Adapter.Wrappers;
public class CheckBoxWrapper : ControlWrapperBase<CheckboxClass>
{
private EventHandler<ControlEventArgs> evtDestroy;
private EventHandler<CheckBoxChangeEventArgs> evtChange;
public bool Checked
{
get
{
return base.Control.Checked;
}
set
{
base.Control.Checked = value;
}
}
public bool RightToLeft
{
get
{
return base.Control.RightToLeft;
}
set
{
base.Control.RightToLeft = value;
}
}
public string Text
{
get
{
return base.Control.Text;
}
set
{
base.Control.Text = value;
}
}
public Color TextColor
{
get
{
return Util.ColorFromBGR(base.Control.TextColor);
}
set
{
base.Control.TextColor = Util.ColorToBGR(value);
}
}
public event EventHandler<CheckBoxChangeEventArgs> Change
{
add
{
if (evtChange == null)
{
base.Control.Change += ChangeEvent;
}
evtChange = (EventHandler<CheckBoxChangeEventArgs>)Delegate.Combine(evtChange, value);
}
remove
{
evtChange = (EventHandler<CheckBoxChangeEventArgs>)Delegate.Remove(evtChange, value);
if (evtChange == null)
{
base.Control.Change -= ChangeEvent;
}
}
}
public event EventHandler<ControlEventArgs> Destroy
{
add
{
if (evtDestroy == null)
{
base.Control.Destroy += DestroyEvent;
}
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Combine(evtDestroy, value);
}
remove
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, value);
if (evtDestroy == null)
{
base.Control.Destroy -= DestroyEvent;
}
}
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
if (evtChange != null)
{
evtChange = (EventHandler<CheckBoxChangeEventArgs>)Delegate.Remove(evtChange, evtChange);
base.Control.Change -= ChangeEvent;
}
if (evtDestroy != null)
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, evtDestroy);
base.Control.Destroy -= DestroyEvent;
}
}
base.Dispose(disposing);
}
private void ChangeEvent(int ID, bool Checked)
{
if (evtChange != null)
{
evtChange(this, new CheckBoxChangeEventArgs(ID, Checked));
}
}
private void DestroyEvent(int ID)
{
if (evtDestroy != null)
{
evtDestroy(this, new ControlEventArgs(ID));
}
}
}

View file

@ -0,0 +1,33 @@
using System;
using System.Runtime.InteropServices;
using Decal.Interop.Controls;
namespace Decal.Adapter.Wrappers;
public sealed class ChoiceDataIndexer : IDisposable
{
private Choice myControl;
public object this[int index]
{
get
{
return ((dynamic)(IChoice)myControl).get_Data(index);
}
set
{
((dynamic)(IChoice)myControl).set_Data(index, value);
}
}
internal ChoiceDataIndexer(Choice control)
{
myControl = control;
}
public void Dispose()
{
Marshal.ReleaseComObject(myControl);
myControl = null;
}
}

View file

@ -0,0 +1,31 @@
using System;
using Decal.Interop.Controls;
namespace Decal.Adapter.Wrappers;
public sealed class ChoiceTextIndexer : IDisposable
{
private Choice myControl;
public string this[int index]
{
get
{
return ((dynamic)(IChoice)myControl).get_Text(index);
}
set
{
((dynamic)(IChoice)myControl).set_Text(index, value);
}
}
internal ChoiceTextIndexer(Choice control)
{
myControl = control;
}
public void Dispose()
{
myControl = null;
}
}

View file

@ -0,0 +1,191 @@
using System;
using Decal.Interop.Controls;
namespace Decal.Adapter.Wrappers;
public class ChoiceWrapper : ControlWrapperBase<ChoiceClass>
{
private EventHandler<ControlEventArgs> evtDropDown;
private EventHandler<ControlEventArgs> evtDestroy;
private EventHandler<IndexChangeEventArgs> evtChange;
private ChoiceTextIndexer myTextIndex;
private ChoiceDataIndexer myDataIndex;
public int Count => base.Control.ChoiceCount;
public int DropLines
{
get
{
return base.Control.DropLines;
}
set
{
base.Control.DropLines = value;
}
}
public bool Dropped
{
get
{
return base.Control.Dropped;
}
set
{
base.Control.Dropped = value;
}
}
public int Selected
{
get
{
return base.Control.Selected;
}
set
{
base.Control.Selected = value;
}
}
public ChoiceTextIndexer Text => myTextIndex;
public ChoiceDataIndexer Data => myDataIndex;
public event EventHandler<ControlEventArgs> DropDown
{
add
{
if (evtDropDown == null)
{
base.Control.DropDown += DropDownEvent;
}
evtDropDown = (EventHandler<ControlEventArgs>)Delegate.Combine(evtDropDown, value);
}
remove
{
evtDropDown = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDropDown, value);
if (evtDropDown == null)
{
base.Control.DropDown -= DropDownEvent;
}
}
}
public event EventHandler<ControlEventArgs> Destroy
{
add
{
if (evtDestroy == null)
{
base.Control.Destroy += DestroyEvent;
}
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Combine(evtDestroy, value);
}
remove
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, value);
if (evtDestroy == null)
{
base.Control.Destroy -= DestroyEvent;
}
}
}
public event EventHandler<IndexChangeEventArgs> Change
{
add
{
if (evtChange == null)
{
base.Control.Change += ChangeEvent;
}
evtChange = (EventHandler<IndexChangeEventArgs>)Delegate.Combine(evtChange, value);
}
remove
{
evtChange = (EventHandler<IndexChangeEventArgs>)Delegate.Remove(evtChange, value);
if (evtChange == null)
{
base.Control.Change -= ChangeEvent;
}
}
}
[CLSCompliant(false)]
public override void Initialize(object control)
{
base.Initialize(control);
myTextIndex = new ChoiceTextIndexer(base.Control);
myDataIndex = new ChoiceDataIndexer(base.Control);
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
if (evtDropDown != null)
{
evtDropDown = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDropDown, evtDropDown);
base.Control.DropDown -= DropDownEvent;
}
if (evtDestroy != null)
{
evtDestroy = (EventHandler<ControlEventArgs>)Delegate.Remove(evtDestroy, evtDestroy);
base.Control.Destroy -= DestroyEvent;
}
if (evtChange != null)
{
evtChange = (EventHandler<IndexChangeEventArgs>)Delegate.Remove(evtChange, evtChange);
base.Control.Change -= ChangeEvent;
}
myTextIndex.Dispose();
myDataIndex.Dispose();
}
base.Dispose(disposing);
}
public void Add(string display, object data)
{
base.Control.AddChoice(display, data);
}
public void Clear()
{
base.Control.Clear();
}
public void Remove(int index)
{
base.Control.RemoveChoice(index);
}
private void DropDownEvent(int ID)
{
if (evtDropDown != null)
{
evtDropDown(this, new ControlEventArgs(ID));
}
}
private void ChangeEvent(int ID, int Index)
{
if (evtChange != null)
{
evtChange(this, new IndexChangeEventArgs(ID, Index));
}
}
private void DestroyEvent(int ID)
{
if (evtDestroy != null)
{
evtDestroy(this, new ControlEventArgs(ID));
}
}
}

View file

@ -0,0 +1,12 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum CombatState
{
Peace = 1,
Melee = 2,
Missile = 4,
Magic = 8
}

View file

@ -0,0 +1,51 @@
using System;
using System.Collections.Generic;
using System.Reflection;
using Decal.Adapter.Support;
using Decal.Interop.Inject;
namespace Decal.Adapter.Wrappers;
public static class ControlRegistry
{
private static Dictionary<Type, Type> myWrappers;
static ControlRegistry()
{
if (myWrappers == null)
{
myWrappers = new Dictionary<Type, Type>();
RegisterControls(Assembly.GetExecutingAssembly());
}
}
public static void RegisterControls(Assembly assembly)
{
Type[] types = assembly.GetTypes();
foreach (Type type in types)
{
try
{
Type baseType = type.BaseType;
if (!(baseType == null) && baseType.IsGenericType && baseType.GetGenericTypeDefinition() == typeof(ControlWrapperBase<>))
{
Type key = baseType.GetGenericArguments()[0];
myWrappers.Add(key, type);
}
}
catch (Exception ex)
{
Util.WriteLine("RegisterControls: " + ex.Message);
}
}
}
internal static IControlWrapper CreateInstance(IControl control)
{
Util.WriteLine("Creating wrapper for: " + control.GetType());
Type value;
IControlWrapper controlWrapper = ((!myWrappers.TryGetValue(control.GetType(), out value)) ? new ControlWrapper() : ((IControlWrapper)Activator.CreateInstance(value)));
controlWrapper.Initialize(control);
return controlWrapper;
}
}

View file

@ -0,0 +1,7 @@
using Decal.Interop.Inject;
namespace Decal.Adapter.Wrappers;
public class ControlWrapper : ControlWrapperBase<IControl>
{
}

View file

@ -0,0 +1,66 @@
using System;
using System.ComponentModel;
using System.Runtime.InteropServices;
using Decal.Interop.Inject;
namespace Decal.Adapter.Wrappers;
public abstract class ControlWrapperBase<T> : MarshalByRefObject, IControlWrapper, IDisposable where T : class
{
private T myControl;
private bool isDisposed;
[EditorBrowsable(EditorBrowsableState.Never)]
public object Underlying => myControl;
public int Id => ((IControl)myControl).ID;
public int ChildCount => ((IControl)myControl).ChildCount;
protected bool Disposed => isDisposed;
protected T Control => myControl;
~ControlWrapperBase()
{
Dispose(disposing: false);
}
[EditorBrowsable(EditorBrowsableState.Never)]
public virtual void Initialize(object control)
{
myControl = control as T;
}
[EditorBrowsable(EditorBrowsableState.Never)]
public object ChildById(int id)
{
return ((dynamic)(IControl)myControl).get_Child(id, ePositionType.ePositionByID);
}
[EditorBrowsable(EditorBrowsableState.Never)]
public object ChildByIndex(int index)
{
return ((dynamic)(IControl)myControl).get_Child(index, ePositionType.ePositionByIndex);
}
public void Dispose()
{
Dispose(disposing: true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (!isDisposed)
{
}
if (myControl != null)
{
Marshal.ReleaseComObject(myControl);
myControl = null;
}
isDisposed = true;
}
}

View file

@ -0,0 +1,106 @@
using System;
namespace Decal.Adapter.Wrappers;
public class CoordsObject
{
private double myNorthSouth;
private double myEastWest;
public double NorthSouth => myNorthSouth;
public double EastWest => myEastWest;
public CoordsObject(double northSouth, double eastWest)
{
myNorthSouth = northSouth;
myEastWest = eastWest;
}
public double DistanceToCoords(CoordsObject destination)
{
if (destination == null)
{
throw new ArgumentNullException("destination");
}
double num = myNorthSouth - destination.myNorthSouth;
double num2 = myEastWest - destination.myEastWest;
return Math.Sqrt(num * num + num2 * num2);
}
public double AngleToCoords(CoordsObject destination)
{
return 180.0 / Math.PI * AngleToCoordsRadians(destination);
}
public double AngleToCoordsRadians(CoordsObject destination)
{
if (destination == null)
{
throw new ArgumentNullException("destination");
}
double num = Math.Atan2(destination.myEastWest - myEastWest, destination.myNorthSouth - myNorthSouth);
if (num < 0.0)
{
num += Math.PI * 2.0;
}
return num;
}
public override string ToString()
{
return ToString("0.0");
}
public string ToString(string numberFormat)
{
return Math.Abs(myNorthSouth).ToString(numberFormat) + ((myNorthSouth >= 0.0) ? "N" : "S") + ", " + Math.Abs(myEastWest).ToString(numberFormat) + ((myEastWest >= 0.0) ? "E" : "W");
}
public override bool Equals(object obj)
{
if (obj is CoordsObject)
{
CoordsObject coordsObject = (CoordsObject)obj;
if (coordsObject.myNorthSouth == myNorthSouth)
{
return coordsObject.myEastWest == myEastWest;
}
return false;
}
return false;
}
public bool Equals(CoordsObject obj)
{
if (obj == null)
{
return false;
}
if (obj.myNorthSouth == myNorthSouth)
{
return obj.myEastWest == myEastWest;
}
return false;
}
public override int GetHashCode()
{
return myNorthSouth.GetHashCode() ^ myEastWest.GetHashCode();
}
public static bool operator ==(CoordsObject a, CoordsObject b)
{
if (object.Equals(a, null))
{
return object.Equals(b, null);
}
return a.Equals(b);
}
public static bool operator !=(CoordsObject a, CoordsObject b)
{
return !(a == b);
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class CreateObjectEventArgs : EventArgs
{
private WorldObject myNewObject;
public WorldObject New => myNewObject;
internal CreateObjectEventArgs(WorldObject newObject)
{
myNewObject = newObject;
}
}

View file

@ -0,0 +1,289 @@
using Decal.Interop.D3DService;
namespace Decal.Adapter.Wrappers;
public class D3DObj : GenericDisposableWrapper<CD3DObj>
{
public int Color
{
get
{
return base.Wrapped.color;
}
set
{
base.Wrapped.color = value;
}
}
public int Color2
{
get
{
return base.Wrapped.color2;
}
set
{
base.Wrapped.color2 = value;
}
}
public bool Autoscale
{
get
{
return base.Wrapped.autoscale;
}
set
{
base.Wrapped.autoscale = value;
}
}
public bool DrawBackface
{
get
{
return base.Wrapped.drawBackface;
}
set
{
base.Wrapped.drawBackface = value;
}
}
public float HBounce
{
get
{
return base.Wrapped.hBounce;
}
set
{
base.Wrapped.hBounce = value;
}
}
public float PBounce
{
get
{
return base.Wrapped.pBounce;
}
set
{
base.Wrapped.pBounce = value;
}
}
public float PFade
{
get
{
return base.Wrapped.pFade;
}
set
{
base.Wrapped.pFade = value;
}
}
public float POrbit
{
get
{
return base.Wrapped.pOrbit;
}
set
{
base.Wrapped.pOrbit = value;
}
}
public float PSpin
{
get
{
return base.Wrapped.pSpin;
}
set
{
base.Wrapped.pSpin = value;
}
}
public float ROrbit
{
get
{
return base.Wrapped.rOrbit;
}
set
{
base.Wrapped.rOrbit = value;
}
}
public float ScaleX
{
get
{
return base.Wrapped.scaleX;
}
set
{
base.Wrapped.scaleX = value;
}
}
public float ScaleY
{
get
{
return base.Wrapped.scaleY;
}
set
{
base.Wrapped.scaleY = value;
}
}
public float ScaleZ
{
get
{
return base.Wrapped.scaleZ;
}
set
{
base.Wrapped.scaleZ = value;
}
}
public bool Visible
{
get
{
return base.Wrapped.visible;
}
set
{
base.Wrapped.visible = value;
}
}
public float AnimationPhaseOffset
{
get
{
return base.Wrapped.AnimationPhaseOffset;
}
set
{
base.Wrapped.AnimationPhaseOffset = value;
}
}
public D3DObj(CD3DObj obj)
: base(obj)
{
}
protected override void Dispose(bool userCalled)
{
base.Dispose(userCalled);
}
public void Scale(float factor)
{
base.Wrapped.SetScale(factor);
}
public void OrientToCamera(bool verticalTilt)
{
base.Wrapped.OrientToCamera(verticalTilt);
}
public void OrientToCoords(float lat, float lng, float alt, bool verticalTilt)
{
base.Wrapped.OrientToCoords(lat, lng, alt, verticalTilt);
}
public void OrientToObject(int guid, float fractHeight, bool verticalTilt)
{
base.Wrapped.OrientToObject(guid, fractHeight, verticalTilt);
}
public void OrientToPlayer(bool verticalTilt)
{
base.Wrapped.OrientToPlayer(verticalTilt);
}
public void Anchor(float lat, float lng, float alt)
{
base.Wrapped.AnchorToCoords(lat, lng, alt);
}
public void Anchor(int id, float height, float dx, float dy, float dz)
{
base.Wrapped.AnchorToObject(id, height, dx, dy, dz);
}
public void SetText(string text)
{
SetText(D3DTextType.Text2D, text, "Arial", 0);
}
public void SetText(string text, string fontName)
{
SetText(D3DTextType.Text2D, text, fontName, 0);
}
public void SetText(string text, string fontName, int options)
{
SetText(D3DTextType.Text2D, text, fontName, options);
}
public void SetText(D3DTextType type, string text, string fontName, int options)
{
switch (type)
{
case D3DTextType.Text2D:
base.Wrapped.Set2DText(text, fontName, options);
break;
case D3DTextType.Text3D:
base.Wrapped.Set3DText(text, fontName, options);
break;
}
}
public void SetIcon(int id)
{
base.Wrapped.SetIcon(id);
}
public void SetIcon(string fileName)
{
base.Wrapped.SetIconFromFile(fileName);
}
public void SetIcon(int module, int res)
{
base.Wrapped.SetIconFromResource(module, res);
}
public void SetShape(D3DShape shape)
{
base.Wrapped.SetShape((eShape)shape);
}
public void SetShape(string fileName)
{
base.Wrapped.SetShapeFromFile(fileName);
}
public void SetShape(int module, int res)
{
base.Wrapped.SetShapeFromResource(module, res);
}
}

View file

@ -0,0 +1,86 @@
using Decal.Interop.D3DService;
namespace Decal.Adapter.Wrappers;
public class D3DService : GenericDisposableWrapper<CService>
{
internal D3DService(CService obj)
: base(obj)
{
}
protected override void Dispose(bool userCalled)
{
base.Dispose(userCalled);
}
public D3DObj NewD3DObj()
{
return new D3DObj(base.Wrapped.NewD3DObj());
}
public D3DObj PointToObject(int guid, int color)
{
return new D3DObj(base.Wrapped.PointToObject(guid, color));
}
public D3DObj PointToCoords(float lat, float lng, float alt, int color)
{
return new D3DObj(base.Wrapped.PointToCoords(lat, lng, alt, color));
}
public D3DObj MarkObjectWithIcon(int guid, int icon)
{
return new D3DObj(base.Wrapped.MarkObjectWithIcon(guid, icon));
}
public D3DObj MarkObjectWithShape(int guid, D3DShape shape, int color)
{
return new D3DObj(base.Wrapped.MarkObjectWithShape(guid, (eShape)shape, color));
}
public D3DObj MarkObjectWithShapeFromFile(int guid, string filename, int color)
{
return new D3DObj(base.Wrapped.MarkObjectWithShapeFromFile(guid, filename, color));
}
public D3DObj MarkObjectWith2DText(int guid, string szText, string szFont, int options)
{
return new D3DObj(base.Wrapped.MarkObjectWith2DText(guid, szText, szFont, options));
}
public D3DObj MarkObjectWith3DText(int guid, string szText, string szFont, int options)
{
return new D3DObj(base.Wrapped.MarkObjectWith3DText(guid, szText, szFont, options));
}
public D3DObj MarkCoordsWithIcon(float lat, float lng, float alt, int icon)
{
return new D3DObj(base.Wrapped.MarkCoordsWithIcon(lat, lng, alt, icon));
}
public D3DObj MarkCoordsWithIconFromFile(float lat, float lng, float alt, string file)
{
return new D3DObj(base.Wrapped.MarkCoordsWithIconFromFile(lat, lng, alt, file));
}
public D3DObj MarkCoordsWithShape(float lat, float lng, float alt, D3DShape shape, int color)
{
return new D3DObj(base.Wrapped.MarkCoordsWithShape(lat, lng, alt, (eShape)shape, color));
}
public D3DObj MarkCoordsWithShapeFromFile(float lat, float lng, float alt, string file, int color)
{
return new D3DObj(base.Wrapped.MarkCoordsWithShapeFromFile(lat, lng, alt, file, color));
}
public D3DObj MarkCoordsWith2DText(float lat, float lng, float alt, string szText, string szFont, int options)
{
return new D3DObj(base.Wrapped.MarkCoordsWith2DText(lat, lng, alt, szText, szFont, options));
}
public D3DObj MarkCoordsWith3DText(float lat, float lng, float alt, string szText, string szFont, int options)
{
return new D3DObj(base.Wrapped.MarkCoordsWith3DText(lat, lng, alt, szText, szFont, options));
}
}

View file

@ -0,0 +1,12 @@
namespace Decal.Adapter.Wrappers;
public enum D3DShape
{
HorizontalArrow,
VerticalArrow,
Ring,
Cylinder,
Sphere,
Cube,
TiltedCube
}

View file

@ -0,0 +1,7 @@
namespace Decal.Adapter.Wrappers;
public enum D3DTextType
{
Text2D,
Text3D
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class DeathEventArgs : EventArgs
{
private string myText;
public string Text => myText;
internal DeathEventArgs(string text)
{
myText = text;
}
}

View file

@ -0,0 +1,84 @@
using System;
using System.ComponentModel;
using System.Runtime.InteropServices;
using Decal.Adapter.Support;
using Decal.Interop.Core;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public class DecalWrapper : MarshalByRefObject, IDisposable
{
internal static Guid IID_IDISPATCH = new Guid("{00020400-0000-0000-C000-000000000046}");
internal static Guid IID_IUNKNOWN = new Guid("{00000000-0000-0000-C000-000000000046}");
private DecalCore myDecal;
private bool isDisposed;
[CLSCompliant(false)]
[EditorBrowsable(EditorBrowsableState.Never)]
public DecalCore Underlying => myDecal;
public IntPtr Hwnd => new IntPtr(myDecal.HWND);
public bool Focus => myDecal.Focus;
internal DecalWrapper(DecalCore decal)
{
myDecal = decal;
}
~DecalWrapper()
{
Dispose(disposing: false);
}
public void Dispose()
{
Dispose(disposing: true);
GC.SuppressFinalize(this);
}
private void Dispose(bool disposing)
{
if (!isDisposed)
{
}
if (myDecal != null)
{
Marshal.ReleaseComObject(myDecal);
myDecal = null;
}
isDisposed = true;
}
public object GetObject(string path)
{
return GetObject(path, IID_IDISPATCH);
}
public object GetObject(string path, string iid)
{
return GetObject(path, new Guid(iid));
}
public object GetObject(string path, Guid iid)
{
try
{
return ((dynamic)(IDecalCore)myDecal).get_Object(path, ref iid);
}
catch (Exception ex)
{
Util.WriteLine("Exception for {0} during get_Object: {1}", path, ex);
return null;
}
}
public string MapPath(string path)
{
return myDecal.MapPath(path);
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class DeclineTradeEventArgs : EventArgs
{
private int mTraderId;
public int TraderId => mTraderId;
internal DeclineTradeEventArgs(int TraderId)
{
mTraderId = TraderId;
}
}

View file

@ -0,0 +1,29 @@
namespace Decal.Adapter.Wrappers;
public enum DoubleValueKey
{
SlashProt = 167772160,
PierceProt = 167772161,
BludgeonProt = 167772162,
AcidProt = 167772163,
LightningProt = 167772164,
FireProt = 167772165,
ColdProt = 167772166,
Heading = 167772167,
ApproachDistance = 167772168,
SalvageWorkmanship = 167772169,
Scale = 167772170,
Variance = 167772171,
AttackBonus = 167772172,
Range = 167772173,
DamageBonus = 167772174,
ManaRateOfChange = 5,
MeleeDefenseBonus = 29,
ManaTransferEfficiency = 87,
HealingKitRestoreBonus = 100,
ManaStoneChanceDestruct = 137,
ManaCBonus = 144,
MissileDBonus = 149,
MagicDBonus = 150,
ElementalDamageVersusMonsters = 152
}

View file

@ -0,0 +1,81 @@
using System;
using Decal.Adapter.NetParser;
using Decal.Adapter.Support;
using Decal.Interop.Filters;
using Decal.Interop.Net;
namespace Decal.Adapter.Wrappers;
public class EchoFilter2 : GenericDisposableWrapper<Decal.Interop.Filters.EchoFilter2>
{
private event EventHandler<NetworkMessageEventArgs> serverDispatch;
private event EventHandler<NetworkMessageEventArgs> clientDispatch;
public event EventHandler<NetworkMessageEventArgs> ServerDispatch
{
add
{
serverDispatch += value;
}
remove
{
serverDispatch -= value;
}
}
public event EventHandler<NetworkMessageEventArgs> ClientDispatch
{
add
{
clientDispatch += value;
}
remove
{
clientDispatch -= value;
}
}
public EchoFilter2(Decal.Interop.Filters.EchoFilter2 obj)
: base(obj)
{
base.Wrapped.EchoClient += onEchoClient;
base.Wrapped.EchoServer += onEchoServer;
}
protected override void Dispose(bool userCalled)
{
if (userCalled && base.Wrapped != null)
{
base.Wrapped.EchoClient -= onEchoClient;
base.Wrapped.EchoServer -= onEchoServer;
}
base.Dispose(userCalled);
}
private void onEchoServer(IMessage2 pMsg)
{
try
{
Message message = null;
Util.SafeFireEvent(args: new NetworkMessageEventArgs((!(pMsg is MessageWrapper messageWrapper)) ? new Message(pMsg, MessageDirection.Inbound) : messageWrapper.Wrapped), sender: this, eventHandler: this.serverDispatch);
}
catch (Exception ex)
{
Util.WriteLine("Exception in onEchoServer {0}", ex);
}
}
private void onEchoClient(IMessage2 pMsg)
{
try
{
Message message = null;
Util.SafeFireEvent(args: new NetworkMessageEventArgs((!(pMsg is MessageWrapper messageWrapper)) ? new Message(pMsg, MessageDirection.Inbound) : messageWrapper.Wrapped), sender: this, eventHandler: this.clientDispatch);
}
catch (Exception ex)
{
Util.WriteLine("Exception in onEchoClient {0}", ex);
}
}
}

View file

@ -0,0 +1,66 @@
using System;
using System.Runtime.InteropServices;
using Decal.Interop.Filters;
namespace Decal.Adapter.Wrappers;
public class EnchantmentWrapper : MarshalByRefObject, IDisposable
{
private Enchantment myEnchantment;
private bool isDisposed;
public double Adjustment => myEnchantment.Adjustment;
public int Affected => myEnchantment.Affected;
public int AffectedMask => myEnchantment.AffectedMask;
public double Duration => myEnchantment.Duration;
public int Family => myEnchantment.Family;
public int Layer => myEnchantment.Layer;
public int SpellId => myEnchantment.SpellID;
public int TimeRemaining => myEnchantment.TimeRemaining;
public DateTime Expires => DateTime.Now.AddSeconds(TimeRemaining);
internal EnchantmentWrapper(Enchantment enchant)
{
myEnchantment = enchant;
}
~EnchantmentWrapper()
{
Dispose(disposing: false);
}
public void Dispose()
{
Dispose(disposing: true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (!isDisposed)
{
}
if (myEnchantment != null)
{
Marshal.ReleaseComObject(myEnchantment);
}
isDisposed = true;
}
protected void EnforceDisposedOnce()
{
if (isDisposed)
{
throw new ObjectDisposedException("EnchantmentWrapper");
}
}
}

View file

@ -0,0 +1,15 @@
using System;
namespace Decal.Adapter.Wrappers;
public class EndTradeEventArgs : EventArgs
{
private int mReasonId;
public int ReasonId => mReasonId;
internal EndTradeEventArgs(int ReasonId)
{
mReasonId = ReasonId;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class EnterTradeEventArgs : EventArgs
{
private int mTraderId;
private int mTradeeId;
public int TraderId => mTraderId;
public int TradeeId => mTradeeId;
internal EnterTradeEventArgs(int TraderId, int TradeeId)
{
mTraderId = TraderId;
mTradeeId = TradeeId;
}
}

View file

@ -0,0 +1,20 @@
using System;
namespace Decal.Adapter.Wrappers;
public class FailToAddTradeItemEventArgs : EventArgs
{
private int mItemId;
private int mReasonId;
public int ItemId => mItemId;
public int ReasonId => mReasonId;
internal FailToAddTradeItemEventArgs(int ItemId, int ReasonId)
{
mItemId = ItemId;
mReasonId = ReasonId;
}
}

View file

@ -0,0 +1,13 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum FellowshipEventType
{
Create,
Quit,
Dismiss,
Recruit,
Disband
}

View file

@ -0,0 +1,23 @@
using System;
namespace Decal.Adapter.Wrappers;
[CLSCompliant(true)]
public enum FontWeight
{
Black = 900,
Bold = 700,
DemiBold = 600,
DoNotCare = 0,
ExtraBold = 800,
ExtraLight = 200,
Heavy = 900,
Light = 300,
Medium = 500,
Normal = 400,
Regular = 400,
SemiBold = 600,
Thin = 100,
UltraBold = 800,
UltraLight = 200
}

View file

@ -0,0 +1,19 @@
using System;
using System.Globalization;
namespace Decal.Adapter.Wrappers;
public sealed class HookIndexer<IndexType> : MarshalByRefObject where IndexType : struct, IConvertible
{
private hookIndexType myIndex;
private IIndexedValueProvider myWrap;
public int this[IndexType item] => myWrap.GetIndexedObject(myIndex, item.ToInt32(CultureInfo.InvariantCulture));
internal HookIndexer(IIndexedValueProvider wrap, hookIndexType index)
{
myIndex = index;
myWrap = wrap;
}
}

Some files were not shown because too many files have changed in this diff Show more