Token *Command::arg(int idx) { for(Shard *it = first(); it; it = it->next()) { if(idx--) continue; it = it->first(); if(!it || it->type() != BLOCK) break; return (Token*) it->first(); } return 0; }
/** * An exception will be thrown if there is an error. */ void RuleSet::generateRule(Command *command) { Rule *rule; Shard *it; GemTest *terms; // Create the rule object. if(command->isName("format")) { rule = new FormatRule(((Block*)command->last()->first())->collect()); } else { rule = new LengthRule; } terms = &rule->terms(); // Compile the terms (command -> shards -> blocks -> tokens). for(it = command->first(); it && it != command->last(); it = it->next()) { if(!it->first()) continue; terms->addBefore(new GemTest((Token*)it->first()->first())); } if(command->isName("format")) { // There must not be format rules with matching terms. removeMatching(*terms, Rule::FORMAT); add(rule); } else { add(rule); Length *len = &((LengthRule*)rule)->length(); // Set the lengths that were given. // Get last argument -> block -> first token. len->init((Token*)command->last()->first()->first()); // Was this all for naught? if(len->isClear()) delete remove(rule); } }
bool Command::hasArg(const String& str) { for(Shard *it = first(); it; it = it->next()) { Block *block = (Block*) it->first(); if(!block || block->type() != BLOCK) continue; for(Shard *arg = block->first(); arg; arg = arg->next()) { // Blocks have only Tokens as children! if(((Token*)arg)->token() == str) return true; } } return false; }