#include "stdafx.h" #include "SUIWorldMapMonsterRegion.h" #include "SUIWorldMapWnd.h" #include "SQuestMgr.h" //#include "KUIControl.h" #include "SMonsterDB.h" #include "SFieldPropResourceDB.h" #include "SItemDB.h" #include "SQuestLinkDB.h" #include #include #include "SQuestDB.h" #include "PropRespawnRegionExtractor.h" void sMonsterRegionInfo::sNpcList::clear() { m_npcId.clear(); m_wnd.clear(); } void sMonsterRegionInfo::sNpcList::clearNpcId() { m_npcId.clear(); } void sMonsterRegionInfo::sNpcList::hide() { std::vector::iterator it = m_wnd.begin(); for (; it != m_wnd.end(); ++it) (*it)->SetShow(false); } /// m_wnd의 유효한 개수 체크 void sMonsterRegionInfo::sNpcList::checkValidWnd(SUIWorldMapWnd* parentWnd) { if (m_npcId.size() > m_wnd.size()) { std::string strId; size_t npcSize = m_npcId.size(); size_t i = m_wnd.size(); for (; i < npcSize; ++i) { XStringUtil::Format(strId, "questTargetNpc%d", i); KUIControl* wnd = dynamicCast(parentWnd->createQuestMarkNpcControl(strId.c_str())); if (wnd) m_wnd.push_back(wnd); } } } void sMonsterRegionInfo::sNpcList::apply(SUIWorldMapWnd* parentWnd) { if (m_npcId.empty()) return ; checkValidWnd(parentWnd); /// hide wnd for (size_t i = 0; i < m_wnd.size(); ++i) { m_wnd[i]->SetShow(false); } KRect r; size_t count = m_npcId.size(); for (size_t i = 0; i < count; ++i) { if (parentWnd->getQuestMarkNpcUIRect(m_npcId[i], r)) { m_wnd[i]->SetRect(r); m_wnd[i]->UpdateBack(); m_wnd[i]->SetShow(true); parentWnd->SetChildAsTop(m_wnd[i]->GetID()); } } } sMonsterRegionInfo::sMonsterRegionInfo() : m_questCode(0) { } sMonsterRegionInfo::~sMonsterRegionInfo() { m_monsterMaxRegionList.clear(); m_monsterMinRegionList.clear(); m_itemMaxRegionList.clear(); m_itemMinRegionList.clear(); m_childList.clear(); m_mobList.clear(); m_itemList.clear(); m_npcList.clear(); } void sMonsterRegionInfo::initialize(SUIWorldMapWnd* parentWnd) { cPropRespawnRegionExtractor propExtractor; //propExtractor.extract(); /// 2011.08.26 item 리젠 지역 추출(추출후 주석처리 해야 됨) - prodongi propExtractor.readData("itemMaxRegion.lst", m_itemMaxRegionList); propExtractor.readData("itemMinRegion.lst", m_itemMinRegionList); cMonsterRespawnRegionExtractor extractor; //extractor.extract(); /// 2011.08.26 몬스터 리젠 지역 추출(추출후 주석처리 해야 됨) - prodongi extractor.readData("monsterMaxRegion.lst", m_monsterMaxRegionList); extractor.readData("monsterMinRegion.lst", m_monsterMinRegionList); } void sMonsterRegionInfo::clearChild(SUIWorldMapWnd *parentWnd) { v_childWnd::iterator it_child = m_childList.begin(); for (; it_child != m_childList.end(); ++it_child) { parentWnd->addRemoveWndList(it_child->m_wnd); } m_childList.clear(); m_npcList.hide(); /// npc를 지우기 전에 디테일 월드맵에 완료로 바뀐 npc 아이콘을 복구해준다 parentWnd->restoreNpcIconToOriginal(m_npcList.m_npcId); m_npcList.clearNpcId(); } void sMonsterRegionInfo::process(DWORD t) { v_childWnd::iterator it_child = m_childList.begin(); for (; it_child != m_childList.end(); ++it_child) { it_child->m_wnd->Process(t); } } template void sMonsterRegionInfo::apply(int id, SUIWorldMapWnd *parentWnd, bool isMax, MAX_T* maxList, MIN_T* minList, int type) { std::map* regionList; if (isMax) regionList = maxList; else regionList = minList; std::map::iterator it_mr = regionList->find(id); if (it_mr == regionList->end()) return ; KRect uiRect; KPoint worldPos, uiPos; T::it_region it_r = it_mr->second.m_regionList.begin(); for (; it_r != it_mr->second.m_regionList.end(); ++it_r) { worldPos.x = it_r->m_rect.left; worldPos.y = it_r->m_rect.top; parentWnd->convertWorldToUiPos(worldPos, uiPos); uiRect.left = uiPos.x; uiRect.top = uiPos.y; worldPos.x = it_r->m_rect.right; worldPos.y = it_r->m_rect.bottom; parentWnd->convertWorldToUiPos(worldPos, uiPos); uiRect.right = uiPos.x; uiRect.bottom = uiPos.y; if (uiRect.top > uiRect.bottom) std::swap(uiRect.top, uiRect.bottom); /// 최소 크기 설정 if (MIN_RECT_LEN > uiRect.GetWidth()) { int s = (MIN_RECT_LEN - uiRect.GetWidth()) >> 1; uiRect.left -= s; uiRect.right += s; } if (MIN_RECT_LEN > uiRect.GetHeight()) { int s = (MIN_RECT_LEN - uiRect.GetHeight()) >> 1; uiRect.top -= s; uiRect.bottom += s; } KRect newR; if (!parentWnd->convertInvalidMonsterRegion(uiRect, newR)) continue; if (!checkIncludeRegion(newR, id)) { KUIWnd* child = parentWnd->createMonsterRegionControl(newR, it_r->m_theta); if (child) { sChildWnd childWnd(child, id, type); m_childList.push_back(childWnd); } } } } bool sMonsterRegionInfo::checkIncludeRegion(KRect const& uiRect, int id) { struct sCheckRegion { bool isIn(KRect const& r, KRect const& c_r) { if (isIn(r, c_r.left, c_r.top) && isIn(r, c_r.right, c_r.top) && isIn(r, c_r.left, c_r.bottom) && isIn(r, c_r.right, c_r.bottom)) return true; return false; } bool isIn(KRect const& r, int x, int y) { if (r.left <= x && r.right >= x && r.top <= y && r.bottom >= y) return true; return false; } }; sCheckRegion check; v_childWnd::iterator it_child = m_childList.begin(); for (; it_child != m_childList.end(); ++it_child) { KUIWnd* wnd = it_child->m_wnd; if (check.isIn(wnd->GetRect(), uiRect)) { it_child->addToolTipList(id); return true; } } return false; } bool sMonsterRegionInfo::setQuestCode(int code, SUIWorldMapWnd *parentWnd) { m_mobList.clear(); m_itemList.clear(); clearChild(parentWnd); m_questCode = code; SQuestMgr::GetInstance().getMonsterList(code, m_mobList); SQuestMgr::GetInstance().getItemList(code, m_itemList); setNpcList(code, parentWnd); setQuestMarkTarget(code); /// 맨 마지막에 호출 되어야 한다 return true; } void sMonsterRegionInfo::setQuestMarkTarget(int code) { int type, id; bool hide; if (!SQuestMgr::GetInstance().getMarkProp((QuestBase::QuestCode)code, type, id, hide)) return ; if (hide) return ; if (QuestBase::QUEST_MARK_TARGET_DEFAULT == type) return ; if (0 == id) return; if (QuestBase::QUEST_MARK_TARGET_MOB == type) { m_mobList.push_back(id); } else if (QuestBase::QUEST_MARK_TARGET_NPC == type) { m_npcList.m_npcId.push_back(id); } else if (QuestBase::QUEST_MARK_TARGET_PROP == type) { FieldPropResource* res = GetFieldPropResourceDB().GetFieldPropResource(id); if (res) { if (res->drop_item_id_00) m_itemList.push_back(res->drop_item_id_00); if (res->drop_item_id_01) m_itemList.push_back(res->drop_item_id_01); } } } void sMonsterRegionInfo::setNpcList(int code, SUIWorldMapWnd *parentWnd) { if (0 == code) return ; int progress = SQuestMgr::GetInstance().GetQuestProgress(code); if (SQuestMgr::STARTABLE == progress) return ; QuestLinkEx* ex = GetQuestLinkDB().GetQuestLinkData(code); if (!ex) return ; if (SQuestMgr::FINISHABLE == progress) { m_npcList.m_npcId = ex->endNpcId; parentWnd->changeNpcIconToFinish(m_npcList.m_npcId); } else if (SQuestMgr::IN_PROGRESS == progress) { QuestBase* quest = GetQuestDB().GetQuestData(code); if (!quest) return ; int type = quest->nType; if (QuestBase::QuestType::QUEST_LEARN_SKILL == type || QuestBase::QuestType::QUEST_UPGRADE_ITEM == type || QuestBase::QuestType::QUEST_CONTACT == type || QuestBase::QuestType::QUEST_JOB_LEVEL == type || QuestBase::QuestType::QUEST_PARAMETER == type || QuestBase::QuestType::QUEST_OUT_OF_CONTROL == type) { m_npcList.m_npcId = ex->startNpcId; } } } void sMonsterRegionInfo::apply(SUIWorldMapWnd* parentWnd, bool maxList) { if (0 == m_questCode) return ; if (!checkValidQuestCode(parentWnd)) return ; std::vector::iterator it; for (it = m_mobList.begin(); it != m_mobList.end(); ++it) { apply(*it, parentWnd, maxList, &m_monsterMaxRegionList, &m_monsterMinRegionList, MOB); } for (it = m_itemList.begin(); it != m_itemList.end(); ++it) { apply(*it, parentWnd, maxList, &m_itemMaxRegionList, &m_itemMinRegionList, ITEM); } m_npcList.apply(parentWnd); setToolTip(); } void sMonsterRegionInfo::refresh(SUIWorldMapWnd* parentWnd, bool maxList) { if (!setQuestCode(m_questCode, parentWnd)) return ; apply(parentWnd, maxList); } bool sMonsterRegionInfo::checkValidQuestCode(SUIWorldMapWnd* parentWnd) { if (!SQuestMgr::GetInstance().IsAddQuest(m_questCode)) { setQuestCode(0, parentWnd); return false; } return true; } void sMonsterRegionInfo::setToolTip() { std::string name; v_childWnd::iterator it_child = m_childList.begin(); for (; it_child != m_childList.end(); ++it_child) { name.clear(); std::vector::iterator it_id; if (MOB == it_child->m_type) { if (!it_child->m_toolTipList.empty()) { it_id = it_child->m_toolTipList.begin(); int nameId = GetMonsterDB().GetTextID(bits_scramble(*it_id)); name += S(nameId); ++it_id; } for (; it_id != it_child->m_toolTipList.end(); ++it_id) { name += "
"; int nameId = GetMonsterDB().GetTextID(bits_scramble(*it_id)); name += S(nameId); } } else if (ITEM == it_child->m_type) { if (!it_child->m_toolTipList.empty()) { it_id = it_child->m_toolTipList.begin(); ItemBaseEx_info const* itemInfo = GetItemDB().GetItemData(*it_id); if (itemInfo) { name += S(itemInfo->nNameId); } ++it_id; } for (; it_id != it_child->m_toolTipList.end(); ++it_id) { name += "
"; ItemBaseEx_info const* itemInfo = GetItemDB().GetItemData(*it_id); if (itemInfo) { name += S(itemInfo->nNameId); } } } KUIControl* control = dynamicCast(it_child->m_wnd); if (control) control->SetTooltip(name.c_str()); } }