@quicktvui/ai 1.0.7 → 1.0.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (204) hide show
  1. package/package.json +1 -1
  2. package/rules/.clinerules +27 -4
  3. package/rules/.cursorrules +27 -4
  4. package/rules/.github/copilot-instructions.md +27 -4
  5. package/rules/.source/hippy/extend_views/CoverFlowHorizontalView.java +203 -0
  6. package/rules/.source/hippy/extend_views/CoverFlowVerticalView.java +203 -0
  7. package/rules/.source/hippy/extend_views/CoverFlowViewController.java +195 -0
  8. package/rules/.source/hippy/extend_views/EngineRootView.java +125 -0
  9. package/rules/.source/hippy/extend_views/ExtendTag.java +83 -0
  10. package/rules/.source/hippy/extend_views/FocusSearchHelper.java +124 -0
  11. package/rules/.source/hippy/extend_views/IRecyclerItemView.java +12 -0
  12. package/rules/.source/hippy/extend_views/JSEventHandleView.java +5 -0
  13. package/rules/.source/hippy/extend_views/MarqueeRelayManager.java +133 -0
  14. package/rules/.source/hippy/extend_views/MarqueeRelayTextView.java +211 -0
  15. package/rules/.source/hippy/extend_views/ProgressBarView.java +83 -0
  16. package/rules/.source/hippy/extend_views/ProgressBarViewController.java +145 -0
  17. package/rules/.source/hippy/extend_views/SeekBarView.java +104 -0
  18. package/rules/.source/hippy/extend_views/SeekBarViewController.java +218 -0
  19. package/rules/.source/hippy/extend_views/StateImageView.java +149 -0
  20. package/rules/.source/hippy/extend_views/StateImageViewController.java +34 -0
  21. package/rules/.source/hippy/extend_views/TVButtonView.java +314 -0
  22. package/rules/.source/hippy/extend_views/TVButtonViewController.java +89 -0
  23. package/rules/.source/hippy/extend_views/TVTextView.java +684 -0
  24. package/rules/.source/hippy/extend_views/TVViewActor.java +811 -0
  25. package/rules/.source/hippy/extend_views/TVViewActorHost.java +6 -0
  26. package/rules/.source/hippy/extend_views/TVViewActor/346/216/245/345/205/245.md +66 -0
  27. package/rules/.source/hippy/extend_views/TemplateUtil.java +336 -0
  28. package/rules/.source/hippy/extend_views/TextButtonNode.java +47 -0
  29. package/rules/.source/hippy/extend_views/TextViewController.java +377 -0
  30. package/rules/.source/hippy/extend_views/fastlist/CenterFlyInAnimator.java +96 -0
  31. package/rules/.source/hippy/extend_views/fastlist/ChildOnScreenScroller.java +548 -0
  32. package/rules/.source/hippy/extend_views/fastlist/ClonedViewTag.java +17 -0
  33. package/rules/.source/hippy/extend_views/fastlist/EventDeliverer.java +55 -0
  34. package/rules/.source/hippy/extend_views/fastlist/FastAdapter.java +4683 -0
  35. package/rules/.source/hippy/extend_views/fastlist/FastAdapterUtil.java +982 -0
  36. package/rules/.source/hippy/extend_views/fastlist/FastFlexNode.java +48 -0
  37. package/rules/.source/hippy/extend_views/fastlist/FastFlexView.java +873 -0
  38. package/rules/.source/hippy/extend_views/fastlist/FastFlexViewController.java +130 -0
  39. package/rules/.source/hippy/extend_views/fastlist/FastItemNode.java +67 -0
  40. package/rules/.source/hippy/extend_views/fastlist/FastItemView.java +306 -0
  41. package/rules/.source/hippy/extend_views/fastlist/FastItemViewController.java +106 -0
  42. package/rules/.source/hippy/extend_views/fastlist/FastListModule.java +95 -0
  43. package/rules/.source/hippy/extend_views/fastlist/FastListNode.java +90 -0
  44. package/rules/.source/hippy/extend_views/fastlist/FastListView.java +2466 -0
  45. package/rules/.source/hippy/extend_views/fastlist/FastListViewController.java +1038 -0
  46. package/rules/.source/hippy/extend_views/fastlist/FastListView/346/270/262/346/237/223/346/265/201/347/250/213/345/233/276.graffle +0 -0
  47. package/rules/.source/hippy/extend_views/fastlist/FastPendingView.java +47 -0
  48. package/rules/.source/hippy/extend_views/fastlist/ItemDecorations.java +71 -0
  49. package/rules/.source/hippy/extend_views/fastlist/ItemStoreNode.java +64 -0
  50. package/rules/.source/hippy/extend_views/fastlist/ItemStoreView.java +13 -0
  51. package/rules/.source/hippy/extend_views/fastlist/ItemStoreViewController.java +45 -0
  52. package/rules/.source/hippy/extend_views/fastlist/ListItemHolder.java +7 -0
  53. package/rules/.source/hippy/extend_views/fastlist/ListViewControlProp.java +41 -0
  54. package/rules/.source/hippy/extend_views/fastlist/MouseRecycleView.java +509 -0
  55. package/rules/.source/hippy/extend_views/fastlist/OnFastItemClickListener.java +12 -0
  56. package/rules/.source/hippy/extend_views/fastlist/OnFastItemFocusChangeListener.java +9 -0
  57. package/rules/.source/hippy/extend_views/fastlist/OnFastScrollStateChangedListener.java +7 -0
  58. package/rules/.source/hippy/extend_views/fastlist/PendingListNode.java +18 -0
  59. package/rules/.source/hippy/extend_views/fastlist/PendingViewController.java +13 -0
  60. package/rules/.source/hippy/extend_views/fastlist/PostHandlerView.java +6 -0
  61. package/rules/.source/hippy/extend_views/fastlist/PostTaskHolder.java +20 -0
  62. package/rules/.source/hippy/extend_views/fastlist/ReplaceChildController.java +105 -0
  63. package/rules/.source/hippy/extend_views/fastlist/ReplaceChildView.java +312 -0
  64. package/rules/.source/hippy/extend_views/fastlist/TVListView.java +3692 -0
  65. package/rules/.source/hippy/extend_views/fastlist/TemplateCodeParser.java +247 -0
  66. package/rules/.source/hippy/extend_views/fastlist/Utils.java +572 -0
  67. package/rules/.source/hippy/extend_views/fastlist/ViewTag.java +317 -0
  68. package/rules/.source/hippy/extend_views/fastlist/VirtualListView.java +8 -0
  69. package/rules/.source/hippy/extend_views/fastlist/diff/FastListDataBindingHelper.java +320 -0
  70. package/rules/.source/hippy/extend_views/fastlist/diff/KeyDiffHelper.java +289 -0
  71. package/rules/.source/hippy/extend_views/fastlist/diff/NoKeyDiffHelper.java +278 -0
  72. package/rules/.source/hippy/extend_views/tag/FontTag.java +53 -0
  73. package/rules/.source/hippy/extend_views/tag/HtmlTag.java +191 -0
  74. package/rules/.source/hippy/extend_views/tag/HtmlTagHandler.java +185 -0
  75. package/rules/.source/hippy/extend_views/tag/SpanTag.java +160 -0
  76. package/rules/.source/hippy/extend_views/tag/TextFontSpan.java +102 -0
  77. package/rules/.source/hippy/extend_views/waterfall/Chunk.java +10 -0
  78. package/rules/.source/hippy/extend_views/waterfall/ChunkGroup.java +5 -0
  79. package/rules/.source/hippy/extend_views/waterfall/Section.java +4 -0
  80. package/rules/.source/hippy/extend_views/waterfall/Tabs.java +5 -0
  81. package/rules/.source/hippy/extend_views/waterfall/WaterfallUtils.java +26 -0
  82. package/rules/.source/hippy/hippy_uimanager/ControllerHolder.java +30 -0
  83. package/rules/.source/hippy/hippy_uimanager/ControllerManager.java +651 -0
  84. package/rules/.source/hippy/hippy_uimanager/ControllerRegistry.java +102 -0
  85. package/rules/.source/hippy/hippy_uimanager/ControllerUpdateManger.java +252 -0
  86. package/rules/.source/hippy/hippy_uimanager/CustomControllerHelper.java +425 -0
  87. package/rules/.source/hippy/hippy_uimanager/DiffUtils.java +526 -0
  88. package/rules/.source/hippy/hippy_uimanager/ExtendViewGroup.java +36 -0
  89. package/rules/.source/hippy/hippy_uimanager/HippyCustomViewCreator.java +29 -0
  90. package/rules/.source/hippy/hippy_uimanager/HippyGroupController.java +83 -0
  91. package/rules/.source/hippy/hippy_uimanager/HippyViewBase.java +27 -0
  92. package/rules/.source/hippy/hippy_uimanager/HippyViewController.java +2189 -0
  93. package/rules/.source/hippy/hippy_uimanager/HippyViewEvent.java +52 -0
  94. package/rules/.source/hippy/hippy_uimanager/IHippyZIndexViewGroup.java +24 -0
  95. package/rules/.source/hippy/hippy_uimanager/InternalExtendViewUtil.java +395 -0
  96. package/rules/.source/hippy/hippy_uimanager/ListItemRenderNode.java +143 -0
  97. package/rules/.source/hippy/hippy_uimanager/ListViewRenderNode.java +44 -0
  98. package/rules/.source/hippy/hippy_uimanager/MatrixUtil.java +470 -0
  99. package/rules/.source/hippy/hippy_uimanager/NativeGestureDispatcher.java +349 -0
  100. package/rules/.source/hippy/hippy_uimanager/NativeGestureProcessor.java +188 -0
  101. package/rules/.source/hippy/hippy_uimanager/PullFooterRenderNode.java +43 -0
  102. package/rules/.source/hippy/hippy_uimanager/PullHeaderRenderNode.java +43 -0
  103. package/rules/.source/hippy/hippy_uimanager/RenderManager.java +304 -0
  104. package/rules/.source/hippy/hippy_uimanager/RenderNode.java +533 -0
  105. package/rules/.source/hippy/hippy_uimanager/StateView.java +17 -0
  106. package/rules/.source/hippy/hippy_uimanager/TransformUtil.java +125 -0
  107. package/rules/.source/hippy/hippy_uimanager/ViewGroupDrawingOrderHelper.java +108 -0
  108. package/rules/.source/hippy/hippy_uimanager/ViewStateProvider.java +10 -0
  109. package/rules/.source/hippy/hippy_views/audioview/AudioPlayManager.java +457 -0
  110. package/rules/.source/hippy/hippy_views/audioview/AudioView.java +225 -0
  111. package/rules/.source/hippy/hippy_views/audioview/AudioViewController.java +135 -0
  112. package/rules/.source/hippy/hippy_views/common/CommonBackgroundDrawable.java +58 -0
  113. package/rules/.source/hippy/hippy_views/common/CommonBorder.java +37 -0
  114. package/rules/.source/hippy/hippy_views/custom/HippyCustomPropsController.java +61 -0
  115. package/rules/.source/hippy/hippy_views/hippylist/HippyRecyclerListAdapter.java +399 -0
  116. package/rules/.source/hippy/hippy_views/hippylist/HippyRecyclerView.java +378 -0
  117. package/rules/.source/hippy/hippy_views/hippylist/HippyRecyclerViewController.java +187 -0
  118. package/rules/.source/hippy/hippy_views/hippylist/HippyRecyclerViewHolder.java +39 -0
  119. package/rules/.source/hippy/hippy_views/hippylist/HippyRecyclerViewWrapper.java +134 -0
  120. package/rules/.source/hippy/hippy_views/hippylist/NodePositionHelper.java +55 -0
  121. package/rules/.source/hippy/hippy_views/hippylist/PreloadHelper.java +54 -0
  122. package/rules/.source/hippy/hippy_views/hippylist/PullFooterEventHelper.java +61 -0
  123. package/rules/.source/hippy/hippy_views/hippylist/PullHeaderEventHelper.java +127 -0
  124. package/rules/.source/hippy/hippy_views/hippylist/RecyclerViewEventHelper.java +394 -0
  125. package/rules/.source/hippy/hippy_views/image/HippyContentDrawable.java +113 -0
  126. package/rules/.source/hippy/hippy_views/image/HippyImageView.java +1608 -0
  127. package/rules/.source/hippy/hippy_views/image/HippyImageViewController.java +382 -0
  128. package/rules/.source/hippy/hippy_views/image/IImageStateListener.java +7 -0
  129. package/rules/.source/hippy/hippy_views/list/ChildOnScreenScroller.java +255 -0
  130. package/rules/.source/hippy/hippy_views/list/HippyListAdapter.java +647 -0
  131. package/rules/.source/hippy/hippy_views/list/HippyListItemView.java +162 -0
  132. package/rules/.source/hippy/hippy_views/list/HippyListItemViewController.java +45 -0
  133. package/rules/.source/hippy/hippy_views/list/HippyListView.java +915 -0
  134. package/rules/.source/hippy/hippy_views/list/HippyListViewController.java +622 -0
  135. package/rules/.source/hippy/hippy_views/list/HippyRecycler.java +31 -0
  136. package/rules/.source/hippy/hippy_views/list/IRecycleItemTypeChange.java +23 -0
  137. package/rules/.source/hippy/hippy_views/list/ItemDecorations.java +70 -0
  138. package/rules/.source/hippy/hippy_views/list/NegativeLongKeyFlinger.java +156 -0
  139. package/rules/.source/hippy/hippy_views/list/NodeHolder.java +34 -0
  140. package/rules/.source/hippy/hippy_views/list/RecycleViewFlinger.java +126 -0
  141. package/rules/.source/hippy/hippy_views/list/TVRecyclerView.java +2070 -0
  142. package/rules/.source/hippy/hippy_views/list/TVSingleLineListView.java +15 -0
  143. package/rules/.source/hippy/hippy_views/modal/HippyModalHostManager.java +102 -0
  144. package/rules/.source/hippy/hippy_views/modal/HippyModalHostView.java +597 -0
  145. package/rules/.source/hippy/hippy_views/modal/ModalHostHelper.java +46 -0
  146. package/rules/.source/hippy/hippy_views/modal/ModalStyleNode.java +34 -0
  147. package/rules/.source/hippy/hippy_views/modal/RequestCloseEvent.java +32 -0
  148. package/rules/.source/hippy/hippy_views/modal/ShowEvent.java +31 -0
  149. package/rules/.source/hippy/hippy_views/navigator/Navigator.java +126 -0
  150. package/rules/.source/hippy/hippy_views/navigator/NavigatorController.java +120 -0
  151. package/rules/.source/hippy/hippy_views/refresh/HippyPullFooterView.java +47 -0
  152. package/rules/.source/hippy/hippy_views/refresh/HippyPullFooterViewController.java +65 -0
  153. package/rules/.source/hippy/hippy_views/refresh/HippyPullHeaderView.java +39 -0
  154. package/rules/.source/hippy/hippy_views/refresh/HippyPullHeaderViewController.java +104 -0
  155. package/rules/.source/hippy/hippy_views/refresh/RefreshWrapper.java +237 -0
  156. package/rules/.source/hippy/hippy_views/refresh/RefreshWrapperController.java +62 -0
  157. package/rules/.source/hippy/hippy_views/refresh/RefreshWrapperItemController.java +39 -0
  158. package/rules/.source/hippy/hippy_views/refresh/RefreshWrapperItemView.java +26 -0
  159. package/rules/.source/hippy/hippy_views/scroll/HippyHorizontalScrollView.java +500 -0
  160. package/rules/.source/hippy/hippy_views/scroll/HippyOnScrollHelper.java +39 -0
  161. package/rules/.source/hippy/hippy_views/scroll/HippyScrollView.java +46 -0
  162. package/rules/.source/hippy/hippy_views/scroll/HippyScrollViewController.java +178 -0
  163. package/rules/.source/hippy/hippy_views/scroll/HippyScrollViewEventHelper.java +92 -0
  164. package/rules/.source/hippy/hippy_views/scroll/HippyVerticalScrollView.java +522 -0
  165. package/rules/.source/hippy/hippy_views/text/HippyTextView.java +512 -0
  166. package/rules/.source/hippy/hippy_views/text/HippyTextViewController.java +77 -0
  167. package/rules/.source/hippy/hippy_views/textinput/HippyTextInput.java +668 -0
  168. package/rules/.source/hippy/hippy_views/textinput/HippyTextInputController.java +528 -0
  169. package/rules/.source/hippy/hippy_views/textinput/TextInputNode.java +115 -0
  170. package/rules/.source/hippy/hippy_views/videoview/APEZProvider.java +287 -0
  171. package/rules/.source/hippy/hippy_views/videoview/APKExpansionSupport.java +82 -0
  172. package/rules/.source/hippy/hippy_views/videoview/PivotPoint.java +13 -0
  173. package/rules/.source/hippy/hippy_views/videoview/ScalableType.java +34 -0
  174. package/rules/.source/hippy/hippy_views/videoview/ScalableVideoView.java +265 -0
  175. package/rules/.source/hippy/hippy_views/videoview/ScaleManager.java +191 -0
  176. package/rules/.source/hippy/hippy_views/videoview/Size.java +19 -0
  177. package/rules/.source/hippy/hippy_views/videoview/VideoHippyView.java +917 -0
  178. package/rules/.source/hippy/hippy_views/videoview/VideoHippyViewController.java +236 -0
  179. package/rules/.source/hippy/hippy_views/videoview/ZipResourceFile.java +427 -0
  180. package/rules/.source/hippy/hippy_views/view/CardRootView.java +28 -0
  181. package/rules/.source/hippy/hippy_views/view/CustomLayoutView.java +10 -0
  182. package/rules/.source/hippy/hippy_views/view/CustomNodeView.java +5 -0
  183. package/rules/.source/hippy/hippy_views/view/DialogViewGroup.java +113 -0
  184. package/rules/.source/hippy/hippy_views/view/HippyViewGroup.java +2042 -0
  185. package/rules/.source/hippy/hippy_views/view/HippyViewGroupController.java +583 -0
  186. package/rules/.source/hippy/hippy_views/view/WindowRoot.java +5 -0
  187. package/rules/.source/hippy/hippy_views/viewpager/HippyViewPager.java +308 -0
  188. package/rules/.source/hippy/hippy_views/viewpager/HippyViewPagerAdapter.java +148 -0
  189. package/rules/.source/hippy/hippy_views/viewpager/HippyViewPagerController.java +246 -0
  190. package/rules/.source/hippy/hippy_views/viewpager/HippyViewPagerItem.java +27 -0
  191. package/rules/.source/hippy/hippy_views/viewpager/HippyViewPagerItemController.java +42 -0
  192. package/rules/.source/hippy/hippy_views/viewpager/ViewPagerPageChangeListener.java +114 -0
  193. package/rules/.source/hippy/hippy_views/viewpager/event/HippyPageItemExposureEvent.java +40 -0
  194. package/rules/.source/hippy/hippy_views/viewpager/event/HippyPageScrollEvent.java +43 -0
  195. package/rules/.source/hippy/hippy_views/viewpager/event/HippyPageScrollStateChangedEvent.java +42 -0
  196. package/rules/.source/hippy/hippy_views/viewpager/event/HippyPageSelectedEvent.java +42 -0
  197. package/rules/.source/hippy/hippy_views/webview/HippyWebView.java +160 -0
  198. package/rules/.source/hippy/hippy_views/webview/HippyWebViewBridge.java +20 -0
  199. package/rules/.source/hippy/hippy_views/webview/HippyWebViewController.java +103 -0
  200. package/rules/.source/hippy/hippy_views/webview/HippyWebViewInner.java +77 -0
  201. package/rules/.windsurfrules +27 -4
  202. package/rules/AGENTS.md +27 -4
  203. package/rules/CLAUDE.md +27 -3
  204. package/rules/GEMINI.md +25 -3
