blob: 1c0751ef95db9f803aff80acbdcbce85e81648d1 [file] [log] [blame] [edit]
# Copyright 2015 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
import datetime, time
from autotest_lib.client.bin import utils
from autotest_lib.client.common_lib import error
from autotest_lib.client.cros.video import method_logger
class VideoPlayer(object):
"""
Provides interface to interact with and control video playback via js.
Specific players such as VimeoPlayer will inherit from this class and
customize its behavior.
"""
def __init__(self, tab, full_url, video_id, video_src_path='',
event_timeout=5, polling_wait_time=1):
"""
@param tab: object, tab to interact with the tab in the browser.
@param full_url: string, full url pointing to html file to load.
@param video_src_path: path, complete path to video used for test.
@param video_id: string, name of the video_id element in the html file.
@param time_out_for_events_s: integer, how long to wait for an event
before timing out
@param time_btwn_polling_s: integer, how long to wait between one call
to check a condition and the next.
"""
self.tab = tab
self.full_url = full_url
self.video_id = video_id
self.video_src_path = video_src_path
self.event_timeout = event_timeout
self.polling_wait_time = polling_wait_time
self.tab.Navigate(self.full_url)
@method_logger.log
def load_video(self, wait_for_canplay=True):
"""
Loads video into browser.
@param wait_for_canplay: video will be verified before play
"""
self.tab.WaitForDocumentReadyStateToBeComplete()
self.wait_for_script_ready()
time.sleep(2)
self.inject_source_file()
if wait_for_canplay:
self.wait_for_video_ready()
def inject_source_file(self):
"""
Injects source file into html file if needed.
Created for subclasses that need it
"""
pass
@method_logger.log
def wait_for_script_ready(self):
"""
Wait for Javascript variables and functions to be defined.
"""
exception_msg = 'Script did not ready in time.'
self._wait_for_event(self.is_javascript_ready, exception_msg)
@method_logger.log
def wait_for_video_ready(self):
"""
Waits for video to signal that is ready.
Each class that inherits from this will define its is_video_ready
function.
"""
exception_msg = 'Video did not signal ready in time.'
self._wait_for_event(self.is_video_ready, exception_msg)
@method_logger.log
def verify_video_can_play(self, duration=0):
"""
Plays video and ensures that reported video current time is > 0.
@param duration: duration to play a video
@raises: error.TestError if current time is not > 0 after time > 0s
"""
exception_msg = 'Expected current time >%ds.' %duration
self.play()
# check that video is playing
self._wait_for_event(
lambda : self.currentTime() > duration, exception_msg)
self.pause()
# seek back to the beginning of video
self.seek_to(datetime.timedelta(seconds=0))
@method_logger.log
def seek_to(self, timestamp):
"""
Uses javascript to set currentTime property of video to desired time.
@param timestamp: timedelta, instance of time to navigate video to.
"""
self.seek_to(timestamp)
@method_logger.log
def wait_for_video_to_seek(self):
"""
Waits for video's currentTime to equal the time it was seeked to.
"""
exception_msg = 'Video did not complete seeking in time.'
self._wait_for_event(self.has_video_finished_seeking, exception_msg)
# it usually takes a little while before new frame renders, so wait
time.sleep(1)
@method_logger.log
def _wait_for_event(self, predicate_function, exception_msg):
"""
Helper method to wait for a desired condition.
@param predicate_function: object, function which returns true when
desired condition is achieved.
@param exception_msg: string, an exception message to show when desired
condition is not achieved in allowed time.
"""
fullmsg = exception_msg + ' Waited for %ss' % self.event_timeout
utils.poll_for_condition(predicate_function,
error.TestError(fullmsg),
self.event_timeout,
self.polling_wait_time)