Hey, how can I change the color of shadow produced...
# compose
a
Hey, how can I change the color of shadow produced by
drawShadow()
modifier? I’m trying to make neumorphism design components. It would be great to have more control on shadows similar to the
box-shadow
property in CSS.
👀 1
👍 2
l
Someone with more direct knowledge can probably say more here, but I think the short answer is “you can’t right now” but I’d like that to not be the case. IIUC, we are hashing out some details about how/if we could support this on earlier API levels where the graphics layer didn’t support it natively
i think for API 28+ (or something like that) you can probably copy the drawShadow modifier and add the parameter if you want to get something working in the near term
also feel free to file a bug on this, it might help send signal on its importance, especially i we can understand your use case more
s
hm, I thought Compose draw shadows on its own 🤔
l
right now we try to use the platform’s canvas, which can draw shadows more efficiently than we can at the compose layer
we might do it ourselves to provide the fallback behavior though
or alternatively, bundle a newer version of skia on older APIs… but that comes with its own bag of trouble
🤗 2
s
Enlarged apk size due to Skia libs bundling can be reduced by using the AppBundle. Flutter is bundling with everything required and the release apk size around 4mb, which in my opinion is pretty small. Or what else problems are you talking about?
l
unlike flutter, we built compose to be embedded in a View hierarchy pretty seamlessly
☹️ 1
so switching canvas implementations in the middle of that is not… easy/cheap/fun
its not just about bundle size
☹️ 1
s
I was about to suggest if a developer needs more advanced graphics capabilities lets give him an extra
compose-skia
module or something like that. Which will not be a part of the Core but can be imported as a library like any other
Jetpack
library. ☹️
l
it might be possible. like i said earlier, i’m not directly involved w/ this and i’m not a graphics programmer so i’m not the best person to comment on the tradeoffs
👍 1
s
Probably @romainguy could suggest something. Anyway thanks for the discussion.
l
👍
r
This would make interoperability with views a lot less seamless
And potentially not possible with the way we do it now
☹️ 1
4 MiB is also a lot for many apps
👍 2
l
yeah, we already have to fight to justify kotlin stdlib
s
I forgot when last time seen a production app smaller than 4Mib.
r
Here’s a simple example, the Square Cash app is ~14 MiB
Adding 4 MiB is a large % of their existing size
We know a lot of developers do care about deployment size
I wish it wasn’t the case, it would make our life easier
s
Sad... Designers like to draw colorful and animated shadows.
r
Note that you can color shadows as of API 28 (if I recall properly)
s
You are correct in API 28 we can adjust elevation color. But API 28 still far from regular development
@romainguy, @Leland Richardson [G] thanks for the discussion. It inspired me to try to implement some sort of asynchronous software shadows rendering. I did something similar with a regular android view. I had to create a dynamic ambient light behind ImageView with a random picture. The "shadow" was baked on background thread by downscaling and blurring the picture. Probably I could "pre-render" several frames to be able to simulate a shadow animation. But the thing is I need to figure out what is the best way to integrate this with Compose. In terms of recomposition, shadow computation, and seamless integration. ✌️
g
right now we try to use the platform’s canvas, which can draw shadows more efficiently than we can at the compose layer
It may sounds reasonable if you expect that standard shadows are more common, but on practice we just replace native shadow with 9-patch or include a couple nested layouts with shadow background just to emulate shadow which designers want I think compose definitely need custom shadow drawing modifier, even if it wouldn’t be perfectly efficient, because all ad-hoc solutions which we use probably even less efficient and often looks not so good Now we are on position when we struggle with every custom shadow (and we have a lot of them, design team is not happy with standard material ones) and it makes developer sad when we implement it properly for every case and it makes designers sad if it was not implemented as they expected (when we cheat and use cardview or elevation for elements to avoid custom shadows)
and it’s not only about shadow color, but also intensity of shadow, low elevation material shadows looks as borders, so you cannot change it to make less intensive to make looks the same
l
@gildor i agree with you. I want to have a fully featured shadow, where it makes the efficient choices when possible as an implementation detail. It is a bit concerning though if there is a huge performance cliff when you tweak one parameter innocently. We would have to figure out the right way to message this or lint or something if it became a problem
g
Maybe having 2 shadow modifiers would be more explicit: drawShadow - for platfrom native shadows drawCustomShadow - for own implementation which supports color, position etc
l
yeah that’s not a bad idea. will make sure we consider that
it gets tricky though if some of it depends on which platform you’re on
because then its not which api you decide to use, its which platform is the code running on
g
drawCustomShadow also may use optimal platforrm implementation if API level is high enough and fallback to custom drawing otherwise
a
I just remember from RenderScript that is was incredibly frustrating that your code would sometimes just suddenly decide to run on the slow path, and there wasn't any obvious reason why
l
yeah. it’s not frustrating until it is. and then it really is.
r
It’s unfortunately common to any solution that relies on hardware acceleration
Anyway, for many cases we could generate 9patches or emulate shadows on the fly with gradients/vertex fields, based on which parameters are set
But that would still mean either performance cliffs or correctness exceptions (good old convex shapes for instance)
a
Sure Leland, I’m opening a bug on this. What I as a user see is the current implementation is oriented towards material specs, shadow is dependent on elevation of view. But a UI toolkit should be able to cater other design languages as well. Just like TextField is raw and bare bones but its implementation is provided in Material Design module. Shadow should also be customisable, eg. its opacity, radius, the sides, color etc
3
One more reason I could give is, even in physical world all shadows are not grey/black. A opaque object cast the shadow of its own color.
l
Thank you for filling! I completely agree
👍 2
r
The 3d rendering engineer in me has to be pendantic here: an opaque object certainly does not cast a colored shadow no. A transparent object would, but that's a wrong way to think about it. Shadows are the absence of light, not the presence of something. Any coloration you may see is either transmitted (transparent objects) or received from other light sources (including light bounces). And if you want to go by the physical world analogy then material shadows are the right shadows (since they are properly computed by projecting a light area through an object). What you are asking for is non physically based shadows. End of the pendantic sidebar :))
😂 7
a
Oops I meant to say Translucent. So I stand corrected. But please also understand that material design just assumes the light source is at the above the surface/top. This assumption alone limits many design implementation which I'm talking about. Allowing to change color can give us ability to change the light source and possibly glow effect. Here are the example designs-
r
I'm aware of such designs yes. That's why recent versions of Android let you move the light source and change colors btw. Anyway I'm not disputing the need for more customization.
👌 1
👍 3
c
@Ankur Gupta my designer asked me to implement something like this today. Do you have a link to the bug so I can star it?
a