ArticyLuaFunctions problems

Announcements, support questions, and discussion for the Dialogue System.
Post Reply
User avatar
Rallix
Posts: 15
Joined: Mon Jul 08, 2019 9:02 am

ArticyLuaFunctions problems

Post by Rallix »

Hi Tony,

I've noticed that while getObj(), getProp() and setProp() are supported by the Dialogue System (and I'm really thankful they are), they don't map as cleanly to DS Lua functions once you involve object references.
Context
I'll briefly explain what I was trying to accomplish to give some context.
Basically, the player character has a set of personality traits which increases/decreases with certain dialogue choices and can affect the future dialogue option (unlock, lock, add some flavour). Changing the numeric value is simple (I wrote a custom sequence for that).

Image

The problem is preventing the player from increasing the traits repeatedly if the conversation can be started again (e.g. it's a part of a dialogue with a party member, or it's echoed back to you in a dream). Giving XP for talking with NPCs only once is a similar thing.
SimStatus seems like a good approach, but since I need it only for a small fraction of the whole dialogue database, I took the documentation's advice and set up a small, local version fulfilling the same purpose.

Image

The choice hub has an initially empty property which is filled with the option you pick. And once you make your choice, the other options will be blocked (and the AddTrait sequence will just pass through with no effect).
I wrote a plugin script with articy macro devkit which automatically generates the appropriate condition/instruction when you link an option to the choice hub.

Ideally, I'd like to end up with something which works in articy (so I can simulate a dialogue via a Journey, and the syntax checker doesn't complain when it stumbles upon non-expresso code) and can be imported in a Dialogue Database without edits (because subsequent reimports would overwrite all changes).
I wrote a condition making sure you can only choose a dialogue option if you didn't pick another one already in the past, otherwise, you'll have to stick with it permanently.

In articy's expresso, it looks like this (the ID belongs to the hub):

Code: Select all

getProp(getObj("0x01000000000636EC"), "Selected.Fragment") == "0_0"
||
getProp(getObj("0x01000000000636EC"), "Selected.Fragment") == self
First part checks if the conversation hub has the selected fragment property filled. "0_0" is what articy:draft returns when there's no object reference instead of null or nil (Id 0 and _0 suffix)… no idea why.
The second part allows you to pick the option if it's referenced by the hub.

The output pin of the fragment adds itself to the choice hub's property:

Code: Select all

setProp(getObj("0x01000000000636EC"), "Selected.Fragment", self)
It works well within articy:draft, but a couple of problems emerge once I export it.
getObj for Flow
Self vs Speaker
In articy:draft, speaker refers to the person currently talking (so does speaker in DS), but self refers to the current dialogue fragment – yet DS points it to the speaker as well.
Image
So in my scenario, it originally went to look up something like Actor["Player"].SimStatus instead of the current dialogue's entry sim status.

getObj
It's not difficult to find the current dialogue entry in C# – but I didn't find a built-in way to do it in Lua, neither did I find a way to get to the dialogue entry's fields. I thought there would be something like "Dialog[thisID].{field}" table, but that seems to be used for SimStatus alone (when the option is enabled). Unless I missed something obvious, of course.
Perhaps that's why getObj() also fails when you're looking for flow elements:
Image
Again, not hard to add a custom line which finds it, but accessing the fields in Lua is the problem.
Image

String ID
As a side note, here is a use case so minimal that I'm quite confident no one in the universe will ever encounter it again. :D
Anyway… :P
getObj() in articy:draft seems to parse the ID back to number and then do a comparison. Which means that as far as articy is concerned "0x01000000000636EC" (HEX, copy-pasted from object properties) and "72057594038335212" (DEC, auto-inserted via articy devkit plugin) point to the same object.
Dialogue System, on the other hand, performs a string equality check, so the format must match exactly.
That's just to point out another difference, once I spotted the problem, it wasn't too hard to fix it.
Image
getProp
getProp has one other issue as well. Articy makes you look up the properties as getProp(obj, "Feature.Property") – but Dialogue System flattens this to a single table which means the code won't work anymore.
Image
Perhaps the property name ought to be split and only the last part after the final dot used.
ObjectReferences after import
Eventually, I found a bit ugly way to extend the getObj and getProp method to get around the above issues and to the dialogue entry fields.

