Подтвердить что ты не робот

Android - установить ProgressBar как вертикальную полосу вместо горизонтальной?

Я пытаюсь использовать ProgressBar в качестве показателя, например дисплея. Я думал, что это будет легкая задача, и подумал, что у ProgressBar есть свойство устанавливать вертикальное, но я ничего не вижу.

Кроме того, я хотел бы показать индикатор линейки, расположенный рядом с панелью, чтобы четко обозначать текущий уровень.

Указатели оценили - Спасибо!

4b9b3361

Ответ 1

По умолчанию вертикальные полосы выполнения не поддерживаются.

Ответ 2

Недавно я столкнулся с необходимостью вертикального индикатора выполнения, но не смог найти решение, используя существующий виджет Progress Bar. Решения, с которыми я столкнулся, обычно требовали расширения текущей панели прогресса или совершенно нового класса в ней. Я не был уверен, что выкатывать новый класс для достижения простого изменения ориентации было необходимо.

В этой статье представлено простое, элегантное и, самое главное, решение без хака для достижения вертикального индикатора выполнения. Я собираюсь пропустить объяснение и просто предоставить решение для резака для печенья. Если вам нужна дополнительная информация, свяжитесь со мной или оставьте комментарий ниже.

Создайте xml в своей выпадающей папке (не drawable-hdpi или drawable-mdpi - поместите его в drawable). В этом примере я вызываю свой xml vertical_progress_bar.xml

Вот что разместить в XML файле:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
  <item android:id="@android:id/background">
    <shape>
      <corners android:radius="5dip" />
      <gradient
        android:startColor="#ff9d9e9d"
        android:centerColor="#ff5a5d5a"
        android:centerY="0.75"
        android:endColor="#ff747674"
        android:angle="180"
      />
    </shape>
  </item>
  <item android:id="@android:id/secondaryProgress">
    <clip android:clipOrientation="vertical" android:gravity="bottom">
      <shape>
        <corners android:radius="5dip" />
        <gradient
          android:startColor="#80ffd300"
          android:centerColor="#80ffb600"
          android:centerY="0.75"
          android:endColor="#a0ffcb00"
          android:angle="180"
        />
      </shape>
    </clip>
  </item>
  <item android:id="@android:id/progress">
    <clip android:clipOrientation="vertical" android:gravity="bottom">
      <shape>
        <corners android:radius="5dip" />
        <gradient
          android:startColor="#ffffd300"
          android:centerColor="#ffffb600"
          android:centerY="0.75"
          android:endColor="#ffffcb00"
          android:angle="180"
        />
      </shape>
    </clip>
</item>
</layer-list>

Создайте xml файл с именем styles.xml и поместите его в res/values. Если в вашем проекте уже есть styles.xml в res/values, пропустите этот шаг.

Измените файл styles.xml и добавьте следующий код в конец файла:

<style name="Widget">
</style>
<style name="Widget.ProgressBar">
  <item name="android:indeterminateOnly">true</item>
  <item name="android:indeterminateBehavior">repeat</item>
  <item name="android:indeterminateDuration">3500</item>
  <item name="android:minWidth">48dip</item>
  <item name="android:maxWidth">48dip</item>
  <item name="android:minHeight">48dip</item>
  <item name="android:maxHeight">48dip</item>
</style>
<style name="Widget.ProgressBar.Vertical">
  <item name="android:indeterminateOnly">false</item>
  <item name="android:progressDrawable">@drawable/progress_bar_vertical</item>
  <item name="android:indeterminateDrawable">@android:drawable/progress_indeterminate_horizontal</item>
  <item name="android:minWidth">1dip</item>
  <item name="android:maxWidth">12dip</item>
</style>

Добавьте свой новый вертикальный индикатор выполнения в свой макет. Вот пример:

<ProgressBar
  android:id="@+id/vertical_progressbar"
  android:layout_width="12dip"
  android:layout_height="300dip"
  style="@style/Widget.ProgressBar.Vertical"
/>

