>adding in new features, and fixing a couple (seriously, only a couple :) >bugs.. I've got one bugfix that I'm sure a few people would love. I've had the following problem with MobProgs before. given following mobprog: (labels so that i can explain the problem) greet_prog 100 if something // if#1 if something else // if#2 goto this // Statement 1 else // else#1 if not something // if #3 say not something // Statement 2 else // else 2 say something // Statement 3 endif // endif 1 endif // endif 2 else // else 3 say something weird // Statement 4 endif // endif 3 -- prog is executed, if#1 is TRUE, if #2 is TRUE, everything is fine. try this one though if #1 is FALSE, logic would dictate we would goto else #3, right? well, according to the default way mobprogs are done, it's not so, the FIRST else statement after the FALSE if will get executed up until endif, then it'll return. -- simple (?maybe?) fix: I'm not sure what everyone's term is of Hack, but i think this is sortof a hack. I had to use an extra (recursively passed) variable to get it to work right. anyway. in mobprog.cpp at the top with all the function proto's change (- = remove, + = add) char * mprog_process_if (char* ifchck, char* com_list, struct char_data* mob, struct char_data* actor, struct obj_data* obj, void* vo, - struct char_data* rndm); + struct char_data *rndm, bool Skip_To_Endif); // Note: Change the function also, not just the proto IN mprog_process_if the first section like this of the function after *null = '\0'; /* check for trueness of the ifcheck */ - if ((legal = mprog_do_ifchck(ifchck, mob, actor, obj, vo, rndm))) - if(legal != 0) +// Skip_To_Endif lets us no if we should process commands or not +// for sake of nested if/else/if/else/endif/endif 's + if (!Skip_To_Endif && + (legal = mprog_do_ifchck(ifchck, mob, actor, obj, vo, rndm))) + { + if(legal != -1) // Not Error (ie TRUE or FALSE) flag = TRUE; else return null; + } --- All the ifchck's return -1 on error anyway, i don't know why they did it the way they did before. bug ("Mob: %d no commands after IF/OR", mob_index[mob->nr].virtual); return null; } morebuf = one_argument(cmnd,buf); if (!str_cmp(buf, "or")) { - if ((legal = mprog_do_ifchck(morebuf,mob,actor,obj,vo,rndm))) - if (legal != 0) + if (!Skip_To_Endif && + (legal = mprog_do_ifchck(morebuf,mob,actor,obj,vo,rndm))) + { + if (legal != -1) // legal must be 1 flag = TRUE; else return null; } + } and after for (; ;) /*ifcheck was true, do commands but ignore else to endif*/ { if (!str_cmp(buf, "if")) { - com_list = mprog_process_if(morebuf,com_list,mob,actor,obj,vo,rndm); + // We WANT to Skip commands if + // the previous 'if' wanted to, but if it didn't we shouldn't + // b/c we were successful + com_list = mprog_process_if(morebuf,com_list,mob,actor,obj,vo,rndm, + Skip_To_Endif); return null; and after while (str_cmp(buf, "endif")) { + // To Process Correct handling of if's in elses + // ie we WANT to NOT process commands, b/c this is an else->endif + // section, and the ifchck was successful + if (!str_cmp(buf, "if")) + com_list = mprog_process_if(morebuf, com_list, mob,actor,obj,vo,rndm, + TRUE); cmnd = com_list; com_list = mprog_next_command(com_list); while (*cmnd == ' ') cmnd++; . . morebuf = one_argument(cmnd, buf); } return com_list; } + if (!Skip_To_Endif) mprog_process_cmnd(cmnd, mob, actor, obj, vo, rndm); cmnd = com_list; com_list = mprog_next_command(com_list); while (*cmnd == ' ') cmnd++; and next: else /*false ifcheck, find else and do existing commands or quit at endif*/ { while ((str_cmp(buf, "else")) && (str_cmp(buf,"endif"))) { + // We want to correctly process all following else/if sections, + // so we skip ALL following if's up until the "else" or "endif" + // section b/c this ifchck was FALSE + if (!str_cmp(buf, "if")) + com_list = mprog_process_if(morebuf, com_list,mob,actor, + obj,vo,rndm,TRUE); cmnd = com_list; com_list = mprog_next_command(com_list); while (*cmnd == ' ') cmnd++; and next: for (; ;) /*process the post-else commands until an endif is found.*/ { - if (!str_cmp(buf, "if")) - { - com_list = mprog_process_if(morebuf, com_list, mob, actor, - obj, vo, rndm); - while (*cmnd == ' ') cmnd++; - if (*com_list == '\0') return null; - cmnd = com_list; - com_list = mprog_next_command(com_list); - morebuf = one_argument(cmnd,buf); - continue; - } if (!str_cmp(buf, "else")) --------- if (!str_cmp(buf, "break")) return null; if (!str_cmp(buf, "endif")) return com_list; + if (!Skip_To_Endif) mprog_process_cmnd(cmnd, mob, actor, obj, vo, rndm); + // for correct handling of post-else if statements up until + // the endif. If we previously didn't want to process commands, we still + // don't. otherwise, we DO + if (!str_cmp(buf, "if")) + com_list = mprog_process_if(morebuf, com_list, mob,actor,obj,vo,rndm, + Skip_To_Endif); cmnd = com_list; com_list = mprog_next_command(com_list); and in mprog_driver(): command_list = tmpcmndlst; cmnd = command_list; command_list = mprog_next_command(command_list); while (*cmnd != '\0') { morebuf = one_argument(cmnd, buf); if (!str_cmp(buf, "if")) command_list = mprog_process_if(morebuf, command_list, mob, - actor, obj, vo, rndm); + actor, obj, vo, rndm, FALSE); ---------------- that should allow for correct if/else/if/else/endif/endif handling. it even takes care of any possible OR errors ( we don't have many or's in our progs) anyway, have fun, code on, and chill out. Akuma the Raging Coder +------------------------------------------------------------+ | "The poets talk about love, but what I talk about is DOOM, | | because in the end, DOOM is all that counts." - | | Alex Machine/George Stark/Stephen King, The Dark Half | | "Nothing is IMPOSSIBLE, Just IMPROBABLE" | | "Easier Said Than Done, But Better Done Than Said..." | +------------------------------------------------------------+ +------------------------------------------------------------+ | Ensure that you have read the CircleMUD Mailing List FAQ: | | http://democracy.queensu.ca/~fletcher/Circle/list-faq.html | +------------------------------------------------------------+
This archive was generated by hypermail 2b30 : 12/08/00 PST