bool ParsePage() { FStrifeDialogueNode *node = new FStrifeDialogueNode; FStrifeDialogueReply **replyptr = &node->Children; memset(node, 0, sizeof(*node)); //node->ItemCheckCount[0] = node->ItemCheckCount[1] = node->ItemCheckCount[2] = -1; node->ThisNodeNum = StrifeDialogues.Push(node); node->ItemCheckNode = -1; FString SpeakerName; FString Dialogue; while (!sc.CheckToken('}')) { bool block = false; FName key = ParseKey(true, &block); if (!block) { switch(key) { case NAME_Name: SpeakerName = CheckString(key); break; case NAME_Panel: node->Backdrop = TexMan.CheckForTexture (CheckString(key), FTexture::TEX_MiscPatch); break; case NAME_Voice: { const char * name = CheckString(key); if (name[0] != 0) { FString soundname = "svox/"; soundname += name; node->SpeakerVoice = FSoundID(S_FindSound(soundname)); if (node->SpeakerVoice == 0 && namespace_bits == Zd) { node->SpeakerVoice = FSoundID(S_FindSound(name)); } } } break; case NAME_Dialog: Dialogue = CheckString(key); break; case NAME_Drop: node->DropType = CheckActorType(key); break; case NAME_Link: node->ItemCheckNode = CheckInt(key); break; } } else { switch(key) { case NAME_Ifitem: if (!ParseIfItem(node)) return false; break; case NAME_Choice: if (!ParseChoice(replyptr)) return false; break; default: sc.UnGet(); Skip(); } } } node->SpeakerName = ncopystring(SpeakerName); node->Dialogue = ncopystring(Dialogue); return true; }
static void GenericParse (FScanner &sc, FGenericParse *parser, const char **keywords, void *fields, const char *type, FName name) { bool notdone = true; int keyword; int val = 0; const PClass *info; do { sc.MustGetString (); keyword = sc.MustMatchString (keywords); switch (parser[keyword].Type) { case GEN_End: notdone = false; break; case GEN_Fixed: sc.MustGetFloat (); SET_FIELD (fixed_t, (fixed_t)(FRACUNIT * sc.Float)); break; case GEN_Sound: sc.MustGetString (); SET_FIELD (FSoundID, FSoundID(sc.String)); /* unknown sounds never produce errors anywhere else so they shouldn't here either. if (val == 0) { Printf ("Unknown sound %s in %s %s\n", sc.String, type, name.GetChars()); } */ break; case GEN_Byte: sc.MustGetNumber (); SET_FIELD (BYTE, sc.Number); break; case GEN_Class: sc.MustGetString (); if (sc.Compare ("None")) { info = NULL; } else { info = PClass::FindClass (sc.String); if (!info->IsDescendantOf (RUNTIME_CLASS(AActor))) { Printf ("%s is not an Actor (in %s %s)\n", sc.String, type, name.GetChars()); info = NULL; } else if (info == NULL) { Printf ("Unknown actor %s in %s %s\n", sc.String, type, name.GetChars()); } } SET_FIELD (const PClass *, info); break; case GEN_Splash: sc.MustGetString (); val = FindSplash (sc.String); SET_FIELD (int, val); if (val == -1) { Printf ("Splash %s is not defined yet (in %s %s)\n", sc.String, type, name.GetChars()); } break; case GEN_Float: sc.MustGetFloat (); SET_FIELD (float, float(sc.Float)); break; case GEN_Time: sc.MustGetFloat (); SET_FIELD (int, (int)(sc.Float * TICRATE)); break; case GEN_Bool: SET_FIELD (bool, true); break; case GEN_Int: sc.MustGetNumber (); SET_FIELD (int, sc.Number); break; case GEN_Custom: parser[keyword].u.Handler (sc, keyword, fields); break; } } while (notdone); }
FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool constant) { FxExpression *x = NULL; int v; if (type == TypeSound) { sc.MustGetString(); x = new FxConstant(FSoundID(sc.String), sc); } else if (type == TypeBool || type == TypeSInt32 || type == TypeFloat64) { x = ParseExpression (sc, cls, constant); if (constant && !x->isConstant()) { sc.ScriptMessage("Default parameter must be constant."); FScriptPosition::ErrorCounter++; } // Do automatic coercion between bools, ints and floats. if (type == TypeBool) { x = new FxBoolCast(x); } else if (type == TypeSInt32) { x = new FxIntCast(x); } else { x = new FxFloatCast(x); } } else if (type == TypeName || type == TypeString) { sc.SetEscape(true); sc.MustGetString(); sc.SetEscape(false); if (type == TypeName) { x = new FxConstant(sc.String[0] ? FName(sc.String) : NAME_None, sc); } else { x = new FxConstant(strbin1(sc.String), sc); } } else if (type == TypeColor) { sc.MustGetString (); if (sc.Compare("none")) { v = -1; } else if (sc.Compare("")) { v = 0; } else { int c = V_GetColor (NULL, sc.String); // 0 needs to be the default so we have to mark the color. v = MAKEARGB(1, RPART(c), GPART(c), BPART(c)); } ExpVal val; val.Type = TypeColor; val.Int = v; x = new FxConstant(val, sc); } else if (type == TypeState) { // This forces quotation marks around the state name. sc.MustGetToken(TK_StringConst); if (sc.String[0] == 0 || sc.Compare("None")) { x = new FxConstant((FState*)NULL, sc); } else if (sc.Compare("*")) { if (constant) { x = new FxConstant((FState*)(intptr_t)-1, sc); } else sc.ScriptError("Invalid state name '*'"); } else { x = new FxMultiNameState(sc.String, sc); } } else if (type->GetClass() == RUNTIME_CLASS(PClassPointer)) { // Actor name sc.SetEscape(true); sc.MustGetString(); sc.SetEscape(false); x = new FxClassTypeCast(static_cast<PClassPointer *>(type)->ClassRestriction, new FxConstant(FName(sc.String), sc)); } else { assert(false && "Unknown parameter type"); x = NULL; } return x; }
FxExpression *ParseParameter(FScanner &sc, PClass *cls, char type, bool constant) { FxExpression *x = NULL; int v; switch(type) { case 'S': case 's': // Sound name sc.MustGetString(); x = new FxConstant(FSoundID(sc.String), sc); break; case 'M': case 'm': // Actor name sc.SetEscape(true); sc.MustGetString(); sc.SetEscape(false); x = new FxClassTypeCast(RUNTIME_CLASS(AActor), new FxConstant(FName(sc.String), sc)); break; case 'T': case 't': // String sc.SetEscape(true); sc.MustGetString(); sc.SetEscape(false); x = new FxConstant(sc.String[0]? FName(sc.String) : NAME_None, sc); break; case 'C': case 'c': // Color sc.MustGetString (); if (sc.Compare("none")) { v = -1; } else if (sc.Compare("")) { v = 0; } else { int c = V_GetColor (NULL, sc.String); // 0 needs to be the default so we have to mark the color. v = MAKEARGB(1, RPART(c), GPART(c), BPART(c)); } { ExpVal val; val.Type = VAL_Color; val.Int = v; x = new FxConstant(val, sc); break; } case 'L': case 'l': { // This forces quotation marks around the state name. sc.MustGetToken(TK_StringConst); if (sc.String[0] == 0 || sc.Compare("None")) { x = new FxConstant((FState*)NULL, sc); } else if (sc.Compare("*")) { if (constant) { x = new FxConstant((FState*)(intptr_t)-1, sc); } else sc.ScriptError("Invalid state name '*'"); } else { x = new FxMultiNameState(sc.String, sc); } break; } case 'X': case 'x': case 'Y': case 'y': x = ParseExpression (sc, cls); if (constant && !x->isConstant()) { sc.ScriptMessage("Default parameter must be constant."); FScriptPosition::ErrorCounter++; } break; default: assert(false); return NULL; } return x; }