/* /std/user/more.c from Nightmare IV inherited player functions for paging files and string arrays created by Descartes of Borg 931204 */ #include "more.h" static private mapping __More; void create() { __More = ([]); } varargs int more(mixed what, string cl, function endmore, mixed args) { string *tmp; if(!pointerp(what) && !stringp(what)) return notify_fail("Unknown file reference.\n"); if(__More["lines"]) __More = ([]); if(!(__More["class"] = cl)) __More["class"] = "info"; if(!(__More["screen"]=to_int((string)this_object()->getenv("LINES")))) __More["screen"] = 20; if(stringp(what)) { if(sizeof(tmp = (string *)this_object()->wild_card(what)) != 1) return notify_fail("Ambiguous file reference.\n"); if(file_size(tmp[0]) < 1) return notify_fail("Ambiguous file reference.\n"); __More["total"] = sizeof(__More["lines"] = explode(read_file(tmp[0]), "\n")); } else if(pointerp(what)) __More["total"] = sizeof(__More["lines"] = what); else return notify_fail("Illegal file reference.\n"); if(creatorp(this_object()) && tmp && tmp[0]) message(__More["class"], "--==** "+tmp[0]+" **==--", this_object()); if(!__More["total"]) { __More = ([]); if(functionp(endmore)) { if(!((int)master()->valid_function(endmore))) error("Illegal function pointer.\n"); else (*endmore)(args); } return 1; } __More["current"] = 0; if(functionp(endmore)) __More["endfun"] = endmore; __More["args"] = args; do_more(" "); return 1; } static void do_more(string cmd) { string args; int i, x; if(!cmd || cmd == "" || cmd == "\r" || cmd == "\n" || cmd[0] == 10) cmd = " "; if((x = strlen(cmd)) > 1) { args = cmd[1..x-1]; cmd = cmd[0..0]; } switch(cmd) { case " ": break; case "b": case "B": __More["current"] -= __More["screen"]*2; if(__More["current"] < 0) __More["current"] = 0; break; case "<": __More["current"] = 0; break; case ">": __More["current"] = __More["total"]-1; break; case "/": if(getenv("MORE") == "off") regexp_fwd(args); else input_to("regexp_fwd"); return; case "?": if(getenv("MORE") == "off") regexp_bkwd(args); else input_to("regexp_bkwd"); return; case "n": if(!__More["regexp"] || __More["regexp"] == "") { message(__More["class"], "\nNo previous search.", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; } if(__More["regexp"][0] == '/') regexp_fwd(__More["regexp"][1..strlen(__More["regexp"])-1]); else regexp_bkwd(__More["regexp"][1..strlen(__More["regexp"])-1]); return; case "=": message(__More["class"], "\nCurrent line: "+ __More["current"], this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; case "v": case "V": message(__More["class"], "\nNightmare Mudlib \"more\" "+ "version 2.1 by Descartes of Borg 931204.", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; case "h": case "H": do_help(); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; case "Q": case "q": message(__More["class"], "", this_object()); if(functionp(__More["endfun"]) && (int)master()->valid_function(__More["endfun"])) (*__More["endfun"])(__More["args"]); __More = ([]); return; default: message(__More["class"], "\nUnrecognized command.", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; } message(__More["class"], "", this_object()); for(i=__More["current"]; i<__More["current"] + __More["screen"]; i++) { if(i>= __More["total"]) { if(functionp(__More["endfun"]) && (int)master()->valid_function(__More["endfun"])) (*__More["endfun"])(__More["args"]); __More = ([]); return; } message(__More["class"], __More["lines"][i], this_object()); } if((__More["current"] = i) >= __More["total"]) { if(functionp(__More["endfun"]) && (int)master()->valid_function(__More["endfun"])) (*__More["endfun"])(__More["args"]); __More = ([]); return; } __More["current"] = i; message("prompt", "%^B_WHITE%^BLACK%^--More-- ("+ to_int(percent(__More["current"], __More["total"]))+"%) ", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; } void do_help() { message("Nhelp", "Help for the \"more\" utility:\n\n" "<spacebar> Display the next page of text.\n" "B or b Display the previous page of text.\n" "< Goto the beginning of the document.\n" "> Goto the end of the document.\n" "= Display the current line number.\n" "/\<exp> Goto the next line with the expression <exp> in it.\n" "?<exp> Goto the previous line with the expression <exp> in it.\n" "v or V See the version information about this pager.\n" "h or H This help screen.\n" "q or Q Quit out of the pager.\n", this_object() ); } static void regexp_fwd(string str) { string *matches; int i; __More["regexp"] = "/"+str; if(!sizeof(matches = regexp(__More["lines"][__More["current"]..__More["total"]-1], str))) { message(__More["class"], "\nPattern not found.\n", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; } for(i=__More["current"]; i<__More["total"]; i++) { if(__More["lines"][i] != matches[0]) continue; __More["current"] = i; break; } message(__More["class"], "\nSkipping to line "+__More["current"]+"...", this_object()); do_more(" "); } static void regexp_bkwd(string str) { string *matches; int i; __More["regexp"] = "?"+str; if(!sizeof(matches=regexp(__More["lines"][0..__More["current"]], str))) { message(__More["class"], "\nPattern not found.", this_object()); if(getenv("MORE") == "off") input_to("do_more"); else get_char("do_more"); return; } __More["current"] = member_array(matches[0],__More["lines"][0..__More["current"]]); message(__More["class"], "\n...Backing up...", this_object()); do_more(" "); } string getenv(string val) { return 0; }