1*9c5db199SXin Li# Copyright 2015 The Chromium OS Authors. All rights reserved. 2*9c5db199SXin Li# Use of this source code is governed by a BSD-style license that can be 3*9c5db199SXin Li# found in the LICENSE file. 4*9c5db199SXin Li 5*9c5db199SXin Li 6*9c5db199SXin Liimport datetime, time 7*9c5db199SXin Li 8*9c5db199SXin Lifrom autotest_lib.client.bin import utils 9*9c5db199SXin Lifrom autotest_lib.client.common_lib import error 10*9c5db199SXin Lifrom autotest_lib.client.cros.video import method_logger 11*9c5db199SXin Li 12*9c5db199SXin Li 13*9c5db199SXin Liclass VideoPlayer(object): 14*9c5db199SXin Li """ 15*9c5db199SXin Li Provides interface to interact with and control video playback via js. 16*9c5db199SXin Li 17*9c5db199SXin Li Specific players such as VimeoPlayer will inherit from this class and 18*9c5db199SXin Li customize its behavior. 19*9c5db199SXin Li 20*9c5db199SXin Li """ 21*9c5db199SXin Li 22*9c5db199SXin Li 23*9c5db199SXin Li def __init__(self, tab, full_url, video_id, video_src_path='', 24*9c5db199SXin Li event_timeout=5, polling_wait_time=1): 25*9c5db199SXin Li """ 26*9c5db199SXin Li @param tab: object, tab to interact with the tab in the browser. 27*9c5db199SXin Li @param full_url: string, full url pointing to html file to load. 28*9c5db199SXin Li @param video_src_path: path, complete path to video used for test. 29*9c5db199SXin Li @param video_id: string, name of the video_id element in the html file. 30*9c5db199SXin Li @param time_out_for_events_s: integer, how long to wait for an event 31*9c5db199SXin Li before timing out 32*9c5db199SXin Li @param time_btwn_polling_s: integer, how long to wait between one call 33*9c5db199SXin Li to check a condition and the next. 34*9c5db199SXin Li 35*9c5db199SXin Li """ 36*9c5db199SXin Li self.tab = tab 37*9c5db199SXin Li self.full_url = full_url 38*9c5db199SXin Li self.video_id = video_id 39*9c5db199SXin Li self.video_src_path = video_src_path 40*9c5db199SXin Li self.event_timeout = event_timeout 41*9c5db199SXin Li self.polling_wait_time = polling_wait_time 42*9c5db199SXin Li self.tab.Navigate(self.full_url) 43*9c5db199SXin Li 44*9c5db199SXin Li 45*9c5db199SXin Li @method_logger.log 46*9c5db199SXin Li def load_video(self, wait_for_canplay=True): 47*9c5db199SXin Li """ 48*9c5db199SXin Li Loads video into browser. 49*9c5db199SXin Li @param wait_for_canplay: video will be verified before play 50*9c5db199SXin Li 51*9c5db199SXin Li """ 52*9c5db199SXin Li self.tab.WaitForDocumentReadyStateToBeComplete() 53*9c5db199SXin Li self.wait_for_script_ready() 54*9c5db199SXin Li time.sleep(2) 55*9c5db199SXin Li self.inject_source_file() 56*9c5db199SXin Li if wait_for_canplay: 57*9c5db199SXin Li self.wait_for_video_ready() 58*9c5db199SXin Li 59*9c5db199SXin Li 60*9c5db199SXin Li def inject_source_file(self): 61*9c5db199SXin Li """ 62*9c5db199SXin Li Injects source file into html file if needed. 63*9c5db199SXin Li 64*9c5db199SXin Li Created for subclasses that need it 65*9c5db199SXin Li 66*9c5db199SXin Li """ 67*9c5db199SXin Li pass 68*9c5db199SXin Li 69*9c5db199SXin Li 70*9c5db199SXin Li @method_logger.log 71*9c5db199SXin Li def wait_for_script_ready(self): 72*9c5db199SXin Li """ 73*9c5db199SXin Li Wait for Javascript variables and functions to be defined. 74*9c5db199SXin Li 75*9c5db199SXin Li """ 76*9c5db199SXin Li exception_msg = 'Script did not ready in time.' 77*9c5db199SXin Li 78*9c5db199SXin Li self._wait_for_event(self.is_javascript_ready, exception_msg) 79*9c5db199SXin Li 80*9c5db199SXin Li 81*9c5db199SXin Li @method_logger.log 82*9c5db199SXin Li def wait_for_video_ready(self): 83*9c5db199SXin Li """ 84*9c5db199SXin Li Waits for video to signal that is ready. 85*9c5db199SXin Li 86*9c5db199SXin Li Each class that inherits from this will define its is_video_ready 87*9c5db199SXin Li function. 88*9c5db199SXin Li 89*9c5db199SXin Li """ 90*9c5db199SXin Li exception_msg = 'Video did not signal ready in time.' 91*9c5db199SXin Li 92*9c5db199SXin Li self._wait_for_event(self.is_video_ready, exception_msg) 93*9c5db199SXin Li 94*9c5db199SXin Li 95*9c5db199SXin Li @method_logger.log 96*9c5db199SXin Li def verify_video_can_play(self, duration=0): 97*9c5db199SXin Li """ 98*9c5db199SXin Li Plays video and ensures that reported video current time is > 0. 99*9c5db199SXin Li 100*9c5db199SXin Li @param duration: duration to play a video 101*9c5db199SXin Li @raises: error.TestError if current time is not > 0 after time > 0s 102*9c5db199SXin Li 103*9c5db199SXin Li """ 104*9c5db199SXin Li exception_msg = 'Expected current time >%ds.' %duration 105*9c5db199SXin Li 106*9c5db199SXin Li self.play() 107*9c5db199SXin Li 108*9c5db199SXin Li # check that video is playing 109*9c5db199SXin Li self._wait_for_event( 110*9c5db199SXin Li lambda : self.currentTime() > duration, exception_msg) 111*9c5db199SXin Li 112*9c5db199SXin Li self.pause() 113*9c5db199SXin Li 114*9c5db199SXin Li # seek back to the beginning of video 115*9c5db199SXin Li self.seek_to(datetime.timedelta(seconds=0)) 116*9c5db199SXin Li 117*9c5db199SXin Li 118*9c5db199SXin Li @method_logger.log 119*9c5db199SXin Li def seek_to(self, timestamp): 120*9c5db199SXin Li """ 121*9c5db199SXin Li Uses javascript to set currentTime property of video to desired time. 122*9c5db199SXin Li 123*9c5db199SXin Li @param timestamp: timedelta, instance of time to navigate video to. 124*9c5db199SXin Li 125*9c5db199SXin Li """ 126*9c5db199SXin Li self.seek_to(timestamp) 127*9c5db199SXin Li 128*9c5db199SXin Li 129*9c5db199SXin Li @method_logger.log 130*9c5db199SXin Li def wait_for_video_to_seek(self): 131*9c5db199SXin Li """ 132*9c5db199SXin Li Waits for video's currentTime to equal the time it was seeked to. 133*9c5db199SXin Li 134*9c5db199SXin Li """ 135*9c5db199SXin Li exception_msg = 'Video did not complete seeking in time.' 136*9c5db199SXin Li 137*9c5db199SXin Li self._wait_for_event(self.has_video_finished_seeking, exception_msg) 138*9c5db199SXin Li 139*9c5db199SXin Li # it usually takes a little while before new frame renders, so wait 140*9c5db199SXin Li time.sleep(1) 141*9c5db199SXin Li 142*9c5db199SXin Li 143*9c5db199SXin Li @method_logger.log 144*9c5db199SXin Li def _wait_for_event(self, predicate_function, exception_msg): 145*9c5db199SXin Li """ 146*9c5db199SXin Li Helper method to wait for a desired condition. 147*9c5db199SXin Li 148*9c5db199SXin Li @param predicate_function: object, function which returns true when 149*9c5db199SXin Li desired condition is achieved. 150*9c5db199SXin Li @param exception_msg: string, an exception message to show when desired 151*9c5db199SXin Li condition is not achieved in allowed time. 152*9c5db199SXin Li 153*9c5db199SXin Li """ 154*9c5db199SXin Li fullmsg = exception_msg + ' Waited for %ss' % self.event_timeout 155*9c5db199SXin Li 156*9c5db199SXin Li utils.poll_for_condition(predicate_function, 157*9c5db199SXin Li error.TestError(fullmsg), 158*9c5db199SXin Li self.event_timeout, 159*9c5db199SXin Li self.polling_wait_time) 160