void SmartAI::OnCharmed(bool /*isNew*/) { bool const charmed = me->IsCharmed(); if (charmed) // do this before we change charmed state, as charmed state might prevent these things from processing { if (HasEscortState(SMART_ESCORT_ESCORTING | SMART_ESCORT_PAUSED | SMART_ESCORT_RETURNING)) EndPath(true); } mIsCharmed = charmed; if (!charmed && !me->IsInEvadeMode()) { if (_repeatWaypointPath) StartPath(mRun, GetScript()->GetPathId(), true); else me->SetWalk(!mRun); if (me->LastCharmerGUID) { if (!me->HasReactState(REACT_PASSIVE)) if (Unit* lastCharmer = ObjectAccessor::GetUnit(*me, me->LastCharmerGUID)) me->EngageWithTarget(lastCharmer); me->LastCharmerGUID.Clear(); } } GetScript()->ProcessEventsFor(SMART_EVENT_CHARMED, nullptr, 0, 0, charmed); }
void SmartAI::EndPath(bool fail) { GetScript()->ProcessEventsFor(SMART_EVENT_WAYPOINT_ENDED, NULL, mLastWP->id, GetScript()->GetPathId()); RemoveEscortState(SMART_ESCORT_ESCORTING | SMART_ESCORT_PAUSED | SMART_ESCORT_RETURNING); mWayPoints = NULL; mCurrentWPID = 0; mWPPauseTimer = 0; mLastWP = NULL; if (mCanRepeatPath) StartPath(mRun, GetScript()->GetPathId(), mCanRepeatPath); else GetScript()->SetPathId(0); ObjectList* targets = GetScript()->GetTargetList(SMART_ESCORT_TARGETS); if (targets && mEscortQuestID) { if (targets->size() == 1 && GetScript()->IsPlayer((*targets->begin()))) { Player* plr = (*targets->begin())->ToPlayer(); if(!fail && plr->IsAtGroupRewardDistance(me) && !plr->GetCorpse()) plr->GroupEventHappens(mEscortQuestID, me); if(fail && plr->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) plr->FailQuest(mEscortQuestID); if (Group *pGroup = plr->GetGroup()) { for (GroupReference *gr = pGroup->GetFirstMember(); gr != NULL; gr = gr->next()) { Player *pGroupGuy = gr->getSource(); if(!fail && pGroupGuy->IsAtGroupRewardDistance(me) && !pGroupGuy->GetCorpse()) pGroupGuy->AreaExploredOrEventHappens(mEscortQuestID); if(fail && pGroupGuy->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) pGroupGuy->FailQuest(mEscortQuestID); } } }else { for (ObjectList::iterator iter = targets->begin(); iter != targets->end(); iter++) { if (GetScript()->IsPlayer((*iter))) { Player* plr = (*iter)->ToPlayer(); if(!fail && plr->IsAtGroupRewardDistance(me) && !plr->GetCorpse()) plr->AreaExploredOrEventHappens(mEscortQuestID); if(fail && plr->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) plr->FailQuest(mEscortQuestID); } } } } if (mDespawnState == 1) StartDespawn(); }
void SmartAI::OnCharmed(bool apply) { if (apply) // do this before we change charmed state, as charmed state might prevent these things from processing { if (HasEscortState(SMART_ESCORT_ESCORTING | SMART_ESCORT_PAUSED | SMART_ESCORT_RETURNING)) EndPath(true); me->StopMoving(); } mIsCharmed = apply; if (!apply && !me->IsInEvadeMode()) { if (mCanRepeatPath) StartPath(mRun, GetScript()->GetPathId(), true); else me->SetWalk(!mRun); if (Unit* charmer = me->GetCharmer()) AttackStart(charmer); } GetScript()->ProcessEventsFor(SMART_EVENT_CHARMED, nullptr, 0, 0, apply); }
void SmartAI::EndPath(bool fail) { RemoveEscortState(SMART_ESCORT_ESCORTING | SMART_ESCORT_PAUSED | SMART_ESCORT_RETURNING); _path.nodes.clear(); _waypointPauseTimer = 0; if (_escortNPCFlags) { me->SetFlag(UNIT_NPC_FLAGS, _escortNPCFlags); _escortNPCFlags = 0; } ObjectVector const* targets = GetScript()->GetStoredTargetVector(SMART_ESCORT_TARGETS, *me); if (targets && mEscortQuestID) { if (targets->size() == 1 && GetScript()->IsPlayer((*targets->begin()))) { Player* player = targets->front()->ToPlayer(); if (!fail && player->IsAtGroupRewardDistance(me) && !player->HasCorpse()) player->GroupEventHappens(mEscortQuestID, me); if (fail) player->FailQuest(mEscortQuestID); if (Group* group = player->GetGroup()) { for (GroupReference* groupRef = group->GetFirstMember(); groupRef != nullptr; groupRef = groupRef->next()) { Player* groupGuy = groupRef->GetSource(); if (!groupGuy->IsInMap(player)) continue; if (!fail && groupGuy->IsAtGroupRewardDistance(me) && !groupGuy->HasCorpse()) groupGuy->AreaExploredOrEventHappens(mEscortQuestID); else if (fail) groupGuy->FailQuest(mEscortQuestID); } } } else { for (WorldObject* target : *targets) { if (GetScript()->IsPlayer(target)) { Player* player = target->ToPlayer(); if (!fail && player->IsAtGroupRewardDistance(me) && !player->HasCorpse()) player->AreaExploredOrEventHappens(mEscortQuestID); else if (fail) player->FailQuest(mEscortQuestID); } } } } // End Path events should be only processed if it was SUCCESSFUL stop or stop called by SMART_ACTION_WAYPOINT_STOP if (fail) return; GetScript()->ProcessEventsFor(SMART_EVENT_WAYPOINT_ENDED, nullptr, _currentWaypointNode, GetScript()->GetPathId()); if (_repeatWaypointPath) { if (IsAIControlled()) StartPath(mRun, GetScript()->GetPathId(), _repeatWaypointPath); } else GetScript()->SetPathId(0); if (mDespawnState == 1) StartDespawn(); }
void SmartAI::EndPath(bool fail) { RemoveEscortState(SMART_ESCORT_ESCORTING | SMART_ESCORT_PAUSED | SMART_ESCORT_RETURNING); mWayPoints = NULL; mLastWP = NULL; mWPPauseTimer = 0; if (mEscortNPCFlags) { me->SetUInt32Value(UNIT_NPC_FLAGS, mEscortNPCFlags); mEscortNPCFlags = 0; } ObjectList* targets = GetScript()->GetTargetList(SMART_ESCORT_TARGETS); if (targets && mEscortQuestID) { if (targets->size() == 1 && GetScript()->IsPlayer((*targets->begin()))) { Player* player = (*targets->begin())->ToPlayer(); if (Group* group = player->GetGroup()) { for (GroupReference* groupRef = group->GetFirstMember(); groupRef != NULL; groupRef = groupRef->next()) { Player* groupGuy = groupRef->GetSource(); if (!groupGuy || !player->IsInMap(groupGuy)) continue; if (!fail && groupGuy->IsAtGroupRewardDistance(me) && !groupGuy->GetCorpse()) groupGuy->AreaExploredOrEventHappens(mEscortQuestID); else if (fail && groupGuy->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) groupGuy->FailQuest(mEscortQuestID); } } else { if (!fail && player->IsAtGroupRewardDistance(me) && !player->GetCorpse()) player->GroupEventHappens(mEscortQuestID, me); else if (fail && player->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) player->FailQuest(mEscortQuestID); } } else { for (ObjectList::iterator iter = targets->begin(); iter != targets->end(); ++iter) { if (GetScript()->IsPlayer((*iter))) { Player* player = (*iter)->ToPlayer(); if (!fail && player->IsAtGroupRewardDistance(me) && !player->GetCorpse()) player->AreaExploredOrEventHappens(mEscortQuestID); else if (fail && player->GetQuestStatus(mEscortQuestID) == QUEST_STATUS_INCOMPLETE) player->FailQuest(mEscortQuestID); } } } } // Xinef: if the escort failed - DO NOT PROCESS ANYTHING, ITS RETARDED // Xinef: End Path events should be only processed if it was SUCCESSFUL stop or stop called by SMART_ACTION_WAYPOINT_STOP if (fail) { mCurrentWPID = 0; return; } GetScript()->ProcessEventsFor(SMART_EVENT_WAYPOINT_ENDED, NULL, mCurrentWPID, GetScript()->GetPathId()); mCurrentWPID = 0; if (mCanRepeatPath) StartPath(mRun, GetScript()->GetPathId(), mCanRepeatPath); else GetScript()->SetPathId(0); if (mDespawnState == 1) StartDespawn(); }
void VectorFileWriter::Output(SBezierLoopSetSet *sblss, SMesh *sm) { STriangle *tr; SBezier *b; // First calculate the bounding box. ptMin = Vector::From(VERY_POSITIVE, VERY_POSITIVE, VERY_POSITIVE); ptMax = Vector::From(VERY_NEGATIVE, VERY_NEGATIVE, VERY_NEGATIVE); if(sm) { for(tr = sm->l.First(); tr; tr = sm->l.NextAfter(tr)) { (tr->a).MakeMaxMin(&ptMax, &ptMin); (tr->b).MakeMaxMin(&ptMax, &ptMin); (tr->c).MakeMaxMin(&ptMax, &ptMin); } } if(sblss) { SBezierLoopSet *sbls; for(sbls = sblss->l.First(); sbls; sbls = sblss->l.NextAfter(sbls)) { SBezierLoop *sbl; for(sbl = sbls->l.First(); sbl; sbl = sbls->l.NextAfter(sbl)) { for(b = sbl->l.First(); b; b = sbl->l.NextAfter(b)) { for(int i = 0; i <= b->deg; i++) { (b->ctrl[i]).MakeMaxMin(&ptMax, &ptMin); } } } } } // And now we compute the canvas size. double s = 1.0 / SS.exportScale; if(SS.exportCanvasSizeAuto) { // It's based on the calculated bounding box; we grow it along each // boundary by the specified amount. ptMin.x -= s*SS.exportMargin.left; ptMax.x += s*SS.exportMargin.right; ptMin.y -= s*SS.exportMargin.bottom; ptMax.y += s*SS.exportMargin.top; } else { ptMin.x = -(s*SS.exportCanvas.dx); ptMin.y = -(s*SS.exportCanvas.dy); ptMax.x = ptMin.x + (s*SS.exportCanvas.width); ptMax.y = ptMin.y + (s*SS.exportCanvas.height); } StartFile(); if(sm && SS.exportShadedTriangles) { for(tr = sm->l.First(); tr; tr = sm->l.NextAfter(tr)) { Triangle(tr); } } if(sblss) { SBezierLoopSet *sbls; for(sbls = sblss->l.First(); sbls; sbls = sblss->l.NextAfter(sbls)) { SBezierLoop *sbl; sbl = sbls->l.First(); if(!sbl) continue; b = sbl->l.First(); if(!b || !Style::Exportable(b->auxA)) continue; hStyle hs = { b->auxA }; Style *stl = Style::Get(hs); double lineWidth = Style::WidthMm(b->auxA)*s; DWORD strokeRgb = Style::Color(hs, true); DWORD fillRgb = Style::FillColor(hs, true); StartPath(strokeRgb, lineWidth, stl->filled, fillRgb); for(sbl = sbls->l.First(); sbl; sbl = sbls->l.NextAfter(sbl)) { for(b = sbl->l.First(); b; b = sbl->l.NextAfter(b)) { Bezier(b); } } FinishPath(strokeRgb, lineWidth, stl->filled, fillRgb); } } FinishAndCloseFile(); }