Quantcast help needed: trying to compact some code (and its not working) - WoWInterface
Thread Tools Display Modes
11-14-16, 10:44 AM   #1
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
help needed: trying to compact some code (and its not working)

Gotten back to workin on an old addon of mine. FinalFantasylization. Plays music based on where you are and what youre doing. (Still only works in WotLK atm, will worry about that later). Been trying to compact the zone detection section.

Here's the github for all the current code: (this bit works fine in WotLK)
https://github.com/Darken5/FinalFant...Route-to-3.3.0

Heres the code im workin on compacting: (this works)
http://pastebin.com/XCZb6ehw
Snippet:
Lua Code:
  1. --'==========================================================================================      
  2. --'  Starting Areas: Sunstrider Isle, Eversong Woods ( Blood Elf Starting Area )
  3. --'==========================================================================================
  4.                
  5.         if not ( IsResting() ) and (  factionEnglish == F["Horde"] ) and (  ZoneName == Z["Eversong Woods"] ) and ( ( SubZoneName == SZ["The Sunspire"] ) or ( SubZoneName == SZ["Sunstrider Isle"] ) or ( SubZoneName == SZ["Falthrien Academy"] ) or ( SubZoneName == SZ["Shrine of Dath'Remar"] ) ) and FinalFantasylization_IsPlaying == false then
  6.             if FinalFantasylization_InStarterAreaSunstriderIsle == false then
  7.                 FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. SubZoneName..", "..ZoneName)
  8.                 FinalFantasylization_StarterAreaSunstriderIsle()
  9.             end
  10.             FinalFantasylization_IsPlaying = true
  11.             FinalFantasylization_InStarterAreaSunstriderIsle = true
  12.         elseif (  factionEnglish == F["Alliance"] ) and (  ZoneName == Z["Eversong Woods"] ) and ( ( SubZoneName == SZ["The Sunspire"] ) or ( SubZoneName == SZ["Sunstrider Isle"] ) or ( SubZoneName == SZ["Falthrien Academy"] ) or ( SubZoneName == SZ["Shrine of Dath'Remar"] ) ) and FinalFantasylization_IsPlaying == false then
  13.             if FinalFantasylization_InStarterAreaSunstriderIsle == false then
  14.                 FinalFantasylization_debugMsg(FFZlib.Color.Crimson .. PlayerInHostileTown .. SubZoneName..", "..ZoneName.. PlayerInHostile)
  15.                 FinalFantasylization_HostileTowns()  -- Music call for all towns you are hostile in.
  16.             end
  17.             FinalFantasylization_IsPlaying = true
  18.             FinalFantasylization_InStarterAreaSunstriderIsle = true
  19.         else
  20.             FinalFantasylization_InStarterAreaSunstriderIsle = false
  21.         end

Heres the compacted code: (this doesn't work)
http://pastebin.com/XpbSgvZL
Snippet:
Lua Code:
  1. --'==========================================================================================      
  2. --' Starting Areas: Sunstrider Isle, Eversong Woods ( Blood Elf Starting Area )
  3. --'==========================================================================================
  4.         if not ( IsResting() ) and ( ZoneName == Z["Eversong Woods"] ) and ( ( MinimapZoneName == SZ["The Sunspire"] ) or ( SubZoneName == SZ["Sunstrider Isle"] ) or ( SubZoneName == SZ["Falthrien Academy"] ) or ( SubZoneName == SZ["Shrine of Dath'Remar"] ) ) and FinalFantasylization_IsPlaying == false then
  5.             if FinalFantasylization_InStarterAreaSunstriderIsle == false then
  6.                 if ( factionEnglish == F["Horde"] ) then
  7.                     FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. SubZoneName..", "..ZoneName)
  8.                     FinalFantasylization_StarterAreaSunstriderIsle()
  9.                 else
  10.                     FinalFantasylization_debugMsg(FFZlib.Color.Crimson .. PlayerInHostileTown .. SubZoneName..", "..ZoneName.. PlayerInHostile)
  11.                     FinalFantasylization_HostileTowns() -- Music call for all towns you are hostile in.
  12.                 end
  13.                 FinalFantasylization_IsPlaying = true
  14.                 FinalFantasylization_InStarterAreaSunstriderIsle = true
  15.             end
  16.             FinalFantasylization_InStarterAreaSunstriderIsle = false
  17.         end