Это должно быть все, что вам нужно сделать, чтобы использовать вертикальный индикатор выполнения в вашем проекте. Возможно, у вас могут быть пользовательские графические изображения с девятью патчами, которые вы используете для индикатора выполнения. Вы должны внести соответствующие изменения в файл progress_bar_vertical.xml. Надеюсь, это поможет вам в вашем проекте!

Ответ 3

Вам нужно создать свой собственный пользовательский индикатор прогресса.

В xml добавьте этот макет:

 <com.example.component.VerticalProgressBar 
        style="?android:attr/progressBarStyleHorizontal"
        android:id="@+id/verticalRatingBar1"
        android:layout_width="wrap_content"
        android:progress="50"
        android:layout_height="fill_parent" />

VerticalProgressBar.java

public class VerticalProgressBar extends ProgressBar{
    private int x, y, z, w;

    @Override
    protected void drawableStateChanged() {
        // TODO Auto-generated method stub
        super.drawableStateChanged();
    }

    public VerticalProgressBar(Context context) {
        super(context);
    }

    public VerticalProgressBar(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }

    public VerticalProgressBar(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
        super.onSizeChanged(h, w, oldh, oldw);
        this.x = w;
        this.y = h;
        this.z = oldw;
        this.w = oldh;
    }

    @Override
    protected synchronized void onMeasure(int widthMeasureSpec,
            int heightMeasureSpec) {
        super.onMeasure(heightMeasureSpec, widthMeasureSpec);
        setMeasuredDimension(getMeasuredHeight(), getMeasuredWidth());
    }

    protected void onDraw(Canvas c) {
        c.rotate(-90);
        c.translate(-getHeight(), 0);
        super.onDraw(c);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        if (!isEnabled()) {
            return false;
        }

        switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:

            setSelected(true);
            setPressed(true);
            break;
        case MotionEvent.ACTION_MOVE:
            setProgress(getMax()
                    - (int) (getMax() * event.getY() / getHeight()));
            onSizeChanged(getWidth(), getHeight(), 0, 0);

            break;
        case MotionEvent.ACTION_UP:
            setSelected(false);
            setPressed(false);
            break;

        case MotionEvent.ACTION_CANCEL:
            break;
        }
        return true;
    }

    @Override
    public synchronized void setProgress(int progress) {

        if (progress >= 0)
            super.setProgress(progress);

        else
            super.setProgress(0);
        onSizeChanged(x, y, z, w);

    }
}

Или:         Решение Jagsaund также прекрасно.

Ответ 4

Я знаю, что это старый пост, но я нашел очень простое решение этой проблемы, которое может кому-то помочь. Сначала создайте файл progress_drawable_vertical.xml следующим образом:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@android:id/background">
    <color android:color="#777" />
</item>
<item android:id="@android:id/progress">
    <clip
        android:clipOrientation="vertical"
        android:gravity="bottom">
        <shape>
            <gradient
                android:startColor="#00FF00"
                android:centerColor="#FFFF00"
                android:endColor="#FF0000"
                android:angle="90" />
        </shape>
    </clip>
</item>
</layer-list>

Тогда просто используйте это в вашем прогрессбар:

<ProgressBar
    android:id="@+id/progress_bar"
    style="@android:style/Widget.ProgressBar.Horizontal"
    android:layout_centerInParent="true"
    android:layout_width="wrap_content"
    android:layout_height="match_parent"
    android:max="100"
    android:progress="33"
    android:progressDrawable="@drawable/progress_drawable_vertical" />

Я также создал progress_drawable_horizont.xml

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@android:id/background">
    <color android:color="#777" />
</item>
<item android:id="@android:id/progress">
    <clip
        android:clipOrientation="horizontal"
        android:gravity="left">
        <shape>
            <gradient
                android:startColor="#00FF00"
                android:centerColor="#FFFF00"
                android:endColor="#FF0000" />
        </shape>
    </clip>
</item>
</layer-list>

с целью сохранения стиля, определенного в progress_drawable_vertical.xml

Ключевым моментом здесь является правильное использование android:clipOrientation и android:gravity.

Я нашел это решение здесь, и суть решения похожа на jagsaund, но немного проще.

Ответ 5

Я нашел наиболее подходящее (самое простое и универсальное) решение:)

