System QuestStruct

luorax

Invasion in Duskwood
Reaction score
67
I didn't want to post this library, but I saw that someone has problems with quest. Then I decided to post this, maybe it'll help people's work a bit.

The system uses operators instead of methods or functions. I used Earth-Fury's library (Board), and I liked the API.

Each method (operator) can work in "generic" and in "single-player" mode. It means you can set the quest's value to something for each player, or only for one player.

For more information read the description in the library.

Requires:
-ARGB

JASS:
library QuestStruct requires ARGB
//==============================================================================
// QuestStruct v1.0.2
//==============================================================================
// Credits:
//------------------------------------------------------------------------------
// Written By:
//     Luorax
//
// API inspiration:
//     Earth-Fury
// 
// Requires:
//     -ARGB by Vexorian
//
//==============================================================================
// Quest API
//==============================================================================
//  To create a new Quest, use the example below. That'll create a new blank 
//  quest.
//
//       local Quest myquest = Quest.create()
//
//------------------------------------------------------------------------------
//  Now you can do 2 things:
//  ???????????????????????      
//      -You can set its data generally, for all player. To do so use the next 
//       syntax:
//
//           set myquest.title = "Test 1"
//
//      -You can set its for one player only. To do so:
//
//           set myquest.title[Player(0)] = "Test 1"
//
//  That syntax works with each operator.
//
//  You can get a member's value in two way:
//
//      -In MPI mode do the next:
//
//          local string s = myquest.title[Player(X)]
//  
//      -In basic mode each player's value is the same, so you work with Player 1's
//        values.
//
//------------------------------------------------------------------------------
//
//  You can also duplicate a Quest. Just call the next method:
//
//       local Quest myquest2 = myquest.duplicate()
//
//  That'll create a new Quest, and will duplicate each QuestItem.
//
//------------------------------------------------------------------------------
//  The list of the available operators (the names're self-speaking):
//  ?????????????????????????????????????????????????????????????????
//
/*
        NAME                   REQUIRES         DEFAULT
        ????                   ????????         ????????
        failed          =      boolean          false
        completed       =      boolean          false
        visible         =      boolean          true
        required        =      boolean          true
        discovered      =      boolean          true
        textColorize    =      boolean          true
        titleColorize   =      boolean          true
        icon            =      string           ""
        title           =      string           ""
        text            =      string           ""
        data            =      integer          0
        titleColor      =      ARGB             0xFFFFFF
        textColor       =      ARGB             0xFFFFFF
*/
//
//------------------------------------------------------------------------------
//      NOTE!
//      If you're using the next syntax:
//      
//           set myquest.data = Extra.create(21, 24)
//
//     then it'll create a new "Extra" type struct, and set each player's data to it.
//     If you need different values per player, then you'll need a loop, and you have to 
//     create it for each player.
//
//==============================================================================
// QuestItem API
//==============================================================================
//  To create a new QuestItem, use the example below. That'll create a new blank 
//  questitem.
//
//       local QuestItem myquestitem = QuestItem.create(myquest)
//
//------------------------------------------------------------------------------
//  Now you can do 2 things:
//  ???????????????????????      
//      -You can set its data generally, for all player. To do so use the next 
//       syntax:
//
//           set myquestitem.text = "Test 1"
//
//      -You can set its for one player only. To do so:
//
//           set myquestitem.text[Player(0)] = "Test 1"
//
//  That syntax works with each operator.
//
//------------------------------------------------------------------------------
//  The owner Quest struct is stored in the QuestItem struct, and you can access
//  it using the syntax below:
//
//       set myquestitem.qOwner.title = "Test "
//
//
//  You can also duplicate a quest item. Just call the next method:
//
//       local QuestItem myquestitem2 = myquestitem.duplicate(myquest)
//
//  That'll create a new QuestItem attached to "myquest", and fill it with 
//  myquestitem's variables' values.
//
//------------------------------------------------------------------------------
//  The list of the available operators (the names're self-speaking):
//  ?????????????????????????????????????????????????????????????????
//
/*

        NAME                   REQUIRES         DEFAULT
        ????                   ????????         ????????
        colorize        =      boolean          true
        completed       =      boolean          false
        color           =      ARGB             0xFFFFFF 
        text            =      string           ""
        data            =      integer          0
*/
//
//==============================================================================
// Configuration
//==============================================================================

    globals
        constant integer MAX_QUESTITEMS = 5
    endglobals