problem i'm having is the compacted code keeps changing the song played. Example, using the above snippet, it'll play "Sunstrider Isle" then about 2 seconds later plays "Eversong Woods" (which is further down the list), and then back again. If not in a subzone detected by FFz, it'll just repeat the music set for the zone.

i've also tried: (my 1st attempt)
Lua Code:
  1. --'==========================================================================================      
  2. --'  Starting Areas: Sunstrider Isle, Eversong Woods ( Blood Elf Starting Area )
  3. --'==========================================================================================
  4.                
  5.         if not ( IsResting() ) and (  ZoneName == Z["Eversong Woods"] ) and ( ( SubZoneName == SZ["The Sunspire"] ) or ( SubZoneName == SZ["Sunstrider Isle"] ) or ( SubZoneName == SZ["Falthrien Academy"] ) or ( SubZoneName == SZ["Shrine of Dath'Remar"] ) ) and FinalFantasylization_IsPlaying == false then
  6.             if FinalFantasylization_InStarterAreaSunstriderIsle == false then
  7.                 if (  factionEnglish == F["Horde"] ) then
  8.                     FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. SubZoneName..", "..ZoneName)
  9.                     FinalFantasylization_StarterAreaSunstriderIsle()
  10.                 else
  11.                     FinalFantasylization_debugMsg(FFZlib.Color.Crimson .. PlayerInHostileTown .. SubZoneName..", "..ZoneName.. PlayerInHostile)
  12.                     FinalFantasylization_HostileTowns() -- Music call for all towns you are hostile in.
  13.                 end
  14.                 FinalFantasylization_IsPlaying = true
  15.                 FinalFantasylization_InStarterAreaSunstriderIsle = true
  16.             else
  17.                 FinalFantasylization_InStarterAreaSunstriderIsle = false
  18.             end
  19.         end


Any help in understanding why the compacted code doesn't work would be VERY much appreciated.

Last edited by Darken5 : 11-14-16 at 11:03 AM. Reason: more input, highlight lua
  Reply With Quote
11-14-16, 01:46 PM   #2
SDPhantom
A Pyroguard Emberseer
 
SDPhantom's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2006
Posts: 1,889
If you're for support on an addon that's going to run on private servers, we won't be able to offer it as it violates the site rules and Blizzard's EULA.

Originally Posted by Cairenn View Post
4. Don't break WoW EULA or ToU. If you come here and post that you are selling your WoW account for real world money, offering or asking for power-levelling, in-game items or gold for real life cash, private servers or any other post that breaks WoW EULA or ToU, your post will be deleted and you will (at minimum) warned not to do it again. Repeated offenses will lead to banning from the site.
http://us.blizzard.com/en-us/company/legal/eula.html
1.C.vii Unauthorized Connections: Facilitate, create or maintain any unauthorized connection to Battle.net or the Game(s) including without limitation (i) any connection to any unauthorized server that emulates, or attempts to emulate, Battle.net; and (ii) any connection using third-party programs or tools not expressly authorized by Blizzard;
__________________
ESOUI AddOns | WoWInterface AddOns
"All I want is a pretty girl, a decent meal, and the right to shoot lightning at fools."
-Anders (Dragon Age: Origins - Awakening)
  Reply With Quote
11-14-16, 02:05 PM   #3
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
I'm trying to get it up to date with Legion. There is a "lot" of work to do. The code is old code, most still from 2009. Just trying to compact the zone detection to make it a bit simpler to work with for future development. Legion 7.0.3 broke the playMusic() function so there was no point in trying to update it then.
libBabble-Zones is depreciated, gonna move to mapID(). Would love to finally use ACE3.0, tho I'd probably be better off rewriting the whole thing from scratch if that's the case. Gonna have to swap over to the mount Journal to detect what mount I'm riding.

Last edited by Darken5 : 11-14-16 at 02:25 PM.
  Reply With Quote
11-14-16, 02:36 PM   #4
Torhal
A Pyroguard Emberseer
 
Torhal's Avatar
AddOn Author - Click to view addons
Join Date: Aug 2008
Posts: 1,196
I use the HereBeDragons library for map detection in Archy and NPCScan. It's also used by TomTom, GatherMate, and a number of other AddOns.
__________________
Whenever someone says "pls" because it's shorter than "please", I say "no" because it's shorter than "yes".

Author of NPCScan and many other AddOns.
  Reply With Quote
