Android 中的椭圆形渐变

发布于 2024-09-15 04:16:37 字数 493 浏览 5 评论 0原文

我知道如何设置和显示椭圆形。我知道如何对这个形状应用渐变。我不知道如何获得椭圆形渐变来匹配形状。

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
       android:shape="oval" >
    <gradient
        android:startColor="#66FFFFFF"
        android:endColor="#00FFFFFF"
        android:gradientRadius="100"
        android:type="radial" />
</shape>

如果你能想象得到,这个渐变在中间有半透明的白光,然后在边缘渐变到 alpha 零。我需要让它以椭圆形出现,而不仅仅是圆形渐变。我怎样才能实现这个目标?

I know how to setup and display an oval shape. I know how to apply a gradient to this shape. What I cant figure out is how I can get an oval gradient to match the shape.

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
       android:shape="oval" >
    <gradient
        android:startColor="#66FFFFFF"
        android:endColor="#00FFFFFF"
        android:gradientRadius="100"
        android:type="radial" />
</shape>

If you can imagine, this gradient has a semi transparent white glow in the middle, then fades to alpha zero at the edges. I need to get it to go out in an oval shape, not just a circular gradient. How can I achieve this?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

烟凡古楼 2024-09-22 04:16:38
<?xml version="1.0" encoding="utf-8"?>

<stroke android:width="1dp" android:color="#ffffffff" />

<size
    android:width="40dp"
    android:height="40dp"/>

<gradient
    android:type="radial"
    android:startColor="#ffff0000"
    android:endColor="#330000ff"
    android:gradientRadius="40dp"
    android:angle="270"
    android:centerX=".5"
    android:centerY=".5"/>

<?xml version="1.0" encoding="utf-8"?>

<stroke android:width="1dp" android:color="#ffffffff" />

<size
    android:width="40dp"
    android:height="40dp"/>

<gradient
    android:type="radial"
    android:startColor="#ffff0000"
    android:endColor="#330000ff"
    android:gradientRadius="40dp"
    android:angle="270"
    android:centerX=".5"
    android:centerY=".5"/>

夏天碎花小短裙 2024-09-22 04:16:38

这很困难,因为以这种方式定义的可绘制对象在运行时自行绘制,适应您放置它们的空间。如果您必须在代码中执行此操作,最好的解决方案是采用您在 XML 中定义的可绘制形状并绘制它作为一个完美的圆放在画布上或位图中。此时,渐变图案将遵循形状轮廓。一旦形状被绘制到静态上下文中,您就可以将形状添加到视图中(比方说,作为背景),当它尝试适应视图边界时,这会将其扭曲成椭圆形。既然你有一个图像,整个事物就会按比例扭曲。

希望这种方法的像素不会太差。

This is difficult since drawables defined in this fashion draw themselves at runtime, adapting to the space you put them in. Your best solution, if you must do this in code, would be to take the shape drawable you have defined in XML and draw it onto a Canvas or into a Bitmap as a perfect circle. At this point, the gradient pattern will follow the shape outline. Once the shape has been drawn into a static context you can add the shape to a view (as a background, let's say), which will distort it into an oval when it tries to fit the view bounds. Since you have an image, the whole thing will distort proportionately.

Hopefully, it won't pixel too bad with this method.

挽袖吟 2024-09-22 04:16:38

我发现的另一个解决方法是使用scaleX =“1.x”或scaleY =“1.x”。然而,这与形状不相符。

Another workaround that I found is to use scaleX="1.x" or scaleY="1.x". However, this dose not match the shape.

恰似旧人归 2024-09-22 04:16:38

一种“愚蠢但有效”的方法是绘制椭圆轮廓​​,然后绘制具有相同“中心”的多个嵌套椭圆,其大小和颜色随着椭圆变小而变化,一直到一个像素椭圆。
如果您自定义渐变编码,请在 HSV 中插入颜色,而不是在 RVB 中!

A "dumb but working" way to do this would be to draw your ellipse contour, then a multitude of nested ellipses with the same "center", whose sizes and colors change as the ellipses grow smaller, all the way to a one-pixel ellipse.
If you custom code your gradient, interpolate the colors in HSV, not in RVB !

情深已缘浅 2024-09-22 04:16:37

我建议更“直接”的绘图方法。如果您可以逐像素绘制渐变,那么您只需要记住,对于

  • 圆形,渐变颜色与r
  • 椭圆形(椭圆形) 渐变颜色与r1+r2成正比

,这里:

r - 到圆心的距离

r1,r2 - 到椭圆两个焦点的距离

编辑:
考虑这个像素着色器代码:

uniform sampler2D tex;

void main()
{
    vec2 center = vec2(0.5,0.5);
    float len = 1.3*(distance(gl_TexCoord[0].xy,center));
    vec2 foc1 = vec2(len,0.);
    vec2 foc2 = vec2(-len,0.);
    float r = distance(center+foc1,gl_TexCoord[0].xy) +
             distance(center+foc2,gl_TexCoord[0].xy);
    float k = pow(r*0.9,1.3);
    vec4 color = vec4(k,k,k,1.);
    gl_FragColor = color;
}

你会得到类似这样的椭圆形:
alt text

祝你好运

I would suggest more 'direct' drawing approach. If you can draw gradient pixel-by-pixel, then you need just to remember that for

  • circle gradient color is proportional to r
  • ellipse (oval) gradient color is proportional to r1+r2

Here:

r - distance to circle center

r1,r2 - distances to two foci of ellipse

EDIT:
Consider this Pixel Shader code:

uniform sampler2D tex;

void main()
{
    vec2 center = vec2(0.5,0.5);
    float len = 1.3*(distance(gl_TexCoord[0].xy,center));
    vec2 foc1 = vec2(len,0.);
    vec2 foc2 = vec2(-len,0.);
    float r = distance(center+foc1,gl_TexCoord[0].xy) +
             distance(center+foc2,gl_TexCoord[0].xy);
    float k = pow(r*0.9,1.3);
    vec4 color = vec4(k,k,k,1.);
    gl_FragColor = color;
}

You will get oval something like that:
alt text

good luck

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文