Set opacity for marks but not in legend - altair

I can modify the classic Simple Scatter Plot with Tooltips, to add opacity to marks, but I'd like to legend colors to stay 100% opaque. In the chart I'm trying to make, I have a df with tens of thousands of rows.
import altair as alt
from vega_datasets import data
source = data.cars()
alt.Chart(source).mark_circle(size=60, opacity=0.1).encode(
x='Horsepower',
y='Miles_per_Gallon',
color='Origin'
)
I've tried alt.Legend's symbolOpacity and gradientOpacity to no avail
color=alt.Color(
'Origin:N',
legend=alt.Legend(
# symbolOpacity=1,
gradientOpacity=1,
)
)

As of now, this seems to be a bug with vega-lite. Per #jvp's suggestion, I've filed a bug report here
UPDATE -- IT'S FIXED

Related

Is there a way to show Altair Tooltip all the time?

I like the way tooltip looks way more than when I add text as labels for the points in my plot, is there a way to make it visible wether the mouse is on it or not?
I looked it up but haven't found any solutions, maybe with messing around with conditions?
example code from doc if you have ideas you'd like to test out :
import altair as alt
from vega_datasets import data
source = data.cars()
alt.Chart(source).mark_circle(size=60).encode(
x='Horsepower',
y='Miles_per_Gallon',
color='Origin',
tooltip=['Name', 'Origin', 'Horsepower', 'Miles_per_Gallon']
).interactive()
thank u :)
As per my comment above, I think the easiest way to do this is adding a styled text box. You can see an example of how to style it in this issue, which I also pasted below:
import altair as alt
from vega_datasets import data
cars = data.cars()
chart = alt.Chart(cars).mark_circle().encode(
alt.X('Miles_per_Gallon', scale=alt.Scale(domain=(5,50))),
y='Weight_in_lbs')
corl = cars[['Miles_per_Gallon','Weight_in_lbs']].corr().iloc[0,1]
text = alt.Chart({'values':[{}]}).mark_text(
align="left", baseline="top"
).encode(
x=alt.value(5), # pixels from left
y=alt.value(5), # pixels from top
text=alt.value([f"r: {corl:.3f}", 'Line 2']))
box = alt.Chart({'values':[{}]}).mark_rect(stroke='black', color='orange').encode(
x=alt.value(3),
x2=alt.value(50),
y=alt.value(3),
y2=alt.value(30))
chart + box + text + chart.transform_regression('Miles_per_Gallon','Weight_in_lbs').mark_line()

Configure x-axis limits after chart creation

I know I can create a chart with custom x-axis limits by, for example:
altair.Chart(source).encode(
x=altair.X("whatever", scale=altair.Scale(domain=(left_limit, right_limit))
)
But given a chart that's been created, with all the bells and whistles on the x-axis and whatnot (my actual usage is more complicated than the simple example above), how do I readjust just the x-axis limits of the chart, without having to specify all of the bells and whistles of my x-axis again???
You can access and override the attributes of the chart object after creation like this:
import altair as alt
from vega_datasets import data
source = data.cars.url
chart = alt.Chart(source).mark_circle().encode(
x=alt.X('Horsepower:Q'), #scale=alt.Scale(domain=[0, 250])),
y='Miles_per_Gallon:Q',
)
chart
chart.encoding.x.scale = alt.Scale(domain=[40, 300])
chart

Is there a way to make a bubble plot in Altair which has circles that aren't filled?

I am trying to develop a new data visualization/graphic, and the bubble plot available here is very similar to what I am trying to make in shape:
https://altair-viz.github.io/gallery/table_bubble_plot_github.html
However, the graph I am trying to make involves some shaded bubbles and some filled in. Is there a way to edit this graph so that the bubble marks are not always filled?
Thank you!
You could use the fillOpacity encoding linked to a field in your data and then set the domain and range of its scale, so that only the values you want have a completely transparent fill:
import altair as alt
from vega_datasets import data
source = data.github.url
fill_threshold = 12
alt.Chart(source).mark_circle(
stroke='black'
).encode(
x='hours(time):O',
y='day(time):O',
size='sum(count):Q',
fillOpacity=alt.FillOpacity(
'sum(count):Q',
scale=alt.Scale(
domain=[fill_threshold, fill_threshold + 0.01],
range=[0 ,1]
)
)
)
You can use the fillOpacity and stroke mark properties to make the marks into circles with no fill. For example:
import altair as alt
from vega_datasets import data
source = data.github.url
alt.Chart(source).mark_circle(
fillOpacity=0,
stroke='black'
).encode(
x='hours(time):O',
y='day(time):O',
size='sum(count):Q',
)

Tooltips not appearing for secondary plot

I’m curious why the tooltips of the 2nd plot (point_max) are not appearing in the final plot though the data points themselves are fine.
The tooltips for the first plot (rule_q) are active in the combined plot and when plotting ‘point_max’ on its own the tooltips do appear normally.
Even if the tooltips for ‘rule_q’ are removed, those for the ‘point_max’ chart never show up in the combined plot.
The relevant code:
base = alt.Chart(yrDF,title=titStr).transform_calculate(
color = 'datum.Complete > 0.95 ? "#f4be2b" : "lightgray"'
).interactive()
rule_q= base.mark_rule(size=3).encode(
alt.X('date:T'),
alt.Y('meanMinus:Q'),
alt.Y2('meanPlus:Q'),
color=alt.Color('color:N',scale=None),
href='urls:N',
tooltip=[
alt.Tooltip('date:T', title='Date',format='%b %d, %Y'),
]
)
point_max= alt.Chart(yrDF).mark_point(size=12).encode(
x=alt.X('date:T'),
y=alt.Y('max:Q'),
tooltip=[
alt.Tooltip('max:Q',format='.0f')
]
)
chart= rule_q + point_max
This is a known bug in Vega-Lite; see https://github.com/vega/vega-lite/issues/5732
A potential workaround is to add interactive() separately to each chart, rather than adding it to the base chart. See also Altair - Unable to get tooltips for one layer in a line chart.

Binding mark_geoshape rotate property to slider selection

I'm trying to recreate something similar to this vega plot in Altair.
I've had luck building the mark_geoshape maps before when binding to something like color, which can be in encode function, but I cannot for the life of me figure out how to bind the slider to the rotate property of the chart, which lives in project.
I presumed I could do something like this, but no luck:
import altair as alt
from vega_datasets import data
# Data generators for the background
sphere = alt.sphere()
graticule = alt.graticule()
# Source of land data
source = alt.topo_feature(data.world_110m.url, 'countries')
slider = alt.binding_range(min=0, max=100, step=1, name='rotate:')
selector = alt.selection_single(name="SelectorName", fields=['rotate'],
bind=slider, init={'rotate': 180})
# Layering and configuring the components
alt.layer(
alt.Chart(sphere).mark_geoshape(),
alt.Chart(graticule).mark_geoshape(stroke='white', strokeWidth=0.5),
alt.Chart(source).mark_geoshape(fill='ForestGreen', stroke='black')
).project(
'orthographic',
).encode(
rotate=['rotate',180,180]
).properties(width=600, height=400, selection=selector).configure_view(stroke=None)
Any help would be much appreciated.
Thanks
leo
There is currently no way to do this in Altair: the Vega-Lite schema only supports constant rotation values. If you wish, you can do this in Vega; there is an example at https://vega.github.io/vega/docs/projections/.

Resources