3

Using ArcGIS Desktop 10.2.2, Advanced license. I created a new coded domain for a string field. I added the domain to an existing field. When I edit the features, i would expect to get a list of the coded values from the domain as a dropdown menu. This is not happening. What am I missing - is there a simple check mark or radio button setting?

  • Your expectation is what I observe whenever I do this. I recommend that you edit your question to list all your steps in detail with pictures. By doing this I suspect that you will spot something astray in your procedure but if not then we will know exactly what you did, and be in a much better position to provide an answer. – PolyGeo Aug 7 '14 at 21:55
  • If, as I suspect, the original poster had this question while working through Exercise 13b in "Esri ArcGIS Desktop Associate Certification Study Guide," as I did, then maffa's answer regarding subtypes is spot on. See the web page on Geonet titled "Errata sheet for Desktop Associate Study Guide book." There is a link to download the errata sheet on there. – Leta Rogers Jul 20 '16 at 23:14
3

Make sure subtypes have not been defined for one of the fields in the feature class you are assigning a domain to. In the Feature Class Properties, choose "Subtypes". If a subtype field has been defined, click into each row in the table "Subtypes" and add the domain in the table "Default Values and Domains" below. A dropdown menu will appear only for the features belonging to one of the subtypes for which you have added the domain.

If your feature class contains subtypes, it is not enough to see the domain assigned to the correct field in the "Fields" tab of the Feature Class Properties.

| improve this answer | |
  • Do you have any ESRI sources that document this? – Simon.y Dec 17 '18 at 21:24
0

maffa's answer can be carried out programmatically using the optional 'subtype_code' parameter of arcpy.AssignDomainToField_management() where (all) the subtype codes and descriptions can be given as a list of strings e.g. ["0: Unknown", "1: Concrete", "2: Asphalt"]

| improve this answer | |
0

The below function consistently adds coded text domains, forcefully if necessary. This function will remove any existing domains of the same name from the geodatabase (including from any existing subtypes if necessary), add it back and apply it to the provided list of features (including within any subtypes that exist). There are also options to set defaults and populate any empty fields with the default value. One caveat, the domain name and field name must match, but that could be changed fairly easily if needed.

Thanks to maffa and nlibassi for the solution and inspiration. Also, adding the domain twice was inspired by jinskipesri-southafrica-esridist in this thread https://community.esri.com/thread/120676. Not sure why it works, but it does. Finally, credit to rvburton (see https://community.esri.com/thread/198384-how-to-remove-domain-from-field-for-gdb) for the portion of this script that removes domains from subtypes.