//
//  Maybe I'll add more, just give me ideas
//    
//==============================================================================
// Here begins the code. Don't touch it, if you don't know how it works!
//==============================================================================

    private function ErrorMsg takes string what, string error returns nothing
        call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, "Quest Error: " + what + ": " + error)
    endfunction
    
    private constant function B2S takes boolean b returns string
        if b then
            return "true"
        endif
        return "false"
    endfunction
    
// ============================================================
// Operator Structs (For , .data[], .title[], etc)
// ============================================================

    // Quest Visibility
    // ============================================================

    private struct OperatorVisible extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.visible[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bVisible[id] = b
            
            if GetLocalPlayer() == p then
                call QuestSetEnabled(Quest(this).qQuest, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.visible[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bVisible[id]
        endmethod
    endstruct
    
    // Quest Required
    // ============================================================
    
    private struct OperatorRequired extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.required[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bRequired[id] = b
            
            if GetLocalPlayer() == p then
                call QuestSetRequired(Quest(this).qQuest, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.required[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bRequired[id]
        endmethod
    endstruct
    
    // Quest Discovered
    // ============================================================
    
    private struct OperatorDiscovered extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.discovered[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bDiscovered[id] = b
            
            if GetLocalPlayer() == p then
                call QuestSetDiscovered(Quest(this).qQuest, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.discovered[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bDiscovered[id]
        endmethod
    endstruct
    
    // Quest Failed
    // ============================================================
    
    private struct OperatorFailed extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.failed[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bFailed[id] = b
            
            if GetLocalPlayer() == p then
                call QuestSetFailed(Quest(this).qQuest, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.failed[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bFailed[id]
        endmethod
    endstruct
    
    // Quest Completed
    // ============================================================
    
    private struct OperatorCompleted extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.completed[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bCompleted[id] = b
            
            if GetLocalPlayer() == p then
                call QuestSetCompleted(Quest(this).qQuest, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.completed[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bCompleted[id]
        endmethod
    endstruct

    // Quest Data
    // ============================================================
    
    private struct OperatorData extends array
        public method operator []= takes player p, integer data returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.data[\"" + GetPlayerName(p) + "\"]=" + I2S(data), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).iData[id] = data
            
        endmethod
        
        public method operator [] takes player p returns integer
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.data[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return 0
            endif
            
            return Quest(this).iData[id]
        endmethod
    endstruct
    
    // Quest Icon
    // ============================================================
    
    private struct OperatorIcon extends array
        public method operator []= takes player p, string s returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.icon[\"" + GetPlayerName(p) + "\"]=" + s, "Given player is a neutral player")
                return
            endif
            
            set Quest(this).sIcon[id] = s
            
            if GetLocalPlayer() == p then
                call QuestSetIconPath(Quest(this).qQuest, s)
            endif
        endmethod
        
        public method operator [] takes player p returns string
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.icon[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return ""
            endif
            
            return Quest(this).sIcon[id]
        endmethod
    endstruct
    
    // Quest Title
    // ============================================================
    
    private struct OperatorTitle extends array
        public method operator []= takes player p, string s returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.title[\"" + GetPlayerName(p) + "\"]=" + s, "Given player is a neutral player")
                return
            endif
            
            set Quest(this).sTitle[id] = s
            
            if GetLocalPlayer() == p then
                if Quest(this).bTitleColorize[id] then
                    call QuestSetTitle(Quest(this).qQuest, Quest(this).aTitleColor[id].str(s))
                else
                    call QuestSetTitle(Quest(this).qQuest, s)
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns string
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.title[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return ""
            endif
            
            return Quest(this).sTitle[id]
        endmethod
    endstruct
    
    // Quest Title Color
    // ============================================================
    
    private struct OperatorTitleColor extends array
        public method operator []= takes player p, ARGB color returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.titlecolor[\"" + GetPlayerName(p) + "\"]" , "Given player is a neutral player")
                return
            endif
            
            set Quest(this).aTitleColor[id] = color
            
            if GetLocalPlayer() == p then
                if Quest(this).bTitleColorize[id] then
                    call QuestSetTitle(Quest(this).qQuest, color.str(Quest(this).sTitle[id]))
                else
                    call QuestSetTitle(Quest(this).qQuest, Quest(this).sTitle[id])
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns ARGB
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.titlecolor[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return 0
            endif
            
            return Quest(this).aTitleColor[id]
        endmethod
    endstruct
    
    // Quest Text
    // ============================================================
    
    private struct OperatorText extends array
        public method operator []= takes player p, string s returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.text[\"" + GetPlayerName(p) + "\"]=" + s, "Given player is a neutral player")
                return
            endif
            
            set Quest(this).sText[id] = s
            
            if GetLocalPlayer() == p then
                if Quest(this).bTextColorize[id] then
                    call QuestSetDescription(Quest(this).qQuest, Quest(this).aTextColor[id].str(s))
                else
                    call QuestSetDescription(Quest(this).qQuest, s)
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns string
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.text[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return ""
            endif
            
            return Quest(this).sText[id]
        endmethod
    endstruct
    
    // Quest Text Color
    // ============================================================
    
    private struct OperatorTextColor extends array
        public method operator []= takes player p, ARGB color returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.textcolor[\"" + GetPlayerName(p) + "\"]" , "Given player is a neutral player")
                return
            endif
            
            set Quest(this).aTextColor[id] = color
            
            if GetLocalPlayer() == p then
                if Quest(this).bTextColorize[id] then
                    call QuestSetDescription(Quest(this).qQuest, color.str(Quest(this).sText[id]))
                else
                    call QuestSetDescription(Quest(this).qQuest, Quest(this).sText[id])
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns ARGB
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.textcolor[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return 0
            endif
            
            return Quest(this).aTextColor[id]
        endmethod
    endstruct

    // Quest Text Colorizing
    // ============================================================
    
    private struct OperatorTextColorize extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.textcolorize[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bTextColorize[id] = b
            
            if GetLocalPlayer() == p then
                if b then
                    call QuestSetDescription(Quest(this).qQuest, Quest(this).aTextColor[id].str(Quest(this).sText[id]))
                else
                    call QuestSetDescription(Quest(this).qQuest, Quest(this).sText[id])
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.textcolorize[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bTextColorize[id]
        endmethod
    endstruct
    
    // Quest Title Colorizing
    // ============================================================
    
    private struct OperatorTitleColorize extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("Quest.titlecolorize[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set Quest(this).bTitleColorize[id] = b
            
            if GetLocalPlayer() == p then
                if b then
                    call QuestSetTitle(Quest(this).qQuest, Quest(this).aTitleColor[id].str(Quest(this).sTitle[id]))
                else
                    call QuestSetTitle(Quest(this).qQuest, Quest(this).sTitle[id])
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.titlecolorize[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return Quest(this).bTitleColorize[id]
        endmethod
    endstruct
    
    //==================
    
    // Quest Item Text
    // ============================================================
    
    private struct OperatorItemText extends array
        public method operator []= takes player p, string s returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.text[\"" + GetPlayerName(p) + "\"]=" + s, "Given player is a neutral player")
                return
            endif
            
            set QuestItem(this).sText[id] = s
            
            if QuestItem(this).bColorize[id] then
                if GetLocalPlayer() == p then
                    call QuestItemSetDescription(QuestItem(this).qItem, QuestItem(this).aColor[id].str(s))
                endif
            else    
                if GetLocalPlayer() == p then
                    call QuestItemSetDescription(QuestItem(this).qItem, s)
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns string
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.text[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return ""
            endif
            
            return QuestItem(this).sText[id]
        endmethod
    endstruct
    
    // Quest Item Text Color
    // ============================================================
    
    private struct OperatorItemColor extends array
        public method operator []= takes player p, ARGB color returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.color[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return
            endif
            
            set QuestItem(this).aColor[id] = color
            
            if QuestItem(this).bColorize[id] then
                if GetLocalPlayer() == p then
                    call QuestItemSetDescription(QuestItem(this).qItem, color.str(QuestItem(this).sText[id]))
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns ARGB
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.color[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return 0
            endif
            
            return QuestItem(this).aColor[id]
        endmethod
    endstruct
    
    // Quest Item Data
    // ============================================================
    
    private struct OperatorItemData extends array
        public method operator []= takes player p, integer data returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.data[\"" + GetPlayerName(p) + "\"]=" + I2S(data), "Given player is a neutral player")
                return
            endif
            
            set QuestItem(this).iData[id] = data
        endmethod
        
        public method operator [] takes player p returns integer
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.data[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return 0
            endif
            
            return QuestItem(this).iData[id]
        endmethod
    endstruct
    
    // Quest Item Completed
    // ============================================================
    
    private struct OperatorItemCompleted extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.completed[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set QuestItem(this).bCompleted[id] = b
            
            if GetLocalPlayer() == p then
                call QuestItemSetCompleted(QuestItem(this).qItem, b)
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.completed[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return QuestItem(this).bCompleted[id]
        endmethod
    endstruct
    
    // Quest Item Text Colorize
    // ============================================================
    
    private struct OperatorItemColorize extends array
        public method operator []= takes player p, boolean b returns nothing
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.colorize[\"" + GetPlayerName(p) + "\"]=" + B2S(b), "Given player is a neutral player")
                return
            endif
            
            set QuestItem(this).bColorize[id] = b
            
            if GetLocalPlayer() == p then
                if b then
                    call QuestItemSetDescription(QuestItem(this).qItem, QuestItem(this).aColor[id].str(QuestItem(this).sText[id]))
                else
                    call QuestItemSetDescription(QuestItem(this).qItem, QuestItem(this).sText[id])
                endif
            endif
        endmethod
        
        public method operator [] takes player p returns boolean
            local integer id = GetPlayerId(p)
            if id > 11 then
                debug call ErrorMsg("QuestItem.colorize[\"" + GetPlayerName(p) + "\"]", "Given player is a neutral player")
                return false
            endif
            
            return QuestItem(this).bColorize[id]
        endmethod
    endstruct
    
// ============================================================
// QuestItem Struct
// ============================================================    
    
    struct QuestItem 
    
        readonly questitem qItem
        Quest qOwner
        
        ARGB array aColor[12]             //0xFFFFFF
        boolean array bCompleted[12]      //false
        boolean array bColorize[12]       //true
        integer array iData[12]           //0
        string array sText[12]            //""
    
        static method create takes Quest q returns thistype
            local thistype this
            local integer i = 0
            
            if q.qItemId > MAX_QUESTITEMS-1 then
                return 0
            endif
            
            set this = .allocate()
            set .qItem = QuestCreateItem(q.qQuest)
            set q.qItem[q.qItemId] = this
            set q.qItemId = q.qItemId + 1
            set .qOwner = q
            loop
                exitwhen i >= 12
                set .iData<i> = 0
                set .bColorize<i> = true
                set .bCompleted<i> = false
                set .aColor<i> = 0xFFFFFF
                
                set i = i + 1
            endloop
            
            return this
        endmethod
        
        method duplicate takes Quest q returns thistype
            local thistype it
            local integer i = 0
            
            if q.qItemId &gt; MAX_QUESTITEMS then
                return 0
            endif
            
            set it = .allocate()
            set it.qItem = QuestCreateItem(q.qQuest)
            set q.qItem[q.qItemId] = it
            set q.qItemId = q.qItemId + 1
            set it.qOwner = q
            loop
                exitwhen i &gt;= 12
                set it.iData<i> = .iData<i>
                set it.bColorize<i> = .bColorize<i>
                set it.bCompleted<i> = .bCompleted<i>
                set it.aColor<i> = .aColor<i>
                set it.sText<i> = .sText<i>
                
                if GetLocalPlayer() == Player(i) then
                    call QuestItemSetCompleted(it.qItem, .bCompleted<i>)
                    if .bColorize<i> then
                        call QuestItemSetDescription(it.qItem, .aColor<i>.str(.sText<i>))
                    else
                        call QuestItemSetDescription(it.qItem, .sText<i>)
                    endif
                endif
                    
                set i = i + 1
            endloop
            
            return it
        endmethod
        
        private method onDestroy takes nothing returns nothing
            set .qItem = null
        endmethod
        
        //==================
        
        public method operator completed takes nothing returns OperatorItemCompleted
            return OperatorItemCompleted(this)
        endmethod
        
        public method operator data takes nothing returns OperatorItemData
            return OperatorItemData(this)
        endmethod
        
        public method operator text takes nothing returns OperatorItemText
            return OperatorItemText(this)
        endmethod
        
        public method operator color takes nothing returns OperatorItemColor
            return OperatorItemColor(this)
        endmethod
        
        public method operator colorize takes nothing returns OperatorItemColorize
            return OperatorItemColorize(this)
        endmethod
        
        //==================
        
        public method operator data= takes integer value returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .iData<i> = value
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator text= takes string value returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .sText<i> = value
                if GetLocalPlayer() == Player(i) then
                    if .bColorize<i> then
                        call QuestItemSetDescription(.qItem, .aColor<i>.str(value))
                    else
                        call QuestItemSetDescription(.qItem, value)
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator color= takes ARGB color returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .aColor<i> = color
                
                if .bColorize<i> then
                    if GetLocalPlayer() == Player(i) then
                        call QuestItemSetDescription(.qItem, color.str(.sText<i>))
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator completed= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bCompleted<i> = b
                
                set i = i + 1
            endloop
            
            call QuestItemSetCompleted(.qItem, b)
        endmethod
        
        public method operator colorize= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bColorize<i> = b
                
                if b then
                    if GetLocalPlayer() == Player(i) then
                        call QuestItemSetDescription(.qItem, .aColor<i>.str(.sText<i>))
                    endif
                else
                    call QuestItemSetDescription(.qItem, .sText<i>)
                endif
                
                set i = i + 1
            endloop
        endmethod
    endstruct
        
// ============================================================
// Quest Struct
// ============================================================
    
    struct Quest
    
        readonly quest qQuest
        QuestItem array qItem[MAX_QUESTITEMS]
        integer qItemId = 0
        
        ARGB array aTitleColor[12]         //0xFFFFFF
        ARGB array aTextColor[12]          //0xFFFFFF
        boolean array bVisible[12]         //true
        boolean array bRequired[12]        //true
        boolean array bDiscovered[12]      //true
        boolean array bFailed[12]          //false
        boolean array bCompleted[12]       //false
        boolean array bTitleColorize[12]   //true
        boolean array bTextColorize[12]    //true
        integer array iData[12]            //0
        string array sTitle[12]            //&quot;&quot;
        string array sIcon[12]             //&quot;&quot;
        string array sText[12]             //&quot;&quot;
        
    
        static method create takes nothing returns thistype
            local thistype this = .allocate()
            local integer i = 0
            
            set .qQuest = CreateQuest()
            loop
                exitwhen i &gt;= 12
                set .iData<i> = 0
                set .aTitleColor<i> = 0xFFFFFF
                set .aTextColor<i> = 0xFFFFFF
                set .bVisible<i> = true
                set .bTitleColorize<i> = true
                set .bTextColorize<i> = true
                set .bRequired<i> = true
                set .bDiscovered<i> = true
                set .bFailed<i> = false
                set .bCompleted<i> = false
                
                set i = i + 1
            endloop
            
            return this
        endmethod
        
        method duplicate takes nothing returns thistype
            local thistype new = .allocate()
            local integer i = 0
            
            set new.qQuest = CreateQuest()
            loop
                exitwhen i &gt;= 12
                set new.aTitleColor<i> = .aTitleColor<i>
                set new.aTextColor<i> = .aTextColor<i>
                set new.bVisible<i> = .bVisible<i>
                set new.bRequired<i> = .bRequired<i>
                set new.bDiscovered<i> = .bDiscovered<i>
                set new.bFailed<i> = .bFailed<i>
                set new.bCompleted<i> = .bCompleted<i>
                set new.bTitleColorize<i> = .bTitleColorize<i>
                set new.bTextColorize<i> = .bTextColorize<i>
                set new.iData<i> = .iData<i>
                set new.sTitle<i> = .sTitle<i>
                set new.sIcon<i> = .sIcon<i>
                set new.sText<i> = .sText<i>
                
                if GetLocalPlayer() == Player(i) then
                    if .bTextColorize<i> then
                        call QuestSetDescription(new.qQuest, .aTextColor<i>.str(.sText<i>))
                    else
                        call QuestSetDescription(new.qQuest, .sText<i>)
                    endif
                    if .bTitleColorize<i> then
                        call QuestSetTitle(new.qQuest, .aTitleColor<i>.str(.sTitle<i>))
                    else
                        call QuestSetTitle(new.qQuest, .sTitle<i>)
                    endif
                    
                    call QuestSetIconPath(new.qQuest, .sIcon<i>)
                    call QuestSetRequired(new.qQuest, .bRequired<i>)
                    call QuestSetDiscovered(new.qQuest, .bDiscovered<i>)
                    call QuestSetCompleted(new.qQuest, .bCompleted<i>)
                    call QuestSetFailed(new.qQuest, .bFailed<i>)
                    call QuestSetEnabled(new.qQuest, .bVisible<i>)
                endif
                set i = i + 1
            endloop
            
            set i = 0
            loop
                exitwhen i == .qItemId
                call .qItem<i>.duplicate(new)
                
                set i = i + 1
            endloop
            
            return new
        endmethod
        
        private method onDestroy takes nothing returns nothing
            local integer i = 0
            call DestroyQuest(.qQuest)
            set .qQuest = null
            loop
                exitwhen i == qItemId
                call qItem<i>.destroy()
                set i = i + 1
            endloop
        endmethod
        
        //==================
        
        public method operator visible takes nothing returns OperatorVisible
            return OperatorVisible(this)
        endmethod
        
        public method operator required takes nothing returns OperatorRequired
            return OperatorRequired(this)
        endmethod
        
        public method operator failed takes nothing returns OperatorFailed
            return OperatorFailed(this)
        endmethod
        
        public method operator completed takes nothing returns OperatorCompleted
            return OperatorCompleted(this)
        endmethod
        
        public method operator discovered takes nothing returns OperatorDiscovered
            return OperatorDiscovered(this)
        endmethod
        
        public method operator data takes nothing returns OperatorData
            return OperatorData(this)
        endmethod
        
        public method operator icon takes nothing returns OperatorIcon
            return OperatorIcon(this)
        endmethod
        
        public method operator title takes nothing returns OperatorTitle
            return OperatorTitle(this)
        endmethod
        
        public method operator titleColor takes nothing returns OperatorTitleColor
            return OperatorTitleColor(this)
        endmethod
        
        public method operator titleColorize takes nothing returns OperatorTitleColorize
            return OperatorTitleColorize(this)
        endmethod
        
        public method operator text takes nothing returns OperatorText
            return OperatorText(this)
        endmethod
        
        public method operator textColor takes nothing returns OperatorTextColor
            return OperatorTextColor(this)
        endmethod
        
        public method operator textColorize takes nothing returns OperatorTextColorize
            return OperatorTextColorize(this)
        endmethod
        
        //==================
        
        public method operator data= takes integer value returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .iData<i> = value
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator text= takes string value returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .sText<i> = value
                if GetLocalPlayer() == Player(i) then
                    if .bTextColorize<i> then
                        call QuestSetDescription(.qQuest, .aTextColor<i>.str(value))
                    else
                        call QuestSetDescription(.qQuest, value)
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator textColor= takes ARGB color returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .aTextColor<i> = color
                if GetLocalPlayer() == Player(i) then
                    if .bTextColorize<i> then
                        call QuestSetDescription(.qQuest, color.str(.sText<i>))
                    else
                        call QuestSetDescription(.qQuest, .sText<i>)
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator title= takes string value returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .sTitle<i> = value
                if GetLocalPlayer() == Player(i) then
                    if .bTitleColorize<i> then
                        call QuestSetTitle(.qQuest, .aTitleColor<i>.str(value))
                    else
                        call QuestSetTitle(.qQuest, value)
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator icon= takes string s returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .sIcon<i> = s
                
                set i = i + 1
            endloop
            
            call QuestSetIconPath(.qQuest, s)
        endmethod
        
        public method operator titleColor= takes ARGB color returns nothing
            local integer i = 0
            
            loop
                exitwhen i == 12
                
                set .aTitleColor<i> = color
                if GetLocalPlayer() == Player(i) then
                    if .bTitleColorize<i> then
                        call QuestSetTitle(.qQuest, color.str(.sTitle<i>))
                    else
                        call QuestSetTitle(.qQuest, .sTitle<i>)
                    endif
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator required= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bRequired<i> = b
                
                set i = i + 1
            endloop
            
            call QuestSetRequired(.qQuest, b)
        endmethod
        
        public method operator discovered= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bDiscovered<i> = b
                
                set i = i + 1
            endloop
            
            call QuestSetDiscovered(.qQuest, b)
        endmethod
        
        public method operator completed= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bCompleted<i> = b
                
                set i = i + 1
            endloop
            
            call QuestSetCompleted(.qQuest, b)
        endmethod
        
        public method operator failed= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bFailed<i> = b
                
                set i = i + 1
            endloop
            
            call QuestSetFailed(.qQuest, b)
        endmethod
        
        public method operator visible= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bVisible<i> = b
                
                set i = i + 1
            endloop
            
            call QuestSetEnabled(.qQuest, b)
        endmethod
        
        public method operator textColorize= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bTextColorize<i> = b
                
                if b then
                    if GetLocalPlayer() == Player(i) then
                        call QuestSetDescription(.qQuest, .aTextColor<i>.str(.sText<i>))
                    endif
                else
                    call QuestSetDescription(.qQuest, .sText<i>)
                endif
                
                set i = i + 1
            endloop
        endmethod
        
        public method operator titleColorize= takes boolean b returns nothing
            local integer i = 0
            loop
                exitwhen i == 12
                
                set .bTitleColorize<i> = b
                
                if b then
                    if GetLocalPlayer() == Player(i) then
                        call QuestSetTitle(.qQuest, .aTitleColor<i>.str(.sTitle<i>))
                    endif
                else
                    call QuestSetTitle(.qQuest, .sTitle<i>)
                endif
                
                set i = i + 1
            endloop
        endmethod
    endstruct

endlibrary</i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i></i>


The test map contains a simple quest to show how do the system works.

Changelog:
1.0.0 >> 12.08.2010
-First release

1.0.1 >> 12.09.2010
-Minor bug & logical fail fixes
-New Quest.duplicate() method

1.0.2 >> 12.09.2010.
-Runtime speed improvements

Please tell me your opinion and suggestions, and let me know if you found a bug.
 

Attachments

  • QuestStruct.w3x
    44.5 KB · Views: 297

luorax

Invasion in Duskwood
Reaction score
67
Update!
I had to hurry when I was writing the description and the QuestItem.duplicate method, so there were a lot of typo errors, and some logical fails... but they're all fixed now.

And there's a new Quest.duplicate() method and a changelog.
 

Laiev

Hey Listen!!
Reaction score
188
I'm crazy or you're lol, what map? Oo

or you just removed it?

Edit: nvm... for some reason the map don't show here the first time, just now :p
 

luorax

Invasion in Duskwood
Reaction score
67
That's just a fast written one. I made it to show how can you use the system. That's all. So it's really not optimized and efficient (also there were question marks and exclamation marks too, but i started making my AutoQuest library, so i changed the functions to the AQ's ones. But it's still under development, so I didn't share it. That's why we don't have any marks now.)
 

Sgqvur

FullOfUltimateTruthsAndEt ernalPrinciples, i.e shi
Reaction score
62
I really don't know all the vJass voodoo you are using but I am noticing you are
calling GetPlayerId(p) a few times in some functions

instead of the local integer pid = GetPlayerId(p)

I personally think that quests should be avoided and instead the
helpstrings.txt and tipstrings.txt should be used.


PS: noticing you are encoding type information in variable names... why is that?
 

luorax

Invasion in Duskwood
Reaction score
67
I am noticing you are calling GetPlayerId(p) a few times in some functions

I thought about it, but I forgot to remove it... nvm, fixed.

PS: noticing you are encoding type information in variable names... why is that?

A bad habbit. They look better, in my opinion.
 

Sgqvur

FullOfUltimateTruthsAndEt ernalPrinciples, i.e shi
Reaction score
62
Would you agree that the multiboard is a much better way to give the player different kinds of information including such regarding quests?

Imagine instead of having to click on the flashy quest button and then click on some more buttons and read some description then scrolling down to read some more and questitems being unable to be removed and their description has a fixed width you could just take a look at the multiboard and read it's description at a glance.
 

tooltiperror

Super Moderator
Reaction score
231
API seems fugly. At least post an example in the first post, too.

I was thinking this was going to be, well, a struct interface? Just a rough draft.

JASS:
struct SomeQuest

	//=====================
	// Required Variables
	//=====================
	private integer questitem = &#039;I000&#039; // Item that starts quest on purchase
	private integer objId     = &#039;I001&#039; // The item to be aquired
	private integer objtick   = 12     // How many items of objId must be aquired
	
	//=====================
	// Optional Variables
	//=====================
	private string startmessage   = &quot;Bring me x&quot;     // Displayed to the player up start
	private string updatemessage  = &quot;x has started!&quot; // Displayed to all players upon start, if not null
	private string competemessage = &quot;Thank you&quot;      // Displayed to player when quest is done
	
	//===========================
	// Played Defined Variables
	//===========================
	private integer tick       = 0
	private boolean completed  = false

	//=====================================
	// Called when objective is completed
	//=====================================
	private static method onObjective takes nothing returns nothing
		set this.completed=true
	endmethod
	
	//==================================================
	// Called when unit is killed/item is acquired/etc
	//==================================================
	private method onUpdate takes nothing returns nothing
		set tick=tick+1
		call thistype.onObjective()
	endmethod
	
	private static method QuestStructInit takes nothing returns nothing
		// Some sort of player set up
	endmethod
	
	implement QuestStruct

endstruct


edit:

JASS:
    debug private function ErrorMsg takes string what, string error returns nothing
        debug call DisplayTimedTextToPlayer(GetLocalPlayer(), 0, 0, 60, &quot;Quest Error: &quot; + what + &quot;: &quot; + error)
    debug endfunction


:rolleyes:

EditEdit: Somewhere around these forums Jesus4Lyf mentioned an interface he made once for a private map he made, ask him about it, it was never released as an official system though.

EditEditEdit: Yeah, I thoroughly believe you should adapt an interface closer to the module type, or at least give it a few modules.

  • QuestStructBase — The core system, including support to define your own quest types
  • QuestStructKill — For quests you must kill something(s)
  • QuestStructAquire — For quests you aquire item(s)
  • QuestStructExplore — For quests where you must explore areas
  • QuestStruct<insert anything here>
 

luorax

Invasion in Duskwood
Reaction score
67
Well, this system is just a quest-handler. So:
The system operates with the quests as handles, not as RPG elements.
My example was a real quest, because the most user will use it to create his own quest, but... This is just the base of my currently undone library (AutoQuest). That's an automatical quest system, so with about 5 lines you have a quest which updates itself automatically, and you can add different objecttive types to a quest. But I haven't finished it yet because I've starteed an ORPG project.

That has a quite ugly API too:


JASS:
function Test takes nothing returns nothing
        local AutoQuest q = AutoQuest.create(unit giver, unit finish, real pickup-distance)
        call q.setTitleForPlayer(Player(0), &quot;The Troll Problem&quot;, ARGB.fromPlayer(Player(0)))
        call q.setTitleForPlayer(Player(1), &quot;The Troll Problem&quot;, ARGB.fromPlayer(Player(1)))
        call q.setText(string description, ARGB color)
        call q.setIcon(&quot;icon&quot;)
        call q.addSlainObjective(&#039;ndtr&#039;, 7)
        call q.addSlainObjective(&#039;ndtp&#039;, 7)
        call q.addCollectObjective(&#039;I000&#039;, 9)
        call q.setGoldReward(100)
        call q.setLumberReward(150)
        call q.setXpReward(200)
endfunction


I saw a topic where a user had problems with the showing of a quest, that's why I've shared this library. I didn't want to do so.
 

tooltiperror

Super Moderator
Reaction score
231
What you are saying makes absolutely no sense. Just because someone has trouble doesn't mean there is need to post a library that you yourself will soon be illogical to use when you post a new system, so this is as good as spam.
 
General chit-chat
Help Users
  • No one is chatting at the moment.

      The Helper Discord

      Members online

      No members online now.

      Affiliates

      Hive Workshop NUON Dome World Editor Tutorials

      Network Sponsors

      Apex Steel Pipe - Buys and sells Steel Pipe.
      Top