11-14-16, 02:43 PM   #5
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
Originally Posted by Torhal View Post
I use the HereBeDragons library for map detection in Archy and NPCScan. It's also used by TomTom, GatherMate, and a number of other AddOns.
Wow. At first glance that looks to be a bit much for what I need. Will look into it a bit more tho and add feedback. Thank you.

Edit: yea, deffinately too much. not looking to incorporate coordinates or anything like that. just lookin to check if a player is in certain zones or subzones (either like above, or in some kind of table) and play music set to that area. It has a song for each Zone, and a song for certain SubZones. As far as i know, libBabble-SubZone is still getting updates (only use it for localization purposes, as i don't think there is a SubZone ID list anywhere)

Thank you though. it did give me a better idea of how mapID() works.

Last edited by Darken5 : 11-14-16 at 03:45 PM.
  Reply With Quote
11-14-16, 10:20 PM   #6
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
By George I think i figured it out.


Faction Dependant Towns/Areas:
Lua Code:
  1. if not ( IsResting() ) and ( ZoneName ==Z["Dragonblight"] ) and ( ( SubZoneName == SZ["Wintergarde Keep"] ) or ( SubZoneName == SZ["The Carrion Fields"] ) or ( SubZoneName == SZ["Wintergarde Mausoleum"] ) or ( SubZoneName == SZ["Wintergarde Crypt"] ) or ( SubZoneName == SZ["Thorson's Post"] ) or ( SubZoneName == SZ["Wintergarde Mine"] ) ) and FinalFantasylization_IsPlaying == false then
  2.     if FinalFantasylization_InAllianceTownWintergardeKeep == false then
  3.         if ( factionEnglish == F["Alliance"] ) then
  4.             FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. SubZoneName..", "..ZoneName)
  5.             FinalFantasylization_AllianceTownWintergardeKeep()
  6.         else
  7.             FinalFantasylization_debugMsg(FFZlib.Color.Crimson .. PlayerInHostileTown .. SubZoneName..", "..ZoneName..PlayerInHostile)
  8.             FinalFantasylization_HostileTowns() -- Music call for all towns you are hostile in.
  9.         end
  10.         FinalFantasylization_IsPlaying = true
  11.         FinalFantasylization_InAllianceTownWintergardeKeep = true
  12.     end
  13.     return
  14. else
  15.     FinalFantasylization_InAllianceTownWintergardeKeep = false
  16. end


Neutral Towns/Areas:
Lua Code:
  1. if not ( IsResting() ) and ( ZoneName == Z["Shadowmoon Valley"] ) and ( SubZoneName == SZ["Altar of Sha'tar"] ) and FinalFantasylization_IsPlaying == false then
  2.     if FinalFantasylization_InNeutralTownAltarOfShatar == false then
  3.         FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. SubZoneName..", "..ZoneName)
  4.         FinalFantasylization_NeutralTownAltarOfShatar()
  5.     end
  6.     FinalFantasylization_IsPlaying = true
  7.     FinalFantasylization_InNeutralTownAltarOfShatar = true
  8.     return
  9. else
  10.     FinalFantasylization_InNeutralTownAltarOfShatar = false
  11. end


Full Zones (at bottom of list):
Lua Code:
  1. if not ( IsResting () ) and ( ZoneName == Z["Alterac Mountains"] ) and FinalFantasylization_IsPlaying == false then
  2.     if FinalFantasylization_InEasternKingdomsAlteracMountains == false then
  3.         FinalFantasylization_debugMsg(FFZlib.Color.Aqua .. PlayerIn.. ZoneName)
  4.         FinalFantasylization_EasternKingdomsAlteracMountains()
  5.     end
  6.     FinalFantasylization_IsPlaying = true
  7.     FinalFantasylization_InEasternKingdomsAlteracMountains = true
  8. else
  9.     FinalFantasylization_InEasternKingdomsAlteracMountains = false
  10. end


whole lot less code to worry about now for the future
  Reply With Quote
11-15-16, 01:12 AM   #7
SDPhantom
A Pyroguard Emberseer
 
SDPhantom's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2006
Posts: 1,889
I would honestly build a generic table and two faction-specific override tables to store the references between each song file and MapIDs. You would have the addon detect when you change zones, look in the appropriate faction-specific table for the song to play, falling back to the generic table if none are found, and play the song if it is different than the one already playing.
__________________
ESOUI AddOns | WoWInterface AddOns
"All I want is a pretty girl, a decent meal, and the right to shoot lightning at fools."
-Anders (Dragon Age: Origins - Awakening)
  Reply With Quote
