diff --git a/lib/pronounsub/pronounsub.py b/lib/pronounsub/pronounsub.py index 3f2d686..cddaac6 100644 --- a/lib/pronounsub/pronounsub.py +++ b/lib/pronounsub/pronounsub.py @@ -67,48 +67,77 @@ def get_pronoun_list(): return script.db.pronouns -def specific_pronoun_from_general(general): - pronoun_list = get_pronoun_list() +def specific_pronoun_from_character(character, caller=None): + pronoun_list = get_pronoun_list()[:] + if caller != None: + pronoun_list += caller.db.pronoun_specs for pronoun in pronoun_list: - if general in pronoun.values(): + if character in pronoun.values(): return pronoun return None +def stringify_specific_pronoun(spec): + return ",".join([ spec[form] for form in _PRONOUN_FORMS ]) + class PronounAdminCommand(Command): """ Configure the list of known server-wide pronouns. Usage: - @pronounadmin add - @pronounadmin remove + @pronounadmin help + @pronounadmin list_known + @pronounadmin spec + @pronounadmin unspec - The commands will add or remove the given pronoun. + On your character and server are stored character pronouns and specific + pronouns. The character pronouns specify what pronouns should actually be + used for your character, and the specific pronouns all the grammatical + forms of a pronoun so the character pronouns can be used in text + substitution. - The pronoun format is: ,,, + The server already has some specific pronouns defined, so it's likely you + can just give your character pronouns and be done. Otherwise you'll have to + tell the server how to use your pronouns with the `spec` command. + + The specific format is: ,,, subjective: *They* went to the store. objective: You took *them* to the store. possessive: You took *their* friend to the store. absolute: The sandwich in the fridge was *theirs*. - Examples: - @pronounadmin add they,them,their,theirs + The `list_known` command lists all specific pronouns known by the server. - @pronounadmin remove they,them,their,theirs + The `spec` command adds a new specific pronoun. + + The `unspec` command removes an existing specific pronoun. + + Examples: + @pronounadmin spec they,them,their,theirs """ key = "pronounadmin" - locks = "cmd:id(1) or perm(Builder)" + locks = "cmd:id(1) or perm(Admin)" def parse(self): + from evennia import set_trace;set_trace() caller = self.caller args = self.args.strip().lower().split() - if len(args) != 2: + if len(args) == 0: caller.msg(self.get_help(caller, self.cmdset)) raise InterruptCommand() command = args[0] - if not command in [ "add", "remove" ]: + + if command == "list_known" and len(args) == 1: + self.args = tuple([command]) + return + + if len(args) != 2: + caller.msg(self.get_help(caller, self.cmdset)) + raise InterruptCommand() + + if not command in [ "spec", "unspec" ] or command == "help": caller.msg(self.get_help(caller, self.cmdset)) raise InterruptCommand() @@ -122,41 +151,47 @@ class PronounAdminCommand(Command): def func(self): caller = self.caller - command, pronoun = self.args - pronoun_str = ",".join([ pronoun[form] for form in _PRONOUN_FORMS ]) + command = self.args[0] + if command == "list_known": + caller.msg("Known server-defined pronouns:") + for spec in get_pronoun_list(): + caller.msg(f" {stringify_specific_pronoun(spec)}") + return + + _, pronoun = self.args pronoun_list = get_pronoun_list() - if command == "add": + + if command == "spec": if not pronoun in pronoun_list: pronoun_list.append(pronoun) - self.caller.msg(f"Added the pronoun \"{pronoun_str}\".") - elif command == "remove": + self.caller.msg(f"Added the pronoun {stringify_specific_pronoun(pronoun)}.") + elif command == "unspec": if pronoun in pronoun_list: pronoun_list.remove(pronoun) - self.caller.msg(f"Removed the pronoun \"{pronoun_str}\".") - + self.caller.msg(f"Removed the pronoun {stringify_specific_pronoun(pronoun)}.") class SetPronounsCommand(Command): """ Sets your pronouns. Usage: - @pronouns list_known + @pronouns help + @pronouns set @pronouns get - @pronouns set [;pronoun2 ...] + @pronouns list_known + @pronouns spec + @pronouns unspec - The `list_known` subcommand lists all pronouns known by the server. - - The `get` command gets your current configured pronouns. + On your character and server are stored character pronouns and specific + pronouns. The character pronouns specify what pronouns should actually be + used for your character, and the specific pronouns all the grammatical + forms of a pronoun so the character pronouns can be used in text + substitution. - The `set` command: - - Pronouns can be specified either in a general form, like "she/they", or a - specific form, like "they,them,their,theirs". - - For the general form, each in the list must match up to a grammatical form - of a specific pronoun in a known database, and that specific pronoun will - be used. + The server already has some specific pronouns defined, so it's likely you + can just give your character pronouns and be done. Otherwise you'll have to + tell the server how to use your pronouns with the `spec` command. The specific format is: ,,, subjective: *They* went to the store. @@ -164,17 +199,30 @@ class SetPronounsCommand(Command): possessive: You took *their* friend to the store. absolute: The sandwich in the fridge was *theirs*. - When multiple pronouns are given, a random one will be used in each text + The `set` command: + + Sets your current character pronouns. Pronouns look the same as how you'd + write them in your bio on social media. They're separated by a slash ("/"), + like "she/they/it", or "he/him". Each pronoun should match to the + grammatical form of a specific pronoun. When multiple pronouns are given, + like both "she" and "they", a random one will be used in each text substitution. + The `get` command gets your current configured pronouns. + + The `list_known` command lists all specific pronouns known by the + server and specified for your acount. + + The `spec` command adds a new specific pronoun. + + The `unspec` command removes an existing specific pronoun. + Examples: @pronouns set he/him @pronouns set she/they/it - @pronouns set they,them,their,theirs - - @pronouns set she/they;fae,faer,faer,faers + @pronouns spec fae,faer,faer,faers """ key = "pronouns" @@ -186,7 +234,7 @@ class SetPronounsCommand(Command): args = self.args.strip().lower().split() if len(args) == 1: command = args[0] - if not command in [ "get", "list_known" ]: + if not command in [ "get", "list_known" ] or command == "help": caller.msg(self.get_help(caller, self.cmdset)) raise InterruptCommand() @@ -198,58 +246,66 @@ class SetPronounsCommand(Command): raise InterruptCommand() command = args[0] - if command != "set": - caller.msg(self.get_help(caller, self.cmdset)) - raise InterruptCommand() - generals = [] - specifics = [] - - pronouns = args[1].split(";") - - for pronoun in pronouns: - slash = ('/' in pronoun) - comma = (',' in pronoun) - if slash and comma: + if command == "spec" or command == "unspec": + new = parse_specific_pronoun(args[1]) + if new == None: caller.msg(self.get_help(caller, self.cmdset)) raise InterruptCommand() - - if comma: - new = parse_specific_pronoun(pronoun) - if new == None: - caller.msg(self.get_help(caller, self.cmdset)) - raise InterruptCommand() - else: - specifics.append(new) else: - generals += [ p.strip() for p in pronoun.split("/") ] + res = new - self.args = (command, generals, specifics) + elif command == "set": + res = args[1].split('/') + + self.args = (command, res) def func(self): caller = self.caller command = self.args[0] - if command == "get": - caller.msg(f"Your pronouns are \"{caller._stringify_pronouns()}\".") - elif command == "list_known": - caller.msg("Known specific pronouns:") - for pronoun in get_pronoun_list(): - caller.msg(" %s" % ",".join([ pronoun[form] for form in _PRONOUN_FORMS ])) - caller.msg("Ask an admin if you want more to be added to the list.") - elif command == "set": - command, generals, specifics = self.args + match self.args[0]: + case "set": + _, pronouns = self.args + has_unmatched = False + for pronoun in pronouns: + if not specific_pronoun_from_character(pronoun, caller): + has_unmatched = True + caller.msg(f"Warning: The character pronoun \"{pronoun}\" is " + "not in any list of specific pronouns. It will " + "be ignored. |/") + if has_unmatched: + caller.msg("You have unkown pronouns set! If you want to " + "actually use them, you'll need to specify their " + "specific form. Type `pronouns help` for " + "details. |/") - for general in generals: - if not specific_pronoun_from_general(general): - caller.msg(f"Warning: The general pronoun \"{general}\" is " - "not in the server's list of pronouns. It will " - "be ignored.") + caller.db.pronouns = pronouns + caller.msg(f"Your pronouns have been set to {caller._stringify_pronouns()}.") - caller.db.pronoun_generals = generals - caller.db.pronoun_specifics = specifics - caller.msg(f"Your pronouns have been set to \"{caller._stringify_pronouns()}\".") + case "get": + caller.msg(f"Your pronouns are {caller._stringify_pronouns()}.") + + case "list_known": + caller.msg("Known user-defined pronouns:") + for spec in caller.db.pronoun_specs: + caller.msg(f" {stringify_specific_pronoun(spec)}") + caller.msg("Known server-defined pronouns:") + for spec in get_pronoun_list(): + caller.msg(f" {stringify_specific_pronoun(spec)}") + + case "spec": + _, pronoun = self.args + if not pronoun in caller.db.pronoun_specs: + caller.db.pronoun_specs.append(pronoun) + self.caller.msg(f"Added the pronoun {stringify_specific_pronoun(pronoun)}.") + + case "unspec": + _, pronoun = self.args + if pronoun in caller.db.pronoun_specs: + caller.db.pronoun_specs.remove(pronoun) + self.caller.msg(f"Remobed the pronoun {stringify_specific_pronoun(pronoun)}.") class PronounCharacter(DefaultCharacter): """ @@ -262,20 +318,14 @@ class PronounCharacter(DefaultCharacter): Called once when the object is created. """ super().at_object_creation() - self.db.pronoun_generals = [ "they", "them" ] - self.db.pronoun_specifics = [] + self.db.pronouns = [ "they", "them" ] + self.db.pronoun_specs = [] def _stringify_pronouns(self): - generals = self.attributes.get("pronoun_generals", default=[ "they", "them" ]) - specifics = self.attributes.get("pronoun_specifics", default=[]) - res = [ "/".join(generals) ] if len(generals) else [] - for specific in specifics: - res.append(",".join([ specific[form] for form in _PRONOUN_FORMS ])) - return ";".join(res) - + pronouns = self.attributes.get("pronouns", default=[ "they", "them" ]) + return "/".join(pronouns) def _get_pronoun(self, regex_match): - logger.log_info("hereee " + str(regex_match)) """ Get pronoun from the pronoun marker in the text. This is used as the callable for the re.sub function. @@ -291,10 +341,9 @@ class PronounCharacter(DefaultCharacter): """ typ = regex_match.group()[1] # "s", "O" etc - logger.log_info("hereee " + typ) - dup_specifics = self.attributes.get("pronoun_specifics", default=[]) - for general in self.attributes.get("pronoun_generals", default=[ "they", "them" ]): - specific = specific_pronoun_from_general(general) + dup_specifics = [] + for pronoun in self.attributes.get("pronouns", default=[ "they", "them" ]): + specific = specific_pronoun_from_character(pronoun, self) if specific != None: dup_specifics.append(specific)