-
Mehrere Fragen zum Handelsmenü
Hey,
wie der Titel schon sage, habe ich einige Fragen zum Handelsmenü von Gothic 2.
1) Ich habe DIESES Skript in unsere Modifikation eingebaut. Nun funktioniert das soweit ganz gut, der Alchemist zum Beispiel kauft nun Pflanzen zu einem höheren Preis an als zum Beispiel der Wirt.
Nun will ich aber, dass manche Händler bestimmte Items gar nicht mehr ankaufen.
Wie mache ich das?
Das Skript, das die Händlerpreise verändert, sieht bei mir (ungefähr) so aus:
Code:
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeLeft()
{
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (Hlp_GetInstanceID(npc) == ABC)
|| (Hlp_GetInstanceID(npc) == DEF)
{
if (Hlp_IsItem (itm, ItMi_DIV_Feder))
|| (Hlp_IsItem (itm, ItMi_DIV_Poison))
(...)
{
value = itm.value/3*2;
} else if
(Hlp_IsItem (itm, ItPo_Mana_01))
|| (Hlp_IsItem (itm, ItPo_Mana_02))
(...)
{
value = itm.value/2;
};
};
if (Hlp_GetInstanceID(npc) == GHI)
|| (Hlp_GetInstanceID(npc) == JKL)
(...)
{
if (Hlp_IsItem (itm, ItFo_Apple))
|| (Hlp_IsItem (itm, ItFo_Cheese))
(...)
{
value = itm.value/3*2;
};
};
(Und so weiter...)
MEM_WriteInt(ESP+20, value);
};
2) Ich würde gerne bei allen Items, wenn sich der Spieler gerade im Handelsmenü befindet, bei
Code:
TEXT[5] = NAME_Value; COUNT[5] = value;
(Wert des Items) den jeweiligen Preis anzeigen lassen, den der aktuelle Händler den Spieler dafür bietet bzw. wenn dieser Händler das ausgewählt Item nicht ankauft, sollte dort zum Beispiel ein "-" stehen. Im moment ist es so, dass bei jedem Händler der gleiche Preis angezeigt wird, nämlich der unveränderte, so wie er von Gothic eigentlich berechnet wird.
Ist das denn möglich? Falls ja, wie?
3) Habe ich vor einiger Zeit schon neue Texturen für das Inventar erstellt. Jetzt ist es nur leider so, dass im Handelsmenü ein Teil des Inventars transparent wird (wenn man sich gerade im eigenen Inventar befindet das des NPCs, wenn man sich gerade in dem vom NPC befindet das des Spielers...), nämlich die Slots, in denen sich Items befinden. Das gleiche Problem gibt es auch mit den Truhen. Das sieht mit den neuen Texturen natürlich sehr unschön aus, wie man auf dem Screen sehen kann.
Lässt sich dieses transparent werden denn irgendwie deaktivieren?
(Der Screen:)
Geändert von Bloodfly91 (20.07.2018 um 03:15 Uhr)
-
Zitat von Bloodfly91
2) Ich würde gerne bei allen Items, wenn sich der Spieler gerade im Handelsmenü befindet, bei
Code:
TEXT[5] = NAME_Value; COUNT[5] = value;
(Wert des Items) den jeweiligen Preis anzeigen lassen, den der aktuelle Händler den Spieler dafür bietet bzw. wenn dieser Händler das ausgewählt Item nicht ankauft, sollte dort zum Beispiel ein "-" stehen. Im moment ist es so, dass bei jedem Händler der gleiche Preis angezeigt wird, nämlich der unveränderte, so wie er von Gothic eigentlich berechnet wird.
Ist das denn möglich? Falls ja, wie?
https://forum.worldofplayers.de/foru...1#post25592086
-
Zitat von Bloodfly91
Nun will ich aber, dass manche Händler bestimmte Items gar nicht mehr ankaufen.
Wie mache ich das?
Hier gibt es was passendes:
https://forum.worldofplayers.de/foru...1#post24695536
-
-
Zitat von Umfi
Dazu habe ich schon mal eine Frage...
Das ganze funktioniert zwar, allerdings weiß ich jetzt nicht, wie ich da den neuen Wert des Händlers anzeigen lasse. Wenn ich
Code:
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
einfach mit in meine Funktion einbaue, wird zwar der richtige Preis angezeigt, allerdings an einer völlig falschen Position im Inventar.
Baue ich es als separate Funktion ein, wird der Verkaufswert an der richtigen Position angezeigt, allerdings nicht der aktuelle, sondern immer noch der von Gothic berechnete, was wohl daran liegt, dass der eigentliche Preis vom Item soweit ich weiß bevor man es dem Händler verkauft von der onTradeLeft Funktion gar nicht aktualisiert wird.
Edit: Ich könnte diese Funktion denke ich zwar ähnlich machen, wie meine onTradeLeft Funktion, also dass der eigentliche Preis, der da steht, bei NPC XYZ zum Beispiel einfach durch zwei geteilt wird, aber das muss doch auch noch einfacher gehen, oder?
Edit2: Funktioniert anscheinend doch nicht so, wie ich es mir vorgestellt habe. Wenn ich das ähnlich wie die onTradeLeft Funktion mache, wird da ein komplett falscher Wert angezeigt.
Geändert von Bloodfly91 (22.07.2018 um 03:33 Uhr)
-
Zitat von Bloodfly91
Dazu habe ich schon mal eine Frage...
Das ganze funktioniert zwar, allerdings weiß ich jetzt nicht, wie ich da den neuen Wert des Händlers anzeigen lasse. Wenn ich
Code:
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
einfach mit in meine Funktion einbaue, wird zwar der richtige Preis angezeigt, allerdings an einer völlig falschen Position im Inventar.
Baue ich es als separate Funktion ein, wird der Verkaufswert an der richtigen Position angezeigt, allerdings nicht der aktuelle, sondern immer noch der von Gothic berechnete, was wohl daran liegt, dass der eigentliche Preis vom Item soweit ich weiß bevor man es dem Händler verkauft von der onTradeLeft Funktion gar nicht aktualisiert wird.
Edit: Ich könnte diese Funktion denke ich zwar ähnlich machen, wie meine onTradeLeft Funktion, also dass der eigentliche Preis, der da steht, bei NPC XYZ zum Beispiel einfach durch zwei geteilt wird, aber das muss doch auch noch einfacher gehen, oder?
Edit2: Funktioniert anscheinend doch nicht so, wie ich es mir vorgestellt habe. Wenn ich das ähnlich wie die onTradeLeft Funktion mache, wird da ein komplett falscher Wert angezeigt.
Hat keiner eine Idee?
-
Das sind zwei unterschiedliche Hooks, d.h. das musst du schon in zwei getrennten Funktionen machen. Am besten baust du dir eine Funktion, die den richtigen Verkaufspreis anhand Item und NPC errechnet und verwendest diese Funktion dann in beiden Hooks (d.h. in onTradeLeft und changeTradeValueDisplay).
Wenn du dann noch Probleme hast, wirst du uns genauer zeigen müssen, was du getan hast.
P.S.: So Ausdrücke wie MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value) machen nur im richtigen Kontext Sinn. Hier wird ein CPU-Register (ESP) verwendet, der natürlich nur in der richtigen Hook auch den richtigen Wert hat. Das kannst du also nicht einfach in eine andere Hook schreiben und erwarten, dass es funktioniert.
-
Zitat von Lehona
Das sind zwei unterschiedliche Hooks, d.h. das musst du schon in zwei getrennten Funktionen machen. Am besten baust du dir eine Funktion, die den richtigen Verkaufspreis anhand Item und NPC errechnet und verwendest diese Funktion dann in beiden Hooks (d.h. in onTradeLeft und changeTradeValueDisplay).
Wenn du dann noch Probleme hast, wirst du uns genauer zeigen müssen, was du getan hast.
P.S.: So Ausdrücke wie MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value) machen nur im richtigen Kontext Sinn. Hier wird ein CPU-Register (ESP) verwendet, der natürlich nur in der richtigen Hook auch den richtigen Wert hat. Das kannst du also nicht einfach in eine andere Hook schreiben und erwarten, dass es funktioniert.
Es scheint jetzt auf jeden Fall schon mal zu funktionieren, der Preis wird beim Verkauf und im Inventar richtig berechnet.
Allerdings besteht jetzt immer noch das Problem, dass der Preis an der falschen Stelle angezeigt wird. Wie bekomme ich den nach unten, hinter "Wert", wo er normalerweise sonst auch steht?
Skript sieht jetzt so aus:
Code:
func void DIV_SetItemPrice()
{
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(npc) == VLK_401_LUIS)
{
value = itm.value/3*2;
};
};
MEM_WriteInt(ESP+20, value);
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
DIV_SetItemPrice();
};
func void changeTradeValueDisplay()
{
DIV_SetItemPrice();
};
Hier ein noch ein Screen: [Bild: F1YCtRaInvPreis_DIV.png]
Geändert von Bloodfly91 (25.07.2018 um 14:37 Uhr)
-
Das ist genau das, was Lehona dir gesagt hat. Du kannst nicht einfach wahllos in den Registern rumschreiben und erwarten, dass das richtige rauskommt. Die Werte in den Registern verändern sich für jeden Hook!
Code:
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
DIV_SetItemPrice();
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(npc) == VLK_401_LUIS)
{
value = itm.value/3*2;
};
};
MEM_WriteInt(ESP+20, value);
};
func void changeTradeValueDisplay()
{
DIV_SetItemPrice();
// somehow you have to calculate 'value'
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
-
Zitat von Neconspictor
Das ist genau das, was Lehona dir gesagt hat. Du kannst nicht einfach wahllos in den Registern rumschreiben und erwarten, dass das richtige rauskommt. Die Werte in den Registern verändern sich für jeden Hook!
Code:
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
DIV_SetItemPrice();
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(npc) == VLK_401_LUIS)
{
value = itm.value/3*2;
};
};
MEM_WriteInt(ESP+20, value);
};
func void changeTradeValueDisplay()
{
DIV_SetItemPrice();
// somehow you have to calculate 'value'
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
Danke, ich glaube, ich habe es jetzt.
Code:
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(npc) == VLK_401_LUIS)
{
value = itm.value/3*2;
};
};
MEM_WriteInt(ESP+20, value);
};
func void changeTradeValueDisplay()
{
var int value; value = MEM_ReadInt(/*esp+144h-ach*/ ESP+152);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(npc) == VLK_401_LUIS)
{
value = itm.value/3*2;
};
};
// somehow you have to calculate 'value'
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
Ingame wird jetzt jedenfalls alles richtig berechnet und auch richtig angezeigt.
-
So meinte ich das ursprünglich, um Code-Duplication zu vermeiden:
Code:
func int CalcRealItemPrice(var int origValue, var c_item itm, var c_npc trader) {
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(trader) == VLK_401_LUIS)
{
origValue = itm.value/3*2;
};
};
return origValue;
};
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
value = CalcRealItemPrice(value, itm, npc);
MEM_WriteInt(ESP+20, value);
};
func void changeTradeValueDisplay()
{
var int value; value = MEM_ReadInt(/*esp+144h-ach*/ ESP+152);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
value = CalcRealItemPrice(value, itm, npc);
// somehow you have to calculate 'value'
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
-
Zitat von Lehona
So meinte ich das ursprünglich, um Code-Duplication zu vermeiden:
Code:
func int CalcRealItemPrice(var int origValue, var c_item itm, var c_npc trader) {
if (itm.flags & ITEM_SHIELD)
{
if (Hlp_GetInstanceID(trader) == VLK_401_LUIS)
{
origValue = itm.value/3*2;
};
};
return origValue;
};
func void onTradeLeft_Init()
{
const int oCViewDialogTrade__OnTransferLeftX = 6863312; //0x68B9D0
HookEngineF(oCViewDialogTrade__OnTransferLeftX, 6, onTradeLeft);
};
func void onTradeRight_Init()
{
const int oCItemContainer__DrawItemInfo = 7369937; //0x7074D1
HookEngineF(oCItemContainer__DrawItemInfo, 7, changeTradeValueDisplay);
};
func void onTradeLeft()
{
var int value; value = MEM_ReadInt(ESP+20);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
value = CalcRealItemPrice(value, itm, npc);
MEM_WriteInt(ESP+20, value);
};
func void changeTradeValueDisplay()
{
var int value; value = MEM_ReadInt(/*esp+144h-ach*/ ESP+152);
var oCItem itm; itm = _^(EBX);
var oCNpc npc; npc = _^(MEM_InformationMan.npc);
value = CalcRealItemPrice(value, itm, npc);
// somehow you have to calculate 'value'
MEM_WriteInt(/*esp+144h-ach*/ ESP+152, value);
};
Scheint soweit zu funktionieren, musste allerdings das oCItem und das oCNpc noch durch C_Item und C_NPC ersetzen, weil der Parser sonst gemeckert hat, dass da C_Item und C_NPC erwartet wird. Danke für den Tipp, ist so zumindest schon mal ETWAS weniger Arbeit, wenn ich das nicht alles mind. 2x machen muss.
Eine Frage hätte ich allerdings trotzdem noch: Ist es nicht möglich, den Wert "0" anzeigen zu lassen? Habe das jetzt ein paar mal mit verschiedenen Items probiert, aber immer wenn ich bei origValue eine Null eintrage, steht ingame trotzdem der Wert "1". Eigentlich wollte ich da ja bei Händlern, die das jeweilige Item gar nicht kaufen, einfach nur "-" anzeigen lassen, wo eigentlich der Wert steht. Aber das ist denke ich auch gar nicht so einfach, oder?
Geändert von Bloodfly91 (25.07.2018 um 18:22 Uhr)
-
Scheint so als würde Gothic automatisch aufrunden
'-' anzuzeigen ist vermutlich aufwändiger, weil man da natürlich erstmal nur eine Zahl eintragen kann. Da müsste man dann anders herangehen.
Wäre es vielleicht auch in Ordnung, wenn das Item im Handelsinventar einfach nicht angezeigt wird? Bonne hat da mal eine Implementierung für geschrieben.
-
Zitat von Lehona
Wäre es vielleicht auch in Ordnung, wenn das Item im Handelsinventar einfach nicht angezeigt wird? Bonne hat da mal eine Implementierung für geschrieben.
Ja, das ginge natürlich auch und wäre denke ich sogar schöner.
Berechtigungen
- Neue Themen erstellen: Nein
- Themen beantworten: Nein
- Anhänge hochladen: Nein
- Beiträge bearbeiten: Nein
|