1 /*
2  * Copyright (C) 2017 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.google.android.exoplayer2.source.ads;
17 
18 import android.view.View;
19 import android.view.ViewGroup;
20 import androidx.annotation.Nullable;
21 import com.google.android.exoplayer2.C;
22 import com.google.android.exoplayer2.Player;
23 import com.google.android.exoplayer2.source.ads.AdsMediaSource.AdLoadException;
24 import com.google.android.exoplayer2.upstream.DataSpec;
25 import java.io.IOException;
26 
27 /**
28  * Interface for loaders of ads, which can be used with {@link AdsMediaSource}.
29  *
30  * <p>Ads loaders notify the {@link AdsMediaSource} about events via {@link EventListener}. In
31  * particular, implementations must call {@link EventListener#onAdPlaybackState(AdPlaybackState)}
32  * with a new copy of the current {@link AdPlaybackState} whenever further information about ads
33  * becomes known (for example, when an ad media URI is available, or an ad has played to the end).
34  *
35  * <p>{@link #start(EventListener, AdViewProvider)} will be called when the ads media source first
36  * initializes, at which point the loader can request ads. If the player enters the background,
37  * {@link #stop()} will be called. Loaders should maintain any ad playback state in preparation for
38  * a later call to {@link #start(EventListener, AdViewProvider)}. If an ad is playing when the
39  * player is detached, update the ad playback state with the current playback position using {@link
40  * AdPlaybackState#withAdResumePositionUs(long)}.
41  *
42  * <p>If {@link EventListener#onAdPlaybackState(AdPlaybackState)} has been called, the
43  * implementation of {@link #start(EventListener, AdViewProvider)} should invoke the same listener
44  * to provide the existing playback state to the new player.
45  */
46 public interface AdsLoader {
47 
48   /** Listener for ads loader events. All methods are called on the main thread. */
49   interface EventListener {
50 
51     /**
52      * Called when the ad playback state has been updated.
53      *
54      * @param adPlaybackState The new ad playback state.
55      */
onAdPlaybackState(AdPlaybackState adPlaybackState)56     default void onAdPlaybackState(AdPlaybackState adPlaybackState) {}
57 
58     /**
59      * Called when there was an error loading ads.
60      *
61      * @param error The error.
62      * @param dataSpec The data spec associated with the load error.
63      */
onAdLoadError(AdLoadException error, DataSpec dataSpec)64     default void onAdLoadError(AdLoadException error, DataSpec dataSpec) {}
65 
66     /** Called when the user clicks through an ad (for example, following a 'learn more' link). */
onAdClicked()67     default void onAdClicked() {}
68 
69     /** Called when the user taps a non-clickthrough part of an ad. */
onAdTapped()70     default void onAdTapped() {}
71   }
72 
73   /** Provides views for the ad UI. */
74   interface AdViewProvider {
75 
76     /** Returns the {@link ViewGroup} on top of the player that will show any ad UI. */
getAdViewGroup()77     ViewGroup getAdViewGroup();
78 
79     /**
80      * Returns an array of views that are shown on top of the ad view group, but that are essential
81      * for controlling playback and should be excluded from ad viewability measurements by the
82      * {@link AdsLoader} (if it supports this).
83      *
84      * <p>Each view must be either a fully transparent overlay (for capturing touch events), or a
85      * small piece of transient UI that is essential to the user experience of playback (such as a
86      * button to pause/resume playback or a transient full-screen or cast button). For more
87      * information see the documentation for your ads loader.
88      */
getAdOverlayViews()89     View[] getAdOverlayViews();
90   }
91 
92   // Methods called by the application.
93 
94   /**
95    * Sets the player that will play the loaded ads.
96    *
97    * <p>This method must be called before the player is prepared with media using this ads loader.
98    *
99    * <p>This method must also be called on the main thread and only players which are accessed on
100    * the main thread are supported ({@code player.getApplicationLooper() ==
101    * Looper.getMainLooper()}).
102    *
103    * @param player The player instance that will play the loaded ads. May be null to delete the
104    *     reference to a previously set player.
105    */
setPlayer(@ullable Player player)106   void setPlayer(@Nullable Player player);
107 
108   /**
109    * Releases the loader. Must be called by the application on the main thread when the instance is
110    * no longer needed.
111    */
release()112   void release();
113 
114   // Methods called by AdsMediaSource.
115 
116   /**
117    * Sets the supported content types for ad media. Must be called before the first call to {@link
118    * #start(EventListener, AdViewProvider)}. Subsequent calls may be ignored. Called on the main
119    * thread by {@link AdsMediaSource}.
120    *
121    * @param contentTypes The supported content types for ad media. Each element must be one of
122    *     {@link C#TYPE_DASH}, {@link C#TYPE_HLS}, {@link C#TYPE_SS} and {@link C#TYPE_OTHER}.
123    */
setSupportedContentTypes(@.ContentType int... contentTypes)124   void setSupportedContentTypes(@C.ContentType int... contentTypes);
125 
126   /**
127    * Starts using the ads loader for playback. Called on the main thread by {@link AdsMediaSource}.
128    *
129    * @param eventListener Listener for ads loader events.
130    * @param adViewProvider Provider of views for the ad UI.
131    */
start(EventListener eventListener, AdViewProvider adViewProvider)132   void start(EventListener eventListener, AdViewProvider adViewProvider);
133 
134   /**
135    * Stops using the ads loader for playback and deregisters the event listener. Called on the main
136    * thread by {@link AdsMediaSource}.
137    */
stop()138   void stop();
139 
140   /**
141    * Notifies the ads loader that the player was not able to prepare media for a given ad.
142    * Implementations should update the ad playback state as the specified ad has failed to load.
143    * Called on the main thread by {@link AdsMediaSource}.
144    *
145    * @param adGroupIndex The index of the ad group.
146    * @param adIndexInAdGroup The index of the ad in the ad group.
147    * @param exception The preparation error.
148    */
handlePrepareError(int adGroupIndex, int adIndexInAdGroup, IOException exception)149   void handlePrepareError(int adGroupIndex, int adIndexInAdGroup, IOException exception);
150 }
151