def AddCodedTextDomain(feature_list, workspace, domain_name, code_list,
                       assign_default=False, populate_default=False):
    """
    Applies the code_list as a domain to the list of feature classes.
    Domain must be the same as the field name to which it is being applied.
    :param feature_list: list of feature classes
    :param workspace: the project's unique gdb
    :param domain_name: name of the domain as a string, must be same as name
    of field to which it is applied
    :param code_list: list of codes as strings
    :param assign_default: True to assign the first code in the code_list as
    default
    :param populate_default: True to populate existing features with the
    default code
    :return: None
    """
    # Create unique list from provided
    uniqueCodes = []
    for code in code_list:
        if code not in uniqueCodes:
            uniqueCodes.append(code)
    # Check for existence of domain; update domain if present, add domain if not
    desc = arcpy.Describe(workspace)
    domains = desc.domains
    if domain_name in domains:
        arcpy.AddMessage(domain_name + " is already specified as a domain")
        try:
            # try removing from all fields in all feature classes
            existingFeatures = arcpy.ListFeatureClasses()
            for existingFeature in existingFeatures:
                fields = arcpy.ListFields(existingFeature)
                for field in fields:
                    if field.domain == domain_name:
                        arcpy.RemoveDomainFromField_management(existingFeature,
                                                                field.name)
                        arcpy.AddMessage(domain_name + " domain removed from "
                                            + existingFeature + " " + field.name
                                            + " field")
                # try removing from all fields in all subtypes
                # Credit to:(https://community.esri.com/thread/
                # 198384-how-to-remove-domain-from-field-for-gdb)
                subtypes = arcpy.da.ListSubtypes(existingFeature)
                for stcode, stdict in list(subtypes.items()):
                    for stkey in list(stdict.keys()):
                        # if there is a Subtype Field
                        if not stdict['SubtypeField'] == '':
                            st_code = "'{}: {}'".format(stcode, stdict['Name'])
                        # if no Subtype Field, use "#" in RemoveDomainFromField
                        # for subtype_code
                        else:
                            st_code = "#"
                        if stkey == 'FieldValues':
                            fields = stdict[stkey]
                            for field, fieldvals in list(fields.items()):
                                # if field has a domain
                                if not fieldvals[1] is None:
                                    # and the domain is in our list
                                    if fieldvals[1].name == domain_name:
                                        # remove the domain
                                        arcpy.AddMessage(fieldvals[1].name
                                                            + " domain removed "
                                                            + "from " + existingFeature
                                                            + " field: " + field
                                                            + " subtype: " + st_code)
                                        arcpy.RemoveDomainFromField_management(
                                            existingFeature, field, st_code)

            arcpy.DeleteDomain_management(workspace, domain_name)
            arcpy.CreateDomain_management(workspace, domain_name,
                                            "Valid " + domain_name + "s",
                                            "TEXT", "CODED")

            for code in uniqueCodes:
                arcpy.AddCodedValueToDomain_management(workspace, domain_name,
                                                        code, code)
            for feature in feature_list:
                try: 
                    arcpy.AssignDomainToField_management(feature, domain_name,
                                                        domain_name)
                    # Check to make sure subtypes exist
                    subtypes = arcpy.da.ListSubtypes(feature)
                    if len(subtypes) == 1 and subtypes[0]['SubtypeField'] == '':
                        pass
                    else:
                        st_codes = [str(stcode) for stcode, stdict in list(subtypes.items())]
                        arcpy.AssignDomainToField_management(feature, domain_name,
                                                            domain_name, st_codes)

                except arcpy.ExecuteError:
                    arcpy.AddMessage("--------------------------------"
                                     "\n" + domain_name
                                     + " domain for feature \n\n"
                                     + str(feature) + "\n\n"
                                     + "could not be updated. Use "
                                     "caution when populating attribute\n"
                                     "---------------------------------")
            arcpy.AddMessage(domain_name + " domain updated")

        except arcpy.ExecuteError:
            arcpy.AddMessage(domain_name + " domain could not be updated. Use "
                             "caution when populating attribute")
    else:
        arcpy.CreateDomain_management(workspace, domain_name,
                                      "Valid " + domain_name + "s",
                                      "TEXT", "CODED")
        for code in uniqueCodes:
            arcpy.AddCodedValueToDomain_management(workspace, domain_name,
                                                   code, code)
        for feature in feature_list:
            try: 
                arcpy.AssignDomainToField_management(feature, domain_name,
                                                        domain_name)
                # Check to make sure subtypes exist
                subtypes = arcpy.da.ListSubtypes(feature)
                if len(subtypes) == 1 and subtypes[0]['SubtypeField'] == '':
                    pass
                else:
                    st_codes = [str(stcode) for stcode, stdict in list(subtypes.items())]
                    arcpy.AssignDomainToField_management(feature, domain_name,
                                                        domain_name, st_codes)
                arcpy.AddMessage(domain_name + " domain updated")

            except arcpy.ExecuteError:
                arcpy.AddMessage(domain_name + " domain could not be updated. Use "
                                 "caution when populating attribute")

    # Assign the first value as the default
    if assign_default:
        for feature in feature_list:
            subtypes = arcpy.da.ListSubtypes(feature)
            st_codes = [str(stcode) for stcode, stdict in list(subtypes.items())]
            arcpy.AssignDefaultToField_management(feature, domain_name, 
                                                  uniqueCodes[0], st_codes)

    # Populate field with default values if Null
    if populate_default:
        arcpy.AddMessage("Populating default values")
        for feature in feature_list:
            where_clause = "{0} = '' OR {0} IS NULL".format(
                arcpy.AddFieldDelimiters(feature, domain_name)
                )
            with arcpy.da.UpdateCursor(feature, domain_name, where_clause) as cursor:
                for row in cursor:
                    row[0] = uniqueCodes[0]
                    cursor.updateRow(row)

Last caveat, I accept no liability if this blows up your geodatabase, just trying to help!

| improve this answer | |

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.