mirror of
https://github.com/Sarjuuk/aowow.git
synced 2025-11-29 15:58:16 +08:00
Pages/Quest
* added map to quest detail page * some minor issues rooted in weired loot templates remain
This commit is contained in:
@@ -552,7 +552,8 @@ trait spawnHelper
|
||||
private $spawnResult = array(
|
||||
SPAWNINFO_FULL => null,
|
||||
SPAWNINFO_SHORT => null,
|
||||
SPAWNINFO_ZONES => null
|
||||
SPAWNINFO_ZONES => null,
|
||||
SPAWNINFO_QUEST => null
|
||||
);
|
||||
|
||||
private function createShortSpawns() // [zoneId, floor, [[x1, y1], [x2, y2], ..]] as tooltip2 if enabled by <a rel="map" ...> or anchor #map (one area, one floor, one creature, no survivors)
|
||||
@@ -675,9 +676,41 @@ trait spawnHelper
|
||||
$this->spawnResult[SPAWNINFO_ZONES] = $res;
|
||||
}
|
||||
|
||||
private function createQuestSpawns() // [zoneId => [floor => [[x1, y1], [x2, y2], ..]]]
|
||||
{
|
||||
if (self::$type == TYPE_SOUND)
|
||||
return;
|
||||
|
||||
$res = DB::Aowow()->select('SELECT areaId, floor, typeId, posX, posY FROM ?_spawns WHERE type = ?d && typeId IN (?a)', self::$type, $this->getFoundIDs());
|
||||
$spawns = [];
|
||||
foreach ($res as $data)
|
||||
{
|
||||
// zone => floor => spawnData
|
||||
// todo (low): why is there a single set of coordinates; which one should be picked, instead of the first? gets used in ShowOnMap.buildTooltip i think
|
||||
if (!isset($spawns[$data['areaId']][$data['floor']][$data['typeId']]))
|
||||
{
|
||||
$spawns[$data['areaId']][$data['floor']][$data['typeId']] = array(
|
||||
'type' => self::$type,
|
||||
'id' => $data['typeId'],
|
||||
'point' => '', // tbd later (start, end, requirement, sourcestart, sourceend, sourcerequirement)
|
||||
'name' => Util::localizedString($this->templates[$data['typeId']], 'name'),
|
||||
'coord' => [$data['posX'], $data['posY']],
|
||||
'coords' => [[$data['posX'], $data['posY']]],
|
||||
'objective' => 0, // tbd later (1-4 set a color; id of creature this entry gives credit for)
|
||||
'reactalliance' => $this->templates[$data['typeId']]['A'] ?: 0,
|
||||
'reacthorde' => $this->templates[$data['typeId']]['H'] ?: 0
|
||||
);
|
||||
}
|
||||
else
|
||||
$spawns[$data['areaId']][$data['floor']][$data['typeId']]['coords'][] = [$data['posX'], $data['posY']];
|
||||
}
|
||||
|
||||
$this->spawnResult[SPAWNINFO_QUEST] = $spawns;
|
||||
}
|
||||
|
||||
public function getSpawns($mode)
|
||||
{
|
||||
// ony Creatures and GOs can be spawned
|
||||
// only Creatures, GOs and SoundEmitters can be spawned
|
||||
if (!self::$type || (self::$type != TYPE_NPC && self::$type != TYPE_OBJECT && self::$type != TYPE_SOUND))
|
||||
return [];
|
||||
|
||||
@@ -698,6 +731,11 @@ trait spawnHelper
|
||||
$this->createZoneSpawns();
|
||||
|
||||
return !empty($this->spawnResult[SPAWNINFO_ZONES][$this->id]) ? $this->spawnResult[SPAWNINFO_ZONES][$this->id] : [];
|
||||
case SPAWNINFO_QUEST:
|
||||
if (empty($this->spawnResult[SPAWNINFO_QUEST]))
|
||||
$this->createQuestSpawns();
|
||||
|
||||
return $this->spawnResult[SPAWNINFO_QUEST];
|
||||
}
|
||||
|
||||
return [];
|
||||
|
||||
@@ -29,6 +29,7 @@ define('TYPE_SOUND', 19);
|
||||
define('TYPE_USER', 500);
|
||||
define('TYPE_EMOTE', 501);
|
||||
define('TYPE_ENCHANTMENT', 502);
|
||||
define('TYPE_AREATRIGGER', 503); // not for display, but indexing in ?_spawns-table
|
||||
|
||||
define('CACHE_TYPE_NONE', 0); // page will not be cached
|
||||
define('CACHE_TYPE_PAGE', 1);
|
||||
@@ -195,6 +196,7 @@ define('ACHIEVEMENTINFO_PROFILE', 0x1);
|
||||
define('SPAWNINFO_ZONES', 1); // not a mask, mutually exclusive
|
||||
define('SPAWNINFO_SHORT', 2);
|
||||
define('SPAWNINFO_FULL', 3);
|
||||
define('SPAWNINFO_QUEST', 4);
|
||||
|
||||
// Community Content
|
||||
define('CC_FLAG_STICKY', 0x1);
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<?php
|
||||
|
||||
define('AOWOW_REVISION', 23);
|
||||
define('AOWOW_REVISION', 24);
|
||||
define('CLI', PHP_SAPI === 'cli');
|
||||
|
||||
|
||||
|
||||
332
pages/quest.php
332
pages/quest.php
@@ -17,6 +17,7 @@ class QuestPage extends GenericPage
|
||||
protected $tabId = 0;
|
||||
protected $mode = CACHE_TYPE_PAGE;
|
||||
protected $css = [['path' => 'Book.css']];
|
||||
protected $js = ['ShowOnMap.js'];
|
||||
|
||||
public function __construct($pageCall, $id)
|
||||
{
|
||||
@@ -348,6 +349,7 @@ class QuestPage extends GenericPage
|
||||
|
||||
// gather ids for lookup
|
||||
$olItems = $olNPCs = $olGOs = $olFactions = [];
|
||||
$olItemData = $olNPCData = $olGOData = null;
|
||||
|
||||
// items
|
||||
$olItems[0] = array( // srcItem on idx:0
|
||||
@@ -459,7 +461,7 @@ class QuestPage extends GenericPage
|
||||
$olGOData = new GameObjectList(array(['id', $ids]));
|
||||
$this->extendGlobalData($olGOData->getJSGlobals(GLOBALINFO_SELF));
|
||||
|
||||
foreach ($olNPCs as $i => $pair)
|
||||
foreach ($olGOs as $i => $pair)
|
||||
{
|
||||
if (!$i || !in_array($i, $olGOData->getFoundIDs()))
|
||||
continue;
|
||||
@@ -531,17 +533,331 @@ class QuestPage extends GenericPage
|
||||
|
||||
$this->addJS('?data=zones&locale='.User::$localeId.'&t='.$_SESSION['dataKey']);
|
||||
|
||||
// gather points of interest
|
||||
$mapNPCs = $mapGOs = []; // [typeId, start|end|objective, startItemId]
|
||||
|
||||
// todo (med): this double list creation very much sucks ...
|
||||
$getItemSource = function ($itemId, $method = 0) use (&$mapNPCs, &$mapGOs)
|
||||
{
|
||||
$lootTabs = new Loot();
|
||||
if ($lootTabs->getByItem($itemId))
|
||||
{
|
||||
/*
|
||||
TODO (GODDAMNIT): jeez..
|
||||
todo (med): sanity check:
|
||||
there are loot templates that are absolute tosh, containing hundrets of random items (e.g. Peacebloom for Quest "The Horde Needs Peacebloom!")
|
||||
even without these .. consider quests like "A Donation of Runecloth" .. oh my .....
|
||||
should we...
|
||||
.. display only a maximum of sources?
|
||||
.. filter sources for low drop chance?
|
||||
|
||||
for the moment:
|
||||
if an item has >10 sources, only display sources with >90% chance
|
||||
always filter sources with <1% chance
|
||||
*/
|
||||
|
||||
// $startend + reqNpcOrGo[1-4]
|
||||
$nSources = 0;
|
||||
foreach ($lootTabs->iterate() as list($type, $data))
|
||||
if ($type == 'creature' || $type == 'object')
|
||||
$nSources += count(array_filter($data['data'], function($val) { return $val['percent'] >= 1.0; }));
|
||||
|
||||
foreach ($lootTabs->iterate() as $idx => list($file, $tabData))
|
||||
{
|
||||
if (!$tabData['data'])
|
||||
continue;
|
||||
|
||||
foreach ($tabData['data'] as $data)
|
||||
{
|
||||
if ($data['percent'] < 1.0)
|
||||
continue;
|
||||
|
||||
if ($nSources > 10 && $data['percent'] < 90.0)
|
||||
continue;
|
||||
|
||||
switch ($file)
|
||||
{
|
||||
case 'creature':
|
||||
$mapNPCs[] = [$data['id'], $method, $itemId];
|
||||
break;
|
||||
case 'object':
|
||||
$mapGOs[] = [$data['id'], $method, $itemId];
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// also there's vendors...
|
||||
// dear god, if you are one of the types who puts queststarter-items in container-items, in conatiner-items, in container-items, in container-GOs .. you should kill yourself by killing yourself!
|
||||
// so yeah .. no recursion checking
|
||||
$vendors = DB::World()->selectCol('
|
||||
SELECT nv.entry FROM npc_vendor nv WHERE nv.item = ?d UNION
|
||||
SELECT c.id FROM game_event_npc_vendor genv JOIN creature c ON c.guid = genv.guid WHERE genv.item = ?d',
|
||||
$itemId, $itemId
|
||||
);
|
||||
foreach ($vendors as $v)
|
||||
$mapNPCs[] = [$v, $method, $itemId];
|
||||
};
|
||||
|
||||
$addObjectiveSpawns = function (array $spawns, callable $processing) use (&$mObjectives)
|
||||
{
|
||||
foreach ($spawns as $zoneId => $zoneData)
|
||||
{
|
||||
if (!isset($mObjectives[$zoneId]))
|
||||
$mObjectives[$zoneId] = array(
|
||||
'zone' => 'Zone #'.$zoneId,
|
||||
'mappable' => 1,
|
||||
'levels' => []
|
||||
);
|
||||
|
||||
foreach ($zoneData as $floor => $floorData)
|
||||
{
|
||||
if (!isset($mObjectives[$zoneId]['levels'][$floor]))
|
||||
$mObjectives[$zoneId]['levels'][$floor] = [];
|
||||
|
||||
foreach ($floorData as $objId => $objData)
|
||||
$mObjectives[$zoneId]['levels'][$floor][] = $processing($objId, $objData);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// POI: start + end
|
||||
foreach ($startEnd as $se)
|
||||
{
|
||||
if ($se['type'] == TYPE_NPC)
|
||||
$mapNPCs[] = [$se['typeId'], $se['method'], 0];
|
||||
else if ($se['type'] == TYPE_OBJECT)
|
||||
$mapGOs[] = [$se['typeId'], $se['method'], 0];
|
||||
else if ($se['type'] == TYPE_ITEM)
|
||||
$getItemSource($se['typeId'], $se['method']);
|
||||
}
|
||||
|
||||
$itemObjectives = [];
|
||||
$mObjectives = [];
|
||||
$mZones = [];
|
||||
$objectiveIdx = 0;
|
||||
|
||||
// POI objectives
|
||||
// also map olItems to objectiveIdx so every container gets the same pin color
|
||||
foreach ($olItems as $i => list($itemId, $qty, $provided))
|
||||
{
|
||||
if (!$provided && $itemId)
|
||||
{
|
||||
$itemObjectives[$itemId] = $objectiveIdx++;
|
||||
$getItemSource($itemId);
|
||||
}
|
||||
}
|
||||
|
||||
// PSA: 'redundant' data is on purpose (e.g. creature required for kill, also dropps item required to collect)
|
||||
|
||||
// external event / areatrigger
|
||||
if ($_specialFlags & QUEST_FLAG_SPECIAL_EXT_COMPLETE)
|
||||
{
|
||||
if ($atir = DB::World()->selectCell('SELECT id FROM areatrigger_involvedrelation WHERE quest = ?d', $this->typeId))
|
||||
if ($atsp = DB::AoWoW()->selectRow('SELECT guid, posX, posY, floor, areaId FROM ?_spawns WHERE `type` = ?d AND `typeId` = ?d', TYPE_AREATRIGGER, $atir))
|
||||
$mObjectives[$atsp['areaId']] = array(
|
||||
'zone' => 'Zone #'.$atsp['areaId'],
|
||||
'mappable' => 1,
|
||||
'levels' => array (
|
||||
$atsp['floor'] => array (
|
||||
array (
|
||||
'type' => -1, // TYPE_AREATRIGGER is internal, the javascript doesn't know it
|
||||
'point' => 'requirement',
|
||||
'name' => $this->subject->parseText('end', false),
|
||||
'coord' => [$atsp['posX'], $atsp['posY']],
|
||||
'coords' => [[$atsp['posX'], $atsp['posY']]],
|
||||
'objective' => $objectiveIdx++
|
||||
)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
// ..adding creature kill requirements
|
||||
if ($olNPCData && !$olNPCData->error)
|
||||
{
|
||||
$spawns = $olNPCData->getSpawns(SPAWNINFO_QUEST);
|
||||
$addObjectiveSpawns($spawns, function ($npcId, $npcData) use ($olNPCs, &$objectiveIdx)
|
||||
{
|
||||
$npcData['point'] = 'requirement'; // always requirement
|
||||
foreach ($olNPCs as $proxyNpcId => $npc)
|
||||
{
|
||||
if (empty($npc[2][$npcId]))
|
||||
continue;
|
||||
|
||||
$npcData['objective'] = $proxyNpcId;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!$npcData['objective'])
|
||||
$npcData['objective'] = $objectiveIdx++;
|
||||
|
||||
return $npcData;
|
||||
});
|
||||
}
|
||||
|
||||
// ..adding object interaction requirements
|
||||
if ($olGOData && !$olGOData->error)
|
||||
{
|
||||
$spawns = $olGOData->getSpawns(SPAWNINFO_QUEST);
|
||||
$addObjectiveSpawns($spawns, function ($goId, $goData, &$objectiveIdx)
|
||||
{
|
||||
$goData['point'] = 'requirement'; // always requirement
|
||||
$goData['objective'] = $objectiveIdx++;
|
||||
return $goData;
|
||||
});
|
||||
}
|
||||
|
||||
// .. adding npc from: droping queststart item; dropping item needed to collect; starting quest; ending quest
|
||||
if ($mapNPCs)
|
||||
{
|
||||
$npcs = new CreatureList(array(['id', array_column($mapNPCs, 0)]));
|
||||
if (!$npcs->error)
|
||||
{
|
||||
$startEndDupe = []; // if quest starter/ender is the same creature, we need to add it twice
|
||||
$spawns = $npcs->getSpawns(SPAWNINFO_QUEST);
|
||||
$addObjectiveSpawns($spawns, function ($npcId, $npcData) use ($mapNPCs, &$startEndDupe, $itemObjectives)
|
||||
{
|
||||
foreach ($mapNPCs as $mn)
|
||||
{
|
||||
if ($mn[0] != $npcId)
|
||||
continue;
|
||||
|
||||
if ($mn[2]) // source for itemId
|
||||
$npcData['item'] = ItemList::getName($mn[2]);
|
||||
|
||||
switch ($mn[1]) // method
|
||||
{
|
||||
case 1: // quest start
|
||||
$npcData['point'] = $mn[2] ? 'sourcestart' : 'start';
|
||||
break;
|
||||
case 2: // quest end (sourceend doesn't actually make sense .. oh well....)
|
||||
$npcData['point'] = $mn[2] ? 'sourceend' : 'end';
|
||||
break;
|
||||
case 3: // quest start & end
|
||||
$npcData['point'] = $mn[2] ? 'sourcestart' : 'start';
|
||||
$startEndDupe = $npcData;
|
||||
$startEndDupe['point'] = $mn[2] ? 'sourceend' : 'end';
|
||||
break;
|
||||
default: // just something to kill for quest
|
||||
$npcData['point'] = $mn[2] ? 'sourcerequirement' : 'requirement';
|
||||
if ($mn[2] && !empty($itemObjectives[$mn[2]]))
|
||||
$npcData['objective'] = $itemObjectives[$mn[2]];
|
||||
}
|
||||
}
|
||||
|
||||
return $npcData;
|
||||
});
|
||||
|
||||
if ($startEndDupe)
|
||||
foreach ($spawns as $zoneId => $zoneData)
|
||||
foreach ($zoneData as $floor => $floorData)
|
||||
foreach ($floorData as $objId => $objData)
|
||||
if ($objId == $startEndDupe['id'])
|
||||
{
|
||||
$mObjectives[$zoneId]['levels'][$floor][] = $startEndDupe;
|
||||
break 3;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// .. adding go from: containing queststart item; containing item needed to collect; starting quest; ending quest
|
||||
if ($mapGOs)
|
||||
{
|
||||
$gos = new GameObjectList(array(['id', array_column($mapGOs, 0)]));
|
||||
if (!$gos->error)
|
||||
{
|
||||
$startEndDupe = []; // if quest starter/ender is the same object, we need to add it twice
|
||||
$spawns = $gos->getSpawns(SPAWNINFO_QUEST);
|
||||
$addObjectiveSpawns($spawns, function ($goId, $goData) use ($mapGOs, &$startEndDupe, $itemObjectives)
|
||||
{
|
||||
foreach ($mapGOs as $mgo)
|
||||
{
|
||||
if ($mgo[0] != $goId)
|
||||
continue;
|
||||
|
||||
if ($mgo[2]) // source for itemId
|
||||
$goData['item'] = ItemList::getName($mgo[2]);
|
||||
|
||||
switch ($mgo[1]) // method
|
||||
{
|
||||
case 1: // quest start
|
||||
$goData['point'] = $mgo[2] ? 'sourcestart' : 'start';
|
||||
break;
|
||||
case 2: // quest end (sourceend doesn't actually make sense .. oh well....)
|
||||
$goData['point'] = $mgo[2] ? 'sourceend' : 'end';
|
||||
break;
|
||||
case 3: // quest start & end
|
||||
$goData['point'] = $mgo[2] ? 'sourcestart' : 'start';
|
||||
$startEndDupe = $goData;
|
||||
$startEndDupe['point'] = $mgo[2] ? 'sourceend' : 'end';
|
||||
break;
|
||||
default: // just something to kill for quest
|
||||
$goData['point'] = $mgo[2] ? 'sourcerequirement' : 'requirement';
|
||||
if ($mgo[2] && !empty($itemObjectives[$mgo[2]]))
|
||||
$goData['objective'] = $itemObjectives[$mgo[2]];
|
||||
}
|
||||
}
|
||||
|
||||
return $goData;
|
||||
});
|
||||
|
||||
if ($startEndDupe)
|
||||
foreach ($spawns as $zoneId => $zoneData)
|
||||
foreach ($zoneData as $floor => $floorData)
|
||||
foreach ($floorData as $objId => $objData)
|
||||
if ($objId == $startEndDupe['id'])
|
||||
{
|
||||
$mObjectives[$zoneId]['levels'][$floor][] = $startEndDupe;
|
||||
break 3;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// ..process zone data
|
||||
if ($mObjectives)
|
||||
{
|
||||
$areas = new ZoneList(array(['id', array_keys($mObjectives)]));
|
||||
if (!$areas->error)
|
||||
{
|
||||
$someIDX = 0; // todo (low): UNK value ... map priority, floor, mapId..? values seen: 0,3; doesn't seem to affect anything
|
||||
foreach ($areas->iterate() as $id => $__)
|
||||
{
|
||||
$mObjectives[$id]['zone'] = $areas->getField('name', true);
|
||||
$mZones[] = [$id, $someIDX];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// has start & end?
|
||||
$hasStartEnd = 0x0;
|
||||
foreach ($mObjectives as $levels)
|
||||
{
|
||||
foreach ($levels['levels'] as $floor)
|
||||
{
|
||||
foreach ($floor as $entry)
|
||||
{
|
||||
if ($entry['point'] == 'start' || $entry['point'] == 'sourcestart')
|
||||
$hasStartEnd |= 0x1;
|
||||
else if ($entry['point'] == 'end' || $entry['point'] == 'sourceend')
|
||||
$hasStartEnd |= 0x2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$this->map = $mObjectives ? array(
|
||||
'mapperData' => [], // always empty
|
||||
'data' => array(
|
||||
'parent' => 'mapper-generic',
|
||||
'objectives' => $mObjectives,
|
||||
'zoneparent' => 'mapper-zone-generic',
|
||||
'zones' => $mZones,
|
||||
'missing' => count($mZones) > 1 || $hasStartEnd != 0x3 ? 1 : 0 // 0 if everything happens in one zone, else 1
|
||||
)
|
||||
) : null;
|
||||
|
||||
$this->map = null;
|
||||
// array(
|
||||
// 'data' => ['zone' => $this->typeId],
|
||||
// 'som' => Util::toJSON($som)
|
||||
// );
|
||||
|
||||
/****************/
|
||||
/* Main Content */
|
||||
|
||||
@@ -1965,7 +1965,7 @@ DROP TABLE IF EXISTS `aowow_spawns`;
|
||||
/*!40101 SET character_set_client = utf8 */;
|
||||
CREATE TABLE `aowow_spawns` (
|
||||
`guid` int(11) NOT NULL COMMENT '< 0: vehicle accessory',
|
||||
`type` tinyint(3) unsigned NOT NULL,
|
||||
`type` smallint(5) unsigned NOT NULL,
|
||||
`typeId` int(10) unsigned NOT NULL,
|
||||
`respawn` int(10) unsigned NOT NULL COMMENT 'in seconds',
|
||||
`spawnMask` tinyint(3) unsigned NOT NULL,
|
||||
|
||||
@@ -45,6 +45,7 @@ class DBC
|
||||
'achievement_category' => 'nisxssxxsxsxxxxxxxxx',
|
||||
'achievement_criteria' => 'niiiiiiiisxssxxsxsxxxxxxxxiixii',
|
||||
'areatable' => 'niixixxiiixsxssxxsxsxxxxxxxxixxxxxxx',
|
||||
'areatrigger' => 'niffxxxxxx',
|
||||
'battlemasterlist' => 'niixxxxxxixxxxxxxxxxxxxxxxxxixii',
|
||||
'charbaseinfo' => 'bb',
|
||||
'charstartoutfit' => 'nbbbXiiiiiiiiiiiiiiiiiiiixxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
|
||||
@@ -145,6 +146,7 @@ class DBC
|
||||
'achievement_category' => 'Id,parentCategory,name_loc0,name_loc2,name_loc3,name_loc6,name_loc8',
|
||||
'achievement_criteria' => 'Id,refAchievementId,type,value1,value2,value3,value4,value5,value6,name_loc0,name_loc2,name_loc3,name_loc6,name_loc8,completionFlags,groupFlags,timeLimit,order',
|
||||
'areatable' => 'Id,mapId,areaTable,flags,soundAmbience,zoneMusic,zoneIntroMusic,name_loc0,name_loc2,name_loc3,name_loc6,name_loc8,factionGroupMask',
|
||||
'areatrigger' => 'Id,mapId,posY,posX',
|
||||
'battlemasterlist' => 'Id,mapId,moreMapId,areaType,maxPlayers,minLevel,maxLevel',
|
||||
'charbaseinfo' => 'raceId,classId',
|
||||
'charstartoutfit' => 'Id,raceId,classId,gender,item1,item2,item3,item4,item5,item6,item7,item8,item9,item10,item11,item12,item13,item14,item15,item16,item17,item18,item19,item20',
|
||||
|
||||
@@ -23,7 +23,7 @@ if (!CLI)
|
||||
|
||||
$customData = array(
|
||||
);
|
||||
$reqDBC = ['worldmaparea', 'map', 'dungeonmap', 'taxipathnode', 'soundemitters'];
|
||||
$reqDBC = ['worldmaparea', 'map', 'dungeonmap', 'taxipathnode', 'soundemitters', 'areatrigger'];
|
||||
|
||||
function spawns() // and waypoints
|
||||
{
|
||||
@@ -102,15 +102,19 @@ function spawns() // and waypoints
|
||||
'FROM dbc_soundemitters',
|
||||
' - assembling '.CLISetup::bold('sound emitter').' spawns'];
|
||||
|
||||
$query[4] = ['SELECT c.guid, w.entry AS "npcOrPath", w.pointId AS "point", c.zoneId AS areaId, c.map, w.waittime AS "wait", w.location_y AS `posX`, w.location_x AS `posY` ' .
|
||||
$query[4] = ['SELECT Id AS "guid", 503 AS "type", Id AS typeId, 0 AS respawn, 0 AS phaseMask, 0 AS areaId, mapId AS "map", 0 AS pathId, posX, posY ' .
|
||||
'FROM dbc_areatrigger',
|
||||
' - assembling '.CLISetup::bold('areatrigger').' spawns'];
|
||||
|
||||
$query[5] = ['SELECT c.guid, w.entry AS "npcOrPath", w.pointId AS "point", c.zoneId AS areaId, c.map, w.waittime AS "wait", w.location_y AS `posX`, w.location_x AS `posY` ' .
|
||||
'FROM creature c JOIN script_waypoint w ON c.id = w.entry',
|
||||
' - assembling waypoints from '.CLISetup::bold('script_waypoint')];
|
||||
|
||||
$query[5] = ['SELECT c.guid, w.entry AS "npcOrPath", w.pointId AS "point", c.zoneId AS areaId, c.map, 0 AS "wait", w.position_y AS `posX`, w.position_x AS `posY` ' .
|
||||
$query[6] = ['SELECT c.guid, w.entry AS "npcOrPath", w.pointId AS "point", c.zoneId AS areaId, c.map, 0 AS "wait", w.position_y AS `posX`, w.position_x AS `posY` ' .
|
||||
'FROM creature c JOIN waypoints w ON c.id = w.entry',
|
||||
' - assembling waypoints from '.CLISetup::bold('waypoints')];
|
||||
|
||||
$query[6] = ['SELECT c.guid, -w.id AS "npcOrPath", w.point, c.zoneId AS areaId, c.map, w.delay AS "wait", w.position_y AS `posX`, w.position_x AS `posY` ' .
|
||||
$query[7] = ['SELECT c.guid, -w.id AS "npcOrPath", w.point, c.zoneId AS areaId, c.map, w.delay AS "wait", w.position_y AS `posX`, w.position_x AS `posY` ' .
|
||||
'FROM creature c JOIN creature_addon ca ON ca.guid = c.guid JOIN waypoint_data w ON w.id = ca.path_id WHERE ca.path_id <> 0',
|
||||
' - assembling waypoints from '.CLISetup::bold('waypoint_data')];
|
||||
|
||||
@@ -154,7 +158,7 @@ function spawns() // and waypoints
|
||||
$n = 0;
|
||||
$sum = 0;
|
||||
|
||||
if ($idx == 3)
|
||||
if ($idx == 3 || $idx == 4)
|
||||
$queryResult = DB::Aowow()->select($q[0]);
|
||||
else
|
||||
$queryResult = DB::World()->select($q[0]);
|
||||
@@ -183,14 +187,14 @@ function spawns() // and waypoints
|
||||
|
||||
if (!$points) // still impossible (there are areas that are intentionally off the map (e.g. the isles south of tanaris))
|
||||
{
|
||||
CLISetup::log('GUID '.$spawn['guid'].($idx < 4 ? '' : ' on path/point '.$spawn['npcOrPath'].'/'.$spawn['point']).' could not be matched to displayable area [A:'.$spawn['areaId'].'; X:'.$spawn['posY'].'; Y:'.$spawn['posX'].']', CLISetup::LOG_WARN);
|
||||
CLISetup::log('GUID '.$spawn['guid'].($idx < 5 ? '' : ' on path/point '.$spawn['npcOrPath'].'/'.$spawn['point']).' could not be matched to displayable area [A:'.$spawn['areaId'].'; X:'.$spawn['posY'].'; Y:'.$spawn['posX'].']', CLISetup::LOG_WARN);
|
||||
continue;
|
||||
}
|
||||
|
||||
// if areaId is set, area was determined by TC .. we're fine .. mostly
|
||||
$final = $spawn['areaId'] ? $points[0] : $checkCoords($points);
|
||||
|
||||
if ($idx < 4)
|
||||
if ($idx < 5)
|
||||
{
|
||||
$set = array(
|
||||
'guid' => $spawn['guid'],
|
||||
|
||||
6
setup/updates/1489291710_01.sql
Normal file
6
setup/updates/1489291710_01.sql
Normal file
@@ -0,0 +1,6 @@
|
||||
ALTER TABLE `aowow_spawns`
|
||||
ALTER `type` DROP DEFAULT;
|
||||
ALTER TABLE `aowow_spawns`
|
||||
CHANGE COLUMN `type` `type` SMALLINT UNSIGNED NOT NULL AFTER `guid`;
|
||||
|
||||
UPDATE `aowow_dbversion` SET `sql` = CONCAT(IFNULL(`sql`, ''), ' spawns');
|
||||
@@ -18385,14 +18385,14 @@ Mapper.prototype = {
|
||||
var maxIdx = [false, -1];
|
||||
for(var i = 0; i < zoneList.length; ++i)
|
||||
{
|
||||
if(i > 0) $WH.ae(span, (i == zoneList.length-1 ? LANG.and : LANG.comma));
|
||||
if(i > 0) $WH.ae(span, $WH.ct(i == zoneList.length-1 ? LANG.and : LANG.comma));
|
||||
var entry = null;
|
||||
if(self.objectives[zoneList[i][0]].mappable > 0)
|
||||
{
|
||||
entry = $WH.ce('a');
|
||||
entry.href = 'javascript:;';
|
||||
$WH.ae(entry, $WH.ct(self.objectives[zoneList[i][0]].zone));
|
||||
entry.onClick = function(link, zone) {
|
||||
entry.onclick = function(link, zone) {
|
||||
self.update({ zone: zone });
|
||||
g_setSelectedLink(link, 'mapper');
|
||||
}.bind(self, entry, zoneList[i][0]);
|
||||
@@ -18509,121 +18509,121 @@ Mapper.prototype = {
|
||||
var parts = LANG.mapper_happensin.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(startEnd && types.objective.length == 0) // starts and ends in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.sex.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(startEnd) // objectives in x, starts and ends in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ox_sey.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, startZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[2]);
|
||||
$WH.ae(span, $WH.ct(parts[2]));
|
||||
}
|
||||
else if(startObj && types.end.length == 0) // objectives and starts in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.osx.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(startObj) // objectives and starts in x, ends in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.osx_ey.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, endZones, typesByZone);
|
||||
$WH.ae(span, parts[2]);
|
||||
$WH.ae(span, $WH.ct(parts[2]));
|
||||
}
|
||||
else if(endObj && types.start.length == 0) // objectives and ends in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.oex.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(endObj) // objectives and ends in x, starts in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.oex_sy.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, startZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(types.start.length > 0 && types.end.length > 0 && types.objective.length > 0) // objectives in x, starts in y, ends in z
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ox_sy_ez.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, startZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
tertiaryLink = zoneLinks(this, span, endZones, typesByZone);
|
||||
$WH.ae(span, parts[3]);
|
||||
$WH.ae(span, $WH.ct(parts[3]));
|
||||
}
|
||||
else if(types.start.length > 0 && types.end.length > 0) // starts in x, ends in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.sx_ey.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, startZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, endZones, typesByZone);
|
||||
$WH.ae(span, parts[2]);
|
||||
$WH.ae(span, $WH.ct(parts[2]));
|
||||
}
|
||||
else if(types.start.length > 0 && types.objective.length > 0) // objectives in x, starts in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ox_sy.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, startZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[2]);
|
||||
$WH.ae(span, $WH.ct(parts[2]));
|
||||
}
|
||||
else if(types.end.length > 0 && types.objective.length > 0) // objectives in x, ends in y
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ox_ey.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, objZones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
secondaryLink = zoneLinks(this, span, endZones, typesByZone);
|
||||
$WH.ae(span, parts[2]);
|
||||
$WH.ae(span, $WH.ct(parts[2]));
|
||||
}
|
||||
else if(types.start.length > 0) // starts in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.sx.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(types.end.length > 0) // ends in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ex.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else if(types.objective.length > 0) // objectives in x
|
||||
{
|
||||
var parts = LANG.mapper_objectives.ox.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
else // wat?
|
||||
{
|
||||
var parts = LANG.mapper_happensin.split('$$');
|
||||
$WH.ae(span, $WH.ct(parts[0]));
|
||||
primaryLink = zoneLinks(this, span, zones, typesByZone);
|
||||
$WH.ae(span, parts[1]);
|
||||
$WH.ae(span, $WH.ct(parts[1]));
|
||||
}
|
||||
$WH.ae(div, span);
|
||||
|
||||
|
||||
@@ -2,8 +2,10 @@
|
||||
if (isset($this->map) && empty($this->map)):
|
||||
echo Lang::zone('noMap');
|
||||
elseif (!empty($this->map['data'])):
|
||||
if ($this->type != TYPE_ZONE):
|
||||
echo ' <div>'.($this->type == TYPE_OBJECT ? Lang::gameObject('foundIn') : ($this->type == TYPE_SOUND ? Lang::sound('foundIn') : Lang::npc('foundIn'))).' <span id="locations">';
|
||||
if ($this->type == TYPE_QUEST) :
|
||||
echo " <div id=\"mapper-zone-generic\"></div>\n";
|
||||
elseif ($this->type != TYPE_ZONE):
|
||||
echo ' <div>'.($this->type == TYPE_OBJECT ? Lang::gameObject('foundIn') : ($this->type == TYPE_SOUND ? Lang::sound('foundIn') : Lang::npc('foundIn'))).' <span id="mapper-zone-generic">';
|
||||
|
||||
$n = count($this->map['mapperData']);
|
||||
$i = 0;
|
||||
@@ -34,10 +36,10 @@ elseif (!empty($this->map['data'])):
|
||||
<?php
|
||||
else:
|
||||
?>
|
||||
<div class="pad"></div>
|
||||
<?php
|
||||
if (isset($this->map['som'])):
|
||||
?>
|
||||
<div class="pad"></div>
|
||||
<div id="som-generic"></div>
|
||||
<?php
|
||||
endif;
|
||||
@@ -52,8 +54,8 @@ elseif (!empty($this->map['data'])):
|
||||
<?php
|
||||
if (!empty($this->map['data']['zone'])):
|
||||
echo " ".(!empty($this->gPageInfo) ? "$.extend(g_pageInfo, {id: ".$this->map['data']['zone']."})" : "var g_pageInfo = {id: ".$this->map['data']['zone']."}").";\n";
|
||||
elseif (!empty($this->map['mapperData'])):
|
||||
echo " var g_mapperData = ".Util::toJSON($this->map['mapperData']).";\n";
|
||||
elseif (isset($this->map['mapperData'])):
|
||||
echo " var g_mapperData = ".Util::toJSON($this->map['mapperData'], empty($this->map['mapperData']) ? JSON_FORCE_OBJECT : 0).";\n";
|
||||
endif;
|
||||
|
||||
// dont forget to set "parent: 'mapper-generic'"
|
||||
@@ -63,8 +65,8 @@ elseif (!empty($this->map['data'])):
|
||||
echo " new ShowOnMap(".Util::toJSON($this->map['som']).");\n";
|
||||
endif;
|
||||
|
||||
if ($this->type != TYPE_ZONE):
|
||||
echo " \$WH.gE(\$WH.ge('locations'), 'a')[0].onclick();\n";
|
||||
if ($this->type != TYPE_ZONE && $this->type != TYPE_QUEST):
|
||||
echo " \$WH.gE(\$WH.ge('mapper-zone-generic'), 'a')[0].onclick();\n";
|
||||
endif;
|
||||
?>
|
||||
//]]></script>
|
||||
|
||||
Reference in New Issue
Block a user