Это старый пост, но мне было так трудно найти это так простое решение, поэтому я подумал, что должен его опубликовать.

Просто используйте scale-drawable (или 9-патч, если хотите), не нужно ЛЮБОГО ДРУГОГО кода.

Пример:

<layer-list xmlns:android="http://schemas.android.com/apk/res/android">  

    <item android:id="@android:id/background" android:drawable="@color/transparent"/>  

    <item android:id="@android:id/progress">
        <scale android:scaleGravity="bottom" android:scaleWidth="0%" android:scaleHeight="100%">
            <shape >
                <solid android:color="@color/blue"/>
                <corners android:topRightRadius="1dp" android:topLeftRadius="1dp"/>
            </shape>
        </scale>
    </item>
</layer-list>  

И, конечно, обычный код:

<ProgressBar
    android:id="@+id/progress_bar"
    style="@android:style/Widget.ProgressBar.Horizontal"
    android:layout_width="24dp"
    android:layout_height="match_parent"
    android:max="1000"
    android:progress="200"
    android:progressDrawable="@drawable/progress_scale_drawable" />  

Обратите внимание на строки scale-drawable xml (магические линии):

android:scaleGravity="bottom"  //scale from 0 in y axis (default scales from center Y)  
android:scaleWidth="0%"        //don't scale width (according to 'progress')
android:scaleHeight="100%"     //do scale the height of the drawable

Ответ 6

This perfectly works

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:id="@android:id/background">
        <shape>
            <gradient
                android:startColor="#DDDDDD"
                android:centerColor="#DDDDDD"
                android:centerY="0.75"
                android:endColor="#DDDDDD"
                android:angle="270"
                />
        </shape>
    </item>

    <item
        android:id="@android:id/progress">
        <clip
            android:clipOrientation="vertical"
            android:gravity="top">
            <shape>
                <gradient
                    android:angle="0"
                    android:startColor="#302367"
                    android:centerColor="#7A5667"
                    android:endColor="#C86D67"/>
            </shape>
        </clip>
    </item>
</layer-list>

    <ProgressBar
            android:id="@+id/progress_bar"
            style="?android:attr/progressBarStyleHorizontal"
            android:layout_width="5dp"
            android:layout_height="match_parent"'enter code here'
            android:progressDrawable="@drawable/progress_dialog"/>

Ответ 7

Чтобы использовать ProgressBar и сделать его вертикальным, вам нужно будет создать свой собственный пользовательский вид, расширяющий представление ProgressBar и переопределяя метод onDraw(). Это позволит вам рисовать его в обратной ориентации. Взгляните на исходный код ProgressBar.onDraw() (расположенный внизу ссылки) для получения справки о том, как это сделать. Лучший сценарий, вам просто придется поменять несколько переменных x и y.

Ответ 8

