Reputation: 2461
I am using RangeSeekBar to set some values for 3 conditions (i.e. Green=OK,Amber=Warning, Red=evacuate)... I am using xml drawable to set the backgroung like this
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<gradient
android:startColor="#27F70C"
android:centerColor="#FFBF00"
android:endColor="#FC0505"
android:angle="0" />
<corners android:radius="0px" />
<stroke
android:width="2dp"
android:color="#70555555" />
<stroke
android:width="0dp"
android:color="#70555555" />
</shape>
which results like this
Now I want to change the background colour according to the seekbar values so that If I change the range it should change the background colour something like this
I know I can change the gradient programmatically but how to narrow down start color and increase end colour ? Anyone has a solution for this ?
Thanks
Upvotes: 3
Views: 775
Reputation: 2461
This is how I did it, in case anyone looking for a complete solution... Thanks to @Dave Morrissey for the help :)
XML code will be
<RelativeLayout
android:id="@+id/layout4"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center">
<LinearLayout
android:id="@+id/colorsLayout"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<View
android:id="@+id/bgGreen"
android:layout_width="100dp"
android:layout_height="25dp"
android:background="#27F70C"/>
<View
android:id="@+id/bgAmber"
android:layout_width="100dp"
android:layout_height="25dp"
android:background="#FFBF00"/>
<View
android:id="@+id/bgRed"
android:layout_width="100dp"
android:layout_height="25dp"
android:background="#FC0505"/>
</LinearLayout>
<LinearLayout
android:id="@+id/seekBarLayout"
android:layout_width="wrap_content"
android:layout_height="wrap_content">
</LinearLayout>
</RelativeLayout>
Java code will be like
LinearLayout ll = (LinearLayout)findViewById(R.id.colorsLayout);
View viewGreen = (View)findViewById(R.id.bgGreen);
View viewAmber = (View)findViewById(R.id.bgAmber);
View viewRed = (View)findViewById(R.id.bgRed);
int sbMaxVal = 4999;
//Create RangeSeekBar as Integer range between 0 and sbMaxVal
seekBar = new RangeSeekBar(0, sbMaxVal, this);
seekBar.setNotifyWhileDragging(true);
//Add RangeSeekBar to Pre-defined layout
ViewGroup layout = (ViewGroup) findViewById(R.id.seekBarLayout);
layout.addView(seekBar);
//Set the onRangeChangeListener for the seekBar
seekBar.setOnRangeSeekBarChangeListener(new RangeSeekBar.OnRangeSeekBarChangeListener<Integer>() {
@Override
public void onRangeSeekBarValuesChanged(RangeSeekBar<?> bar, Integer minValue, Integer maxValue) {
int width = ll.getWidth();
int minVal = (int) Math.floor((Integer.parseInt(amberValue)*width)/sbMaxVal);
int maxVal = (int) Math.floor((Integer.parseInt(redValue)*width)/sbMaxVal);
int wg = minVal;
int wy = maxVal-minVal;
int wr = ll.getWidth()-wg-wy;
//Change the length of background views green,amber,red
LinearLayout.LayoutParams paramsGreen = (LinearLayout.LayoutParams)
viewGreen.getLayoutParams();
paramsGreen.width = wg;
viewGreen.setLayoutParams(paramsGreen);
LinearLayout.LayoutParams paramsAmber = (LinearLayout.LayoutParams)
viewAmber.getLayoutParams();
paramsAmber.width = wy;
viewAmber.setLayoutParams(paramsAmber);
LinearLayout.LayoutParams paramsRed = (LinearLayout.LayoutParams)
viewRed.getLayoutParams();
paramsRed.width = wr ;
viewRed.setLayoutParams(paramsRed);
}
});
Upvotes: 1
Reputation: 9572
The LinearGradient has an optional parameter called positions - these positions tell how long the different sections of colors will be.
@miroslavign posted a function here which seems to set gradient background for a view by code (not XML) - I haven't tried it, but it looks promising. Simply change it to your colors and set the gradient positions according to the Seekbar.
Copy pasted here for people who don't like following links:
private void FillCustomGradient(View v) {
final View view = v;
Drawable[] layers = new Drawable[1];
ShapeDrawable.ShaderFactory sf = new ShapeDrawable.ShaderFactory() {
@Override
public Shader resize(int width, int height) {
LinearGradient lg = new LinearGradient(
0,
0,
0,
view.getHeight(),
new int[] {
getResources().getColor(R.color.color1), // please input your color from resource for color-4
getResources().getColor(R.color.color2),
getResources().getColor(R.color.color3),
getResources().getColor(R.color.color4)},
new float[] { 0, 0.49f, 0.50f, 1 }, // positions
Shader.TileMode.CLAMP);
return lg;
}
};
PaintDrawable p = new PaintDrawable();
p.setShape(new RectShape());
p.setShaderFactory(sf);
p.setCornerRadii(new float[] { 5, 5, 5, 5, 0, 0, 0, 0 });
layers[0] = (Drawable) p;
LayerDrawable composite = new LayerDrawable(layers);
view.setBackgroundDrawable(composite);
}
Upvotes: 1
Reputation: 4421
Try creating three View
s underneath the RangeSeekBar
, and updating the widths of each as the sliders are moved.
Very roughly, this might look like:
<RelativeLayout android:layout_width="wrap_content" android:layout_height="wrap_content">
<View
android:id="@+id/green"
android:layout_width="100dp"
android:layout_height="match_parent"
android:background="#00FF00"/>
<View
android:id="@+id/orange"
android:layout_toRightOf="@id/green"
android:layout_width="100dp"
android:layout_height="match_parent"
android:background="#FFFF00"/>
<View
android:id="@+id/red"
android:layout_toRightOf="@id/orange"
android:layout_width="100dp"
android:layout_height="match_parent"
android:background="#FF0000"/>
<RangeSeekBar android:layout_width="300dp" android:layout_height="wrap_content">
</RelativeLayout>
In this example, you would update the widths of the three colour views so that they add up to 300dp, as the sliders are moved.
You can either use solid colours for the backgrounds of the three views, which would look like your second image, or create three gradients (green to green-yellow, yellow-orange, orange-red).
Upvotes: 1