Hucaru / Valhalla

A Golang MapleStory (v28) server
MIT License
274 stars 71 forks source link

NPC scripting #23

Closed Hucaru closed 4 years ago

Hucaru commented 4 years ago

@ErwinsExpertise I have made progress on a script system for NPCs - the scripts are written in JavaScript. Is the following script clear?:

var state = 0
var styles = [31050, 31040, 31000, 31060, 31090, 31020, 31130, 31120, 31140, 31330, 31010]
var goods = [ [1332020],[1332020, 1],[1332009, 0] ]

function run(npc, player) {
    if (npc.next()) {
        state++
    } else if (npc.back()) {
        state--
    }

    if (state == 2) {
        if (npc.yes()) {
            state = 3
        } else if (npc.no()) {
            state = 4
        }
    } else if (state == 4) {
        if (npc.selection() == 1) {
            state = 0
        } else if (npc.selection() == 2) {
            state = 5
        } else if (npc.selection() == 3) {
            state = 6
        } else if (npc.selection() == 4) {
            state = 7
        } else if (npc.selection() == 5) {
            state = 8
        }
    }

    switch(state) {
    case 0:
        npc.sendBackNext("first", false, true)
        break
    case 1:
        npc.sendBackNext("second", true, false)
        break
    case 2:
        npc.sendYesNo("finished")
        break
    case 3:
        npc.sendOK("selection:" + npc.selection() + ", input number:" + npc.inputNumber() + ", input text: " + npc.inputString())
        npc.terminate()
        break
    case 4:
        npc.sendSelection("Select from one of the following:\r\n#L1#Back to start #l\r\n#L2#Styles#l\r\n#L3#Input number#l#L4#Input text#l\r\n#L5#Shop#l")
        break
    case 5:
        npc.sendStyles("Select from the following", styles)
        state = 3
        break
    case 6:
        npc.sendInputNumber("Input a number:", 100, 0, 100)
        state = 3
        break
    case 7:
        npc.sendInputText("Input text:", "default", 0, 100)
        state = 3
        break
    case 8:
        npc.sendShop(goods)
        break
    default:
        npc.sendOK("state " + state)
        npc.terminate()
    }
}
ErwinsExpertise commented 4 years ago

Will the source be moving from gomacro to JS? Yes, it does make sense and it is structured well. Will state be required for scripting or is that just for this test script?

Hucaru commented 4 years ago

Yea, I will be moving from gomacro to JS.

Will state be required for scripting or is that just for this test script?

State management will be up to the writer to implement in whatever fashion they want (could write their own fancy lookup table for a super complicated npc). For example if you have a shop script you could implement it in just:

var goods = [ [id1] , [id2, custom_price], [id3] ]

function run(npc, player) {
    npc.sendShop(goods)
}

Since this npc isn't doing anything stateful then no state is managed. Whereas the example provided earlier is a demo of all the npc chat windows that can be used (apart from the pet one and an unknown one I need to figure out)

ErwinsExpertise commented 4 years ago

That makes sense. This seems like a logical switch. This way scripts can be pulled from existing sources and modified to work, rather than creating new scripts.

Hucaru commented 4 years ago

I have a PR up for the new script system and script hot loading. I have also converted the Henesys taxi script to the new format and tested it. I will merge it tomorrow unless there are any comments to address.