11-15-16, 09:50 AM   #8
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
I don't really understand how tables work yet. How would I go about doing that? That sounds awesome.
Edit: song files are stored in separate dependent add-ons called soundpacks that can be switched between with a slash command. Using above code as example "FinalFantasylization_EasternKingdomsAlteracMountains()" is what calls the function in the soundpack that plays the song for Alterac Mountains.

Last edited by Darken5 : 11-15-16 at 10:18 AM.
  Reply With Quote
11-15-16, 10:35 AM   #9
Seerah
Fishing Trainer
 
Seerah's Avatar
WoWInterface Super Mod
Featured
Join Date: Oct 2006
Posts: 10,703
http://lua-users.org/wiki/TablesTutorial
__________________
"You'd be surprised how many people violate this simple principle every day of their lives and try to fit square pegs into round holes, ignoring the clear reality that Things Are As They Are." -Benjamin Hoff, The Tao of Pooh

  Reply With Quote
11-15-16, 04:15 PM   #10
SDPhantom
A Pyroguard Emberseer
 
SDPhantom's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2006
Posts: 1,889
Here's code for the main part of the addon that I whipped up. It uses metatables to handle falling back to a generic song table. Be sure the file containing this code loads first in your ToC.
Lua Code:
  1. --  Grab access to our shared addon table
  2. local _,Addon=...;
  3.  
  4. --  Set up our default song table and metatable for fallback
  5. local DefaultSongTable={};
  6. local FallbackMeta={__index=DefaultSongTable};
  7.  
  8. local SongTables={Alliance={},Horde={}};--  Build faction-based song tables
  9. for _,tbl in pairs(SongTables) do setmetatable(tbl,FallbackMeta); end-- Set our fallback metatable
  10. SongTables.Default=DefaultSongTable;--  Register the default song table
  11. Addon.SongTables=SongTables;--  Enable access to our song tables through the shared addon table
  12.  
  13. local CurrentSong;
  14. local function PlaySongForMap(mapid)
  15. --  Select the song table and grab the song for the map
  16.     local song=(SongTables[UnitFactionGroup("player")] or DefaultSongTable)[mapid];
  17.  
  18. --  Play the new song if different or stop if there is none
  19.     if song and song~=CurrentSong then
  20.         PlayMusic(song);
  21.     elseif not song then
  22.         StopMusic();
  23.     end
  24.  
  25. --  Update our saved variable
  26.     CurrentSong=song;
  27. end
  28.  
  29. local EventFrame=CreateFrame("Frame");
  30. EventFrame:RegisterEvent("PLAYER_ENTERING_WORLD");--    Player enters from loading screen
  31. EventFrame:RegisterEvent("ZONE_CHANGED_NEW_AREA");--    Zones changed
  32. EventFrame:RegisterEvent("ZONE_CHANGED_INDOORS");-- Some indoor zone changing requires this
  33.  
  34. EventFrame:SetScript("OnEvent",function()
  35. --  We don't want to mess around with the map while the user is looking at it, but we need our MapID, so we'll do some tricky stuff
  36.     if WorldMapFrame:IsShown() then
  37. --      Get a list of frames listening for map updates and disable them
  38.         local frames={GetFramesRegisteredByEvent("WORLD_MAP_UPDATE")};
  39.         for _,frame in ipairs(frames) do frame:UnregisterEvent("WORLD_MAP_UPDATE"); end
  40.  
  41. --      Save old MapID and select current zone (MapID is invalid if viewing a continent, store that too)
  42.         local mapid,continent=GetCurrentMapAreaID(),GetCurrentMapContinent();
  43.         SetMapToCurrentZone();
  44.  
  45. --      We have the zone we want, find and play our song
  46.         PlaySongForMap(GetCurrentMapAreaID());
  47.  
  48. --      Restore the map and re-enable the frames so the user would never know we did anything
  49.         if mapid>=0 then SetMapByID(mapid); else SetMapZoom(continent); end
  50.         for _,frame in ipairs(frames) do frame:RegisterEvent("WORLD_MAP_UPDATE"); end
  51.     else
  52. --      User isn't looking at the map, we'll use a more straightforward approach
  53.         SetMapToCurrentZone();
  54.         PlaySongForMap(GetCurrentMapAreaID());
  55.     end
  56. end);

