|
You last visited: Today at 07:12
Advertisement
mob killreihenfolge festlegen
Discussion on mob killreihenfolge festlegen within the Diablo 2 Programming forum part of the Diablo 2 category.
07/28/2010, 23:11
|
#1
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
mob killreihenfolge festlegen
weiß einer aus dem stehgreif ob es eine einfache methode gibt um eine allgemeine killreihenfolge für monstergruppen festzulegen.
beispiel:
mein zealer portet sich in ein pack bestehend aus 34234234 monstern, wovon 1 phys immun ist.
er greift dieses ziel mit vengeance an, aber leecht dabei nicht so stark life, wie wenn er zeal benutzen würde.
wenn das ziel dann noch stone skin hat, versäuft er alle pots und chickend letztendlich noch - bei großen gruppen.
was ich bräuchte wäre ein script, dass den phys immunen mob aus jeglicher gruppe als letztes tötet z.B.
mfg und thx
|
|
|
07/28/2010, 23:41
|
#2
|
elite*gold: 0
Join Date: Apr 2010
Posts: 1,675
Received Thanks: 789
|
Quote:
Originally Posted by fuuch
weiß einer aus dem stehgreif ob es eine einfache methode gibt um eine allgemeine killreihenfolge für monstergruppen festzulegen.
beispiel:
mein zealer portet sich in ein pack bestehend aus 34234234 monstern, wovon 1 phys immun ist.
er greift dieses ziel mit vengeance an, aber leecht dabei nicht so stark life, wie wenn er zeal benutzen würde.
wenn das ziel dann noch stone skin hat, versäuft er alle pots und chickend letztendlich noch - bei großen gruppen.
was ich bräuchte wäre ein script, dass den phys immunen mob aus jeglicher gruppe als letztes tötet z.B.
mfg und thx
|
hatte mal auf eon einen threat gelesen in dem stand wie man zu erst die minions angreifen und danach den boss machen kann! aber da ich ja einen speziellen counter bei mir eingebaut habe für hamemr necro und soso´s hat mich das nicht weiter interesiert!
atm bin ich auch zu faul den zu suchen also kannst dich ja selbst auch die suche begeben :P
jedoch würde es dir in deinem speziellen wunsch auch nicht wirklich helfen da es bei dir um die resis geht!
denke so wie du es dir wünscht geht es nicht da du dieses monster nur ganz auslassen kannst oder hinnehmen musst das er es vielleicht zu früh macht ;(
in meinem bot gibt es auch einen townchicken der könnte dich vor deinem gamechicken bewahren! also das er in die stadt geht tränke auffüllt und zurück geht und weiter kämpft! wäre dann aber wieder nur eine verlagerung des problems und keine wirkliche lösung dafür!
mal schauen ob muddy was besseres weiß *g*
|
|
|
07/28/2010, 23:55
|
#3
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
thx ich ziehe es mir rein
|
|
|
07/29/2010, 11:05
|
#4
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
man könnte es über NTC_FindUnit(NTC_UNIT_MONSTER, MonID, retries) und unit.GetNext() versuchen, bis nur das target übrigbleibt - das target wäre dann spectype 0x0A (phys immune mobs sind in der regel 0x0A, also Champions, Uniques und Bosse - bis auf ubertrist vielleicht) und bekäme z.B. als phys immuner mob mit einer speziellen funktion nen non-phys attack, um schneller gekillt zu werden.
|
|
|
07/29/2010, 11:11
|
#5
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
Code:
function NTA_NextMob()
{
if(target.spectype&0x0A)
{ do{
target.GetNext();
} while( [COLOR="Red"]hier fehlt mir die bedingung dafür, um festzulegen, dass das 0x0A target der letzte mob ist in einer range von z.B. "8"[/COLOR]);
}
}
|
|
|
07/29/2010, 15:56
|
#6
|
Administrator
elite*gold: 41624
Join Date: Jan 2010
Posts: 22,728
Received Thanks: 12,654
|
Quote:
Originally Posted by fuuch
Code:
function NTA_NextMob()
{
if(target.spectype&0x0A)
{ do{
target.GetNext();
} while( [COLOR=Red]hier fehlt mir die bedingung dafür, um festzulegen, dass das 0x0A target der letzte mob ist in einer range von z.B. "8"[/COLOR]);
}
}
|
Die Bedingung ist target.GetNext(), die Überprüfung sollte in der Schleife stattfinden.
Aber mal zurück zu deiner eigentlichen Frage: Ich würde mal sagen, es hängt davon ab, ab wann du etwas nicht mehr als einfach erachtest. 
Prinzipiell müsste man die gids sowie die gesuchte Resistenz in einem Array speichern und für dieses dann einen Sortieralgorithmus schreiben, der die Datensätze der Resistenz nach sortiert.
Alternativ könnte man aber auch nur ein sortiertes Einfügen realisieren, das kann man halten wie man möchte.
Danach muss nurnoch dieses nun sortierte Array durchlaufen werden, wobei du jeweils mit der gespeicherten gid direkt das Monster Objekt instantiierst, um es danach anzugreifen.
Um ein unübersichtliches mehrdimensionales Array zu vermeiden, könnte man für die Daten eine eigene Klasse entwerfen und in dem Array dann einfach Objekte dieser neuen Klasse instantiieren. Letzteres hätte den Vorteil, dass man die Klasse leicht durch andere eventuell interessante Attribute erweitern könnte, wobei sich jeweils nur der Konstruktoraufruf minimal verkompliziert.
Fragt sich eigentlich nurnoch, ob du so eine Umsetzung eher leicht oder doch eher weniger leicht findest, es würde so definitiv funktionieren.
Lg
Muddy
|
|
|
07/29/2010, 18:09
|
#7
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
naja informatikerfachchinesisch xd
reicht es im grunde nicht ein array mit den resistenzen zu erstellen, bei dem man mit einer simplen for-loop die reihenfolge bestimmt?
also
Code:
var resiArray = [NTA_DAMAGE_PHYSICAL, NTA_DAMAGE_MAGIC,...]
und dann
Code:
for (var i=0;i<resiArray.length,i++)
{
if(NTA_GetResistance(target,i>=100))
{
target.GetNext()
}
}
oder irgendwie so
|
|
|
07/29/2010, 19:14
|
#8
|
Administrator
elite*gold: 41624
Join Date: Jan 2010
Posts: 22,728
Received Thanks: 12,654
|
Quote:
Originally Posted by fuuch
naja informatikerfachchinesisch xd
reicht es im grunde nicht ein array mit den resistenzen zu erstellen, bei dem man mit einer simplen for-loop die reihenfolge bestimmt?
also
Code:
var resiArray = [NTA_DAMAGE_PHYSICAL, NTA_DAMAGE_MAGIC,...]
und dann
Code:
for (var i=0;i<resiArray.length,i++)
{
if(NTA_GetResistance(target,i>=100))
{
target.GetNext()
}
}
oder irgendwie so
|
Ich habe mir die Bezeichnungen ja nicht ausgedacht, trotzdem sind sie irre praktisch, um sich bei der Fülle an verschiedenene Dingen doch noch relativ präzise auszudrücken.
Und nein, das reicht nicht, weil du ja auch das dazugehörige Monster irgendwie wiederfinden willst, um es anzugreifen.
Jedes Objekt wird - innerhalb eines einzelnen Spieles - durch das Attribut gid eindeutig beschrieben. Um vom Informatikerdeutsch wegzukommen, könnte man sich das auch als Startnummer vorstellen, mit der jede Kiste, jedes Monster, jedes Item im Spiel ins Rennen geht.
Du merkst dir im Array die Resistenzen eines Monsters, sowie seine Startnummer. Hinterher kannst du dann über diese Startnummer ein Monster Objekt instantiieren und zwar von genau dem Monster, zu dem diese Startnummer auch gehört.
Ansonsten hättest du zwar geordnete Resistenzen, die aber eigentlich nicht nutzbar sind, weil du nicht das dazugehörige Monster hast.
Die gid bleibt übrigens wirklich innerhalb eines Spieles konstant und eindeutig, sprich wenn beispielsweise ein Monster Objekt am Anfang die gid 123 hat, ist diese auch noch nach 10 Minuten 123, wenn das Monster schon tot am Boden liegt.
Und das Array kannst du natürlich nicht statisch initialisieren, weil du ja nicht weisst, mit wievielen verschiedenen Monstern du es zu tun hast.
Die Initialisierung sollte darum dynamisch per new-Operator erfolgen, wobei du die neuen Datensätze einfach mit der Methode push() hinten anhängst.
Wobei ja leicht ersichtlich ist, dass du mehrere Variablen pro Datensatz speichern musst, dazu brauchst du entweder ein mehrdimensionales Array (unübersichtlich) oder du baust dir eine eigene Datenstruktur, was in JavaScript nichts anderes ist als eine Klasse. Ist bekannt, wie man Klassen aufbaut?
Über die Klasse kann man die Daten dann in Form von Objekten, mit beliebig vielen Attributen, in einem eindimensionalen Array speichern.
Ich könnte mich jetzt auch noch über den Aufbau eines geeigneten Sortieralgorithmus auslassen, aber ich denke wir machen das mal besser Schritt für Schritt und unterhalten uns - falls nötig - erstmal darüber, wie man eine geeignete Klasse schreibt, um hinterher übersichtliche Datensätze zu haben.
Lg
Muddy
|
|
|
07/29/2010, 20:27
|
#9
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
jo thx muddy das bringt mich weiter
|
|
|
07/29/2010, 22:16
|
#10
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
Code:
function beispiel()
{
var monster = new Object();
monster.gid = '';
monster.resi = '';
monster.setGid = setGid;
monster.getGid = getGid;
monster.setResi = setResi;
monster.getResi = getResi;
var monsterArray = [];
var mob = new monster();
if (target.hp > 0)
{
mob.setGid = target.gid;
mob.setResi = NTA_GetResistance(target, NTA_DAMAGE_PHYSICAL)
}
var _target = NTC_FindUnit(NTC_UNIT_MONSTER);
if(_target)
{
do
{
monsterArray.push(mob);
}while(_target.GetNext());
}
}
function setGid(gid)
{
this.gid = gid;
}
function getGid(gid)
{
return this.gid = gid;
}
function setResi (resi)
{
this.resi = resi;
}
function getResi (resi)
{
return this.resi = resi;
}
das ist jetzt erstmal pseudocode mit nur 1 resi.
ich wollte wissen ob ich auf dem richtigen pfad bin xd
any suggestions?
|
|
|
07/30/2010, 14:16
|
#11
|
Administrator
elite*gold: 41624
Join Date: Jan 2010
Posts: 22,728
Received Thanks: 12,654
|
Quote:
Originally Posted by fuuch
Code:
function beispiel() // <-- Das soll aber schon die Klasse sein oder?
{
var monster = new Object();
monster.gid = ''; // <-- Mal abgesehen davon, dass das so unsinnig ist, sind sowohl die gid als auch die Resistenzen ganzzahlige numerische Werte und KEINE Zeichenketten!
monster.resi = '';
monster.setGid = setGid; // <-- Du brauchst eigentlich keine Getter und Setter Funktionen, weil die Atribute später ohnehin public sein werden ;)
monster.getGid = getGid;
monster.setResi = setResi;
monster.getResi = getResi;
var monsterArray = [];
var mob = new monster();
if (target.hp > 0)
{
mob.setGid = target.gid; // <-- A bit holprig...du überschreibst eine Funktion jetzt auf einmal mit einer einfachen Variable
mob.setResi = NTA_GetResistance(target, NTA_DAMAGE_PHYSICAL)
}
var _target = NTC_FindUnit(NTC_UNIT_MONSTER); // <-- Sofern "beispiel" die Klasse sein soll, hat dieser ganze Teil hier eigentlich nicht wirklich etwas verloren
if(_target)
{
do
{
monsterArray.push(mob);
}while(_target.GetNext());
}
}
function setGid(gid)
{
this.gid = gid;
}
function getGid(gid) // <-- Getter Funktionen werden in der Regel parameterlos aufgerufen (==void)
{
return this.gid = gid; // <-- Und sie geben auch keine Zuweisung zurück, sondern private Klassenvariablen (welche man hier eigentlich gar nicht hat ;) )
}
function setResi (resi)
{
this.resi = resi;
}
function getResi (resi)
{
return this.resi = resi;
}
das ist jetzt erstmal pseudocode mit nur 1 resi.
ich wollte wissen ob ich auf dem richtigen pfad bin xd
any suggestions?
|
Naja, nicht so richtig, ich habe mal ein paar Teile kommentiert.
Ist zwar nur ein Entwurf, sind aber schon ein paar gröbere Sachen drin.
Ich habe mal schnell eine grobe 10 Minuten Variante aufgeschrieben, für was ordentliches fehlen mir gerade Zeit und Lust, darum ist es auch schlecht kommentiert. 
Voila:
Code:
function MW_MachWas()
{
var _monsters, _monster, _range;
_monster = NTC_FindUnit(NTC_UNIT_MONSTER);
_monsters = new Array();
_range = 42;
if(_monster)
{
do
{
if(_monster.IsAttackable() && NTA_IsValidMonster(_monster) && GetDistance(me, _monster) < _range)
_monsters.push(new MonsterData(_monster.gid, NTA_GetResistance(_monster, NTA_DAMAGE_FIRE), NTA_GetResistance(_monster, NTA_DAMAGE_COLD), NTA_GetResistance(_monster, NTA_DAMAGE_LIGHTNING), NTA_GetResistance(_monster, NTA_DAMAGE_POISON), NTA_GetResistance(_monster, NTA_DAMAGE_PHYSICAL), NTA_GetResistance(_monster, NTA_DAMAGE_MAGIC)));
}while(_monster.GetNext());
}
_monsters.sort(MW_SortByResistance);
}
function MonsterData(gid, fres, cres, lres, pres, phys, magic)
{
this.gid = gid;
this.res = new MonsterRes(fres, cres, lres, pres, phys, magic);
}
function MonsterRes(fres, cres, lres, pres, phys, magic)
{
this.fire = fres;
this.cold = cres;
this.light = lres;
this.poison = pres;
this.phys = phys;
this.magic = magic;
}
// Simpler Bubble Sort Algorithmus zur aufsteigenden Sortierung nach physischer Resistenz
function MW_SortByResistance(a, b)
{
if(a.res.phys > b.res.phys)
return 1;
else if(a.res.phys < b.res.phys)
return -1;
else
return 0;
}
Ich war mal so frei die Resistenzen als eingebettetes Objekt einzubinden, macht die Sache noch etwas übersichtliches finde ich.
Prinzipiell müsste das aber keine eigene Funktion werden sonder vielmehr auf eine entsprechende Modifikation der Funktion NTA_ClearPosition() hinauslaufen, aber das weisst du bestimmt schon selbst, weil du dich mit der längst mit dieser Funktion auseinandergesetzt hast.
Lg
Muddy
|
|
|
07/30/2010, 14:34
|
#12
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
thx muddy, bist the best
|
|
|
07/30/2010, 17:35
|
#13
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
Code:
function NTA_ClearPosition(range, pickitem, safelevel)
{
var _orgx, _orgy;
var _spectype = [0x0A, 0x01, 0x01];
var _skiplist;
var _attackcount = 0;
var _target;
var _distance, _mingid, _mindistance;
var _result;
var _monsters;
_monsters = new Array();
if(NTConfig_AttackSkill[1] < 1 || NTConfig_AttackSkill[3] < 1)
return false;
switch(arguments.length)
{
case 0:
range = 20;
case 1:
pickitem = false;
case 2:
safelevel = 0;
default:
if(NTConfig_CheckSelfSafe < 0x01 && NTConfig_CheckMercSafe < 0x01)
safelevel = 0;
break;
}
_orgx = me.x;
_orgy = me.y;
for(var i = 0 ; i < _spectype.length ; i++)
{
_skiplist = new Array();
while(_attackcount < (i+1)*100)
{
_mindistance = 100000;
_target = NTC_FindUnit(NTC_UNIT_MONSTER);
if(_target)
{
do
{
if(_skiplist.indexOf(_target.gid) < 0)
{
if(_target.IsAttackable() && (_target.spectype&_spectype[i]))
{
if(GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTA_IsValidMonster(_target))
{
_distance = GetDistance(me, _target);
if(_distance < _mindistance)
{
_mingid = _target.gid;
_mindistance = _distance;
_monsters.push(new MonsterData(_mingid, NTA_GetResistance(_target, NTA_DAMAGE_FIRE), NTA_GetResistance(_target, NTA_DAMAGE_COLD), NTA_GetResistance(_target, NTA_DAMAGE_LIGHTNING), NTA_GetResistance(_target, NTA_DAMAGE_POISON), NTA_GetResistance(_target, NTA_DAMAGE_PHYSICAL), NTA_GetResistance(_target, NTA_DAMAGE_MAGIC)));
}
}
}
else
_skiplist.push(_target.gid);
}
} while(_target.GetNext());
}
_monsters.sort(MW_SortByResistance);
if(_mindistance < 100000)
{
var tempMob = _monsters.pop();
if(NTC_FindUnit(NTC_UNIT_MONSTER, tempMob.gid))
{
_target = NTC_FindUnit(NTC_UNIT_MONSTER, tempMob.gid);
}
else
{
_target = NTC_FindUnit(NTC_UNIT_MONSTER, _mingid);
}
if(_target)
{
_result = NTA_Attack(_target, (_attackcount%30) == 0);
switch(_result)
{
case 1:
_skiplist.push(_mingid);
break;
case 2:
case 3:
if(NTConfig_PickItemsInstantly && (_target.hp <= 0 || _target.mode == 0 || _target.mode == 12))
NTSI_PickItems();
_attackcount++;
break;
default:
return false;
}
}
}
else
break;
}
}
if(me.classid == NTC_CHAR_CLASS_PALADIN)
{
if(_attackcount > 2 && (parseInt(me.hp*100/me.hpmax) < NTConfig_UseRedemptionHP || parseInt(me.mp*100/me.mpmax) < NTConfig_UseRedemptionMP))
{
if(NTC_PutSkill(124, NTC_HAND_RIGHT))
NTC_PingDelay(2000);
}
}
if(NTConfig_UseFindItem && me.classid == NTC_CHAR_CLASS_BARBARIAN && _attackcount > 2)
{
if(!NTA_CheckForCloseMonsters(10))
NTL_FindItem(NTConfig_FindItemRange);
}
if(NTConfig_OpenChest)
{
_target = NTC_GetSpecialChest();
if(_target && GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTC_OpenChest(_target))
_attackcount++;
}
if(pickitem && _attackcount > 0)
NTSI_PickItems();
if(NTConfig_OpenAllNearbyChests)
NTL_OpenNearbyChests();
switch(safelevel)
{
case 1:
return NTTMGR_CheckSafe(0x00, NTConfig_CheckMercSafe&0x01);
case 2:
return NTTMGR_CheckSafe(NTConfig_CheckSelfSafe, NTConfig_CheckMercSafe);
}
return true;
}
function MonsterData(gid, fres, cres, lres, pres, phys, magic)
{
this.gid = gid;
this.res = new MonsterRes(fres, cres, lres, pres, phys, magic);
}
function MonsterRes(fres, cres, lres, pres, phys, magic)
{
this.fire = fres;
this.cold = cres;
this.light = lres;
this.poison = pres;
this.phys = phys;
this.magic = magic;
}
// Simpler Bubble Sort Algorithmus zur aufsteigenden Sortierung nach physischer Resistenz
function MW_SortByResistance(a, b)
{
if(a.res.phys > b.res.phys)
return 1;
else if(a.res.phys < b.res.phys)
return -1;
else
return 0;
}
ich weiß nicht, ob pop() der richtige aufruf ist, da ich kp von bubblesort habe unter javascript..
geradeeben hat er einen phys immunen stehen lassen, aber irgendwie klappt es nicht immer
|
|
|
07/30/2010, 19:24
|
#14
|
Administrator
elite*gold: 41624
Join Date: Jan 2010
Posts: 22,728
Received Thanks: 12,654
|
Quote:
Originally Posted by fuuch
Code:
function NTA_ClearPosition(range, pickitem, safelevel)
{
var _orgx, _orgy;
var _spectype = [0x0A, 0x01, 0x01];
var _skiplist;
var _attackcount = 0;
var _target;
var _distance, _mingid, _mindistance;
var _result;
var _monsters;
_monsters = new Array();
if(NTConfig_AttackSkill[1] < 1 || NTConfig_AttackSkill[3] < 1)
return false;
switch(arguments.length)
{
case 0:
range = 20;
case 1:
pickitem = false;
case 2:
safelevel = 0;
default:
if(NTConfig_CheckSelfSafe < 0x01 && NTConfig_CheckMercSafe < 0x01)
safelevel = 0;
break;
}
_orgx = me.x;
_orgy = me.y;
for(var i = 0 ; i < _spectype.length ; i++)
{
_skiplist = new Array();
while(_attackcount < (i+1)*100)
{
_mindistance = 100000;
_target = NTC_FindUnit(NTC_UNIT_MONSTER);
if(_target)
{
do
{
if(_skiplist.indexOf(_target.gid) < 0)
{
if(_target.IsAttackable() && (_target.spectype&_spectype[i]))
{
if(GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTA_IsValidMonster(_target))
{
_distance = GetDistance(me, _target);
if(_distance < _mindistance)
{
_mingid = _target.gid;
_mindistance = _distance;
_monsters.push(new MonsterData(_mingid, NTA_GetResistance(_target, NTA_DAMAGE_FIRE), NTA_GetResistance(_target, NTA_DAMAGE_COLD), NTA_GetResistance(_target, NTA_DAMAGE_LIGHTNING), NTA_GetResistance(_target, NTA_DAMAGE_POISON), NTA_GetResistance(_target, NTA_DAMAGE_PHYSICAL), NTA_GetResistance(_target, NTA_DAMAGE_MAGIC)));
}
}
}
else
_skiplist.push(_target.gid);
}
} while(_target.GetNext());
}
_monsters.sort(MW_SortByResistance);
if(_mindistance < 100000)
{
var tempMob = _monsters.pop();
if(NTC_FindUnit(NTC_UNIT_MONSTER, tempMob.gid))
{
_target = NTC_FindUnit(NTC_UNIT_MONSTER, tempMob.gid);
}
else
{
_target = NTC_FindUnit(NTC_UNIT_MONSTER, _mingid);
}
if(_target)
{
_result = NTA_Attack(_target, (_attackcount%30) == 0);
switch(_result)
{
case 1:
_skiplist.push(_mingid);
break;
case 2:
case 3:
if(NTConfig_PickItemsInstantly && (_target.hp <= 0 || _target.mode == 0 || _target.mode == 12))
NTSI_PickItems();
_attackcount++;
break;
default:
return false;
}
}
}
else
break;
}
}
if(me.classid == NTC_CHAR_CLASS_PALADIN)
{
if(_attackcount > 2 && (parseInt(me.hp*100/me.hpmax) < NTConfig_UseRedemptionHP || parseInt(me.mp*100/me.mpmax) < NTConfig_UseRedemptionMP))
{
if(NTC_PutSkill(124, NTC_HAND_RIGHT))
NTC_PingDelay(2000);
}
}
if(NTConfig_UseFindItem && me.classid == NTC_CHAR_CLASS_BARBARIAN && _attackcount > 2)
{
if(!NTA_CheckForCloseMonsters(10))
NTL_FindItem(NTConfig_FindItemRange);
}
if(NTConfig_OpenChest)
{
_target = NTC_GetSpecialChest();
if(_target && GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTC_OpenChest(_target))
_attackcount++;
}
if(pickitem && _attackcount > 0)
NTSI_PickItems();
if(NTConfig_OpenAllNearbyChests)
NTL_OpenNearbyChests();
switch(safelevel)
{
case 1:
return NTTMGR_CheckSafe(0x00, NTConfig_CheckMercSafe&0x01);
case 2:
return NTTMGR_CheckSafe(NTConfig_CheckSelfSafe, NTConfig_CheckMercSafe);
}
return true;
}
function MonsterData(gid, fres, cres, lres, pres, phys, magic)
{
this.gid = gid;
this.res = new MonsterRes(fres, cres, lres, pres, phys, magic);
}
function MonsterRes(fres, cres, lres, pres, phys, magic)
{
this.fire = fres;
this.cold = cres;
this.light = lres;
this.poison = pres;
this.phys = phys;
this.magic = magic;
}
// Simpler Bubble Sort Algorithmus zur aufsteigenden Sortierung nach physischer Resistenz
function MW_SortByResistance(a, b)
{
if(a.res.phys > b.res.phys)
return 1;
else if(a.res.phys < b.res.phys)
return -1;
else
return 0;
}
ich weiß nicht, ob pop() der richtige aufruf ist, da ich kp von bubblesort habe unter javascript..
geradeeben hat er einen phys immunen stehen lassen, aber irgendwie klappt es nicht immer
|
Sind auch noch ein paar kleine Denkfehler drin, sieht aber schon sehr viel besser aus als dein vorheriger Ansatz.
Wenn du dir die normale Funktion anschaust, wird ja jeweils das nächstgelegene Monster angegriffen (natürlich spielt hier auch noch der derzeit betrachtete spectype eine Rolle).
Prinzipiell wollen wir uns ja alle naheliegenden Monster bzw. deren gid und Resistenzen merken, um sie danach den jeweiligen Resistenzen nach anzugreifen, wobei wir mit den niedrigeren anfangen.
Bei dem aktuellen Aufbau merkst du dir aber nicht alle Monster, sondern nur die, die jeweils näher beim Charakter sind, als das letzte Monster, welches dem Char am nächsten war.
Es werden darum längst nicht alle Monster gespeichert, sodass das Array deutlich weniger Elemente enthält, als es eigentlich der Fall sein sollte.
Man könnte sich leicht einen Schlimmstfall vorstellen: Ein PI Monster steht direkt neben dir (soll also insgesamt den geringsten Abstand von allen anderen Monstern haben) und das dazugehörige Objekt ist im ersten Durchlauf der do-while-Schleife ausgewählt.
In diesem Fall würde dem Array zur Resistenzenauswertung nur genau ein Datensatz hinzugefügt werden.
Natürlich würde dann entsprechend das passende Objekt über die gespeicherte gid instantiiert und angegriffen - die durchgeführte Änderung hätte gar keine Bedeutung.
Ein Extrembeispiel, aber ich denke man kann das Problem dabei ganz gut nachvollziehen.
Damit das funktioniert, müssen wirklich alle Monster im gültigen Radius im Array gespeichert werden. Der Abstand spielt dann auch erstmal pauschal keine Rolle mehr.
Um das zu Ändern müsste man das nun entstandene Array nochmal sortieren, wobei man sich diesmal nur den Anfang des Arrays anschaut (also die kleinsten Resistenzen), weil ja vermutlich am Anfang eine ganze Gruppe von Monstern stehen wird, deren Resistenzen identisch sind - es gilt nun diese Gruppe nochmal nach dem Abstand zu sortieren, sodass wir im Endeffekt das Monster mit den niedrigsten Resistenzen, welches uns gleichzeitig am nächsten ist, angreifen.
Um nochmal auf deine Funktion zurückzukommen:
Die Methode pop() trennt das letzte Element eines Arrays ab und gibt es zurück - das letzte Element entspricht bei unserer Sortierung aber gerade den höchsten Resistenzen, ist also nicht wirklich das was wir wollen.
Achja, das mit der alternativen Instantiierung des nächstgelegenen Monsters im Fehlerfall gefällt mir gut, soll ja auch mal vorkommen.
Versuchs mal in etwa so:
Code:
function NTA_ClearPosition(range, pickitem, safelevel)
{
var _orgx, _orgy;
var _spectype = [0x0A, 0x01, 0x01];
var _skiplist;
var _attackcount = 0;
var _target;
var _distance, _mingid, _mindistance;
var _result;
var _monsters;
_monsters = new Array();
if(NTConfig_AttackSkill[1] < 1 || NTConfig_AttackSkill[3] < 1)
return false;
switch(arguments.length)
{
case 0:
range = 20;
case 1:
pickitem = false;
case 2:
safelevel = 0;
default:
if(NTConfig_CheckSelfSafe < 0x01 && NTConfig_CheckMercSafe < 0x01)
safelevel = 0;
break;
}
_orgx = me.x;
_orgy = me.y;
for(var i = 0 ; i < _spectype.length ; i++)
{
_skiplist = new Array();
while(_attackcount < (i+1)*100)
{
_mindistance = 100000;
_target = NTC_FindUnit(NTC_UNIT_MONSTER);
if(_target)
{
do
{
if(_skiplist.indexOf(_target.gid) < 0)
{
if(_target.IsAttackable() && (_target.spectype&_spectype[i]))
{
if(GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTA_IsValidMonster(_target))
{
_distance = GetDistance(me, _target);
if(_distance < _mindistance)
{
_mingid = _target.gid;
_mindistance = _distance;
}
_monsters.push(new MonsterData(_mingid, NTA_GetResistance(_target, NTA_DAMAGE_FIRE), NTA_GetResistance(_target, NTA_DAMAGE_COLD), NTA_GetResistance(_target, NTA_DAMAGE_LIGHTNING), NTA_GetResistance(_target, NTA_DAMAGE_POISON), NTA_GetResistance(_target, NTA_DAMAGE_PHYSICAL), NTA_GetResistance(_target, NTA_DAMAGE_MAGIC)));
}
}
else
_skiplist.push(_target.gid);
}
} while(_target.GetNext());
}
_monsters.sort(MW_SortByResistance);
var _mingidRes = 0;
var _mindistRes = 1E6;
var _tempTarget;
for(var i = 0; i < _monsters.length; i++)
{
_tempTarget = NTC_FindUnit(NTC_UNIT_MONSTER, _monsters[i].gid);
if(_tempTarget)
{
if(i > 0 && _monsters[i].res.phys != _monsters[i-1].res.phys)
break;
/* Alternativ: Nicht niedrigste Resistenz prüfen, sondern nächstes Monster angreifen, das nicht immun ist
if(i > 0 && _monsters[i].res.phys > 99)
break;
*/
_distance = GetDistance(me, _target);
if(_distance < _mindistance)
{
_mingidRes = _tempTarget.gid;
_mindistRes = _distance;
}
}
}
if(_mindistance < 100000)
{
if(!(_target = NTC_FindUnit(NTC_UNIT_MONSTER, _mingidRes)))
_target = NTC_FindUnit(NTC_UNIT_MONSTER, _mingid);
if(_target)
{
_result = NTA_Attack(_target, (_attackcount%30) == 0);
switch(_result)
{
case 1:
_skiplist.push(_mingid);
break;
case 2:
case 3:
if(NTConfig_PickItemsInstantly && (_target.hp <= 0 || _target.mode == 0 || _target.mode == 12))
NTSI_PickItems();
_attackcount++;
break;
default:
return false;
}
}
}
else
break;
}
}
if(me.classid == NTC_CHAR_CLASS_PALADIN)
{
if(_attackcount > 2 && (parseInt(me.hp*100/me.hpmax) < NTConfig_UseRedemptionHP || parseInt(me.mp*100/me.mpmax) < NTConfig_UseRedemptionMP))
{
if(NTC_PutSkill(124, NTC_HAND_RIGHT))
NTC_PingDelay(2000);
}
}
if(NTConfig_UseFindItem && me.classid == NTC_CHAR_CLASS_BARBARIAN && _attackcount > 2)
{
if(!NTA_CheckForCloseMonsters(10))
NTL_FindItem(NTConfig_FindItemRange);
}
if(NTConfig_OpenChest)
{
_target = NTC_GetSpecialChest();
if(_target && GetDistance(_orgx, _orgy, _target.x, _target.y) <= range && NTC_OpenChest(_target))
_attackcount++;
}
if(pickitem && _attackcount > 0)
NTSI_PickItems();
if(NTConfig_OpenAllNearbyChests)
NTL_OpenNearbyChests();
switch(safelevel)
{
case 1:
return NTTMGR_CheckSafe(0x00, NTConfig_CheckMercSafe&0x01);
case 2:
return NTTMGR_CheckSafe(NTConfig_CheckSelfSafe, NTConfig_CheckMercSafe);
}
return true;
}
Achja, es ist offensichtlich, dass der spectype hier ziemlich negativ reinfunkt, weil PI Bosse trotzdem immer zuerst angegriffen werden.
Lg
Muddy
|
|
|
07/30/2010, 22:19
|
#15
|
elite*gold: 0
Join Date: Jul 2008
Posts: 169
Received Thanks: 14
|
danke das du dir die zeit nimmst, dich damit zu befassen muddy
|
|
|
 |
|
Similar Threads
|
[V-Tut]Rates in der DB festlegen.
08/21/2010 - Metin2 PServer Guides & Strategies - 13 Replies
Hallo EPvPers,YouTube - Rates in der DB festlegen
Das tut hab ich gerade für einen User aufgenommen,
ich poste es schnell noch mal in der Section, damit man es auch leichter über die SuFu findet ;)
MfG, Xel~
|
Fenstergröße festlegen
05/26/2010 - GW Bots - 1 Replies
Hallo, kann man mit einem au3 script die Größe vom Guild Wars Fenster festlegen lassen?
Wenn ja wie?
Danke
|
NPC Positionen festlegen
04/25/2010 - Metin2 Private Server - 4 Replies
hey also wie der name schon sag will ich gerne wissen wie man bei den npc eine bestimmte position festlegt bezogen auf den betrunkenen bürger ich will ihn nicht dumm rum gurken lassen weil er alle fbs in sich trägt un deshalb will ich ihn halt an eine bestimmte position stellen wäre nett wenn jemand ein tut hat oda so habe nämlich nichts gefunden!!!
:D
|
value mit $_get festlegen
04/05/2010 - General Coding - 0 Replies
ich probiere grade ein vorher festgelegte get form ueber post zu uebermitteln
meine idee war nun
das
<input type="hidden" name="hauptkate" value="<?php echo '$_GET'?> ">
einzubauen in der post form und dies sollte dann als value den wert von choosekate nehmen
|
FPS festlegen?
07/11/2008 - Kal Online - 7 Replies
Hi,
Wollte euch mal Fragen ob ihr wisst, wie ich die FPS in Kal auf eine bestimmte zahl fixen kann. Weil manchmal geht das auf 500+ und es ist Zeitlupe.
Über nvidia ControlPanel hab ich bei der engine.exe vertikale Synchronisation eingestellt. Müsste als nicht über 60Hz gehen tuts aber dennoch.
Kann man das noch irgendwie anders auf eine unkomplizierte Art lösen?
MfG
|
All times are GMT +1. The time now is 07:14.
|
|