http://macroquest2.com/phpBB2/viewtopic ... 7902#17902
UPDATE! ok implemented /selectitem slot <slotnumber> and put in a few checkas against unruly merchants that couldnt keep their items in order...
NOTE! that I changed EQWINDOW struct so you need to use this one.
ok here is the fix for /merchant.
This version will take /selectitem list || "item name" || slot <slotnumber> and select that item for buying. I will release the /sellitem as well, thats why I wanted this command to be called selectitem and not merchant, because in the next version we will be able to specify where to select from, for example your own bags... or inventory i.e /selectitem "item name" self || merchant , if someone feels up for the finetuning, feel free to paste some code in this thread I could use some ideas and help. The list prints IDs maybe /selectitem <ID> ? or /selectitem <slot> ? post code or feedback.
someone wanted $merchant(has,"item name") and $corpse(has,"item name") that shouldnt be hard to fix now since the function works again...
NOTE! the cyan text is the section under which you paste the code, it doesnt mean you can paste it directly under that section, just a pointer to get you started, if you look in the section you will see lines that looks like the code you are going to insert, and you need to paste it under a similar line... also note that some lines might allready exist... just replace them
ok here goes->
in EQLib.h :
// ***************************************************************************
// EQ Addresses
// ***************************************************************************
Code: Select all
extern DWORD *EQADDR_CLASSMERCHWND;
extern DWORD *EQADDR_CLASSTEXTUREANIMATION; // EQ Functions
// *******************************************************
Code: Select all
extern fEQSelectItem cmdSelectItem; in EQLib_Commands.cpp :
Code: Select all
[color=green]// ***************************************************************************
// Function: SelectItem
// Description: Our '/selectitem' command
// targets an item.
// Usage: /selectitem list || "item name" || slot <slotnumber>
// ***************************************************************************
// uses public: void __thiscall CMerchantWnd::SelectBuySellSlot(int,class CTextureAnimation *)
// ***************************************************************************[/color]
VOID SelectItem(PSPAWNINFO pChar, PCHAR szLine)
{
bRunNextCommand = FALSE;
PEQWINDOW pMainWindow = (PEQWINDOW)*EQADDR_CLASSMERCHWND;
PEQCURRENTSELECTION pSelectedSlot = (PEQCURRENTSELECTION)*EQADDR_CLASSTEXTUREANIMATION;
PEQWINDOW pCurSlot = NULL;
PEQWINDOW pDestSlot = NULL;
DWORD MerchTraderWnd = *EQADDR_CLASSMERCHWND;
BOOL Found;
CHAR szBuffer[MAX_STRING] = {0};
CHAR szArg1[MAX_STRING] = {0};
CHAR szArg2[MAX_STRING] = {0};
int SelectSlot, i;
if (!MerchTraderWnd || !cmdSelectItem) return;
GetArg(szArg1,szLine,1);
GetArg(szArg2,szLine,2);
Found = FALSE;
if ((!_stricmp(szArg1,"slot") && (szArg2[0]!=0)))
{
i = atoi(szArg2);
i--;
if (pMainWindow->ItemDesc[i] == NULL)
return;
SelectSlot = (int)pMainWindow->SlotsHandles[i]->SlotID;
Found = TRUE;
}
if ((!_stricmp(szArg1,"list") && (szArg2[0]==0) && (Found == FALSE)))
{
WriteChatBuffer("Merchant Inventory:",USERCOLOR_DEFAULT);
WriteChatBuffer("--------------------------",USERCOLOR_DEFAULT);
i=0;
while (i < 79)
{
if (!_stricmp(szArg1,"list"))// && (szArg2[0]==0))
{
if (pMainWindow->ItemDesc[i] != NULL)
{
sprintf(szBuffer,"%d:'%s' : (slot %d)",pMainWindow->ItemDesc[i]->ItemNumber,pMainWindow->ItemDesc[i]->Name,(pMainWindow->SlotsHandles[i]->SlotID-5999));
WriteChatBuffer(szBuffer,CONCOLOR_YELLOW);
}else
i=80;
}
i++;
}
}
if ((_stricmp(szArg1,"list") && (szArg1[0]!=0) && (Found == FALSE)))
{
i=0;
while (i < 79 && Found == FALSE)
{
if (pMainWindow->ItemDesc[i] != NULL)
{
if (!_stricmp(pMainWindow->ItemDesc[i]->Name , szArg1))
{
sprintf(szBuffer,"'%s' Found in slot '%d'",pMainWindow->ItemDesc[i]->Name,(pMainWindow->SlotsHandles[i]->SlotID-5999));
WriteChatBuffer(szBuffer,USERCOLOR_DEFAULT);
SelectSlot = (int)pMainWindow->SlotsHandles[i]->SlotID;
Found = TRUE;
i--;
}
}else
i=80;
i++;
}
}
if (Found == TRUE)
{
if (pMainWindow->ItemDesc[i] != NULL)
{
pCurSlot = (PEQWINDOW)((int *)pSelectedSlot->SelectedWnd);
pDestSlot = (PEQWINDOW)((int *)pMainWindow->SlotsHandles[i]);//(PEQMERCHANT)(DWORD)TextureAnim;
pCurSlot->Selector = 0;
pDestSlot->Selector = 1;
*((int *)EQADDR_CLASSTEXTUREANIMATION) = ((int)pDestSlot->PushToSelector);
int TextureAnim = (int)pMainWindow->SlotsHandles[i]->InvDecription;
__asm {
push ecx;
push TextureAnim;
mov ecx, dword ptr [MerchTraderWnd];
push SelectSlot;
call dword ptr [cmdSelectItem];
pop ecx;
}
}
}else
{
if(_stricmp(szArg1,"list"))
{
WriteChatBuffer("Item not found.",CONCOLOR_RED);
}
}
return;
}// ***************************************************************************
// Function: TakeControlOfCommandList
// Description: Creates custom command list with our commands
// Points help/parsing at our list
// ***************************************************************************
Code: Select all
{"/selectitem", "SelectItem"},// EQ Functions Initialization
Code: Select all
fEQSelectItem cmdSelectItem = NULL; Code: Select all
DWORD *EQADDR_CLASSMERCHWND;
DWORD *EQADDR_CLASSTEXTUREANIMATION; // Function: ParseINIFile
// Description: Parse INI file for memory locations
// ***************************************************************************
Code: Select all
GetPrivateProfileString("Function Locations","SelectItem","0",szBuffer,MAX_STRING,ClientINI); cmdSelectItem = (fEQSelectItem)strtoul(szBuffer,NULL,16);
GetPrivateProfileString("Class Locations","ClassMerchWnd","0",szBuffer,MAX_STRING,ClientINI); EQADDR_CLASSMERCHWND = (DWORD *)strtoul(szBuffer,NULL,16);
GetPrivateProfileString("Class Locations","ClassTextureAnim","0",szBuffer,MAX_STRING,ClientINI); EQADDR_CLASSTEXTUREANIMATION = (DWORD *)strtoul(szBuffer,NULL,16);
// ***************************************************************************
// Everquest function typedefs
// ***************************************************************************
Code: Select all
typedef VOID (__cdecl *fEQSelectItem)(int,DWORD); [color=green]//public: void __thiscall CMerchantWnd::SelectBuySellSlot(int,class CTextureAnimation *)[/color]
// Exports
// ***************************************************************************
Code: Select all
extern "C" EQLIB_API VOID SelectItem (PSPAWNINFO, PCHAR);
Code: Select all
[Function Locations]
SelectItem=004E932D
[Class Locations]
ClassMerchWnd=005FE270
ClassTextureAnim=0077BF04 replace the one in MQ.h with theese two:
Code: Select all
//7-7-2003 eqmule
typedef struct _EQWINDOWINFO {
DWORD WindowStyle; //if it is style then 04 = Window 01 = button
DWORD Unknown1;
DWORD Unknown2;
DWORD Unknown3;
DWORD Unknown4;
CHAR WindowTitle[140];
BYTE Unknown5[12];
DWORD pNextAddress; //most likely pointers to another structure...
DWORD pPrevAddress;
} EQWINDOWINFO, *PEQWINDOWINFO; //ok it goes on and there are plenty more to pick up here, but I just need the name for now...
typedef struct _EQWINDOW {
DWORD WindowID;
DWORD TimeMouseOver; //how many ms the window has had the mouse over it...
DWORD Unknown0x008; // 2000 seems a common value
DWORD Unknown0x00c; //500 seems a common value
BYTE Flag;
BYTE MouseOver; //01 yes 00 no
BYTE Unknown0x012;
BYTE Unknown0x013;
BYTE Unknown0x014[12];
struct _EQWINDOW *pDownTheTreeOnSameWindow;
struct _EQWINDOW *pNextWindow;
DWORD Flags4;
DWORD Z; //not sure but its logical to assume it at this point...
DWORD X;
DWORD Y;
DWORD Height;
DWORD Width;
DWORD Depth; //hmmm...
BYTE Unknown0x040[12];
BYTE Open; //1 open 0 closed
BYTE Unknown0x051[7];
DWORD somekindofID;
DWORD *pUnknownStruct0x060;
struct _EQWINDOWINFO *Info;
BYTE Unknown[84];
union{
PITEMINFO Item;//only when structure is filled with a slot...
struct _EQWINDOW *InvDecription;
};
BYTE Unknown1[68];
DWORD SlotID; //merchantslots start at 1770h bags at 16 and bagslots at fb inventory start at 0.
BYTE Unknown2[16];
BYTE Selector; //this graphically selects an item on/off
BYTE Unknown3[3];
DWORD PushToSelector;
BYTE Unknown4[36];//364
PITEMINFO ItemDesc[80]; //the mainwindow has pointers directly to the items in the slots...
DWORD Unknown5;
DWORD FirstSlotIDforWindow;
DWORD AddressToPointerForSelectedItem;//
DWORD Unknown6;
DWORD ItemIconwnd;
DWORD Unknown7;
DWORD SellBuyButton;
struct _EQWINDOW *SlotsHandles[80];
DWORD DoneButton;
DWORD WindowFace;
} EQWINDOW, *PEQWINDOW;
typedef struct _EQCURRENTSELECTION {
DWORD Unknown;
DWORD SelectedWnd;//address to selection in tree
} EQCURRENTSELECTION, *PEQCURRENTSELECTION;OK any feedback for making the code cleaner/better will be appreaciated, Im not a mastercoder by any means...
I will expand on this theeme making buying, selling, trading, possible by commandline only. /autoloot is comming as well as the new windowscanner, so we dont need so many damn offsets...
Play nice.
[edit] ok everything works now.

donations for this month's patches.
