2011-08-22 69 views
27

我想要实现的是使用一个带有几个图层的Drawable,但在运行时控制一些值,例如渐变的startColor。下面是我在my_layered_shape.xml:Android - 如何以编程方式定义ShapeDrawables?

<?xml version="1.0" encoding="utf-8"?> 
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" > 
    <item> 
    <shape android:shape="rectangle"> 
     <stroke android:width="1dp" android:color="#FF000000" /> 
     <solid android:color="#FFFFFFFF" /> 
    </shape> 
    </item> 
    <item android:top="1dp" android:bottom="1dp"> 
    <shape android:shape="rectangle"> 
    <stroke android:width="1dp" android:color="#FF000000" /> 
    <gradient 
     android:startColor="#FFFFFFFF" 
     android:centerColor="#FFFFFF88" 
     android:endColor="#FFFFFFFF" 
     android:gradientRadius="250" 
     android:centerX="1" 
     android:centerY="0" 
     android:angle="315" 
    />    
    </shape> 
    </item> 
</layer-list> 

如果我使用mMyImageView.setBackgroundResource(R.drawable.my_layered_shape)它的工作原理。 我不介意如果必须拆分xml,或者只要有办法获取各种颜色值,就可以通过编程实现整个事物。我将以编程方式进行的概念(即我最擅长的在代码中做这个xml)是:

Drawable[] layers = new Drawable[2]; 

ShapeDrawable sd1 = new ShapeDrawable(new RectShape()); 
sd1.getPaint().setColor(0xFFFFFFFF); 
sd1.getPaint().setStyle(Style.STROKE); 
sd1.getPaint().setStrokeWidth(1); 
// sd1.getPaint().somehow_set_stroke_color? 

ShapeDrawable sd2 = new ShapeDrawable(new RectShape()); 
sd2.getPaint().setColor(0xFF000000); 
sd2.getPaint().setStyle(Style.STROKE); 
// sd2.getPaint().somehow_set_stroke_color? 
// sd2.getPaint().somehow_set_gradient_params? 

layers[0] = sd1; 
layers[1] = sd2; 
LayerDrawable composite = new LayerDrawable(layers); 
mMyImageView.setBackgroundDrawable(composite); 

谢谢。

回答

25

似乎是不ShapeDrawable工作,但看看我的GradientDrawable例如:

GradientDrawable gd = new GradientDrawable(Orientation.BOTTOM_TOP, new int[]{Color.RED, Color.GREEN}); 
gd.setStroke(10, Color.BLUE); 

您可能还需要下面的方法:

gd.setGradientCenter(float x, float y); 
gd.setGradientRadius(float gradientRadius); 
+7

奇怪的是,GradientDrawable类没有'setPadding'方法,有什么办法吗? – Palani

+0

非常好,它解决了我的问题 – Goofy

5

只是要去在此留下...未经测试

/** 
* Created by Nedo on 09.04.2015. 
*/ 
public class ShapeBuilder { 

    public static Drawable generateSelectorFromDrawables(Drawable pressed, Drawable normal) { 
     StateListDrawable states = new StateListDrawable(); 
     states.addState(new int[]{ -android.R.attr.state_focused, -android.R.attr.state_pressed, -android.R.attr.state_selected}, normal); 
     states.addState(new int[]{ android.R.attr.state_pressed}, pressed); 
     states.addState(new int[]{ android.R.attr.state_focused}, pressed); 
     states.addState(new int[]{ android.R.attr.state_selected}, pressed); 

     return states; 
    } 

    public static Drawable generateShape(String colorTop, String colorBot, String colorStroke, int stokeSize, float strokeRadius) { 
     int top, bot, stroke; 
     top = Color.parseColor(colorTop); 
     bot = Color.parseColor(colorBot); 
     stroke = Color.parseColor(colorStroke); 

     GradientDrawable drawable = new GradientDrawable(GradientDrawable.Orientation.BOTTOM_TOP, new int[]{top, bot}); 
     drawable.setStroke(stokeSize, stroke); 
     drawable.setCornerRadius(strokeRadius); 

     return drawable; 
    } 

    public static Drawable buildSelectorShapeFromColors(String colorNormalStroke, String colorNormalBackTop, String colorNormalBackBot, 
                 String colorPressedStroke, String colorPressedBackTop, String colorPressedBackBot, 
                 int strokeSize, float strokeRadius) { 

     Drawable pressed = generateShape(colorPressedBackTop, colorPressedBackBot, colorPressedStroke, strokeSize, strokeRadius); 
     Drawable normal = generateShape(colorNormalBackTop, colorNormalBackBot, colorNormalStroke, strokeSize, strokeRadius); 
     return generateSelectorFromDrawables(pressed, normal); 
    } 
} 

编辑:测试现在,有一个错误。 你实际上必须描述每一个状态。如果你将状态组合起来,只有当它们全部合格时才会被触发...

相关问题