i try to draw LinearGradient in a layout but the gradient is not fit into my view.
Instead of gradient i see only one color.
I think its because im not giving the right dimension of the view
Here is my code:
backGroundColorView = (LinearLayout) findViewById(R.id.backGroundColorView);
int[] tempColors = data.getAppBackgroundColor();
LinearGradient test = new LinearGradient(0.f, 0.f, backGroundColorView.getWidth(), backGroundColorView.getHeight(), tempColors, null, TileMode.CLAMP);
ShapeDrawable shape = new ShapeDrawable(new RectShape());
shape.getPaint().setShader(test);
backGroundColorView.setBackgroundDrawable(shape);
Thank for helping
just use GradientDrawable as a background http://developer.android.com/reference/android/graphics/drawable/GradientDrawable.html
You can use this site do create the gradient you want and then add a file in your res/drawable and put the code inside.
After that all you have to do is set the background of your layout to be the drawable file you just created.
If you have any questions just ask ;)
EDIT:
Change your code to this:
GradientDrawable gd = new GradientDrawable(GradientDrawable.Orientation.TOP_BOTTOM,tempColors);
gd.setCornerRadius(0f);
backGroundColorView.setBackgroundDrawable(gd);
Try this
backGroundColorView = (LinearLayout) findViewById(R.id.backGroundColorView);
int[] tempColors = data.getAppBackgroundColor();
GradientDrawable gd = new GradientDrawable(
GradientDrawable.Orientation.TOP_BOTTOM,tempColors);
gd.setCornerRadius(0f);
backGroundColorView .setBackgroundDrawable(gd);
Instead of
backGroundColorView = (LinearLayout) findViewById(R.id.backGroundColorView);
int[] tempColors = data.getAppBackgroundColor();
LinearGradient test = new LinearGradient(0.f, 0.f, backGroundColorView.getWidth(), backGroundColorView.getHeight(), tempColors, null, TileMode.CLAMP);
ShapeDrawable shape = new ShapeDrawable(new RectShape());
shape.getPaint().setShader(test);
backGroundColorView.setBackgroundDrawable(shape);
GradientDrawable
you can create linear gradiant like this:
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle" >
<gradient
android:type="linear"
android:centerX="50%"
android:startColor="#FF003333"
android:centerColor="#FF05C1FF"
android:endColor="#FF003333"
android:angle="270"/>
<!-- <gradient
android:centerColor="#FF05C1FF"
android:centerX="50%"
android:centerY="50%"
android:endColor="#FF003333"
android:gradientRadius="50"
android:startColor="#FF003333"
android:type="radial" /> -->
<corners
android:bottomLeftRadius="15dp"
android:bottomRightRadius="15dp"
android:topLeftRadius="15dp"
android:topRightRadius="15dp" />
</shape>
and use it as background of linear layout.
ihope it solves your problem.
see i have used this in my post: customToast
you can use this also:
GradientDrawable grad = new GradientDrawable(Orientation.LEFT_RIGHT,
new int[]{0xffffffff, 0xffff00ff, 0xffffff00,
0xff0000ff, 0xf0f0f0f0, 0xfefefefe});
grad.setBounds(0, 0, 320, 480);
Related
The linear gradient which I am trying to create programatically:
<shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle" >
<gradient
android:type="linear"
android:centerX="50%"
android:startColor="#FFFFFFFF"
android:centerColor="#99FF8A8A"
android:endColor="#FFF8F8F8"
android:angle="90"/>
</shape>
I wrote this code:But I didn't get the same result.
GradientDrawable _gradientDrawable = new GradientDrawable(
GradientDrawable.Orientation.BOTTOM_TOP, new int[]{
Color.parseColor("#FFFFFFFF"),
Color.parseColor("#99FF8A8A"),
Color.parseColor("#FF8F8F8")
});
myimage.setBackground(_gradientDrawable);
Where's my mistake?
To do this in code, you create a GradientDrawable.
The only chance to set the angle and color is in the constructor.
If you want to change the color or angle, just create a new GradientDrawable and set it as the background.
View layout = findViewById(R.id.mainlayout);
GradientDrawable gd = new GradientDrawable(
GradientDrawable.Orientation.TOP_BOTTOM,
new int[] {0xFF616261,0xFF131313});
gd.setCornerRadius(0f);
layout.setBackgroundDrawable(gd);
What I'm trying to achieve is to use a Drawable with a couple of layers inside it, but control some values at runtime such as the startColor for the gradient. Here's what I have in my_layered_shape.xml:
<?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>
And if I use mMyImageView.setBackgroundResource(R.drawable.my_layered_shape) it works.
I don't mind splitting the xml if I have to, or doing the whole thing programatically as long as there's a way to get at the various color values. The concept I'm going for programmatically (i.e. my best shot at doing the same in code as this xml) is:
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);
Thanks.
It seems that is does not work with ShapeDrawable, but take a look at my GradientDrawable example:
GradientDrawable gd = new GradientDrawable(Orientation.BOTTOM_TOP, new int[]{Color.RED, Color.GREEN});
gd.setStroke(10, Color.BLUE);
You may also need following method:
gd.setGradientCenter(float x, float y);
gd.setGradientRadius(float gradientRadius);
Just gonna leave this here... Not tested yet
/**
* 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);
}
}
Edit: tested Now, had one mistake.
You actually have to describe every single state. If you group states they will only be triggered if all of them accure at once...
This is a xml for triangle shape:
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:id="#+id/shape_id">
<rotate
android:fromDegrees="45"
android:toDegrees="45"
android:pivotX="-40%"
android:pivotY="87%" >
<shape android:shape="rectangle" >
<stroke android:width="10dp"/>
</shape>
</rotate>
</item>
</layer-list>
And this is a background of a textview
<TextView
android:id="#+id/headlineSelect_TXT2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_weight="1"
android:background="#drawable/category_triangle_shape1"
android:visibility="invisible" />
And I want to change color of shape programmatically. I tried this but I am getting null pointer exception
LayerDrawable bgDrawable = (LayerDrawable) getActivity()
.getResources()
.getDrawable(R.drawable.category_triangle_shape1);
final GradientDrawable shape = (GradientDrawable) bgDrawable
.findDrawableByLayerId(R.id.shape_id);
shape.setStroke(10,Color.GREEN);
How can I do that? Thanks for help.
This is somewhat tricky and involves a lot of casts:
TextView view = (TextView) findViewById( R.id.my_text_view );
// Get the drawable from the view, if you're using an imageview src
// element you'll go with view.getDrawable()
LayerDrawable layers = (LayerDrawable) view.getBackground();
// Now get your shape by selecting the id
RotateDrawable rotate = (RotateDrawable) layers.findDrawableByLayerId( R.id.shape_id );
// Finally you can access the underlying shape
GradientDrawable drawable = (GradientDrawable) rotate.getDrawable();
// ... and do you fancy things
drawable.setColor( ... );
Forget about XML and do it by code like that:
TextView txtView = (TextView)findViewById(R.id. headlineSelect_TXT2);
ShapeDrawable.ShaderFactory sf = new ShapeDrawable.ShaderFactory() {
#Override
public Shader resize(int width, int height) {
LinearGradient lg = new LinearGradient(0, 0, 0, txtView.getHeight(),
new int[] {
Color.LIGHT_GREEN,
Color.WHITE,
Color.MID_GREEN,
Color.DARK_GREEN },
new float[] {
0, 0.45f, 0.55f, 1 },
Shader.TileMode.REPEAT);
return lg;
}
};
PaintDrawable p = new PaintDrawable();
p.setShape(new RectShape());
p.setShaderFactory(sf);
txtView.setBackgroundDrawable((Drawable)p);
If you have RotateDrawable in your xml file inside res/drawable then you could try the below code to change the color of rotate drawable.
LayerDrawable layers = (LayerDrawable) getResources().getDrawable(R.drawable.triangle);
RotateDrawable rotateShape = (RotateDrawable) (layers.findDrawableByLayerId(R.id.user_color));
GradientDrawable shape = (GradientDrawable) rotateShape.getDrawable();
shape.setColor(Color.parseColor("#FF0000"));
TextView NotchTV = (TextView) view.findViewById(R.id.bubble_notch);
NotchTV.setBackgroundDrawable(layers);
`
I have a gradient drawable defined in xml that I use it as a background, like this:
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:bottom="4dp">
<shape>
<gradient
android:startColor="#color/blue"
android:endColor="#color/dark_blue"
android:angle="270" />
</shape>
</item>
<item android:top="98dp">
<shape>
<gradient
android:startColor="#color/black"
android:endColor="#color/transparent_black"
android:angle="270" />
</shape>
</item>
</layer-list>
I need to implement this programmatically. I have tried to use a GradientDrawable as follows (this method is implemented on a custom view):
int[] colors1 = {getResources().getColor(R.color.black), getResources().getColor(R.color.trasparent_black)};
GradientDrawable shadow = new GradientDrawable(Orientation.TOP_BOTTOM, colors1);
shadow.setBounds(0,98, 0, 0);
int[] colors = new int[2];
colors[0] = getResources().getColor(R.color.blue);
colors[1] = getResources().getColor(R.color.dark_blue);
GradientDrawable backColor = new GradientDrawable(Orientation.TOP_BOTTOM, colors);
backColor.setBounds(0, 0,0, 4);
//finally create a layer list and set them as background.
Drawable[] layers = new Drawable[2];
layers[0] = backColor;
layers[1] = shadow;
LayerDrawable layerList = new LayerDrawable(layers);
setBackgroundDrawable(layerList);
The problem is that it seems that setting the bounds is useless or doesn't work the same way as (android:top, android:bottom xml parameters). The resulting background is each layer painted from top to bottom, one above the other.
I want to generate something like this:
Found the answer!. Possible duplicate Multi-gradient shapes.
Replaced:
backColor.setBounds(0, 0,0, 4);
shadow.setBounds(0,98, 0, 0);
for
layerList.setLayerInset(0, 0, 0, 0, 4);
layerList.setLayerInset(1, 0, 98, 0, 0);
What I'm trying to achieve is to use a Drawable with a couple of layers inside it, but control some values at runtime such as the startColor for the gradient. Here's what I have in my_layered_shape.xml:
<?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>
And if I use mMyImageView.setBackgroundResource(R.drawable.my_layered_shape) it works.
I don't mind splitting the xml if I have to, or doing the whole thing programatically as long as there's a way to get at the various color values. The concept I'm going for programmatically (i.e. my best shot at doing the same in code as this xml) is:
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);
Thanks.
It seems that is does not work with ShapeDrawable, but take a look at my GradientDrawable example:
GradientDrawable gd = new GradientDrawable(Orientation.BOTTOM_TOP, new int[]{Color.RED, Color.GREEN});
gd.setStroke(10, Color.BLUE);
You may also need following method:
gd.setGradientCenter(float x, float y);
gd.setGradientRadius(float gradientRadius);
Just gonna leave this here... Not tested yet
/**
* 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);
}
}
Edit: tested Now, had one mistake.
You actually have to describe every single state. If you group states they will only be triggered if all of them accure at once...