Select to view content in your preferred language

Apply the same colors to line and point layers with matching field values

132
5
Jump to solution
a week ago
JohnGoat
Occasional Contributor

Hello,

In ArcGIS Pro, I have two layers: one Line and one Point. Both have a field named SEB, and this field contains the same values.

For the line layer, I applied Unique Values symbology based on the SEBfield. This created about 40,000 groups, each with a different color.

Now I want to apply the same symbology to the point layer. However, ArcGIS Pro automatically assigns different colors. What I need is: if the value in the SEB field is the same, then the point layer should use the same color as the line layer.

JohnGoat_0-1759397924610.png

 

How can I do this in ArcGIS Pro?
Thanks!

0 Kudos
2 Solutions

Accepted Solutions
Robert_LeClair
Esri Esteemed Contributor

@JohnGoat - so I'm wondering if you can setup attribute driven symbology for the SEB field?  You can learn more about how to do this workflow here:

Attribute-driven symbology—ArcGIS Pro | Documentation
Setting up the attribute-driven color in symbology... - Esri Community

View solution in original post

0 Kudos
BrennanSmith1
Frequent Contributor

This could be done with arcpy and CIM.  This is not a robust script, but it worked on my test data. Fingers crossed you can just update `pts` and `lines` and it will work for you too.

'''
This script assumes you already have both layers set up with unique symbology on the target field.
It will only update colors in the points for unique values also found in the lines
It will not change symbology rendering style (e.g. Unique Values vs Single Symbol vs Graduated Colors)
It will only work if every color is set up in HSV space (having RGB colors will break it)
'''
import arcpy

## Define your point and line layers in the TOC, and the common Field Name for symbology
pts = r"point"
lines = r"lines"

aprx = arcpy.mp.ArcGISProject("CURRENT")
m = aprx.activeMap

line_lyr = m.listLayers(lines)[0]
pt_lyr = m.listLayers(pts)[0]

## Define a dictionary of field value and color definition
d_color = {}
for group in line_lyr.symbology.renderer.groups:
    for item in group.items:
        val = item.values[0][0]
        color = item.symbol.color
        d_color[val] = color
        
## Update symbology of the points
cim = pt_lyr.getDefinition('V2')
for group in cim.renderer.groups:
    for cls in group.classes:
        #get name
        val = cls.values[0].fieldValues[0]
        # color goes here
        cls.symbol.symbol.symbolLayers[0].markerGraphics[0].symbol.symbolLayers[1].color.values = d_color[val]['HSV']
        
pt_lyr.setDefinition(cim)

View solution in original post

0 Kudos
5 Replies
Robert_LeClair
Esri Esteemed Contributor

@JohnGoat - so I'm wondering if you can setup attribute driven symbology for the SEB field?  You can learn more about how to do this workflow here:

Attribute-driven symbology—ArcGIS Pro | Documentation
Setting up the attribute-driven color in symbology... - Esri Community

0 Kudos
JohnGoat
Occasional Contributor

 

.

 

 

0 Kudos
BrennanSmith1
Frequent Contributor

This could be done with arcpy and CIM.  This is not a robust script, but it worked on my test data. Fingers crossed you can just update `pts` and `lines` and it will work for you too.

'''
This script assumes you already have both layers set up with unique symbology on the target field.
It will only update colors in the points for unique values also found in the lines
It will not change symbology rendering style (e.g. Unique Values vs Single Symbol vs Graduated Colors)
It will only work if every color is set up in HSV space (having RGB colors will break it)
'''
import arcpy

## Define your point and line layers in the TOC, and the common Field Name for symbology
pts = r"point"
lines = r"lines"

aprx = arcpy.mp.ArcGISProject("CURRENT")
m = aprx.activeMap

line_lyr = m.listLayers(lines)[0]
pt_lyr = m.listLayers(pts)[0]

## Define a dictionary of field value and color definition
d_color = {}
for group in line_lyr.symbology.renderer.groups:
    for item in group.items:
        val = item.values[0][0]
        color = item.symbol.color
        d_color[val] = color
        
## Update symbology of the points
cim = pt_lyr.getDefinition('V2')
for group in cim.renderer.groups:
    for cls in group.classes:
        #get name
        val = cls.values[0].fieldValues[0]
        # color goes here
        cls.symbol.symbol.symbolLayers[0].markerGraphics[0].symbol.symbolLayers[1].color.values = d_color[val]['HSV']
        
pt_lyr.setDefinition(cim)
0 Kudos
JohnGoat
Occasional Contributor

@BrennanSmith1 Thank you so much  JohnGoat_0-1760014934572.png

 

I didn't implement it very quickly and it didn't work. But from there, I revised it a bit and it worked perfectly.

0 Kudos
JohnGoat
Occasional Contributor

 

This is the code that works for me

import arcpy

# Layer names
line_layer_name = "FIDER"                     # Name of the line layer
point_layer_name = "Structure_Junction_NO_UN" # Name of the point layer

# Field names used for symbology
line_field = "Trace_Start_Point"  # Field used for symbology in the line layer
point_field = "FIDER"             # Field used for symbology in the point layer

# Get the current project and map
aprx = arcpy.mp.ArcGISProject("CURRENT")
m = aprx.activeMap
line_layer = m.listLayers(line_layer_name)[0]
point_layer = m.listLayers(point_layer_name)[0]

# Read color definitions from the line layer
color_dict = {}
sym = line_layer.symbology

if hasattr(sym, "renderer") and hasattr(sym.renderer, "groups"):
    for group in sym.renderer.groups:
        for item in group.items:
            val = item.values[0][0]    # Class value (e.g., Fider name)
            color = item.symbol.color  # Symbol color for that class
            color_dict[val] = color    # Store value-color pair in dictionary
else:
    arcpy.AddWarning("'Unique Values' symbology not found in the line layer!")

# Get the CIM (Cartographic Information Model) definition of the point layer
cim = point_layer.getDefinition('V2')

# Update the symbology colors of the point layer based on the line layer
for group in cim.renderer.groups:
    for cls in group.classes:
        try:
            val = cls.values[0].fieldValues[0]  # Class value (e.g., Fider name)
            if val in color_dict:
                color = color_dict[val]

                # Support both RGB and HSV color models
                if 'RGB' in color:
                    cls.symbol.symbol.symbolLayers[0].markerGraphics[0].symbol.symbolLayers[1].color.values = color['RGB']
                elif 'HSV' in color:
                    cls.symbol.symbol.symbolLayers[0].markerGraphics[0].symbol.symbolLayers[1].color.values = color['HSV']

        except Exception as e:
            arcpy.AddWarning(f"Color could not be assigned for {val}: {e}")

# Apply the updated symbology to the point layer
point_layer.setDefinition(cim)
arcpy.AddMessage("Point layer colors successfully updated based on the line layer!")

 

 

JohnGoat_0-1760014772515.png

 

 

0 Kudos