2011-08-22 83 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); 
    } 
} 

編輯:測試現在,有一個錯誤。 你實際上必須描述每一個狀態。如果你將狀態組合起來,只有當它們全部合格時纔會被觸發...

相關問題