diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS new file mode 100644 index 0000000..6663b68 --- /dev/null +++ b/.github/CODEOWNERS @@ -0,0 +1 @@ +* @rovxbot diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml new file mode 100644 index 0000000..576ebfa --- /dev/null +++ b/.github/workflows/codeql.yml @@ -0,0 +1,33 @@ +name: CodeQL + +on: + push: + branches: + - master + - fix/** + pull_request: + branches: + - master + workflow_dispatch: + +permissions: + actions: read + contents: read + security-events: write + +jobs: + CodeQLExpected: + name: CodeQLExpected + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Initialize CodeQL + uses: github/codeql-action/init@v4 + with: + languages: cpp + build-mode: none + + - name: Analyze + uses: github/codeql-action/analyze@v4 diff --git a/.github/workflows/gitleaks.yml b/.github/workflows/gitleaks.yml new file mode 100644 index 0000000..a17dad4 --- /dev/null +++ b/.github/workflows/gitleaks.yml @@ -0,0 +1,29 @@ +name: Gitleaks + +on: + push: + branches: + - master + - fix/** + pull_request: + branches: + - master + workflow_dispatch: + +permissions: + contents: read + +jobs: + GitleaksExpected: + name: GitleaksExpected + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Run Gitleaks + uses: gitleaks/gitleaks-action@v2 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/data/sql/db-world/base/daish.sql b/data/sql/db-world/base/daish.sql index 3f1a004..13b4913 100644 --- a/data/sql/db-world/base/daish.sql +++ b/data/sql/db-world/base/daish.sql @@ -126,14 +126,13 @@ VALUES -- ==================================================================== -- Formation: healers flank Daish --- Leader must appear as a member with dist=0 for the core to register. --- groupAI 3 = mutual assist (leader ↔ members) +-- AzerothCore stores follow angles in degrees. +-- Register only the escorts as members of the leader's formation. -- ==================================================================== INSERT INTO creature_formations (leaderGUID, memberGUID, dist, angle, groupAI, point_1, point_2) VALUES - (@GUID_DAISH, @GUID_DAISH, 0, 0, 3, 0, 0), -- leader entry (required!) - (@GUID_DAISH, @GUID_HEAL1, 3.0, 2.2, 3, 0, 0), -- left flank - (@GUID_DAISH, @GUID_HEAL2, 3.0, 4.1, 3, 0, 0); -- right flank + (@GUID_DAISH, @GUID_HEAL1, 3.0, 90.0, 0, 0, 0), -- left flank + (@GUID_DAISH, @GUID_HEAL2, 3.0, 270.0, 0, 0, 0); -- right flank -- ==================================================================== -- Waypoints: Blackrock Mountain patrol loop (12-point circuit) diff --git a/src/npc_nubmage.cpp b/src/npc_nubmage.cpp index 353ce3a..c19dbe1 100644 --- a/src/npc_nubmage.cpp +++ b/src/npc_nubmage.cpp @@ -35,11 +35,11 @@ static const NubmagePortalDest portalDests[] = { // Coordinates sourced from AzerothCore spell_target_position table. // OptionID 1 — Thunder Bluff (spell 3566 — Teleport: Thunder Bluff) - { 1, 1, -1019.44f, -2.78f, 38.85f, 5.35f, "Thunder Bluff" }, + { 1, 1, -962.97f, 282.91f, 111.68f, 4.02f, "Thunder Bluff" }, // OptionID 2 — Undercity (spell 3563 — Teleport: Undercity) - { 2, 0, 1584.07f, 241.99f, -52.15f, 0.05f, "Undercity" }, + { 2, 0, 1773.43f, 61.31f, -46.32f, 2.43f, "Undercity" }, // OptionID 3 — Silvermoon (spell 32272 — Teleport: Silvermoon) - { 3, 530, 9997.95f, -7106.08f, 47.71f, 2.44f, "Silvermoon" }, + { 3, 530, 10021.26f, -7014.27f, 49.72f, 4.01f, "Silvermoon" }, }; static constexpr uint32 PORTAL_DEST_COUNT = sizeof(portalDests) / sizeof(portalDests[0]); @@ -78,10 +78,22 @@ class npc_nubmage : public CreatureScript { ClearGossipMenuFor(player); + // DB-backed gossip can arrive here either as the raw OptionID or as a + // gossip list index depending on the core path. Resolve through + // PlayerTalkClass first so stale/shifted menu rows do not misroute the + // destination. + uint32 selectedAction = action; + if (player->PlayerTalkClass) + { + uint32 const menuAction = player->PlayerTalkClass->GetGossipOptionAction(action); + if (menuAction != 0) + selectedAction = menuAction; + } + // Walk the portal table to find the matching OptionID. for (uint32 i = 0; i < PORTAL_DEST_COUNT; ++i) { - if (portalDests[i].optionId != action) + if (portalDests[i].optionId != selectedAction) continue; const NubmagePortalDest& dest = portalDests[i];