I was recently working on a project that needed something like 100 unique symbols. Each symbol was a circle or square with a four letter code on it. This is something that lent itself perfectly to being done programatically. I really didn't want to have to generate those symbols one by one, so I started searching of ways to do this programatically, but didn't find much information on how I might get this done using Python.
The first glimmer of hope was when I found how to apply symbols from style gallery (i.e. Favorites or project Styles .stylx). I had accepted the fact that I'd just programatically create a bunch of png's, add them to my Favorites, and then write some code to apply the symbols in my Pro project. Then I stumbled upon an Esri blog post that mentioned that .stylx files are just SQLite databases. This got me thinking that I'd be able to further program the generation of these symbols.
I used DB Browser for SQLite to take a look at the structure of the .stylx db. Most of what you need is stored in the ITEMS table. There's a content field where the json representation of the symbol is stored. For some reason, the json string has a character at the end that makes DB Browser think it's a blob instead of text. If you delete the 00 at the end, it will then display as text and you can get an idea of what the json looks like for a CIMPointSymbol for example.
Things to know about the .stylx file:
I broke my code up into two python scripts. Here's the pseudocode and some real code for each script:
Generate symbols - programmatically generate symbols and add to your Favorites .stylx
execute sql code to insert row into db
new_row = (new_id,3,'',code,'rgb;black',json.dumps(new_sym),code)
commit changes to db and close db
cursor.execute('INSERT INTO ITEMS(ID, CLASS, CATEGORY, NAME, TAGS, CONTENT, KEY) VALUES(?,?,?,?,?,?,?)', new_row)
At this point, I now have a bunch of new symbols in my .stylx file. While testing I worked on a copy of my Favorites.stylx, but as long as Pro is closed, I don't think there's any issues with working on the real file in its default location ("C:\Users\userxxxx\AppData\Roaming\ESRI\ArcGISPro\Favorites.stylx"). Just make sure you have a backup copy of it just in case you ruin it.
Apply symbols - as long as the name of your new symbols matches the symbol item values in your Pro project, it's relatively easy to apply the symbology programmatically
m = p.listMaps('Map')
lyr = m.listLayers("layer name")
sym = lyr.symbology
for grp in sym.renderer.groups:
for item in grp.items:
I hope this helps someone that found themselves in the same position that I was. If anyone needs any more details on how this was done, just let me know.
Here's a list of posts that I found while searching how to do this