@@ -0,0 +1,811 @@
1
+ package com.tencent.extend.views;
2
+
3
+ import android.animation.Animator;
4
+ import android.animation.AnimatorListenerAdapter;
5
+ import android.animation.ObjectAnimator;
6
+ import android.graphics.Canvas;
7
+ import android.graphics.Color;
8
+ import android.graphics.Rect;
9
+ import android.support.annotation.ColorInt;
10
+ import android.util.Log;
11
+ import android.view.View;
12
+ import android.view.ViewGroup;
13
+ import android.view.ViewParent;
14
+ import android.view.ViewTreeObserver;
15
+ import android.view.animation.CycleInterpolator;
16
+
17
+
18
+ import com.tencent.extend.AttachInfo;
19
+ import com.tencent.extend.FocusManagerModule;
20
+ import com.tencent.extend.IFloatFocusManager;
21
+ import com.tencent.extend.ITVView;
22
+ import com.tencent.extend.TVFocusScaleExcuter;
23
+ import com.tencent.extend.TVViewUtil;
24
+ import com.tencent.extend.graphic.BaseBorderDrawable;
25
+ import com.tencent.extend.graphic.BorderFrontDrawable;
26
+ import com.tencent.mtt.hippy.HippyInstanceContext;
27
+ import com.tencent.mtt.hippy.utils.ExtendUtil;
28
+ import com.tencent.mtt.hippy.utils.LogUtils;
29
+ import com.tencent.mtt.hippy.utils.PixelUtil;
30
+
31
+ import java.util.ArrayList;
32
+ import java.util.concurrent.ConcurrentHashMap;
33
+
34
+ /**
35
+ * 为了各种View实现TV端特有功能(焦点、放大效果等),此类嵌入到各个view中,实际执行代码逻辑,都在此类中。
36
+ *
37
+ * onFocusChanged
38
+ * onDetachedFromWindow
39
+ * onAttachedToWindow
40
+ * addFocusables
41
+ * onSizeChanged
42
+ * drawFocusBorder
43
+ * setFocusBorderType
44
+ * focusSearch
45
+ * //绘制
46
+ * drawableStateChanged
47
+ *
48
+ */
49
+ public class TVViewActor implements ITVView {
50
+
51
+ public static final String TAG = "TVViewActor";
52
+
53
+ final View view;
54
+ String name;
55
+ int mDuration = TVFocusScaleExcuter.DEFAULT_DURATION;
56
+ float mFocusScaleX = FocusManagerModule.defaultFocusScale;
57
+ float mFocusScaleY = FocusManagerModule.defaultFocusScale;
58
+ private boolean mInReFocus = false;
59
+ String nextFocusUp,nextFocusDown,nextFocusLeft,nextFocusRight;
60
+
61
+ private final AttachInfo mAttachInfo = new AttachInfo();
62
+
63
+ public TVViewActor(View view) {
64
+ this.view = view;
65
+ }
66
+
67
+ public String getName() {
68
+ return name;
69
+ }
70
+
71
+ public void setName(String name) {
72
+ this.name = name;
73
+ }
74
+
75
+ public int getId(){
76
+ return view.getId();
77
+ }
78
+
79
+ @Override
80
+ public int getWidth() {
81
+ return view.getWidth();
82
+ }
83
+
84
+ @Override
85
+ public int getHeight() {
86
+ return view.getHeight();
87
+ }
88
+
89
+ @Override
90
+ public ViewParent getParent() {
91
+ return view.getParent();
92
+ }
93
+
94
+ public boolean isFocusable(){
95
+ return view.isFocusable();
96
+ }
97
+
98
+ /**
99
+ * -------------------------------------------------------------------------------------
100
+ **/
101
+
102
+ @Override
103
+ public void onHandleFocusScale(boolean gainFocus, int direction, Rect previouslyFocusedRect) {
104
+ if (isFocusable() && mFocusScaleX != 1 || mFocusScaleY != 1) {
105
+ handleFocusScale(gainFocus, direction, previouslyFocusedRect, mDuration);
106
+ }
107
+
108
+ }
109
+
110
+ public void handleFocusScale(boolean gainFocus, int direction, Rect previouslyFocusedRect, int duration) {
111
+ if (isFocusable() && (mFocusScaleX != 1 || mFocusScaleY != 1)) {
112
+ // Log.e("zhaopeng","###handleFocusScale gainFocus:"+gainFocus+" duration:"+duration);
113
+ TVFocusScaleExcuter.handleOnFocusChange(view, gainFocus, mFocusScaleX, mFocusScaleY, duration);
114
+ }
115
+ }
116
+
117
+ public void handleFocusScaleImmediately(boolean gainFocus, int direction, Rect previouslyFocusedRect) {
118
+ if (isFocusable() && (mFocusScaleX != 1 || mFocusScaleY != 1)) {
119
+ // Log.e("zhaopeng","!!!!!!handleFocusScaleImmediately gainFocus:"+gainFocus);
120
+ TVFocusScaleExcuter.handleOnFocusChange(view, gainFocus, mFocusScaleX, mFocusScaleY, 0);
121
+ }
122
+ }
123
+
124
+ @Override
125
+ public Rect getFloatFocusMarginRect() {
126
+ return mAttachInfo.mFloatFocusMarginRect;
127
+ }
128
+
129
+ public void onFocusChanged(final boolean gainFocus, final int direction, final Rect previouslyFocusedRect) {
130
+ if (isInReFocus()) {
131
+ handleFocusScaleImmediately(gainFocus, direction, previouslyFocusedRect);
132
+ } else {
133
+ onHandleFocusScale(gainFocus, direction, previouslyFocusedRect);
134
+ }
135
+ //drawableStateChanged();
136
+ // isBorderVisible = gainFocus;
137
+ if (borderDrawable != null) {
138
+ borderDrawable.setBorderVisible(gainFocus);
139
+ borderDrawable.onFocusChanged(view, gainFocus);
140
+ }
141
+ view.postInvalidate();
142
+ }
143
+
144
+
145
+ /**
146
+ * {@link ITVView#setFocusScale(float)}
147
+ *
148
+ * @param scale 缩放倍数
149
+ */
150
+ @Override
151
+ public void setFocusScale(float scale) {
152
+ this.mFocusScaleX = scale;
153
+ this.mFocusScaleY = scale;
154
+ }
155
+
156
+ @Override
157
+ public float getFocusScale() {
158
+ return mFocusScaleX;
159
+ }
160
+
161
+ @Override
162
+ public void setSkipRequestFocus(boolean b) {
163
+
164
+ }
165
+
166
+ @Override
167
+ public void onSetSid(String sid) {
168
+
169
+ }
170
+
171
+
172
+ /**
173
+ * 设置View获得焦点的放大倍数
174
+ */
175
+ @Override
176
+ public void setFocusScaleX(float scale) {
177
+ this.mFocusScaleX = scale;
178
+ }
179
+
180
+ /**
181
+ * 设置View获得焦点的放大倍数
182
+ */
183
+ @Override
184
+ public void setFocusScaleY(float scale) {
185
+ this.mFocusScaleY = scale;
186
+ }
187
+
188
+
189
+ /**
190
+ * {@link ITVView#setFocusScaleDuration(int)}
191
+ *
192
+ * @param duration 缩放动画时长 单位:毫秒
193
+ */
194
+ @Override
195
+ public void setFocusScaleDuration(int duration) {
196
+ this.mDuration = duration;
197
+ }
198
+
199
+
200
+ @Override
201
+ public float getFocusScaleX() {
202
+ return mFocusScaleX;
203
+ }
204
+
205
+ @Override
206
+ public float getFocusScaleY() {
207
+ return mFocusScaleY;
208
+ }
209
+
210
+ @Override
211
+ public void setFillParent(boolean b) {
212
+
213
+ }
214
+
215
+ @Override
216
+ public boolean isFillParent() {
217
+ return false;
218
+ }
219
+
220
+ @Override
221
+ public IFloatFocusManager getFloatFocusManager() {
222
+ return null;
223
+ }
224
+
225
+ @Override
226
+ public void setFloatFocusFocusedAlpha(float alpha) {
227
+ mAttachInfo.setFloatFocusFocusedAlpha(alpha);
228
+ }
229
+
230
+ @Override
231
+ public void notifyBringToFront(boolean b) {
232
+
233
+ }
234
+
235
+ @Override
236
+ public AttachInfo getAttachInfo() {
237
+ return mAttachInfo;
238
+ }
239
+
240
+ @Override
241
+ public boolean isAutoFocus() {
242
+ return false;
243
+ }
244
+
245
+ @Override
246
+ public void setAutoFocus(boolean b) {
247
+
248
+ }
249
+
250
+ @Override
251
+ public void setAutoFocus(boolean b, boolean requestFocusOnExit) {
252
+
253
+ }
254
+
255
+ @Override
256
+ public View getView() {
257
+ return view;
258
+ }
259
+
260
+
261
+ @Override
262
+ public void notifyInReFocus(boolean isIn) {
263
+ this.mInReFocus = isIn;
264
+ // Log.d("zhaopeng"," notifyInReFocus :"+isIn+" this:"+this);
265
+ if (!isFocusable() && view instanceof ViewGroup) {
266
+ for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) {
267
+ final View child = ((ViewGroup) view).getChildAt(i);
268
+ if (child instanceof ITVView) {
269
+ ((ITVView) child).notifyInReFocus(isIn);
270
+ }
271
+ }
272
+ }
273
+ }
274
+
275
+ @Override
276
+ public boolean isInReFocus() {
277
+ return mInReFocus;
278
+ }
279
+
280
+ public void onDetachedFromWindow(){
281
+ if (isFocusable()) {
282
+ TVFocusScaleExcuter.changeFocusScaleDirectly(view, 1, 1);
283
+ }
284
+ if (view.isSelected()) {
285
+ view.setSelected(false);
286
+ }
287
+ stopListenGlobalFocusChange();
288
+ }
289
+
290
+ public void onAttachedToWindow() {
291
+ listenGlobalFocusChangeIfNeed();
292
+ }
293
+
294
+
295
+ public void stopListenGlobalFocusChange() {
296
+ if (mOnGlobalFocusChangeListener != null) {
297
+ view.getViewTreeObserver().removeOnGlobalFocusChangeListener(mOnGlobalFocusChangeListener);
298
+ mOnGlobalFocusChangeListener = null;
299
+ }
300
+ }
301
+
302
+ public void setListenGlobalFocusChange(boolean listenGlobalFocusChange) {
303
+ isListenGlobalFocusChange = listenGlobalFocusChange;
304
+ }
305
+
306
+ public boolean hasFocus(){
307
+ return view.hasFocus();
308
+ }
309
+
310
+ public void listenGlobalFocusChangeIfNeed() {
311
+ stopListenGlobalFocusChange();
312
+ if (isListenGlobalFocusChange && view instanceof ViewGroup) {
313
+ mOnGlobalFocusChangeListener = new ViewTreeObserver.OnGlobalFocusChangeListener() {
314
+ @Override
315
+ public void onGlobalFocusChanged(View oldFocus, View newFocus) {
316
+ if (LogUtils.isDebug()) {
317
+ Log.d(TAG, "onGlobalFocusChanged hasFocus : " + hasFocus() + " this :" + this);
318
+ }
319
+ if (hasFocus()) {
320
+ if (oldFocus == null) {
321
+ //首次获得焦点
322
+ notifyViewFocusChanged(true, false, null, newFocus, false);
323
+ } else {
324
+ //焦点在内部,但上一个view不属于内部
325
+ final boolean isOldFocusDescendantOf = TVViewUtil.isViewDescendantOf(oldFocus, (ViewGroup) view);
326
+ if (!isOldFocusDescendantOf) {
327
+ notifyViewFocusChanged(true, false, oldFocus, newFocus, false);
328
+ }
329
+ }
330
+ } else {
331
+ final boolean isNewFocusDescendantOf = TVViewUtil.isViewDescendantOf(newFocus, (ViewGroup) view);
332
+ if (LogUtils.isDebug()) {
333
+ Log.d(TAG, "onGlobalFocusChanged hasFocus : " + hasFocus() + " isNewFocusDescendantOf : " + isNewFocusDescendantOf);
334
+ }
335
+ if (!isNewFocusDescendantOf) {
336
+ //焦点丢失
337
+ final boolean isOldFocusDescendantOf = TVViewUtil.isViewDescendantOf(oldFocus, (ViewGroup) view);
338
+
339
+ if (isOldFocusDescendantOf) {
340
+ notifyViewFocusChanged(false, true, oldFocus, newFocus, true);
341
+ }
342
+ }
343
+ }
344
+ }
345
+ };
346
+ view.getViewTreeObserver().addOnGlobalFocusChangeListener(mOnGlobalFocusChangeListener);
347
+ }
348
+ }
349
+
350
+ private boolean isListenGlobalFocusChange = false;
351
+ private ViewTreeObserver.OnGlobalFocusChangeListener mOnGlobalFocusChangeListener;
352
+
353
+ boolean lastFocusState = false;
354
+
355
+ private void notifyViewFocusChanged(boolean hasFocus, boolean isOldFocusDescendantOf, View oldFocus, View focused, boolean loseFocus) {
356
+ //
357
+ Log.d(TAG, "notifyViewGroupFocusChanged lastFocusState != hasFocus:" + (lastFocusState != hasFocus) + ",loseFocus:" + loseFocus + ",isOldFocusDescendantOf:" + isOldFocusDescendantOf);
358
+ if (lastFocusState != hasFocus) {
359
+ onViewFocusChanged(hasFocus, focused);
360
+ lastFocusState = hasFocus;
361
+ }
362
+ }
363
+
364
+ protected void onViewFocusChanged(boolean hasFocus, View focused){
365
+
366
+ }
367
+
368
+ public void setClipChildren(boolean b){
369
+ if(view instanceof ViewGroup){
370
+ ((ViewGroup) view).setClipChildren(b);
371
+ }
372
+ }
373
+
374
+ // public static @Nullable TVViewActor findTVActor(@Nullable View view){
375
+ // if (view != null) {
376
+ // if(view instanceof TVViewActorHost){
377
+ // return ((TVViewActorHost) view).getTVActor();
378
+ // }
379
+ // final Object o = view.getTag(R.id.tag_tv_actor);
380
+ // if(o instanceof TVViewActor){
381
+ // return (TVViewActor) o;
382
+ // }
383
+ // }
384
+ // return null;
385
+ // }
386
+ //
387
+ //
388
+ // static void putTVActorTag(@Nullable View view, @Nullable TVViewActor actor){
389
+ // if (view != null) {
390
+ // view.setTag(R.id.tag_tv_actor,actor);
391
+ // }
392
+ // }
393
+
394
+ // static @Nullable String findViewName(@Nullable View view){
395
+ // final TVViewActor actor = findTVActor(view);
396
+ // if (actor != null) {
397
+ // return actor.name;
398
+ // }
399
+ // return null;
400
+ // }
401
+
402
+ public ViewGroup getAsViewGroup(){
403
+ return (ViewGroup) view;
404
+ }
405
+
406
+
407
+ /**
408
+ * begin:寻焦
409
+ * -------------------------------------------------------------------------------------------
410
+ */
411
+
412
+ private boolean useAdvancedFocusSearch = false;
413
+ private View mSpecialFocusSearchRequest;
414
+ //在tvList焦点滚动时是否以此为目标
415
+ private boolean isFocusScrollTarget = false;
416
+
417
+ public View focusSearch(View focused, int direction) {
418
+ if(useAdvancedFocusSearch){
419
+ return advanceFocusSearch(focused, direction);
420
+ }
421
+ return null;
422
+ }
423
+
424
+ void markSpecifiedFocusSearch(View specialTarget) {
425
+ // Log.d(TAG, "+mark SpecifiedFocusSearch target : "+specialTarget)
426
+ mSpecialFocusSearchRequest = specialTarget;
427
+ }
428
+
429
+ void consumeSpecifiedFocusSearchRequest() {
430
+ if (mSpecialFocusSearchRequest != null) {
431
+ // Log.d(TAG, "-consume SpecifiedFocusSearchRequest")
432
+ mSpecialFocusSearchRequest = null;
433
+ }
434
+ }
435
+
436
+ private boolean isSpecifiedFocusSearch() {
437
+ return mSpecialFocusSearchRequest != null;
438
+ }
439
+
440
+ ArrayList<View> mTempFocusList = new ArrayList<>();
441
+
442
+ protected View advanceFocusSearch(View focused, int direction) {
443
+ // if(view instanceof ViewGroup) {
444
+ // return FocusSystemUtil.advanceFocusSearch((ViewGroup) view, focused, direction, false);
445
+ // }
446
+ return null;
447
+ }
448
+
449
+
450
+ // private String firstFocusTargetName = null;
451
+ //
452
+ // public void setFirstFocusTargetName(String name) {
453
+ // this.firstFocusTargetName = name;
454
+ // }
455
+ //
456
+ // public View findFocusTargetName(int direction) {
457
+ // final String target = FocusSystemUtil.findSpecifiedNextFocusName(this,direction);
458
+ // return TVViewActorUtil.findViewByName(target, view);
459
+ // }
460
+ //
461
+ // public View findNextSpecialFocusView(View focused, int direction) {
462
+ // return view instanceof ViewGroup? FocusSystemUtil.advanceFocusSearch((ViewGroup) view, focused, direction, true)
463
+ // : null;
464
+ // }
465
+
466
+ // public boolean addFocusables(ArrayList<View> views, int direction, int focusableMode) {
467
+ // if (!hasFocus()) {
468
+ // final View view = findFocusTargetName(direction);
469
+ // if (view != null) {
470
+ // if (LogUtils.isDebug()) {
471
+ // LogUtils.d(TAG, "div: +addFocusables by focusSearchTarget : " + direction + ",view :" + view.getId());
472
+ // }
473
+ // view.addFocusables(views, direction, focusableMode);
474
+ // return true;
475
+ // } else {
476
+ // if (LogUtils.isDebug()) {
477
+ // LogUtils.d(TAG, "div: +addFocusables by focusSearchTarget : " + direction + ",view :" + null);
478
+ // }
479
+ // }
480
+ // }
481
+ // if (!hasFocus() && firstFocusTargetName != null) {
482
+ // final View view = TVViewActorUtil.findViewByName(firstFocusTargetName,getView());
483
+ // if (view != null) {
484
+ // LogUtils.d(TAG, "div: +addFocusables by firstTargetName : " + firstFocusTargetName + ",view :" + view.getId());
485
+ // view.addFocusables(views, direction, focusableMode);
486
+ // return true;
487
+ // }
488
+ // }
489
+ // if (useAdvancedFocusSearch && mTempFocusList != null && mTempFocusList.size() > 0) {
490
+ // if (LogUtils.isDebug()) Log.d(TAG, "+addFocusables views : $mTempFocusList");
491
+ // if (views != null) views.addAll(mTempFocusList);
492
+ // }
493
+ // return false;
494
+ // }
495
+
496
+ public void invalidate(){
497
+ view.invalidate();
498
+ }
499
+
500
+ /**
501
+ * end:寻焦
502
+ * -------------------------------------------------------------------------------------------
503
+ */
504
+
505
+ /**
506
+ * begin:焦点状态背景、边框
507
+ * -------------------------------------------------------------------------------------------
508
+ */
509
+
510
+ //zhaopeng add
511
+
512
+ private boolean mHasSetTempBackgroundColor = false;
513
+ private boolean mUserHasSetBackgroudnColor = false;
514
+ private int mUserSetBackgroundColor = Color.TRANSPARENT;
515
+
516
+ //zhaopeng add
517
+ // private final BorderFrontDrawable focusFrontDrawable;
518
+
519
+ //border相关配置本地变量
520
+ private boolean isBorderVisible = true;
521
+ private boolean isBlackRectEnable;
522
+ private int borderColor = Color.WHITE;
523
+ private float borderCorner;
524
+ private int borderWidth;
525
+ //添加自定义borderDrawable
526
+ protected BaseBorderDrawable borderDrawable;
527
+ //自定义边框type 默认type = 0
528
+ protected int borderType;
529
+
530
+
531
+ //设置focusDrawable样式
532
+ public void setFocusBorderType(int type) {
533
+ this.borderType = type;
534
+ setBorderDrawable(getBorderDrawableProvider());
535
+ initBorderDrawable();
536
+ invalidate();
537
+ }
538
+ public ConcurrentHashMap<Integer, BaseBorderDrawable> getBorderDrawableProvider(){
539
+ ConcurrentHashMap<Integer, BaseBorderDrawable> map = new ConcurrentHashMap<>();
540
+ map.put(0,new BorderFrontDrawable());
541
+ return map;
542
+ }
543
+
544
+ public void initBorderDrawable() {
545
+ if (borderDrawable != null) {
546
+ borderDrawable.setBorderVisible(this.isBorderVisible);
547
+ borderDrawable.setCallback(view);
548
+ borderDrawable.setVisible(false, false);
549
+ //borderDrawable.setBorderColor(this.borderColor);
550
+ if (view.getContext() instanceof HippyInstanceContext) {
551
+ FocusManagerModule.GlobalFocusConfig config = FocusManagerModule.getGlobalFocusConfig(((HippyInstanceContext) view.getContext()).getEngineContext());
552
+ if (config.defaultFocusBorderWidth != -1) {
553
+ borderDrawable.setBorderWidth(PixelUtil.dp2pxInt(config.defaultFocusBorderWidth));
554
+ }
555
+
556
+ borderDrawable.setBlackRectEnable(config.defaultFocusBorderInnerRectEnable);
557
+ // Log.i(TAG,"initBorderDrawable config:"+config+",this.borderCorner:"+this.borderCorner);
558
+ if (this.borderCorner <= 0) {
559
+ borderDrawable.setBorderCorner(PixelUtil.dp2px(config.defaultFocusBorderRadius));
560
+ }else{
561
+ borderDrawable.setBorderCorner(this.borderCorner);
562
+ }
563
+ borderDrawable.setBorderColor(config.defaultFocusBorderColor);
564
+
565
+ if(config.defaultBlackFocusBorderRadius != -1){
566
+ borderDrawable.setBlackBorderCorner(PixelUtil.dp2px(config.defaultBlackFocusBorderRadius));
567
+ }
568
+ if(config.defaultBlackFocusBorderWidth != -1){
569
+ borderDrawable.setBlackBorderWidth(PixelUtil.dp2pxInt(config.defaultBlackFocusBorderWidth));
570
+ }
571
+ }
572
+ }
573
+ }
574
+
575
+ public BaseBorderDrawable getBorderDrawable() {
576
+ return borderDrawable;
577
+ }
578
+
579
+ //设置默认borderDrawable
580
+ public void setBorderDrawable(ConcurrentHashMap<Integer, BaseBorderDrawable> borderMap) {
581
+ if (borderMap != null && borderMap.size() > 0) {
582
+ for (Integer i : borderMap.keySet()) {
583
+ if (i == borderType) {
584
+ this.borderDrawable = borderMap.get(i);
585
+ }
586
+ }
587
+ if (borderType == 0 && this.borderDrawable == null) {
588
+ this.borderDrawable = new BorderFrontDrawable();
589
+ }
590
+ } else {
591
+ this.borderDrawable = new BorderFrontDrawable();
592
+ }
593
+ }
594
+
595
+ /**
596
+ * 设置边框颜色
597
+ *
598
+ * @param color
599
+ */
600
+ public void setFocusBorderColor(@ColorInt int color) {
601
+ if (borderDrawable != null) {
602
+ this.borderColor = color;
603
+ borderDrawable.setBorderColor(color);
604
+ invalidate();
605
+ }
606
+ }
607
+
608
+ /**
609
+ * 设置边框弧度
610
+ *
611
+ * @param
612
+ */
613
+ public void setFocusBorderCorner(float radius) {
614
+ if (borderDrawable != null) {
615
+ this.borderCorner = radius;
616
+ borderDrawable.setBorderCorner(radius);
617
+ invalidate();
618
+ }
619
+ }
620
+
621
+ /**
622
+ * 设置边框宽度
623
+ *
624
+ * @param
625
+ */
626
+ public void setFocusBorderWidth(int radius) {
627
+ if (borderDrawable != null) {
628
+ this.borderWidth = radius;
629
+ borderDrawable.setBorderWidth(radius);
630
+ invalidate();
631
+ }
632
+ }
633
+
634
+ public void setFocusBorderEnable(boolean enable) {
635
+ if (borderDrawable != null) {
636
+ this.isBorderVisible = enable;
637
+ borderDrawable.setBorderVisible(enable);
638
+ invalidate();
639
+ }
640
+ }
641
+
642
+ public void setBlackRectEnable(boolean enable) {
643
+ if (borderDrawable != null) {
644
+ this.isBlackRectEnable = enable;
645
+ borderDrawable.setBlackRectEnable(enable);
646
+ invalidate();
647
+ }
648
+ }
649
+
650
+ /**
651
+ * 绘制焦点边框
652
+ * @param canvas
653
+ */
654
+ public void draw(Canvas canvas) {
655
+ if (borderDrawable != null) {
656
+ borderDrawable.onDraw(canvas);
657
+ }
658
+ }
659
+
660
+
661
+ public void onSizeChanged(int w, int h, int oldw, int oldh) {
662
+ if (borderDrawable != null) {
663
+ borderDrawable.onSizeChanged(w, h, oldw, oldh);
664
+ }
665
+ }
666
+
667
+ private int mUserSetFocusBackgroundColor = 0;
668
+ private int mUserSetSelectBackgroundColor = 0;
669
+ private boolean relayoutAfterAttach = false;
670
+
671
+
672
+ /***
673
+ *
674
+ * @param color
675
+ */
676
+ public void setFocusBackGroundColor(int color) {
677
+ this.mUserSetFocusBackgroundColor = color;
678
+ // invalidate();
679
+ drawableStateChanged();
680
+ }
681
+
682
+ /***
683
+ *
684
+ * @param color
685
+ */
686
+ public void setSelectBackGroundColor(int color) {
687
+ this.mUserSetSelectBackgroundColor = color;
688
+ // invalidate();
689
+ drawableStateChanged();
690
+ }
691
+
692
+ private void postSetBGColor(final int bg) {
693
+
694
+ view.setBackgroundColor(bg);
695
+ view.postInvalidateDelayed(16);
696
+ // invalidate();
697
+ }
698
+
699
+ public void drawableStateChanged() {
700
+ int[] states = view.getDrawableState();
701
+ if (!view.isFocused() && view.isDuplicateParentStateEnabled()) {
702
+ final boolean focused = ExtendUtil.stateContainsAttribute(states, android.R.attr.state_focused);
703
+ if(isBorderVisible){
704
+ if (borderDrawable != null) {
705
+ borderDrawable.onDrawableStateChanged(view, focused);
706
+ }
707
+ }
708
+ if (focusScaleOnDuplicateParentState && (mFocusScaleX != 1 || mFocusScaleY != 1)) {
709
+ handleFocusScale(focused,-1,null,mDuration);
710
+ }
711
+ }
712
+
713
+ ExtendUtil.handleShowOnState(view, states, showOnState);
714
+ if (isFocusable() || view.isDuplicateParentStateEnabled()) {
715
+ if (mUserSetFocusBackgroundColor != 0) {
716
+ final boolean focused = ExtendUtil.stateContainsAttribute(states, android.R.attr.state_focused);
717
+ if (focused || view.isFocused()) {
718
+ postSetBGColor(mUserSetFocusBackgroundColor);
719
+ return;
720
+ }
721
+ }
722
+ final boolean select = ExtendUtil.stateContainsAttribute(states, android.R.attr.state_selected);
723
+ if (mUserSetSelectBackgroundColor != 0) {
724
+ if (select || view.isSelected()) {
725
+ postSetBGColor(mUserSetSelectBackgroundColor);
726
+ return;
727
+ }
728
+ }
729
+ // if (mUrlFetchState != IMAGE_LOADED || onBindNew || getId() != -1) {
730
+ // //zhaopeng 因为图片已经加载成功,直接展示图片,不需要再展示背景
731
+ // //getId != -1的判断是由于在fastList里会走onBindNew,而在普通的img标签上却没有机会执行,所以这里做一下修正
732
+ // postSetBGColor(getUserSetBackgroundColor());
733
+ // } else {
734
+ // postInvalidateDelayed(16);
735
+ // }
736
+ }
737
+ }
738
+
739
+ private boolean focusScaleOnDuplicateParentState = false;
740
+
741
+
742
+ public void setFocusScaleOnDuplicateParentState(boolean focusScaleOnDuplicateParentState) {
743
+ this.focusScaleOnDuplicateParentState = focusScaleOnDuplicateParentState;
744
+ }
745
+
746
+
747
+
748
+ private int[] showOnState;
749
+
750
+
751
+ public void setShowOnState(int[] showOnState) {
752
+ if (LogUtils.isDebug()) {
753
+ LogUtils.i("HippyDrawable", "setShowOnState ,showOnState size:" + showOnState.length + ",this:" + hashCode());
754
+ }
755
+ this.showOnState = showOnState;
756
+ }
757
+
758
+ //zhaopeng add
759
+
760
+ /**
761
+ * end:drawable
762
+ * -------------------------------------------------------------------------------------------
763
+ */
764
+ private boolean animRunning = false;
765
+
766
+ protected void shakeSelf(View view, int direction) {
767
+ if (direction == View.FOCUS_DOWN || direction == View.FOCUS_UP) {
768
+ if (!animRunning) {
769
+ animRunning = true;
770
+ ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(view, View.TRANSLATION_Y.getName(), 0, 5f);//抖动幅度0到5
771
+ objectAnimator.setDuration(250);//持续时间
772
+ objectAnimator.setInterpolator(new CycleInterpolator(2));//抖动次数
773
+ objectAnimator.addListener(new AnimatorListenerAdapter() {
774
+ @Override
775
+ public void onAnimationCancel(Animator animation) {
776
+ animRunning = false;
777
+ }
778
+
779
+ @Override
780
+ public void onAnimationEnd(Animator animation) {
781
+ animRunning = false;
782
+ }
783
+ });
784
+ objectAnimator.start();//开始动画
785
+ }
786
+ } else {
787
+ if (!animRunning) {
788
+ animRunning = true;
789
+ ObjectAnimator objectAnimator = ObjectAnimator.ofFloat(view, View.TRANSLATION_X.getName(), 0, 5f);//抖动幅度0到5
790
+ objectAnimator.setDuration(250);//持续时间
791
+ objectAnimator.setInterpolator(new CycleInterpolator(2));//抖动次数
792
+ objectAnimator.addListener(new AnimatorListenerAdapter() {
793
+ @Override
794
+ public void onAnimationCancel(Animator animation) {
795
+ animRunning = false;
796
+ }
797
+
798
+ @Override
799
+ public void onAnimationEnd(Animator animation) {
800
+ animRunning = false;
801
+ }
802
+ });
803
+ objectAnimator.start();//开始动画
804
+ }
805
+ }
806
+ }
807
+
808
+
809
+
810
+
811
+ }