Commit cda8590c authored by mengcuiguang's avatar mengcuiguang

代码优化

parent 4e0cc1f4
......@@ -228,6 +228,7 @@ dependencies {
api project(':wxpay')
api project(':alipay')
api project(':oaid')
api project(':library_tagflow')
implementation 'com.github.CymChad:BaseRecyclerViewAdapterHelper:3.0.4'
// bugly
implementation 'com.tencent.bugly:crashreport:3.3.92'
......
......@@ -56,8 +56,8 @@ public class MintsApplication extends MultiDexApplication {
// 友盟SDK预初始化函数
// preInit预初始化函数耗时极少,不会影响App首次冷启动用户体验
UmengManager.INSTANCE.preInit(this,
MateUtils.INSTANCE.getAppMetaData(this, "CHANNEL_NAME"));
// UmengManager.INSTANCE.preInit(this,
// MateUtils.INSTANCE.getAppMetaData(this, "CHANNEL_NAME"));
// 判断应用是否在前台
ForegroundOrBackground.init(this);
......
package com.duben.happyplaylet.ui.adapter
import android.annotation.SuppressLint
import android.app.Activity
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.TextView
import androidx.core.content.ContextCompat
import com.duben.happyplaylet.R
import com.duben.happyplaylet.mvp.model.HotStyleTypesBean
import com.framework.tagflow.adapter.BaseTagAdapter
@SuppressLint("ViewHolder")
class MainTypeAdapter(private val mActivity: Activity) :
BaseTagAdapter<HotStyleTypesBean?>() {
var currentCheckedItemPosition = 0
override fun getView(
position: Int,
convertView: View?,
parent: ViewGroup
): View {
val view =
LayoutInflater.from(mActivity).inflate(R.layout.item_video_tab, parent, false)
val textView: TextView = view.findViewById<TextView>(R.id.item_tv)
val bean = getItem(position)
if (bean != null) {
if(position%2==0){
textView.text = bean.type
}else{
textView.text = bean.type+"testtesttesttest"
}
}
if (currentCheckedItemPosition == position) {
textView.setTextColor(ContextCompat.getColor(mActivity, R.color.red))
} else {
textView.setTextColor(ContextCompat.getColor(mActivity, R.color.color_8D8F90))
}
return view
}
fun setCheck(position: Int) {
currentCheckedItemPosition = position
notifyDataSetChanged()
}
}
\ No newline at end of file
......@@ -11,10 +11,6 @@ import androidx.core.content.ContextCompat
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import androidx.viewpager2.widget.ViewPager2
import com.google.android.material.tabs.TabLayout
import com.google.android.material.tabs.TabLayoutMediator
import com.scwang.smartrefresh.layout.api.RefreshLayout
import com.scwang.smartrefresh.layout.listener.OnRefreshListener
import com.duben.happyplaylet.R
import com.duben.happyplaylet.ad.AdManager
import com.duben.happyplaylet.ad.banner.BannerManager
......@@ -27,11 +23,11 @@ import com.duben.happyplaylet.mvp.model.*
import com.duben.happyplaylet.mvp.presenters.HomePresenter
import com.duben.happyplaylet.mvp.views.HomeView
import com.duben.happyplaylet.ui.activitys.NineActivity
import com.duben.happyplaylet.ui.activitys.NinePayActivity
import com.duben.happyplaylet.ui.activitys.RecommendActivity
import com.duben.happyplaylet.ui.activitys.VipActivity
import com.duben.happyplaylet.ui.adapter.HomeVideoPageAdapter
import com.duben.happyplaylet.ui.adapter.ImageTitleAdapter
import com.duben.happyplaylet.ui.adapter.MainTypeAdapter
import com.duben.happyplaylet.ui.adapter.TopAdapter
import com.duben.happyplaylet.ui.fragment.base.LazyLoadBaseFragment
import com.duben.happyplaylet.utils.AppPreferencesManager
......@@ -39,6 +35,10 @@ import com.duben.happyplaylet.utils.SpanUtils
import com.duben.library.utils.GlideUtils
import com.duben.library.utils.json.JsonUtil
import com.duben.library.utils.nodoubleclick.AntiShake
import com.framework.tagflow.interfac.OnTagClickListener
import com.google.android.material.tabs.TabLayout
import com.scwang.smartrefresh.layout.api.RefreshLayout
import com.scwang.smartrefresh.layout.listener.OnRefreshListener
import kotlinx.android.synthetic.main.fragment_main.*
import java.lang.reflect.Field
import java.util.*
......@@ -52,7 +52,7 @@ import kotlin.concurrent.schedule
class MainFragment : LazyLoadBaseFragment(), HomeView, View.OnClickListener, OnRefreshListener {
companion object {
var mSelectTabIndex = -1
var mSelectTabIndex = 0
}
private val tabsData = mutableListOf<HotStyleTypesBean>()
......@@ -201,45 +201,10 @@ class MainFragment : LazyLoadBaseFragment(), HomeView, View.OnClickListener, OnR
vpAdapter = HomeVideoPageAdapter(tabsData, this)
vp2.adapter = vpAdapter
vp2.desensitization()
TabLayoutMediator(tablayout, vp2) { tab, position ->
// 初始化Tab
tab.id = position
if (tabsData.size > 0) {
tab.customView = getTabView(tabsData[position].type)
}
}.attach()
tablayout.addOnTabSelectedListener(object : TabLayout.OnTabSelectedListener {
override fun onTabSelected(tab: TabLayout.Tab?) {
updateTab(tab, true)
mSelectTabIndex = tab!!.id
}
override fun onTabUnselected(tab: TabLayout.Tab?) {
updateTab(tab, false)
}
override fun onTabReselected(tab: TabLayout.Tab?) {
}
})
vp2.offscreenPageLimit = 100
}
private fun updateTab(tab: TabLayout.Tab?, isSelected: Boolean) {
tab?.customView?.let {
val text = it.findViewById<TextView>(R.id.item_tv)
if (isSelected) {
text.setTextColor(ContextCompat.getColor(requireContext(), R.color.red))
} else {
text.setTextColor(ContextCompat.getColor(requireContext(), R.color.color_8D8F90))
}
}
}
private fun getTabView(text: String): View {
val view = LayoutInflater.from(requireContext()).inflate(R.layout.item_video_tab, null)
view.findViewById<TextView>(R.id.item_tv).text = text
return view
vp2.isUserInputEnabled = false
}
override fun onRefresh(refreshLayout: RefreshLayout) {
......@@ -287,6 +252,24 @@ class MainFragment : LazyLoadBaseFragment(), HomeView, View.OnClickListener, OnR
mSelectTabIndex = 0
vpAdapter?.notifyDataSetChanged()
}
val mainTypeAdapter = MainTypeAdapter(requireActivity())
if (tabsData.size > 0) {
for (index in 0..tabsData.size - 1) {
mainTypeAdapter.addData(tabsData.get(index))
}
}
multiFlowTagSelf.setAdapter(mainTypeAdapter)
multiFlowTagSelf.setOnTagClickListener(object : OnTagClickListener {
override fun onClick(view: View?, position: Int) {
mSelectTabIndex = position
vp2.setCurrentItem(mSelectTabIndex,false)
mainTypeAdapter.setCheck(position)
}
override fun onLongClick(view: View?, position: Int) {
}
})
}
override fun topTabsSuc(data: BannerList?) {
......
......@@ -121,21 +121,16 @@
</com.google.android.material.appbar.CollapsingToolbarLayout>
<com.google.android.material.tabs.TabLayout
android:id="@+id/tablayout"
android:layout_width="wrap_content"
android:layout_height="38dp"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:paddingTop="-10dp"
app:tabBackground="@null"
app:tabIndicatorHeight="0dp"
app:tabMaxWidth="200dp"
app:tabMinWidth="20dp"
app:tabMode="scrollable"
app:tabPaddingEnd="6dp"
app:tabPaddingStart="6dp"
app:tabRippleColor="@null" />
<com.framework.tagflow.MultiTagFlowLayout
android:layout_marginLeft="16dp"
android:layout_marginRight="16dp"
android:id="@+id/multiFlowTagSelf"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:hasMore="true"
app:layout_type="FlowLayout"
app:tagsHorizontalSpace="@dimen/dp_5"
app:tagsVerticalSpace="@dimen/dp_5"/>
</com.google.android.material.appbar.AppBarLayout>
......@@ -159,6 +154,7 @@
</LinearLayout>
<LinearLayout
android:visibility="gone"
android:id="@+id/ll_main_watching_root"
android:layout_width="match_parent"
android:layout_height="wrap_content"
......
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/constraint_layout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical">
android:layout_gravity="center_vertical|center_horizontal"
android:layout_margin="@dimen/dp_8"
android:background="@drawable/common_bg_radius_15_white"
android:paddingLeft="16dp"
android:paddingTop="4dp"
android:paddingRight="16dp"
android:paddingBottom="4dp">
<TextView
android:id="@+id/item_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:paddingLeft="2dp"
android:paddingTop="6dp"
android:paddingRight="5dp"
android:paddingBottom="6dp"
android:textColor="@color/color_8D8F90"
android:textSize="16sp"
android:textStyle="bold" />
android:ellipsize="end"
android:text="香港"
android:textColor="@color/color_333333"
android:textSize="@dimen/sp_13"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</LinearLayout>
\ No newline at end of file
</androidx.constraintlayout.widget.ConstraintLayout>
\ No newline at end of file
......@@ -44,7 +44,7 @@ WEIXIN_APP_SECRET =9eff885315f5f74fc9d6980e2bb1714a
RELEASE_UMENG_KEY=64d214b2a1a164591b65956b
#TalkingData
RELEASE_TALKING_DATA_KEY="E91735A7978140A8ABD1BB32D337CCAB"
RELEASE_TALKING_DATA_KEY="C4092984E50144DD802C4AC32DD40F74"
GROMORE_APP_ID="5423447"
GROMORE_SPLASH_CODE="102416580"
......
plugins {
id 'com.android.library'
id 'org.jetbrains.kotlin.android'
}
version = '1.0'
android {
namespace 'com.framework.tagflow'
compileSdk 31
defaultConfig {
minSdk 21
targetSdk 31
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
consumerProguardFiles "consumer-rules.pro"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
}
dependencies {
implementation 'androidx.core:core-ktx:1.3.2'
implementation 'androidx.appcompat:appcompat:1.2.0'
implementation 'com.google.android.material:material:1.2.1'
implementation 'androidx.constraintlayout:constraintlayout:2.0.4'
}
\ No newline at end of file
# Add project specific ProGuard rules here.
# You can control the set of applied configuration files using the
# proguardFiles setting in build.gradle.
#
# For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html
# If your project uses WebView with JS, uncomment the following
# and specify the fully qualified class name to the JavaScript interface
# class:
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
# public *;
#}
# Uncomment this to preserve the line number information for
# debugging stack traces.
#-keepattributes SourceFile,LineNumberTable
# If you keep the line number information, uncomment this to
# hide the original source file name.
#-renamesourcefileattribute SourceFile
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<manifest>
</manifest>
\ No newline at end of file
package com.framework.tagflow
import android.graphics.Rect
import android.view.View
import androidx.recyclerview.widget.RecyclerView
/**
* @author: xiaxueyi
* @date: 2022-10-25
* @time: 13:55
* @说明:
*/
class GridLayoutItemDecoration(
private val spanCount: Int,
private val spacing: Int,
private val includeEdge: Boolean = false
) :
RecyclerView.ItemDecoration() {
override fun getItemOffsets(
outRect: Rect,
view: View,
parent: RecyclerView,
state: RecyclerView.State
) {
val position = parent.getChildAdapterPosition(view) // item position
val column = position % spanCount // item column
if (includeEdge) {
outRect.left = spacing - column * spacing / spanCount // spacing - column * ((1f / spanCount) * spacing)
outRect.right = (column + 1) * spacing / spanCount // (column + 1) * ((1f / spanCount) * spacing)
if (position < spanCount) { // top edge
outRect.top = spacing
}
outRect.bottom = spacing // item bottom
} else {
outRect.left = column * spacing / spanCount // column * ((1f / spanCount) * spacing)
outRect.right = spacing - (column + 1) * spacing / spanCount // spacing - (column + 1) * ((1f / spanCount) * spacing)
if (position >= spanCount) {
outRect.top = spacing // item top
}
}
}
/**
* 获取分割线的高度
* @return Int
*/
fun getSpaceHeight():Int{
return spacing
}
/**
*
* @return Int
*/
fun getSpaceCount():Int{
return spanCount
}
/**
*
* @return Boolean
*/
fun getIncludeEdge():Boolean{
return includeEdge
}
}
\ No newline at end of file
package com.framework.tagflow.adapter
import android.view.View
import android.view.ViewGroup
import android.widget.BaseAdapter
import com.framework.tagflow.bean.BaseTagBean
abstract class BaseTagAdapter<T> : BaseAdapter() {
private var dataList: MutableList<T> = mutableListOf()
override fun getCount(): Int {
return dataList.size
}
override fun getItem(position: Int): T {
return dataList[position]
}
override fun getItemId(position: Int): Long {
return position.toLong()
}
abstract override fun getView(position: Int, convertView: View?, parent: ViewGroup): View
fun getData(): List<T> {
return dataList
}
/**
* 增加一条数据
* @param dataList T
*/
fun addData(dataList: T) {
this.dataList.add(dataList)
notifyDataSetChanged()
}
/**
* 增加列表
* @param dataList List<T>?
*/
fun addAllList(dataList: List<T>?) {
this.dataList.clear()
if (null != dataList) {
this.dataList.addAll(dataList)
}
notifyDataSetChanged()
}
/**
*
*/
open fun select(position: Int) {
if (position < 0 || position >= dataList.size) {
return
}
if(dataList[position] is BaseTagBean){
(dataList[position] as BaseTagBean).setIsSelected(true)
}
}
/**
*
*/
open fun unSelect(position: Int) {
if (position < 0 || position >= dataList.size) {
return
}
if(dataList[position] is BaseTagBean){
(dataList[position] as BaseTagBean).setIsSelected(false)
}
}
}
\ No newline at end of file
package com.framework.tagflow.bean
/**
* @author: xiaxueyi
* @date: 2022-09-16
* @time: 16:02
* @说明:
*/
open class BaseTagBean {
private var id = 0
private var title: String? = null
private var isSelected = false//是否选中
private var tag: Any? = null //标签额外信息
fun getId(): Int {
return id
}
fun setId(id: Int) {
this.id = id
}
fun getTitle(): String? {
return title
}
fun setTitle(title: String?) {
this.title = title
}
fun getTag(): Any? {
return tag
}
fun setTag(tag: Any?) {
this.tag = tag
}
fun isSelected(): Boolean {
return isSelected
}
fun setIsSelected(selected: Boolean) {
this.isSelected = selected
}
}
\ No newline at end of file
package com.framework.tagflow.interfac
import android.view.View
/**
* @author: xiaxueyi
* @date: 2022-09-13
* @time: 15:30
* @说明:
*/
interface OnTagClickListener {
fun onClick(view: View?, position: Int)
fun onLongClick(view: View?, position: Int)
}
\ No newline at end of file
package com.framework.tagflow.interfac
import android.view.View
import com.framework.tagflow.bean.BaseTagBean
/**
* @author: xiaxueyi
* @date: 2022-09-13
* @time: 15:30
* @说明:标签被选中或取消选中监听
*/
interface OnTagSelectedListener {
fun selected(view: View?, position: Int, selected: List<BaseTagBean?>?)
fun unSelected(view: View?, position: Int, selected: List<BaseTagBean?>?)
}
\ No newline at end of file
package com.framework.tagflow.tags
import android.content.Context
import android.util.AttributeSet
/**
* @author: xiaxueyi
* @date: 2022-09-19
* @time: 16:02
* @说明:
*/
class ColorfulStrokeTagView : ColorfulTagView {
constructor(context: Context) : super(context) {}
constructor(context: Context, attrs: AttributeSet?) : super(context, attrs) {}
constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(
context,
attrs,
defStyleAttr
) {
}
override fun isSolid(): Boolean {
return false
}
override fun getStrokeWidth(): Float {
return 1F
}
}
\ No newline at end of file
package com.framework.tagflow.tags
import android.content.Context
import android.graphics.Color
import android.util.AttributeSet
import java.util.*
/**
* @author: xiaxueyi
* @date: 2022-09-16
* @time: 16:02
* @说明:
*/
open class ColorfulTagView : DefaultTagView {
constructor(context: Context) : super(context) {}
constructor(context: Context, attrs: AttributeSet?) : super(context, attrs) {}
constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(
context,
attrs,
defStyleAttr
) {
}
override fun getNormalBackgroundColor(): Int {
val random = Random()
val red = random.nextInt(200) + 50
val green = random.nextInt(200) + 50
val blue = random.nextInt(200) + 50
return Color.rgb(red, green, blue)
}
}
\ No newline at end of file
package com.framework.tagflow.tags
import android.content.Context
import android.graphics.drawable.Drawable
import android.graphics.drawable.GradientDrawable
import android.graphics.drawable.StateListDrawable
import android.util.AttributeSet
import android.view.Gravity
import androidx.annotation.ColorInt
import androidx.appcompat.widget.AppCompatTextView
import androidx.core.content.ContextCompat
import com.framework.tagflow.R
import com.framework.tagflow.utils.DensityUtils
/**
* @author: xiaxueyi
* @date: 2022-09-16
* @time: 16:02
* @说明:
*/
open class DefaultTagView @JvmOverloads constructor(
protected var mContext: Context,
attrs: AttributeSet? = null,
defStyleAttr: Int = 0
) : AppCompatTextView(
mContext, attrs, defStyleAttr
) {
//默认标签内间距
private val DEFAULT_TAG_PADDING = 5f
//默认标签背景圆角大小
private val DEFAULT_TAG_CORNER = 3f
//默认边框宽度(仅在非实心背景有效),单位dp
private val DEFAULT_TAG_STROKE = 1f
//默认标签背景正常颜色
private val DEFAULT_TAG_BACKGROUND_COLOR = -0x1
//默认标签背景按下颜色
private val DEFAULT_TAG_BACKGROUND_PRESSED_COLOR = -0x68bba4
private fun init() {
val padding: Int = DensityUtils.dp2px(mContext, getTagPadding())
setPadding(padding, padding, padding, padding)
gravity = Gravity.CENTER
setBackgroundDrawable(getBackgroundDrawable())
}//设置字体颜色的选择器
//完全自定义tag的样式请重写此方法
//返回一个Drawable背景样式
protected open fun getBackgroundDrawable(): Drawable? {
//设置字体颜色的选择器
val colorSateList =ContextCompat.getColorStateList(context,R.color.secondary_text)
setTextColor(colorSateList)
val normal = GradientDrawable()
normal.shape = GradientDrawable.RECTANGLE
normal.cornerRadius = DensityUtils.dp2px(mContext, getTagRadius()).toFloat()
if (isSolid()) {
normal.setColor(getNormalBackgroundColor())
} else {
normal.setStroke(
DensityUtils.dp2px(mContext, getStrokeWidth()),
getNormalBackgroundColor()
)
normal.setColor(getBackgroundColor())
}
val pressed = GradientDrawable()
pressed.shape = GradientDrawable.RECTANGLE
pressed.cornerRadius = DensityUtils.dp2px(mContext, getTagRadius()).toFloat()
if (isSolid()) {
pressed.setColor(getPressedBackgroundColor())
} else {
pressed.setStroke(
DensityUtils.dp2px(mContext, getStrokeWidth()),
getPressedBackgroundColor()
)
pressed.setColor(getPressedBackgroundColor())
}
val selector = StateListDrawable()
selector.addState(intArrayOf(android.R.attr.state_pressed), pressed)
selector.addState(intArrayOf(), normal)
return selector
}
//默认tag背景颜色
@ColorInt
protected open fun getNormalBackgroundColor(): Int {
return DEFAULT_TAG_BACKGROUND_COLOR
}
//按下tag时背景颜色
@ColorInt
protected open fun getPressedBackgroundColor(): Int {
return DEFAULT_TAG_BACKGROUND_PRESSED_COLOR
}
//tag的圆角角度
protected open fun getTagRadius(): Float {
return DEFAULT_TAG_CORNER
}
//tag内间距
protected open fun getTagPadding(): Float {
return DEFAULT_TAG_PADDING
}
/***
* 是否为实心背景
*
* @return true:实心的,false:空心,可通过[.getStrokeWidth]设置边框宽度
*/
protected open fun isSolid(): Boolean {
return true
}
//设置边框的宽度,单位dp
protected open fun getStrokeWidth(): Float {
return DEFAULT_TAG_STROKE
}
//当设置了空心加边框的tag时给tag加一个背景,
//防止在透明背景上无法显示点击颜色
@ColorInt
protected open fun getBackgroundColor(): Int {
return DEFAULT_TAG_BACKGROUND_COLOR
}
init {
init()
}
}
\ No newline at end of file
package com.framework.tagflow.tags
import android.content.Context
import android.graphics.drawable.Drawable
import android.graphics.drawable.GradientDrawable
import android.graphics.drawable.StateListDrawable
import android.util.AttributeSet
import androidx.core.content.ContextCompat
import com.framework.tagflow.R
import com.framework.tagflow.utils.DensityUtils
/**
* @author: xiaxueyi
* @date: 2022-09-16
* @time: 15:02
* @说明:
*/
class MutSelectedTagView : DefaultTagView {
constructor(context: Context) : super(context) {}
constructor(context: Context, attrs: AttributeSet?) : super(context, attrs) {}
constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(
context,
attrs,
defStyleAttr
) {
}
override fun getBackgroundDrawable(): Drawable? {
//设置字体颜色的选择器
val colorSateList = ContextCompat.getColorStateList(context,R.color.secondary_text)
setTextColor(colorSateList)
val normal = GradientDrawable()
normal.shape = GradientDrawable.RECTANGLE
normal.cornerRadius = DensityUtils.dp2px(mContext, getTagRadius()).toFloat()
if (isSolid()) {
normal.setColor(getNormalBackgroundColor())
} else {
normal.setStroke(
DensityUtils.dp2px(mContext, getStrokeWidth()),
getNormalBackgroundColor()
)
normal.setColor(getBackgroundColor())
}
val pressed = GradientDrawable()
pressed.shape = GradientDrawable.RECTANGLE
pressed.cornerRadius = DensityUtils.dp2px(mContext, getTagRadius()).toFloat()
if (isSolid()) {
pressed.setColor(getPressedBackgroundColor())
} else {
pressed.setStroke(
DensityUtils.dp2px(mContext, getStrokeWidth()),
getPressedBackgroundColor()
)
pressed.setColor(getPressedBackgroundColor())
}
val selector = StateListDrawable()
selector.addState(intArrayOf(android.R.attr.state_pressed), pressed)
selector.addState(intArrayOf(android.R.attr.state_selected), pressed)
selector.addState(intArrayOf(), normal)
return selector
}
fun toggle() {
this.isSelected = !isSelected
}
}
\ No newline at end of file
package com.aa.cat.ui.view.tagFlow.tags
import android.content.Context
import android.graphics.Color
import android.util.AttributeSet
import com.framework.tagflow.tags.DefaultTagView
/**
* @author: xiaxueyi
* @date: 2022-09-16
* @time: 11:02
* @说明:
*/
class StrokeTagView : DefaultTagView {
constructor(context: Context) : super(context) {}
constructor(context: Context, attrs: AttributeSet?) : super(context, attrs) {}
constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : super(
context,
attrs,
defStyleAttr
) {
}
override fun isSolid(): Boolean {
return false
}
override fun getStrokeWidth(): Float {
return 1F
}
override fun getNormalBackgroundColor(): Int {
return Color.parseColor("#000000")
}
override fun getPressedBackgroundColor(): Int {
return Color.parseColor("#aa666666")
}
}
\ No newline at end of file
package com.framework.tagflow.utils
import android.content.Context
import android.util.TypedValue
/**
* @author: xiaxueyi
* @date: 2022-09-19
* @time: 13:02
* @说明:
*/
class DensityUtils private constructor() {
companion object {
/**
* dp转px
*
* @param context 上下文
* @param dpVal dp值
* @return result in px
*/
fun dp2px(context: Context, dpVal: Float): Int {
return TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP,
dpVal, context.resources.displayMetrics
).toInt()
}
/**
* sp转px
*
* @param context 上下文
* @param spVal sp值
* @return result in px
*/
fun sp2px(context: Context, spVal: Float): Int {
return TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_SP,
spVal, context.resources.displayMetrics
).toInt()
}
/**
* px转dp
*
* @param context 上下文
* @param pxVal px值
* @return result in dp
*/
fun px2dp(context: Context, pxVal: Float): Float {
val scale = context.resources.displayMetrics.density
return pxVal / scale
}
/**
* px转sp
*
* @param context 上下文
* @param pxVal px值
* @return result in sp
*/
fun px2sp(context: Context, pxVal: Float): Float {
return pxVal / context.resources.displayMetrics.scaledDensity
}
}
init {
/* cannot be instantiated */
throw UnsupportedOperationException("cannot be instantiated")
}
}
\ No newline at end of file
package com.framework.tagflow.view
import android.content.Context
import android.util.AttributeSet
import android.view.MotionEvent
import android.widget.ScrollView
/**
* 可控制滑动,可控制固定
*/
class ControlScrollView : ScrollView {
private var forceFixed = false//强制固定
private var canScroll = false
constructor(context: Context?) : super(context) {}
constructor(context: Context?, attrs: AttributeSet?) : super(context, attrs) {}
/**
* 是否可以滑动
* @return
*/
fun isCanScroll(): Boolean {
return canScroll
}
/**
* 设置是否可以滑动
* @param isCan
*/
fun setCanScroll(isCan: Boolean) {
canScroll = isCan
}
/**
* 是否强制固定
* @return
*/
fun isForceFixed(): Boolean {
return forceFixed
}
/**
* 设置是否强制固定
* @param forceFixed
*/
fun setForceFixed(forceFixed: Boolean) {
this.forceFixed = forceFixed
}
override fun dispatchTouchEvent(event: MotionEvent): Boolean {
if (!forceFixed && canScroll) {
parent.requestDisallowInterceptTouchEvent(true)
}
return super.dispatchTouchEvent(event)
}
}
\ No newline at end of file
package com.framework.tagflow.view
import android.annotation.SuppressLint
import android.content.Context
import android.util.AttributeSet
import android.view.View
import android.view.ViewGroup
import com.framework.tagflow.utils.DensityUtils
open class FlowLayout : ViewGroup {
private var mContext: Context? = null
private var mLines: MutableList<Line> = ArrayList() // 记录当前有多少行
private var horizontalSpace = 0
private var verticalSpace = 0
private var mDefaultViewMaxWidth:Int=100 //子view默认宽度的最大值
private var mDefaultColumn:Int=3;//默认列数三列
private var mAverageWidth:Int=0 // 存储屏幕的1/3宽度
private var isNeedMinimumWidth:Boolean=true //是否需要最小宽度值
/**
*
* @param context Context?
* @constructor
*/
constructor(context: Context?) : super(context) {
mContext = context
}
/**
*
* @param context Context?
* @param attrs AttributeSet?
* @constructor
*/
constructor(context: Context?, attrs: AttributeSet?) : super(context, attrs) {}
/**
*
* @param horizontalSpace Int
* @param verticalSpace Int
*/
fun setSpace(horizontalSpace: Int, verticalSpace: Int) {
this.horizontalSpace = horizontalSpace
this.verticalSpace = verticalSpace
}
/**
* 获取单行的高度
* @return
*/
fun getLineHeight(): Int {
return if (mLines.size > 0) {
mLines[0].height
} else{
0
}
}
/**
* 获取行数
* @return
*/
fun getLineSize(): Int {
return if (mLines.size > 0) {
mLines.size
} else {
0
}
}
override fun onLayout(changed: Boolean, l: Int, t: Int, r: Int, b: Int) {
var top = this.paddingTop
for (i in mLines.indices) {
val line = mLines[i]
// 自己布局
line.layout(top, this.paddingStart)
top += line.height
if (i != mLines.size - 1) {
top += verticalSpace
}
}
}
@SuppressLint("DrawAllocation")
override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
// 清空
mLines.clear()
var mCurrentLine: Line? = null
// 获得容器的宽度
val widthSize = MeasureSpec.getSize(widthMeasureSpec)
//获取最大的宽
val maxWidth = widthSize - this.paddingStart - this.paddingEnd
//子类的数量
val childCount = this.childCount
//计算屏幕的三分之一宽度
mAverageWidth=maxWidth/mDefaultColumn
for (i in 0 until childCount) {
val view = getChildAt(i)
if (view.visibility == GONE) {
continue
}
if(isNeedMinimumWidth){
val min = widthSize.coerceAtMost(DensityUtils.dp2px(context, mDefaultViewMaxWidth.toFloat()))
view.minimumWidth=min
}
// 测量孩子
measureChild(view, widthMeasureSpec, heightMeasureSpec)
// 将孩子记录到行中
if (mCurrentLine == null) {
// 新建行
mCurrentLine = Line(maxWidth, horizontalSpace)
// 记录行
mLines.add(mCurrentLine)
// 给行添加孩子
mCurrentLine.addView(view)
} else {
// 判断是否可以添加
if (mCurrentLine.canAdd(view)) {
// 可以添加
mCurrentLine.addView(view)
} else {
// 不可以添加
// 新建一行
mCurrentLine = Line(maxWidth, horizontalSpace)
// 记录行
mLines.add(mCurrentLine)
// 给行添加孩子
mCurrentLine.addView(view)
}
}
}
// 设置自己的宽度和高度
var measuredHeight = this.paddingTop + this.paddingBottom
// 添加行的高度
for (i in mLines.indices) {
measuredHeight += mLines[i].height
}
// 间距
measuredHeight += (mLines.size - 1) * verticalSpace
// 设置自己的宽度和高度
setMeasuredDimension(widthSize, measuredHeight)
}
private inner class Line(
private var maxWidth: Int,// 行最大宽度
private var space: Int // view和view之间的间隔
) {
// 属性,方法,构造
// 行中的控件
private val mViews: MutableList<View> = ArrayList()
private var usedWidth = 0// 已经使用的宽度
var height = 0 // 行的高度
/**
*
* @param top Int
* @param left Int
*/
fun layout(top: Int, left: Int) {
// 给view布局
var mleft = left
for (i in mViews.indices) {
val view = mViews[i]
var viewWidth = view.measuredWidth
var viewHeight = view.measuredHeight
view.measure(MeasureSpec.makeMeasureSpec(viewWidth, MeasureSpec.EXACTLY), MeasureSpec.makeMeasureSpec(viewHeight, MeasureSpec.EXACTLY))
viewWidth = view.measuredWidth
viewHeight = view.measuredHeight
val avgHeight = ((height - viewHeight) / 2f + 0.5f).toInt()
val vLeft = mleft
val vTop = top + avgHeight
val vRight = vLeft + viewWidth
val vBottom = vTop + viewHeight
view.layout(vLeft, vTop, vRight, vBottom)
mleft += space + viewWidth
}
}
/**
* 添加view的方法
*
* @param view
*/
fun addView(view: View) {
val viewWidth = view.measuredWidth
val viewHeight = view.measuredHeight
if (mViews.size == 0) {
if (viewWidth > maxWidth) {
usedWidth = maxWidth
height = viewHeight
} else {
usedWidth = viewWidth
height = viewHeight
}
} else {
usedWidth += space + viewWidth
height = if (height > viewHeight) height else viewHeight // 选择大的高度
}
mViews.add(view)
}
/**
* 判断是否可以往行中添加控件
*
* @param view
*/
fun canAdd(view: View): Boolean {
if (mViews.size == 0) {
return true
}
// 已经使用的 + 间距+ 要加的view的宽度 > maxWidth ,添加不进来
// return usedWidth + space + view.measuredWidth <= maxWidth
return usedWidth+ view.measuredWidth <= maxWidth
}
}
fun clearAllView() {
mLines = ArrayList()
this.invalidate()
}
}
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="@color/color_F5F3F0" />
<stroke android:width="@dimen/dp_1"
android:color="@color/color_CCC8C2"/>
<corners android:radius="@dimen/dp_30" />
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<corners android:radius="@dimen/dp_8"/>
<solid android:color="#80000000"/>
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="@color/white" />
<corners android:radius="@dimen/dp_15" />
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="@color/white" />
<corners android:radius="@dimen/dp_0" />
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="@color/color_F5F3F0" />
<stroke android:width="@dimen/dp_1"
android:color="@color/color_CCC8C2"/>
<corners android:radius="@dimen/dp_30" />
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<corners android:radius="@dimen/dp_8"/>
<solid android:color="#80000000"/>
</shape>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<!--toast Textview-->
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/ad_hoc_toast_textview"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingStart="@dimen/dp_15"
android:paddingEnd="@dimen/dp_15"
android:paddingTop="@dimen/dp_12"
android:paddingBottom="@dimen/dp_12"
android:layout_margin="@dimen/dp_20"
android:background="@drawable/toast_background"
android:textColor="#1e1e1e"
android:gravity="center"
android:visibility="visible"
android:layout_alignParentBottom="true"
tools:text="message ..." />
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/empty_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:background="@color/color_transparent"
android:orientation="vertical">
<TextView
android:id="@+id/title"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:gravity="center"
android:textColor="@color/color_333333"
android:textSize="@dimen/sp_15"
android:textStyle="normal"
android:text="暂无数据"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"/>
</androidx.constraintlayout.widget.ConstraintLayout>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<LinearLayout
android:id="@+id/ll_tag_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<FrameLayout
android:id="@+id/fl_empty"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
android:visibility="gone"/>
<com.framework.tagflow.view.ControlScrollView
android:id="@+id/hsv_tag_content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:scrollbars="none" />
<LinearLayout
android:id="@+id/rl_show_more"
android:orientation="vertical"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:padding="@dimen/dp_3">
<LinearLayout
android:orientation="horizontal"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:focusable="auto"
android:gravity="center"
android:layout_margin="@dimen/dp_2"
android:paddingStart="@dimen/dp_5"
android:paddingEnd="@dimen/dp_5">
<TextView
android:id="@+id/tv_more_hint"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/expandHint"
android:textStyle="bold"
android:textColor="#262626"
android:textSize="@dimen/sp_14"
android:layout_gravity="center"
android:layout_marginStart="@dimen/dp_5"
android:layout_marginEnd="@dimen/dp_5"
android:gravity="center"
android:visibility="visible" />
<ImageView
android:id="@+id/iv_arrow_more"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:src="@drawable/common_icon_down_arrow" />
</LinearLayout>
</LinearLayout>
</LinearLayout>
</merge>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!--流布局-->
<declare-styleable name="TagFlowLayout">
<attr name="tagsHorizontalSpace" format="dimension" />
<attr name="tagsVerticalSpace" format="dimension" />
<attr name="animationDuration" format="integer" />
<attr name="hasMore" format="boolean" />
<attr name="foldHint" format="reference|string" />
<attr name="expandHint" format="reference|string" />
<!--布局类型,列表或者-->
<attr name="layout_type" format="reference">
<enum name="RecyclerView" value="0" />
<enum name="FlowLayout" value="1" />
</attr>
<!--LayoutManager 模式-->
<attr name="layoutManager_Mode" format="reference">
<enum name="LinearLayoutManager" value="0"/>
<enum name="GridLayoutManager" value="1"/>
</attr>
</declare-styleable>
</resources>
\ No newline at end of file
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!-- text color -->
<color name="color_4D4D4D">#4D4D4D</color>
<color name="color_333333">#333333</color>
<color name="color_FCFCFC">#FCFCFC</color>
<color name="color_808080">#808080</color>
<!-- image color -->
<color name="color_D6D0C7">#D6D0C7</color>
<color name="color_E8E4DF">#E8E4DF</color>
<color name="color_F5B95F">#F5B95F</color>
<color name="color_F8E49E">#F8E49E</color>
<color name="color_959595">#959595</color>
<!-- bg color -->
<color name="color_F2FFFFFF">#F2FFFFFF</color>
<color name="color_11AB9B">#11AB9B</color>
<color name="color_EF6A39">#EF6A39</color>
<color name="color_F0E4D3">#F0E4D3</color>
<color name="color_F0EDE9">#F0EDE9</color>
<color name="color_F0E8DE">#F0E8DE</color>
<color name="color_f6Ce7e">#f6Ce7e</color>
<color name="color_FFFDFA">#FFFDFA</color>
<color name="color_FFFFFF">#FFFFFF</color>
<color name="color_FAF9F7">#FAF9F7</color>
<color name="color_F5A05F">#f5a05f</color>
<!-- shadow color-->
<color name="color_F5F3F0">#F5F3F0</color>
<color name="white">#FFFFFF</color>
<color name="color_8C8B89">#8C8B89</color>
<!--Line-->
<color name="color_CCC8C2">#33CCC8C2</color>
<color name="color_8A8A8A">#8a8a8a</color>
<color name="color_EAEAEA">#EAEAEA</color>
<!--tagflow-->
<color name="secondary_text">#8a000000</color>
<color name="tag_layout_bg">#def2f2f2</color>
<color name="dividers">#1f000000</color>
<!--标题搜索框背景颜色-->
<color name="common_toolbar_search_bg_color">#208C8B89</color>
<!--标题搜索框说明性文字颜色-->
<color name="common_toolbar_search_title_hint_text_color">#7f7f7f</color>
<color name="color_transparent">#00000000</color>
<!-- 彈窗 -->
<color name="list_line_color">#ccc8c2</color>
<color name="color_8a8894">#8a8894</color>
</resources>
\ No newline at end of file
This diff is collapsed.
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string name="more">更多</string>
<string name="cancel">取消</string>
<string name="foldHint">收起</string>
<string name="expandHint">展开</string>
</resources>
\ No newline at end of file
......@@ -3,3 +3,4 @@ include ':oaid'
include ':rxpay'
include ':alipay'
include ':wxpay'
include ':library_tagflow'
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment