88import android .content .Context ;
99import android .graphics .Rect ;
1010import android .graphics .drawable .Drawable ;
11+ import android .os .Handler ;
1112import android .util .AttributeSet ;
1213import android .view .MotionEvent ;
1314import android .view .View ;
1415import android .widget .FrameLayout ;
1516import android .widget .TextView ;
1617
18+ import org .mozilla .telemetry .schedule .jobscheduler .TelemetryJobService ;
1719import org .mozilla .vrbrowser .R ;
1820import org .mozilla .geckoview .MediaElement ;
1921import org .mozilla .vrbrowser .browser .Media ;
@@ -42,6 +44,10 @@ public class MediaControlsWidget extends UIWidget implements MediaElement.Delega
4244 private boolean mPlayOnSeekEnd ;
4345 private Rect mOffsetViewBounds ;
4446 private VideoProjectionMenuWidget mProjectionMenu ;
47+ static long VOLUME_SLIDER_CHECK_DELAY = 1000 ;
48+ private Handler mVolumeCtrlHandler = new Handler ();
49+ private boolean mHideVolumeSlider = false ;
50+ private Runnable mVolumeCtrlRunnable ;
4551
4652 public MediaControlsWidget (Context aContext ) {
4753 super (aContext );
@@ -76,6 +82,13 @@ private void initialize(Context aContext) {
7682 mVolumeIcon = aContext .getDrawable (R .drawable .ic_icon_media_volume );
7783 mOffsetViewBounds = new Rect ();
7884
85+ mVolumeCtrlRunnable = () -> {
86+ if ((mHideVolumeSlider ) && (mVolumeControl .getVisibility () == View .VISIBLE )) {
87+ mVolumeControl .setVisibility (View .INVISIBLE );
88+ stopVolumeCtrlHandler ();
89+ }
90+ };
91+
7992 mMediaPlayButton .setOnClickListener (v -> {
8093 if (mMedia .isEnded ()) {
8194 mMedia .seek (0 );
@@ -179,8 +192,8 @@ public void onSeekPreview(String aText, double aRatio) {
179192 childView .getDrawingRect (mOffsetViewBounds );
180193 MediaControlsWidget .this .offsetDescendantRectToMyCoords (childView , mOffsetViewBounds );
181194
182- FrameLayout .LayoutParams params = (FrameLayout .LayoutParams )mMediaSeekLabel .getLayoutParams ();
183- params .setMarginStart (mOffsetViewBounds .left + (int )(aRatio * mOffsetViewBounds .width ()) - mMediaSeekLabel .getMeasuredWidth () / 2 );
195+ FrameLayout .LayoutParams params = (FrameLayout .LayoutParams ) mMediaSeekLabel .getLayoutParams ();
196+ params .setMarginStart (mOffsetViewBounds .left + (int ) (aRatio * mOffsetViewBounds .width ()) - mMediaSeekLabel .getMeasuredWidth () / 2 );
184197 mMediaSeekLabel .setLayoutParams (params );
185198 }
186199 });
@@ -192,37 +205,38 @@ public void onSeekPreview(String aText, double aRatio) {
192205 }
193206 mVolumeControl .requestFocusFromTouch ();
194207 });
195-
196- this .setOnHoverListener ((v , event ) -> {
197- if (mMedia == null ) {
198- return false ;
199- }
200- if (event .getAction () == MotionEvent .ACTION_HOVER_MOVE || event .getAction () == MotionEvent .ACTION_HOVER_ENTER ) {
201- float threshold = (float )MediaControlsWidget .this .getMeasuredWidth () * 0.65f ;
202- boolean isVisible = mVolumeControl .getVisibility () == View .VISIBLE ;
203- boolean makeVisible = event .getX () >= threshold ;
204- if (isVisible != makeVisible ) {
205- mVolumeControl .setVisibility (makeVisible ? View .VISIBLE : View .GONE );
206- }
207- } else if (event .getAction () == MotionEvent .ACTION_HOVER_EXIT && !mMediaVolumeButton .isHovered () && this .isInTouchMode ()) {
208- mVolumeControl .setVisibility (View .INVISIBLE );
209- }
210- return false ;
211- });
212-
213208 mMediaVolumeButton .setOnHoverListener ((v , event ) -> {
214- if (event .getAction () == MotionEvent .ACTION_HOVER_ENTER || event .getAction () == MotionEvent .ACTION_HOVER_MOVE ) {
209+ float startY = v .getY ();
210+ float maxY = startY + v .getHeight ();
211+ //for this we only hide on the left side of volume button or outside y area of button
212+ if ((event .getX () <= 0 ) || (event .getX () >= v .getWidth ()) || (!(event .getY () > startY && event .getY () < maxY ))) {
213+ mHideVolumeSlider = true ;
214+ startVolumeCtrlHandler ();
215+
216+ } else {
215217 mVolumeControl .setVisibility (View .VISIBLE );
218+ mHideVolumeSlider = false ;
219+ stopVolumeCtrlHandler ();
216220 }
217221 return false ;
218222 });
219223
220- mMediaProjectionButton .setOnHoverListener ((v , event ) -> {
221- if (event .getAction () == MotionEvent .ACTION_HOVER_ENTER || event .getAction () == MotionEvent .ACTION_HOVER_MOVE ) {
222- mVolumeControl .setVisibility (View .INVISIBLE );
224+ mVolumeControl .setOnHoverListener ((v , event ) -> {
225+ float startY = 0 ;
226+ float maxY = startY + v .getHeight ();
227+ if ((event .getX () > 0 && event .getX () < v .getWidth ()) && (event .getY () > startY && event .getY () < maxY )) {
228+ mHideVolumeSlider = false ;
229+ stopVolumeCtrlHandler ();
230+ }
231+ //for this we only hide on the right side of volume button or outside y area of button
232+ else if ((event .getX () <= 0 ) || (event .getX () >= v .getWidth ()) || (!(event .getY () > startY && event .getY () < maxY ))) {
233+ mHideVolumeSlider = true ;
234+ startVolumeCtrlHandler ();
223235 }
224236 return false ;
225237 });
238+
239+
226240 }
227241
228242 @ Override
@@ -322,7 +336,7 @@ public void onMetadataChange(MediaElement mediaElement, MediaElement.Metadata me
322336 @ Override
323337 public void onLoadProgress (MediaElement mediaElement , MediaElement .LoadProgressInfo progressInfo ) {
324338 if (progressInfo .buffered != null ) {
325- mSeekBar .setBuffered (progressInfo .buffered [progressInfo .buffered .length -1 ].end );
339+ mSeekBar .setBuffered (progressInfo .buffered [progressInfo .buffered .length - 1 ].end );
326340 }
327341 }
328342
@@ -353,4 +367,11 @@ public void onFullscreenChange(MediaElement mediaElement, boolean fullscreen) {
353367 public void onError (MediaElement mediaElement , int code ) {
354368 }
355369
370+ private void startVolumeCtrlHandler () {
371+ mVolumeCtrlHandler .postDelayed (mVolumeCtrlRunnable , VOLUME_SLIDER_CHECK_DELAY );
372+ }
373+
374+ public void stopVolumeCtrlHandler () {
375+ mVolumeCtrlHandler .removeCallbacks (mVolumeCtrlRunnable );
376+ }
356377}
0 commit comments