Opened 9 years ago
Closed 6 years ago
#545 closed defect (fixed)
Volume API for setting surface colors is not intuitive
Reported by: | Owned by: | Tom Goddard | |
---|---|---|---|
Priority: | major | Milestone: | |
Component: | Volume Data | Version: | |
Keywords: | Cc: | ||
Blocked By: | Blocking: | ||
Notify when closed: | Platform: | all | |
Project: | ChimeraX |
Description
Hi all,
I have something strange going on when I try to create multiple volumes (different crystallographic maps) and group them under a single Model: whatever color I initialise them with is ignored, and they just come out the default grey. I don't have a nice compact code example, but the basic flow in pseudocode is:
DEFAULT_SOLID_MAP_COLOR = [0,255,255,153] # Transparent cyan
DEFAULT_DIFF_MAP_COLORS = 0,255,0,153],[255,0,0,153
master_model = Model('map display', session)
for m in map_list:
data = numpy.empty(dim, numpy.double)
grid_data = Array_Grid_Data(data, origin, step, cell_angles)
volume = Volume(grid_data, session)
fill_volume_data(m, data)
volume.initialize_thresholds()
master_model.add([volume])
if not m.is_difference_map:
contour_val = [standard_contour] # single value
volume.set_color(DEFAULT_SOLID_MAP_COLOR)
else:
contour_val = [standard_difference_map_contours] # two levels
volume.set_colors(DEFAULT_DIFF_MAP_COLORS)
for cv in contour_val:
volumecommand.volume(session, [volume], level=cv, cap_faces = False)
volume.show()
session.models.add(master_model)
After this, I have the following results (where I have loaded two normal maps and one difference map):
for v in volumes:
print(v.colors)
[[ 0 255 0 153]
[255 0 0 153]]
178 178 178 255
178 178 178 255
So set_colors() has set the correct color values for the (two level) difference map - but both contours are displayed on screen as flat white and solid. Meanwhile, the other two maps have their colours recorded as the default grey, but in the display they're transparent (but still grey). Changing their values from the console, either by set_color()/set_colors() or v.color = [rgba] does not change the displayed colours. Using the direct equality or set_colors() changes the result of print(v.colors), whereas set_color() doesn't.
Cheers,
Tristan
Follow-up: I see I have my handling of multiple contour levels mixed up. I'll have a closer read of volumecommand to work that out. In other news, when I use the command-line interface to do:
vol #2.1 level 0.099 color 0,100,0,60 cap_faces False level -0.099 color 100,0,0,60
... it works correctly. I'll have a closer look through the code to see where I'm going wrong.
OK, I can set these by following through the logic in volumecommand.level_and_color_settings(), but the behaviour at that higher level still seems rather counter-intuitive.
Change History (8)
comment:1 by , 9 years ago
follow-up: 2 comment:2 by , 9 years ago
Yep - worked out the basics of the set_parameters() call today. Works nicely once you get the hang of it. Tristan Croll Research Fellow Cambridge Institute for Medical Research University of Cambridge CB2 0XY
comment:3 by , 9 years ago
Milestone: | → Beta Release |
---|
comment:6 by , 8 years ago
Milestone: | 0.6 → 0.7 |
---|
comment:7 by , 7 years ago
Milestone: | 0.7 |
---|
comment:8 by , 6 years ago
Resolution: | → fixed |
---|---|
Status: | assigned → closed |
Summary: | Volume API not intuitive → Volume API for setting surface colors is not intuitive |
Currently volume colors can be set using the Volume.set_parameters(surface_colors = [...]) call, or by code like
for s in v.surfaces:
s.color = some color
I think these are reasonable APIs for setting the colors.
I agree the color API for Volume models is a mess. Here's an explanation, but will need some thought about how to improve it.
Volume models have multiple colors (one for each contour level, and a color map for grayscale type rendering), but you are using the base class Drawing color methods and those colors for the Volume Drawing are ignored -- in fact surfaces and image style rendering is done by child Drawing objects, not the Volume Drawing which itself draws nothing, so its colors don't matter. Colors are not inherited. When you use the set_colors() method you are in fact setting colors for two instances of the Drawing. Volumes generally don't use instances.
Some of your problems will be solved if you use the "single_color" attribute:
But for coloring two surfaces of a difference map you will need to use
I don't like this "set_parameters()" API and think there should be separate "set_colors()", "set_levels()" methods as you tried to use. Need to develop those.