diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 9c36f0e49..9b1b9aaba 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -1136,4 +1136,48 @@ DEFINE_ACTION_FUNCTION(FStringStruct, AppendFormat) FString s = FStringFormat(param+1, defaultparam, numparam-1, ret, numret); (*self) += s; return 0; -} \ No newline at end of file +} + +DEFINE_ACTION_FUNCTION(FStringStruct, Mid) +{ + PARAM_SELF_STRUCT_PROLOGUE(FString); + PARAM_INT(pos); + PARAM_INT(len); + // validate. we don't want to crash if someone passes negative values. + // with size_t it's handled naturally I think, as it's unsigned, but not in ZScript. + if (pos < 0) pos = 0; + if (len < 0) len = 0; + int slen = self->Len(); + if (pos > slen) pos = slen - 1; + if (pos + len > slen) + len = slen - pos; + FString s = self->Mid(pos, len); + ACTION_RETURN_STRING(s); +} + +DEFINE_ACTION_FUNCTION(FStringStruct, Len) +{ + PARAM_SELF_STRUCT_PROLOGUE(FString); + ACTION_RETURN_INT(self->Len()); +} + +// CharAt and CharCodeAt is how JS does it, and JS is similar here in that it doesn't have char type as int. +DEFINE_ACTION_FUNCTION(FStringStruct, CharAt) +{ + PARAM_SELF_STRUCT_PROLOGUE(FString); + PARAM_INT(pos); + int slen = self->Len(); + if (pos < 0 || pos >= slen) + ACTION_RETURN_STRING(""); + ACTION_RETURN_STRING(FString((*self)[pos])); +} + +DEFINE_ACTION_FUNCTION(FStringStruct, CharCodeAt) +{ + PARAM_SELF_STRUCT_PROLOGUE(FString); + PARAM_INT(pos); + int slen = self->Len(); + if (pos < 0 || pos >= slen) + ACTION_RETURN_INT(0); + ACTION_RETURN_INT((*self)[pos]); +} diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt index 175f8341d..83d714684 100644 --- a/wadsrc/static/zscript/base.txt +++ b/wadsrc/static/zscript/base.txt @@ -417,9 +417,14 @@ enum EPickStart // Although String is a builtin type, this is a convenient way to attach methods to it. struct StringStruct native { - native void Replace(String pattern, String replacement); native static vararg String Format(String fmt, ...); native vararg void AppendFormat(String fmt, ...); + + native void Replace(String pattern, String replacement); + native String Mid(int pos = 0, int len = 2147483647); + native int Len(); + native String CharAt(int pos); + native int CharCodeAt(int pos); } class Floor : Thinker native