Unfortunately, object references in DS appear like this:

Image

which is great if you need a human-readable title, but bad if you have a condition comparing this to self, which didn't originally exist either but you made it reference DS's dialogue entry ID; not the Articy Id, so I'd have to find a way to convert another dialogue entry's title to its Articy Id (otherwise there's a Lua exception when it tries to evaluate this: return Dirk: "[-1 Honest]: A lie.) or find other objects using the title and pray that there's no conflict, while keeping in mind that DS is probably not going to understand "0_0" as null (or 'nil') and getProp(obj, "Id") will also need to change to getProp(obj, "Articy Id") after import –
…And at this point, I gave up. :D
I opted for another solution for my initial problem which seemed like too much micromanagement at first, but with each new extension method I had to add, it became increasingly viable. ;)
Context conclusion
I figured out the best way to do the permanent, one-time-only choice would most likely be to create a new variable set, e.g. "Choice" and then create an integer global variable marking the index of a chosen option.
For example Choice.TutorialConversation – starting at 0, allowing every option, then setting it to e.g. 3 (index of the chosen option) and blocking everything once the variable's value is greater than 0.
The purpose of this essay is to both show that I put some effort to try to make do with what was available before posting, and to point out possible problems with the articy Lua functions before others encounter them, too.

Please consider looking into some of these problems where it's viable – if not, it'd be great if they could at least get a mention in their relevant pages (articy, Lua).
I'm mostly asking to know where the limits of these functions are in the Dialogue System and I bet other people in the future would be glad to know as well.

I think at least the getProp's "Feature.Variable" deserves a fix, because otherwise you can only retrieve the basic object's variables like "Id" or "MenuText", not your custom properties in templates, which kinda defeats the purpose.
Also, did I overlook a simple way to access the dialogue entry's fields in Lua, or is there a reason why it's not there?

Thank you very much. ;)
User avatar
Tony Li
Posts: 21079
Joined: Thu Jul 18, 2013 1:27 pm

Re: ArticyLuaFunctions problems

Post by Tony Li »

Thank you for taking the time to provide all those details. I'll work on this and implement as much as possible to align the way the Dialogue System handles content with the way articy does. I'll make getProp Feature.Variable a first priority for that.

To conserve memory, the Dialogue System doesn't load dialogue entry fields into the Lua environment. It's almost always static data, and people rarely access it from Lua. But I can certainly see how it would be useful. I'll add a Lua function to get a dialogue entry field.
User avatar
Rallix
Posts: 15
Joined: Mon Jul 08, 2019 9:02 am

Re: ArticyLuaFunctions problems

Post by Rallix »

Thank you! Those are great news. :)

Yep, I understand; it's absolutely reasonable not to keep the metadata in memory. Having a function to extract field data from the entries when needed would be great. Thanks again. ;)
User avatar
Tony Li
Posts: 21079
Joined: Thu Jul 18, 2013 1:27 pm

Re: ArticyLuaFunctions problems

Post by Tony Li »

To keep you updated on this, the articy improvements probably won't make it into the upcoming version 2.2.0, but the Lua function to get dialogue entry fields will. Version 2.2.0 is already behind schedule, and I'd like to get it out as soon as possible to get already-implemented features in the hands of people who are waiting for them.
User avatar
Rallix
Posts: 15
Joined: Mon Jul 08, 2019 9:02 am

Re: ArticyLuaFunctions problems

Post by Rallix »

No, no; it's absolutely fine. While I look forward to seeing this working, it can wait; especially if you currently need to focus on other things. ;)
Post Reply