29
29
*/
30
30
@ SuppressWarnings ({"unused" , "UnusedReturnValue" })
31
31
public class TitleBar extends FrameLayout
32
- implements View .OnClickListener ,
33
- View .OnLayoutChangeListener {
32
+ implements View .OnClickListener {
34
33
35
34
private static final String LOG_TAG = "TitleBar" ;
36
35
@@ -275,7 +274,8 @@ public TitleBar(Context context, AttributeSet attrs, int defStyleAttr) {
275
274
addView (mRightView , 2 );
276
275
addView (mLineView , 3 );
277
276
278
- addOnLayoutChangeListener (this );
277
+ addOnLayoutChangeListener (mConstraintChildViewWidthListener );
278
+ addOnLayoutChangeListener (mLimitChildViewStatusListener );
279
279
280
280
// 如果当前是布局预览模式
281
281
if (isInEditMode ()) {
@@ -291,56 +291,6 @@ public TitleBar(Context context, AttributeSet attrs, int defStyleAttr) {
291
291
}
292
292
}
293
293
294
- /**
295
- * {@link View.OnLayoutChangeListener}
296
- */
297
-
298
- @ Override
299
- public void onLayoutChange (View v , int left , int top , int right , int bottom , int oldLeft , int oldTop , int oldRight , int oldBottom ) {
300
- // 先移除当前的监听,因为 TextView.setMaxWidth 方法会重新触发监听
301
- removeOnLayoutChangeListener (this );
302
-
303
- // 标题栏子 View 最大宽度限制算法
304
- post (() -> {
305
- // 这里要延迟执行,否则会导致子 View.getWidth 的时候为零
306
- int barWidth = right - left ;
307
- int sideWidth = Math .max (mLeftView .getWidth (), mRightView .getWidth ());
308
- int maxWidth = sideWidth * 2 + mTitleView .getWidth ();
309
- // 算出来子 View 的宽大于标题栏的宽度
310
- if (maxWidth >= barWidth ) {
311
- // 判断是左右项太长还是标题项太长
312
- if (sideWidth > barWidth / 3 ) {
313
- // 如果是左右项太长,那么按照比例进行划分
314
- TitleBarSupport .setMaxWidth (mLeftView , barWidth / 4 );
315
- TitleBarSupport .setMaxWidth (mTitleView , barWidth / 2 );
316
- TitleBarSupport .setMaxWidth (mRightView , barWidth / 4 );
317
- } else {
318
- // 如果是标题项太长,那么就进行动态计算
319
- TitleBarSupport .setMaxWidth (mLeftView , sideWidth );
320
- TitleBarSupport .setMaxWidth (mTitleView , barWidth - sideWidth * 2 );
321
- TitleBarSupport .setMaxWidth (mRightView , sideWidth );
322
- }
323
- } else {
324
- // 不限制子 View 的最大宽度
325
- TitleBarSupport .setMaxWidth (mLeftView , Integer .MAX_VALUE );
326
- TitleBarSupport .setMaxWidth (mTitleView , Integer .MAX_VALUE );
327
- TitleBarSupport .setMaxWidth (mRightView , Integer .MAX_VALUE );
328
- }
329
-
330
- // 解决在外部触摸时触发点击效果的问题
331
- mLeftView .setClickable (true );
332
- mTitleView .setClickable (true );
333
- mRightView .setClickable (true );
334
- // TextView 里面必须有东西才能被点击
335
- mLeftView .setEnabled (TitleBarSupport .isContainContent (mLeftView ));
336
- mTitleView .setEnabled (TitleBarSupport .isContainContent (mTitleView ));
337
- mRightView .setEnabled (TitleBarSupport .isContainContent (mRightView ));
338
-
339
- // 这里再次监听需要延迟,否则会导致递归的情况发生
340
- addOnLayoutChangeListener (TitleBar .this );
341
- });
342
- }
343
-
344
294
/**
345
295
* {@link View.OnClickListener}
346
296
*/
@@ -701,7 +651,7 @@ public TitleBar setRightIconTint(int color) {
701
651
}
702
652
703
653
/**
704
- * 清楚标题的图标着色器
654
+ * 清除标题的图标着色器
705
655
*/
706
656
public TitleBar clearTitleIconTint () {
707
657
mTitleIconTint = TitleBarSupport .NO_COLOR ;
@@ -710,7 +660,7 @@ public TitleBar clearTitleIconTint() {
710
660
}
711
661
712
662
/**
713
- * 清楚左标题的图标着色器
663
+ * 清除左标题的图标着色器
714
664
*/
715
665
public TitleBar clearLeftIconTint () {
716
666
mLeftIconTint = TitleBarSupport .NO_COLOR ;
@@ -719,7 +669,7 @@ public TitleBar clearLeftIconTint() {
719
669
}
720
670
721
671
/**
722
- * 清楚右标题的图标着色器
672
+ * 清除右标题的图标着色器
723
673
*/
724
674
public TitleBar clearRightIconTint () {
725
675
mRightIconTint = TitleBarSupport .NO_COLOR ;
@@ -930,4 +880,80 @@ public ITitleBarStyle getCurrentStyle() {
930
880
public static void setDefaultStyle (ITitleBarStyle style ) {
931
881
sGlobalStyle = style ;
932
882
}
883
+
884
+ private final View .OnLayoutChangeListener mConstraintChildViewWidthListener = new OnLayoutChangeListener () {
885
+
886
+ @ Override
887
+ public void onLayoutChange (View v , int left , int top , int right , int bottom , int oldLeft , int oldTop , int oldRight , int oldBottom ) {
888
+ // 暂时先移除当前的监听,因为 TextView.setMaxWidth 方法会重新触发监听
889
+ removeOnLayoutChangeListener (this );
890
+
891
+ // 标题栏子 View 最大宽度限制算法
892
+ post (() -> {
893
+ // 这里要延迟执行,否则会导致子 View.getWidth 的时候为零
894
+ int titleBarWidth = right - left ;
895
+ int leftViewWidth = mLeftView .getWidth ();
896
+ int centerViewWidth = mTitleView .getWidth ();
897
+ int rightViewWidth = mRightView .getWidth ();
898
+
899
+ int maxEdgeWidth = Math .max (leftViewWidth , rightViewWidth );
900
+ int calculateTotalWidth = maxEdgeWidth * 2 + centerViewWidth ;
901
+ // 算出来子 View 的宽大于标题栏的宽度
902
+ if (calculateTotalWidth >= titleBarWidth ) {
903
+ // 判断是左右项太长还是标题项太长
904
+ if (maxEdgeWidth > titleBarWidth / 3 ) {
905
+ // 如果是左右项太长,那么按照比例进行划分
906
+ TitleBarSupport .setMaxWidth (mLeftView , titleBarWidth / 4 );
907
+ TitleBarSupport .setMaxWidth (mTitleView , titleBarWidth / 2 );
908
+ TitleBarSupport .setMaxWidth (mRightView , titleBarWidth / 4 );
909
+ } else {
910
+ // 如果是标题项太长,那么就进行动态计算
911
+ TitleBarSupport .setMaxWidth (mLeftView , maxEdgeWidth );
912
+ TitleBarSupport .setMaxWidth (mTitleView , titleBarWidth - maxEdgeWidth * 2 );
913
+ TitleBarSupport .setMaxWidth (mRightView , maxEdgeWidth );
914
+ }
915
+ } else {
916
+ // 不限制子 View 的最大宽度
917
+ TitleBarSupport .setMaxWidth (mLeftView , Integer .MAX_VALUE );
918
+ TitleBarSupport .setMaxWidth (mTitleView , Integer .MAX_VALUE );
919
+ TitleBarSupport .setMaxWidth (mRightView , Integer .MAX_VALUE );
920
+ }
921
+
922
+ removeCallbacks (mAddOnLayoutChangeListenerRunnable );
923
+ // 这里再次监听需要延迟,否则会导致递归的情况发生
924
+ post (mAddOnLayoutChangeListenerRunnable );
925
+ });
926
+ }
927
+ };
928
+
929
+ @ SuppressWarnings ("all" )
930
+ private final View .OnLayoutChangeListener mLimitChildViewStatusListener = new OnLayoutChangeListener () {
931
+
932
+ @ Override
933
+ public void onLayoutChange (View v , int left , int top , int right , int bottom , int oldLeft , int oldTop , int oldRight , int oldBottom ) {
934
+ // 解决在外部触摸时触发点击效果的问题
935
+ if (!mLeftView .isClickable ()) {
936
+ mLeftView .setClickable (true );
937
+ }
938
+ if (!mTitleView .isClickable ()) {
939
+ mTitleView .setClickable (true );
940
+ }
941
+ if (!mRightView .isClickable ()) {
942
+ mRightView .setClickable (true );
943
+ }
944
+
945
+ // TextView 里面必须有东西才能被点击
946
+ if (!mLeftView .isEnabled ()) {
947
+ mLeftView .setEnabled (TitleBarSupport .isContainContent (mLeftView ));
948
+ }
949
+ if (!mTitleView .isEnabled ()) {
950
+ mTitleView .setEnabled (TitleBarSupport .isContainContent (mTitleView ));
951
+ }
952
+ if (!mRightView .isEnabled ()) {
953
+ mRightView .setEnabled (TitleBarSupport .isContainContent (mRightView ));
954
+ }
955
+ }
956
+ };
957
+
958
+ private final Runnable mAddOnLayoutChangeListenerRunnable = () -> addOnLayoutChangeListener (mConstraintChildViewWidthListener );
933
959
}
0 commit comments