From 3c9fa2c1d4b53b15d2748566d95a7ed76056d34b Mon Sep 17 00:00:00 2001 From: Benny Malengier Date: Fri, 18 Mar 2011 10:42:03 +0000 Subject: [PATCH] 4598: (trunk 3.3) new name format copies patronymic into surname as well as leaving it as a patronymic when importing This extends what name display can be svn: r16848 --- src/Utils.py | 35 ++++++- src/gen/display/name.py | 222 ++++++++++++++++++++++++++++++---------- src/gen/lib/name.py | 3 +- src/gui/configure.py | 12 ++- 4 files changed, 211 insertions(+), 61 deletions(-) diff --git a/src/Utils.py b/src/Utils.py index 372ffb8bd..92c4449b1 100644 --- a/src/Utils.py +++ b/src/Utils.py @@ -1169,6 +1169,29 @@ def profile(func, *args): #------------------------------------------------------------------------- # keyword, code, translated standard, translated upper +# in gen.display.name.py we find: +# 't' : title = title +# 'f' : given = given (first names) +# 'l' : surname = full surname (lastname) +# 'c' : call = callname +# 'x' : common = nick name if existing, otherwise first first name (common name) +# 'i' : initials = initials of the first names +# 'm' : primary = primary surname (main) +# '0m': primary[pre]= prefix primary surname (main) +# '1m': primary[sur]= surname primary surname (main) +# '2m': primary[con]= connector primary surname (main) +# 'y' : patronymic = pa/matronymic surname (father/mother) - assumed unique +# '0y': patronymic[pre] = prefix " +# '1y': patronymic[sur] = surname " +# '2y': patronymic[con] = connector " +# 'o' : notpatronymic = surnames without pa/matronymic and primary +# 'r' : rest = non primary surnames +# 'p' : prefix = list of all prefixes +# 'q' : rawsurnames = surnames without prefixes and connectors +# 's' : suffix = suffix +# 'n' : nickname = nick name +# 'g' : familynick = family nick name + KEYWORDS = [("title", "t", _("Person|Title"), _("Person|TITLE")), ("given", "f", _("Given"), _("GIVEN")), ("surname", "l", _("Surname"), _("SURNAME")), @@ -1176,10 +1199,16 @@ KEYWORDS = [("title", "t", _("Person|Title"), _("Person|TITLE")), ("common", "x", _("Name|Common"), _("Name|COMMON")), ("initials", "i", _("Initials"), _("INITIALS")), ("suffix", "s", _("Suffix"), _("SUFFIX")), - ("rawsurnames", "q", _("Rawsurnames"), _("RAWSURNAMES")), - ("patronymic", "y", _("Patronymic"), _("PATRONYMIC")), - ("notpatronymic", "o", _("Notpatronymic"),_("NOTPATRONYMIC")), ("primary", "m", _("Primary"), _("PRIMARY")), + ("primary[pre]", "0m", _("Primary[pre]"), _("PRIMARY[PRE]")), + ("primary[sur]", "1m", _("Primary[sur]"), _("PRIMARY[SUR]")), + ("primary[con]", "2m", _("Primary[con]"), _("PRIMARY[CON]")), + ("patronymic", "y", _("Patronymic"), _("PATRONYMIC")), + ("patronymic[pre]", "0y", _("Patronymic[pre]"), _("PATRONYMIC[PRE]")), + ("patronymic[sur]", "1y", _("Patronymic[sur]"), _("PATRONYMIC[SUR]")), + ("patronymic[con]", "2y", _("Patronymic[con]"), _("PATRONYMIC[CON]")), + ("rawsurnames", "q", _("Rawsurnames"), _("RAWSURNAMES")), + ("notpatronymic", "o", _("Notpatronymic"),_("NOTPATRONYMIC")), ("prefix", "p", _("Prefix"), _("PREFIX")), ("nickname", "n", _("Nickname"), _("NICKNAME")), ("familynick", "g", _("Familynick"), _("FAMILYNICK")), diff --git a/src/gen/display/name.py b/src/gen/display/name.py index a17253c15..b3927a516 100644 --- a/src/gen/display/name.py +++ b/src/gen/display/name.py @@ -31,9 +31,15 @@ Specific symbols for parts of a name are defined: 'c' : callname 'x' : nick name if existing, otherwise first first name (common name) 'i' : initials of the first names - 'y' : patronymic surname (father) - 'o' : surnames without patronymic 'm' : primary surname (main) + '0m': primary surname prefix + '1m': primary surname surname + '2m': primary surname connector + 'y' : pa/matronymic surname (father/mother) - assumed unique + '0y': " prefix + '1y': " surname + '2y': " connector + 'o' : surnames without pa/matronymic and primary 'r' : non primary surnames (rest) 'p' : list of all prefixes 'q' : surnames without prefixes and connectors @@ -86,6 +92,7 @@ _PRIMARY_IN_LIST = 2 _TYPE_IN_LIST = 3 _CONNECTOR_IN_LIST = 4 _ORIGINPATRO = NameOriginType.PATRONYMIC +_ORIGINMATRO = NameOriginType.MATRONYMIC _ACT = True _INA = False @@ -129,7 +136,7 @@ class NameDisplayError(Exception): # Functions to extract data from raw lists (unserialized objects) # #------------------------------------------------------------------------- - + def _raw_full_surname(raw_surn_data_list): """method for the 'l' symbol: full surnames""" result = "" @@ -143,8 +150,9 @@ def _raw_primary_surname(raw_surn_data_list): """method for the 'm' symbol: primary surname""" for raw_surn_data in raw_surn_data_list: if raw_surn_data[_PRIMARY_IN_LIST]: - result = "%s %s" % (raw_surn_data[_PREFIX_IN_LIST], - raw_surn_data[_SURNAME_IN_LIST]) + result = "%s %s %s" % (raw_surn_data[_PREFIX_IN_LIST], + raw_surn_data[_SURNAME_IN_LIST], + raw_surn_data[_CONNECTOR_IN_LIST]) return ' '.join(result.split()) return '' @@ -155,34 +163,82 @@ def _raw_primary_surname_only(raw_surn_data_list): return raw_surn_data[_SURNAME_IN_LIST] return '' +def _raw_primary_prefix_only(raw_surn_data_list): + """method to obtain the raw primary surname data""" + for raw_surn_data in raw_surn_data_list: + if raw_surn_data[_PRIMARY_IN_LIST]: + return raw_surn_data[_PREFIX_IN_LIST] + return '' + +def _raw_primary_conn_only(raw_surn_data_list): + """method to obtain the raw primary surname data""" + for raw_surn_data in raw_surn_data_list: + if raw_surn_data[_PRIMARY_IN_LIST]: + return raw_surn_data[_CONNECTOR_IN_LIST] + return '' + +def _raw_patro_surname(raw_surn_data_list): + """method for the 'y' symbol: patronymic surname""" + for raw_surn_data in raw_surn_data_list: + if (raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINPATRO or + raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINMATRO): + result = "%s %s %s" % (raw_surn_data[_PREFIX_IN_LIST], + raw_surn_data[_SURNAME_IN_LIST], + raw_surn_data[_CONNECTOR_IN_LIST]) + return ' '.join(result.split()) + return '' + +def _raw_patro_surname_only(raw_surn_data_list): + """method for the '1y' symbol: patronymic surname only""" + for raw_surn_data in raw_surn_data_list: + if (raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINPATRO or + raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINMATRO): + result = "%s" % (raw_surn_data[_SURNAME_IN_LIST]) + return ' '.join(result.split()) + return '' + +def _raw_patro_prefix_only(raw_surn_data_list): + """method for the '0y' symbol: patronymic prefix only""" + for raw_surn_data in raw_surn_data_list: + if (raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINPATRO or + raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINMATRO): + result = "%s" % (raw_surn_data[_PREFIX_IN_LIST]) + return ' '.join(result.split()) + return '' + +def _raw_patro_conn_only(raw_surn_data_list): + """method for the '2y' symbol: patronymic conn only""" + for raw_surn_data in raw_surn_data_list: + if (raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINPATRO or + raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINMATRO): + result = "%s" % (raw_surn_data[_CONNECTOR_IN_LIST]) + return ' '.join(result.split()) + return '' + +def _raw_nonpatro_surname(raw_surn_data_list): + """method for the 'o' symbol: full surnames without pa/matronymic or + primary + """ + result = "" + for raw_surn_data in raw_surn_data_list: + if ((not raw_surn_data[_PRIMARY_IN_LIST]) and + raw_surn_data[_TYPE_IN_LIST][0] != _ORIGINPATRO and + raw_surn_data[_TYPE_IN_LIST][0] != _ORIGINMATRO): + result += "%s %s %s " % (raw_surn_data[_PREFIX_IN_LIST], + raw_surn_data[_SURNAME_IN_LIST], + raw_surn_data[_CONNECTOR_IN_LIST]) + return ' '.join(result.split()).strip() + def _raw_nonprimary_surname(raw_surn_data_list): """method for the 'r' symbol: nonprimary surnames""" result = '' for raw_surn_data in raw_surn_data_list: if not raw_surn_data[_PRIMARY_IN_LIST]: - result = "%s %s %s" % (result, raw_surn_data[_PREFIX_IN_LIST], - raw_surn_data[_SURNAME_IN_LIST]) + result = "%s %s %s %s" % (result, raw_surn_data[_PREFIX_IN_LIST], + raw_surn_data[_SURNAME_IN_LIST], + raw_surn_data[_CONNECTOR_IN_LIST]) return ' '.join(result.split()) -def _raw_patro_surname(raw_surn_data_list): - """method for the 'y' symbol: patronymic surname""" - for raw_surn_data in raw_surn_data_list: - if raw_surn_data[_TYPE_IN_LIST][0] == _ORIGINPATRO: - result = "%s %s" % (raw_surn_data[_PREFIX_IN_LIST], - raw_surn_data[_SURNAME_IN_LIST]) - return ' '.join(result.split()) - return '' - -def _raw_nonpatro_surname(raw_surn_data_list): - """method for the 'o' symbol: full surnames without patronymic""" - result = "" - for raw_surn_data in raw_surn_data_list: - if raw_surn_data[_TYPE_IN_LIST][0] != _ORIGINPATRO: - result += "%s %s %s " % (raw_surn_data[_PREFIX_IN_LIST], - raw_surn_data[_SURNAME_IN_LIST], - raw_surn_data[_CONNECTOR_IN_LIST]) - return ' '.join(result.split()).strip() - def _raw_prefix_surname(raw_surn_data_list): """method for the 'p' symbol: all prefixes""" result = "" @@ -197,6 +253,18 @@ def _raw_single_surname(raw_surn_data_list): result += "%s " % (raw_surn_data[_SURNAME_IN_LIST]) return ' '.join(result.split()).strip() +def cleanup_name(namestring): + """Remove too long white space due to missing name parts, + so "a b" becomes "a b" and "a , b" becomes "a, b" + """ + result = '' + for val in namestring.split(): + if len(val) == 1 and val in [',', ';', ':']: + result += val + else: + result += ' '+val + return result + #------------------------------------------------------------------------- # # NameDisplay class @@ -211,14 +279,17 @@ class NameDisplay(object): raw_format_funcs = {} STANDARD_FORMATS = [ - (Name.DEF,_("Default format (defined by Gramps preferences)"),'',_ACT), - (Name.LNFN,_("Surname, Given"),'%l, %f %s',_ACT), - (Name.FN,_("Given"),'%f',_ACT), - (Name.FNLN,_("Given Surname"),'%f %l %s',_ACT), + (Name.DEF, _("Default format (defined by Gramps preferences)"), '', _ACT), + (Name.LNFN, _("Surname, Given Suffix"), '%l, %f %s', _ACT), + (Name.FN, _("Given"), '%f', _ACT), + (Name.FNLN, _("Given Surname Suffix"), '%f %l %s', _ACT), + # primary name primconnector other, given pa/matronynic suffix, primprefix + (Name.LNFNP, _("Main Surnames, Given Patronymic Suffix Prefix"), + '%1m %2m %o, %f %1y %s %0m', _ACT), # DEPRECATED FORMATS - (Name.PTFN,_("Patronymic, Given"),'%y, %s %f',_INA), + (Name.PTFN, _("Patronymic, Given"), '%y, %s %f', _INA), ] - + def __init__(self): global WITH_GRAMP_CONFIG self.name_formats = {} @@ -282,13 +353,13 @@ class NameDisplay(object): self.set_name_format([(num, name, fmt_str,_ACT)]) if self.default_format == num: self.set_default_format(num) - + def del_name_format(self, num): try: del self.name_formats[num] except: pass - + def set_default_format(self, num): if num not in self.name_formats: num = Name.LNFN @@ -384,9 +455,15 @@ class NameDisplay(object): 'c' : call = callname 'x' : common = nick name if existing, otherwise first first name (common name) 'i' : initials = initials of the first names - 'y' : patronymic = patronymic surname (father) - 'o' : notpatronymic = surnames without patronymic 'm' : primary = primary surname (main) + '0m': primary[pre]= prefix primary surname (main) + '1m': primary[sur]= surname primary surname (main) + '2m': primary[con]= connector primary surname (main) + 'y' : patronymic = pa/matronymic surname (father/mother) - assumed unique + '0y': patronymic[pre] = prefix " + '1y': patronymic[sur] = surname " + '2y': patronymic[con] = connector " + 'o' : notpatronymic = surnames without pa/matronymic and primary 'r' : rest = non primary surnames 'p' : prefix = list of all prefixes 'q' : rawsurnames = surnames without prefixes and connectors @@ -394,6 +471,7 @@ class NameDisplay(object): 'n' : nickname = nick name 'g' : familynick = family nick name + """ # we need the names of each of the variables or methods that are @@ -416,13 +494,28 @@ class NameDisplay(object): " raw_data[_FIRSTNAME]).split()][1:])", "initials", _("initials")), - "y": ("_raw_patro_surname(raw_data[_SURNAME_LIST])", "patronymic", - _("patronymic")), - "o": ("_raw_nonpatro_surname(raw_data[_SURNAME_LIST])", "notpatronymic", - _("notpatronymic")), "m": ("_raw_primary_surname(raw_data[_SURNAME_LIST])", "primary", _("Name|primary")), + "0m": ("_raw_primary_prefix_only(raw_data[_SURNAME_LIST])", + "primary[pre]", + _("primary[pre]")), + "1m": ("_raw_primary_surname_only(raw_data[_SURNAME_LIST])", + "primary[sur]", + _("primary[sur]")), + "2m": ("_raw_primary_conn_only(raw_data[_SURNAME_LIST])", + "primary[con]", + _("primary[con]")), + "y": ("_raw_patro_surname(raw_data[_SURNAME_LIST])", "patronymic", + _("patronymic")), + "0y": ("_raw_patro_prefix_only(raw_data[_SURNAME_LIST])", "patronymic[pre]", + _("patronymic[pre]")), + "1y": ("_raw_patro_surname_only(raw_data[_SURNAME_LIST])", "patronymic[sur]", + _("patronymic[sur]")), + "2y": ("_raw_patro_conn_only(raw_data[_SURNAME_LIST])", "patronymic[con]", + _("patronymic[con]")), + "o": ("_raw_nonpatro_surname(raw_data[_SURNAME_LIST])", "notpatronymic", + _("notpatronymic")), "r": ("_raw_nonprimary_surname(raw_data[_SURNAME_LIST])", "rest", _("Remaining names|rest")), @@ -463,9 +556,15 @@ class NameDisplay(object): 'c' : call = callname 'x' : common = nick name if existing, otherwise first first name (common name) 'i' : initials = initials of the first names - 'y' : patronymic = patronymic surname (father) - 'o' : notpatronymic = surnames without patronymic 'm' : primary = primary surname (main) + '0m': primary[pre]= prefix primary surname (main) + '1m': primary[sur]= surname primary surname (main) + '2m': primary[con]= connector primary surname (main) + 'y' : patronymic = pa/matronymic surname (father/mother) - assumed unique + '0y': patronymic[pre] = prefix " + '1y': patronymic[sur] = surname " + '2y': patronymic[con] = connector " + 'o' : notpatronymic = surnames without pa/matronymic and primary 'r' : rest = non primary surnames 'p' : prefix = list of all prefixes 'q' : rawsurnames = surnames without prefixes and connectors @@ -493,12 +592,24 @@ class NameDisplay(object): "i": ("''.join([word[0] +'.' for word in ('. ' + first).split()][1:])", "initials", _("initials")), - "y": ("_raw_patro_surname(raw_surname_list)", "patronymic", - _("patronymic")), - "o": ("_raw_nonpatro_surname(raw_surname_list)", "notpatronymic", - _("notpatronymic")), "m": ("_raw_primary_surname(raw_surname_list)", "primary", _("Name|primary")), + "0m":("_raw_primary_prefix_only(raw_surname_list)", + "primary[pre]", _("primary[pre]")), + "1m":("_raw_primary_surname_only(raw_surname_list)", + "primary[sur]",_("primary[sur]")), + "2m":("_raw_primary_conn_only(raw_surname_list)", + "primary[con]", _("primary[con]")), + "y": ("_raw_patro_surname(raw_surname_list)", "patronymic", + _("patronymic")), + "0y":("_raw_patro_prefix_only(raw_surname_list)", "patronymic[pre]", + _("patronymic[pre]")), + "1y":("_raw_patro_surname_only(raw_surname_list)", "patronymic[sur]", + _("patronymic[sur]")), + "2y":("_raw_patro_conn_only(raw_surname_list)", "patronymic[con]", + _("patronymic[con]")), + "o": ("_raw_nonpatro_surname(raw_surname_list)", "notpatronymic", + _("notpatronymic")), "r": ("_raw_nonprimary_surname(raw_surname_list)", "rest", _("Remaining names|rest")), "p": ("_raw_prefix_surname(raw_surname_list)", "prefix", @@ -591,6 +702,9 @@ class NameDisplay(object): match_pattern = mat.group(0) # the matching pattern # prefix, code, suffix: p, code, s = re.split("%(.)", match_pattern) + if code in '0123456789': + code = code + s[0] + s = s[1:] field = d[code.lower()][0] if code.isupper(): field += ".upper()" @@ -630,9 +744,7 @@ def fn(%s): func = self._gen_raw_func(format_str) self.__class__.raw_format_funcs[format_str] = func - s = func(raw_data) - return ' '.join(s.split()) - + return cleanup_name(func(raw_data)) def _format_str_base(self, first, surname_list, suffix, title, call, nick, famnick, format_str): @@ -646,9 +758,15 @@ def fn(%s): '%c' : callname '%x' : nick name if existing, otherwise first first name (common name) '%i' : initials of the first names - '%y' : patronymic surname (father) - '%o' : surnames without patronymic '%m' : primary surname (main) + '%0m': prefix primary surname (main) + '%1m': surname primary surname (main) + '%2m': connector primary surname (main) + '%y' : pa/matronymic surname (father/mother) - assumed unique + '%0y': prefix " + '%1y': surname " + '%2y': connector " + '%o' : surnames without patronymic '%r' : non-primary surnames (rest) '%p' : list of all prefixes '%q' : surnames without prefixes and connectors @@ -669,7 +787,7 @@ def fn(%s): except (ValueError, TypeError,): raise NameDisplayError, "Incomplete format string" - return ' '.join(s.split()) + return cleanup_name(s) #------------------------------------------------------------------------- diff --git a/src/gen/lib/name.py b/src/gen/lib/name.py index 81620e476..ae5f39ce8 100644 --- a/src/gen/lib/name.py +++ b/src/gen/lib/name.py @@ -57,8 +57,9 @@ class Name(SecondaryObject, PrivacyBase, SurnameBase, SourceBase, NoteBase, LNFN = 1 # last name first name FNLN = 2 # first name last name FN = 4 # first name + LNFNP= 5 # primary name primconnector rest, given pa/ma suffix, primprefix - NAMEFORMATS = (DEF, LNFN, FNLN, FN) + NAMEFORMATS = (DEF, LNFN, FNLN, FN, LNFNP) #deprecated : PTFN = 3 # patronymic first name diff --git a/src/gui/configure.py b/src/gui/configure.py index c45494d18..6cab13bfe 100644 --- a/src/gui/configure.py +++ b/src/gui/configure.py @@ -102,16 +102,18 @@ class DisplayNameEditor(ManagedWindow.ManagedWindow): Title - title (Dr., Mrs.) Suffix - suffix (Jr., Sr.) Call - call name Nickname - nick name Initials - first letters of Given Common - nick name, otherwise first of Given - Primary - primary surname (main) Familynick - family nick name - Patronymic - father's surname Notpatronymic- all surnames, except patronymic - Prefix - all prefixes (von, de) Rawsurnames - surnames (no prefixes and connectors) - Rest - non primary surnames + Primary, Primary[pre] or [sur] or [con]- full primary surname, prefix, surname only, connector + Patronymic, or [pre] or [sur] or [con] - full pa/matronic surname, prefix, surname only, connector + Familynick - family nick name Prefix - all prefixes (von, de) + Rest - non primary surnames Notpatronymic- all surnames, except pa/matronymic & primary + Rawsurnames- surnames (no prefixes and connectors) + UPPERCASE keyword forces uppercase. Extra parentheses, commas are removed. Other text appears literally. Example: 'Dr. Edwin Jose von der Smith and Weston Wilson Sr ("Ed") - Underhills' Edwin Jose is given name, von der is the prefix, Smith and Weston surnames, - Wilson patronymic surname, Dr. title, Sr suffix, Ed nick name, + and a connector, Wilson patronymic surname, Dr. title, Sr suffix, Ed nick name, Underhills family nick name, Jose callname. """)) label.set_use_markup(True)