In your sound packs placed in other Lua files in the same addon, you can register songs like this.
Lua Code:
  1. --  Grab access to our shared addon table
  2. local _,Addon=...;
  3.  
  4. --  Alliance and Horde have their own songs, though it's a good idea to define a default anyway
  5. Addon.SongTable.Default[123]="Path\\To\\DefaultSong";
  6. Addon.SongTable.Alliance[123]="Path\\To\\AllianceSong";
  7. Addon.SongTable.Horde[123]="Path\\To\\HordeSong";
  8.  
  9. --  Alliance has their own song, Horde uses default
  10. Addon.SongTable.Default[345]="Path\\To\\DefaultSong";
  11. Addon.SongTable.Alliance[345]="Path\\To\\AllianceSong";
  12.  
  13. --  Horde has their own song, Alliance uses default
  14. Addon.SongTable.Default[567]="Path\\To\\DefaultSong";
  15. Addon.SongTable.Horde[567]="Path\\To\\HordeSong";
  16.  
  17. --  Both factions use the default
  18. Addon.SongTable.Default[789]="Path\\To\\DefaultSong";



PS: The first return of UnitFactionGroup() is locale-independant, so it doesn't need to be localized.
__________________
ESOUI AddOns | WoWInterface AddOns
"All I want is a pretty girl, a decent meal, and the right to shoot lightning at fools."
-Anders (Dragon Age: Origins - Awakening)

Last edited by SDPhantom : 11-15-16 at 04:24 PM.
  Reply With Quote
11-15-16, 07:03 PM   #11
Layback_
An Onyxian Warder
Join Date: Feb 2016
Posts: 356
Sorry to interrupt, but I just got a quick question to SDPhantom.

After watching some tutorials about metatable, I got the generic concept of it in Lua. However, I am still struggling to understand how and why metatable is used in your example.

So, if you don't mind, could I please get some further explanation regarding this?

Thank you.
  Reply With Quote
11-15-16, 09:35 PM   #12
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
To SDPhantom: thank you for the write up, I'll check it out a bit more after I get home.

To Layback_: mind sharing the metatable guides? That would be awesome.
  Reply With Quote
11-16-16, 05:22 AM   #13
Layback_
An Onyxian Warder
Join Date: Feb 2016
Posts: 356
Hi Darken5,

Here are two video links that I personally find useful.

https://www.youtube.com/watch?v=CYxMfVy5W00
This one seems to explain the brief concept of metatable in Lua..

https://www.youtube.com/watch?v=22QTG81kJaQ
After I posted a previous reply, I've done some further research, because I was unsure of metamethod and this video explains on how you could implement them.

Now I think I got why SDPhantom had used metatable in his example

https://www.lua.org/pil/13.html
This is just a link to official lua documentation page of metatable section.

Hope this helps!

Last edited by Layback_ : 11-16-16 at 05:59 AM.
  Reply With Quote
11-16-16, 05:50 AM   #14
SDPhantom
A Pyroguard Emberseer
 
SDPhantom's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2006
Posts: 1,889
Originally Posted by Layback_ View Post
After watching some tutorials about metatable, I got the generic concept of it in Lua. However, I am still struggling to understand how and why metatable is used in your example.
The code I posted isn't really a good reference about metatables and how powerful they can be as it's highly optimized for its specific application.

Metatables offer a way to control how tables respond to different operations. To implement a fallback table to another, I assigned it to the index operation by setting it to __index in its metatable. This operation is referred to when Lua looks for an entry in a table and doesn't find anything. If another table is assigned to __index in the metatable, it looks through that in addition to the original table.

If you're interested in the official documentation, here's the link.
Lua 5.1 Reference Manual Section 2.8
__________________
ESOUI AddOns | WoWInterface AddOns
"All I want is a pretty girl, a decent meal, and the right to shoot lightning at fools."
-Anders (Dragon Age: Origins - Awakening)
  Reply With Quote
11-16-16, 10:56 PM   #15
Darken5
A Murloc Raider
Join Date: Nov 2016
Posts: 7
Thank you both so much. This is far beyond what I expected. And the code is amazing now that I actually understand what it's Doing.
  Reply With Quote

WoWInterface » Developer Discussions » Lua/XML Help » help needed: trying to compact some code (and its not working)

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off