Создание индикатора выполнения (я преобразовал свой код из С# в java, поэтому не может быть на 100% правильным)

ProgressBar progBar = new ProgressBar(Context, null, Android.resource.attribute.progressDrawable);
progBar.progressDrawable = ContextCompat.getDrawable(Context, resource.drawable.vertical_progress_bar);
progBar.indeterminate = false;

vertical_progress_bar.xml

<?xml version="1.0" encoding="utf-8"?>
    <layer-list xmlns:android="http://schemas.android.com/apk/res/android" >

      <item android:id="@android:id/background">
        <shape>
          <solid android:color="@color/grey" />

          <corners android:radius="20dip" />
        </shape>
      </item>
      <item android:id="@android:id/progress">
        <scale
            android:drawable="@drawable/vertical_progress_bar_blue_progress"
            android:scaleHeight="100%"
            android:scaleGravity="bottom"/>
      </item>
    </layer-list>

vertical_progress_bar_blue_progress.xml

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" >

  <corners
      android:radius="20dip" />

  <solid android:color="@color/ProgressBarFourth" />

</shape>

Что нужно сделать, чтобы ваша вертикальная панель была атрибутами scaleHeight и scaleGravity в vertical_progress_bar.xml.

В результате он выглядит примерно так:

введите описание изображения здесь

Ответ 9

У меня есть точная проблема. Создание пользовательского класса (расширение ProgressBar) приведет к созданию кода, который трудно поддерживать. Использование пользовательского стиля вызовет проблему совместимости с другой темой из новой ОС (например, леденец)

В конце концов, я просто применил анимацию вращения к горизонтальной панели выполнения. Вдохновленный Пит.

  • Создайте тег в вашем макете xml, как обычный горизонтальный индикатор выполнения.
  • Убедитесь, что размер и положение ProgressBar - это то, что вы хотите после вращения. (Возможно, установление отрицательной маржи поможет). В моем коде я поворачиваю представление из 0,0.
  • Используйте приведенный ниже метод, чтобы повернуть и установить новый прогресс.

код:

private void setProgress(final ProgressBar progressBar, int progress) {
    progressBar.setWillNotDraw(true);
    progressBar.setProgress(progress);
    progressBar.setWillNotDraw(false);
    progressBar.invalidate();
}

private void rotateView(final View v, float degree) {
    Animation an = new RotateAnimation(0.0f, degree);
    an.setDuration(0);
    an.setRepeatCount(0);
    an.setFillAfter(true);               // keep rotation after animation
    v.setAnimation(an);
}

Ответ 10

Простой просмотр изображения в режиме прожектора

Пример

viewHolder.proBarTrueImage.setMaximalValue(147);
viewHolder.proBarTrueImage.setLevel(45);
viewHolder.proBarTrueImage.setColorResource(R.color.corner_blue);

простой класс

public class ProgressImageView extends ImageView {

private Context mContext;
private Paint paint;
private RectF rectf;

private int maximalValue = 1;
private int level = 0;
private int width;
private int height;

public ProgressImageView(Context context) {
    super(context);
    init(context, null, 0);
}

public ProgressImageView(Context context, AttributeSet attrs) {
    super(context, attrs);
    init(context, attrs, 0);
}

public ProgressImageView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    init(context, attrs, defStyleAttr);
}

private  void init(Context context, AttributeSet attrs, int defStyleAttr){

    mContext = context;
    paint = new Paint();
    rectf = new RectF();
    paint.setColor(Color.GRAY);
    paint.setStyle(Paint.Style.FILL);
};

@Override
protected void onDraw(Canvas canvas) {

    float dif = (float) height / (float) maximalValue;
    int newHeight = height - (int) (dif * level);

    rectf.set(0,newHeight, width, height);
    canvas.drawRect(rectf, paint);

    super.onDraw(canvas);
}

@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
    super.onSizeChanged(w, h, oldw, oldh);
    this.width = w;
    this.height = h;
}

public void setMaximalValue(int maximalValue) {
    this.maximalValue = maximalValue;
    invalidate();
}

public void setLevel(int level) {
    this.level = level;
    invalidate();
}

public void setColorResource(int color) {

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        color = mContext.getResources().getColor(color,mContext.getTheme());
    }else {
        color = mContext.getResources().getColor(R.color.corner_blue);
    }

    setColor(color);
}

public void setColor(int color){
    if (paint != null){
        paint.setColor(color);
        invalidate();
    }
}

}

Ответ 11

введите описание ссылки здесь

** Проверьте эту ссылку, я пытался использовать аналогичную вещь, и вы также можете использовать степпер для ваших нужд, на Github доступно несколько проектов о том, КАК ИСПОЛЬЗОВАТЬ STEPPER В ANDROID STUDIO **

Ответ 12

Добавьте это в код XML       Android: вращение = "90"       андроид: transformPivotX = "0dp" Так вот как должен выглядеть ваш Progress Bar xml

<ProgressBar
    android:id="@+id/progressBar6"
    style="?android:attr/progressBarStyleHorizontal"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:rotation="90"
    android:transformPivotX="0dp"
    tools:layout_editor_absoluteX="101dp"
    tools:layout_editor_absoluteY="187dp" />

Ответ 13

Вот простое решение, просто поверните индикатор выполнения

android:rotation="270"

Ответ 14

<ProgressBar
        android:id="@+id/battery_pb"
        android:rotation="270"
        android:progress="100"
...
/>

Используйте android: вращение = "270" до 100%, как внизу вверх или андроид: вращение = "90" до 100%, как сверху вниз