Skip to content

Commit

Permalink
RTL mode supported.
Browse files Browse the repository at this point in the history
  • Loading branch information
zhpanvip committed Jan 28, 2021
1 parent 5fdbe1f commit 06129d3
Show file tree
Hide file tree
Showing 6 changed files with 199 additions and 8 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
import com.scwang.smartrefresh.layout.SmartRefreshLayout;
import com.zhpan.bannerview.BannerViewPager;
import com.zhpan.bannerview.constants.IndicatorGravity;
import com.zhpan.bannerview.indicator.DrawableIndicator;
import com.zhpan.bannerview.utils.BannerUtils;
import com.zhpan.indicator.DrawableIndicator;
import com.zhpan.indicator.IndicatorView;
import com.zhpan.indicator.base.IIndicator;
import com.zhpan.indicator.enums.IndicatorSlideMode;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ protected void initView(Bundle savedInstanceState, View view) {
.setIndicatorSlideMode(IndicatorSlideMode.SCALE)
.setIndicatorSliderColor(getColor(R.color.red_normal_color), getColor(R.color.red_checked_color))
.setIndicatorSliderRadius(getResources().getDimensionPixelOffset(R.dimen.dp_4), getResources().getDimensionPixelOffset(R.dimen.dp_5))
.setRTLMode(true)
.setLifecycleRegistry(getLifecycle())
.setOnPageClickListener(this::pageClick)
.setAdapter(new ViewBindingSampleAdapter(getResources().getDimensionPixelOffset(R.dimen.dp_8)))
Expand Down
4 changes: 2 additions & 2 deletions bannerview/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ android {
compileSdkVersion 28

defaultConfig {
minSdkVersion 16
minSdkVersion 19
}

buildTypes {
Expand All @@ -19,6 +19,6 @@ android {

dependencies {
implementation 'androidx.viewpager2:viewpager2:1.0.0'
api 'com.github.zhpanvip:viewpagerindicator:1.1.0'
api 'com.github.zhpanvip:viewpagerindicator:1.2.0'
// api project(path: ':indicator')
}
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
import com.zhpan.indicator.annotation.AIndicatorSlideMode;
import com.zhpan.indicator.annotation.AIndicatorStyle;
import com.zhpan.indicator.base.IIndicator;
import com.zhpan.indicator.enums.IndicatorOrientation;
import com.zhpan.indicator.option.IndicatorOptions;

import java.util.ArrayList;
Expand Down Expand Up @@ -1037,11 +1038,15 @@ public BannerViewPager<T> disallowParentInterceptDownEvent(boolean disallowParen
return this;
}

/**
* Set right to left mode.
*
* @param rtlMode true:right to left mode,
* false:right to left mode.
*/
public BannerViewPager<T> setRTLMode(boolean rtlMode) {
if (Build.VERSION.SDK_INT >= JELLY_BEAN_MR1) {
mViewPager.setLayoutDirection(rtlMode ? View.LAYOUT_DIRECTION_RTL : View.LAYOUT_DIRECTION_LTR);
// TODO set indicator RTL mode.
}
mViewPager.setLayoutDirection(rtlMode ? View.LAYOUT_DIRECTION_RTL : View.LAYOUT_DIRECTION_LTR);
mBannerManager.getBannerOptions().setRtl(rtlMode);
return this;
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,172 @@
package com.zhpan.bannerview.indicator

import android.content.Context
import android.graphics.*
import android.os.Build
import android.util.AttributeSet
import androidx.annotation.DrawableRes
import androidx.core.content.ContextCompat
import androidx.core.graphics.drawable.DrawableCompat
import com.zhpan.indicator.base.BaseIndicatorView

/**
* @ author : zhouweibin
* @ time: 2019/12/18 17:04.
* @ desc: 选中与未选中的图片长宽可能不一样
*/
class DrawableIndicator @JvmOverloads constructor(context: Context?, attrs: AttributeSet? = null, defStyleAttr: Int = 0) : BaseIndicatorView(context!!, attrs, defStyleAttr) {
// 选中时的Bitmap
private var mCheckedBitmap: Bitmap? = null

// 未选中时的Bitmap
private var mNormalBitmap: Bitmap? = null

// 图片之间的间距
private var mIndicatorPadding = 0

// 选中图片的宽度
private var mCheckedBitmapWidth = 0

// 选中图片的高度
private var mCheckedBitmapHeight = 0

//未选中图片的宽高
private var mNormalBitmapWidth = 0
private var mNormalBitmapHeight = 0
private var mIndicatorSize: IndicatorSize? = null
private var normalCanResize = true
private var checkCanResize = true
override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec)
val maxHeight = mCheckedBitmapHeight.coerceAtLeast(mNormalBitmapHeight)
val realWidth = mCheckedBitmapWidth + (mNormalBitmapWidth + mIndicatorPadding) * (getPageSize() - 1)
setMeasuredDimension(realWidth, maxHeight)
}

override fun onDraw(canvas: Canvas) {
super.onDraw(canvas)
if (getPageSize() > 1 && mCheckedBitmap != null && mNormalBitmap != null) {
for (i in 1 until getPageSize() + 1) {
var left: Int
var top: Int
var bitmap = mNormalBitmap
val index = i - 1
when {
index < getCurrentPosition() -> {
left = (i - 1) * (mNormalBitmapWidth + mIndicatorPadding)
top = measuredHeight / 2 - mNormalBitmapHeight / 2
}
index == getCurrentPosition() -> {
left = (i - 1) * (mNormalBitmapWidth + mIndicatorPadding)
top = measuredHeight / 2 - mCheckedBitmapHeight / 2
bitmap = mCheckedBitmap
}
else -> {
left = (i - 1) * mIndicatorPadding + (i - 2) * mNormalBitmapWidth + mCheckedBitmapWidth
top = measuredHeight / 2 - mNormalBitmapHeight / 2
}
}
drawIcon(canvas, left, top, bitmap)
}
}
}

override fun rotateCanvas(canvas: Canvas) {

}

private fun drawIcon(canvas: Canvas, left: Int, top: Int, icon: Bitmap?) {
if (icon == null) {
return
}
canvas.drawBitmap(icon, left.toFloat(), top.toFloat(), null)
}

private fun initIconSize() {
mCheckedBitmap?.let {
mIndicatorSize?.let {
if (mCheckedBitmap!!.isMutable && checkCanResize) {
mCheckedBitmap!!.width = mIndicatorSize!!.checkedWidth
mCheckedBitmap!!.height = mIndicatorSize!!.checkedHeight
} else {
val width = mCheckedBitmap!!.width
val height = mCheckedBitmap!!.height
val scaleWidth = mIndicatorSize!!.checkedWidth.toFloat() / width
val scaleHeight = mIndicatorSize!!.checkedHeight.toFloat() / height
val matrix = Matrix()
matrix.postScale(scaleWidth, scaleHeight)
mCheckedBitmap = Bitmap.createBitmap(mCheckedBitmap!!, 0, 0, width, height, matrix, true)
}
}
mCheckedBitmapWidth = mCheckedBitmap!!.width
mCheckedBitmapHeight = mCheckedBitmap!!.height
}
mNormalBitmap?.let {
mIndicatorSize?.let {
if (mNormalBitmap!!.isMutable && normalCanResize) {
mNormalBitmap!!.width = mIndicatorSize!!.normalWidth
mNormalBitmap!!.height = mIndicatorSize!!.normalHeight
} else {
val width = mNormalBitmap!!.width
val height = mNormalBitmap!!.height
val scaleWidth = mIndicatorSize!!.normalWidth.toFloat() / mNormalBitmap!!.width
val scaleHeight = mIndicatorSize!!.normalHeight.toFloat() / mNormalBitmap!!.height
val matrix = Matrix()
matrix.postScale(scaleWidth, scaleHeight)
mNormalBitmap = Bitmap.createBitmap(mNormalBitmap!!, 0, 0, width, height, matrix, true)
}
}
mNormalBitmapWidth = mNormalBitmap!!.width
mNormalBitmapHeight = mNormalBitmap!!.height
}
}

fun setIndicatorDrawable(@DrawableRes normalDrawable: Int, @DrawableRes checkedDrawable: Int): DrawableIndicator {
mNormalBitmap = BitmapFactory.decodeResource(resources, normalDrawable)
mCheckedBitmap = BitmapFactory.decodeResource(resources, checkedDrawable)
if (mNormalBitmap == null) {
mNormalBitmap = getBitmapFromVectorDrawable(context, normalDrawable)
normalCanResize = false
}
if (mCheckedBitmap == null) {
mCheckedBitmap = getBitmapFromVectorDrawable(context, checkedDrawable)
checkCanResize = false
}
initIconSize()
postInvalidate()
return this
}

fun setIndicatorSize(normalWidth: Int, normalHeight: Int, checkedWidth: Int, checkedHeight: Int): DrawableIndicator {
mIndicatorSize = IndicatorSize(normalWidth, normalHeight, checkedWidth, checkedHeight)
initIconSize()
postInvalidate()
return this
}

fun setIndicatorGap(padding: Int): DrawableIndicator {
if (padding >= 0) {
mIndicatorPadding = padding
postInvalidate()
}
return this
}

internal class IndicatorSize(var normalWidth: Int, var normalHeight: Int, var checkedWidth: Int, var checkedHeight: Int)

private fun getBitmapFromVectorDrawable(context: Context, drawableId: Int): Bitmap? {
var drawable = ContextCompat.getDrawable(context, drawableId)
drawable?.let {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
drawable = DrawableCompat.wrap(drawable!!).mutate()
}
val bitmap = Bitmap.createBitmap(drawable!!.intrinsicWidth,
drawable!!.intrinsicHeight, Bitmap.Config.ARGB_8888)
val canvas = Canvas(bitmap)
drawable!!.setBounds(0, 0, canvas.width, canvas.height)
drawable!!.draw(canvas)
return bitmap
}
return null
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

import com.zhpan.bannerview.constants.PageStyle;
import com.zhpan.bannerview.utils.BannerUtils;
import com.zhpan.indicator.enums.IndicatorOrientation;
import com.zhpan.indicator.option.IndicatorOptions;

import static com.zhpan.bannerview.transform.ScaleInTransformer.DEFAULT_MIN_SCALE;
Expand All @@ -24,6 +25,7 @@ public BannerOptions() {
pageMargin = BannerUtils.dp2px(20);
rightRevealWidth = DEFAULT_REVEAL_WIDTH;
leftRevealWidth = DEFAULT_REVEAL_WIDTH;
rtl = false;
}

public static final int DEFAULT_REVEAL_WIDTH = -1000;
Expand Down Expand Up @@ -60,6 +62,8 @@ public BannerOptions() {

private int orientation = ViewPager2.ORIENTATION_HORIZONTAL;

private boolean rtl;

private boolean disallowParentInterceptDownEvent;

private final IndicatorOptions mIndicatorOptions;
Expand Down Expand Up @@ -268,6 +272,17 @@ public void setOffScreenPageLimit(int offScreenPageLimit) {
this.offScreenPageLimit = offScreenPageLimit;
}

public boolean isRtl() {
return rtl;
}

public void setRtl(boolean rtl) {
this.rtl = rtl;
if (rtl) {
mIndicatorOptions.setOrientation(IndicatorOrientation.INDICATOR_RTL);
}
}

public static class IndicatorMargin {

private final int left, right, top, bottom;
Expand Down

0 comments on commit 06129d3

Please sign in to comment.