Skip to content

Commit 9c44d00

Browse files
nventimiglicopybara-github
authored andcommitted
Fixed Swift APIDemo custom playback controls issue.
PiperOrigin-RevId: 676514146
1 parent f125409 commit 9c44d00

23 files changed

+249
-232
lines changed

java/advanced/APIDemo/app/src/main/java/com/google/android/gms/example/apidemo/AdManagerCustomControlsFragment.java

Lines changed: 29 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -56,16 +56,14 @@ public class AdManagerCustomControlsFragment extends Fragment {
5656
private CheckBox customControlsCheckbox;
5757
private CheckBox nativeAdsCheckbox;
5858
private CheckBox customFormatAdsCheckbox;
59-
private CustomControlsView customControlsView;
6059
private NativeAd nativeAd;
6160
private NativeCustomFormatAd nativeCustomFormatAd;
6261

63-
public AdManagerCustomControlsFragment() {
64-
}
62+
public AdManagerCustomControlsFragment() {}
6563

6664
@Override
67-
public View onCreateView(LayoutInflater inflater, ViewGroup container,
68-
Bundle savedInstanceState) {
65+
public View onCreateView(
66+
LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
6967
return inflater.inflate(R.layout.fragment_gam_customcontrols, container, false);
7068
}
7169

@@ -77,7 +75,6 @@ public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceStat
7775
customControlsCheckbox = view.findViewById(R.id.cb_custom_controls);
7876
nativeAdsCheckbox = view.findViewById(R.id.cb_native);
7977
customFormatAdsCheckbox = view.findViewById(R.id.cb_custom_format);
80-
customControlsView = view.findViewById(R.id.custom_controls);
8178

8279
refresh.setOnClickListener(unusedView -> refreshAd());
8380

@@ -111,6 +108,7 @@ private void populateNativeAdView(NativeAd nativeAd, NativeAdView adView) {
111108
adView.setPriceView(adView.findViewById(R.id.ad_price));
112109
adView.setStarRatingView(adView.findViewById(R.id.ad_stars));
113110
adView.setStoreView(adView.findViewById(R.id.ad_store));
111+
adView.setMediaView(adView.findViewById(R.id.ad_media));
114112

115113
// Some assets are guaranteed to be in every NativeAd.
116114
((TextView) adView.getHeadlineView()).setText(nativeAd.getHeadline());
@@ -137,20 +135,20 @@ private void populateNativeAdView(NativeAd nativeAd, NativeAdView adView) {
137135
if (nativeAd.getStarRating() == null) {
138136
adView.getStarRatingView().setVisibility(View.INVISIBLE);
139137
} else {
140-
((RatingBar) adView.getStarRatingView())
141-
.setRating(nativeAd.getStarRating().floatValue());
138+
((RatingBar) adView.getStarRatingView()).setRating(nativeAd.getStarRating().floatValue());
142139
adView.getStarRatingView().setVisibility(View.VISIBLE);
143140
}
144141

145-
// Assign native ad object to the native view.
146-
adView.setNativeAd(nativeAd);
147-
148-
// Set up the custom video controls functionality.
142+
// Set up the custom video controls.
149143
MediaContent mediaContent = nativeAd.getMediaContent();
150144
if (mediaContent != null) {
151-
customControlsView.setMediaContent(mediaContent);
145+
CustomControlsView customControls = adView.findViewById(R.id.custom_video_controls);
146+
customControls.initialize(mediaContent, startVideoAdsMuted.isChecked());
152147
}
153148

149+
// Assign native ad object to the native view.
150+
adView.setNativeAd(nativeAd);
151+
154152
refresh.setEnabled(true);
155153
}
156154

@@ -161,8 +159,8 @@ private void populateNativeAdView(NativeAd nativeAd, NativeAdView adView) {
161159
* @param nativeCustomFormatAd the object containing the ad's assets
162160
* @param adView the view to be populated
163161
*/
164-
private void populateSimpleTemplateAdView(final NativeCustomFormatAd nativeCustomFormatAd,
165-
View adView) {
162+
private void populateSimpleTemplateAdView(
163+
final NativeCustomFormatAd nativeCustomFormatAd, View adView) {
166164
TextView headline = adView.findViewById(R.id.simplecustom_headline);
167165
TextView caption = adView.findViewById(R.id.simplecustom_caption);
168166

@@ -175,11 +173,15 @@ private void populateSimpleTemplateAdView(final NativeCustomFormatAd nativeCusto
175173

176174
// Apps can check the MediaContent's hasVideoContent property to determine if the
177175
// NativeCustomTemplateAd has a video asset.
178-
if (nativeCustomFormatAd.getMediaContent() != null
179-
&& nativeCustomFormatAd.getMediaContent().hasVideoContent()) {
176+
MediaContent mediaContent = nativeCustomFormatAd.getMediaContent();
177+
if (mediaContent != null && mediaContent.hasVideoContent()) {
180178
MediaView mediaView = new MediaView(requireActivity());
181-
mediaView.setMediaContent(nativeCustomFormatAd.getMediaContent());
179+
mediaView.setMediaContent(mediaContent);
182180
mediaPlaceholder.addView(mediaView);
181+
CustomControlsView customControls = new CustomControlsView(getContext());
182+
customControls.initialize(mediaContent, startVideoAdsMuted.isChecked());
183+
ViewGroup videoControlHolder = adView.findViewById(R.id.simplecustom_video_control_holder);
184+
videoControlHolder.addView(customControls);
183185
} else {
184186
ImageView mainImage = new ImageView(getActivity());
185187
mainImage.setAdjustViewBounds(true);
@@ -188,12 +190,10 @@ private void populateSimpleTemplateAdView(final NativeCustomFormatAd nativeCusto
188190
mainImage.setOnClickListener(unusedView -> nativeCustomFormatAd.performClick("MainImage"));
189191
mediaPlaceholder.addView(mainImage);
190192
}
191-
customControlsView.setMediaContent(nativeCustomFormatAd.getMediaContent());
192193

193194
refresh.setEnabled(true);
194195
}
195196

196-
197197
/**
198198
* Creates a request for a new native ad based on the boolean parameters and calls the
199199
* corresponding "populate" method when one is successfully returned.
@@ -202,8 +202,9 @@ private void refreshAd() {
202202
refresh.setEnabled(false);
203203

204204
Resources resources = getActivity().getResources();
205-
AdLoader.Builder builder = new AdLoader.Builder(getActivity(),
206-
resources.getString(R.string.customcontrols_fragment_ad_unit_id));
205+
AdLoader.Builder builder =
206+
new AdLoader.Builder(
207+
getActivity(), resources.getString(R.string.customcontrols_fragment_ad_unit_id));
207208

208209
if (customFormatAdsCheckbox.isChecked()) {
209210
builder.forCustomFormatAd(
@@ -264,14 +265,13 @@ public void onNativeAdLoaded(NativeAd ad) {
264265
});
265266
}
266267

267-
VideoOptions videoOptions = new VideoOptions.Builder()
268-
.setStartMuted(startVideoAdsMuted.isChecked())
269-
.setCustomControlsRequested(customControlsCheckbox.isChecked())
270-
.build();
268+
VideoOptions videoOptions =
269+
new VideoOptions.Builder()
270+
.setStartMuted(startVideoAdsMuted.isChecked())
271+
.setCustomControlsRequested(customControlsCheckbox.isChecked())
272+
.build();
271273

272-
NativeAdOptions adOptions = new NativeAdOptions.Builder()
273-
.setVideoOptions(videoOptions)
274-
.build();
274+
NativeAdOptions adOptions = new NativeAdOptions.Builder().setVideoOptions(videoOptions).build();
275275

276276
builder.withNativeAdOptions(adOptions);
277277

@@ -296,7 +296,5 @@ public void onAdFailedToLoad(LoadAdError loadAdError) {
296296
})
297297
.build();
298298
adLoader.loadAd(new AdManagerAdRequest.Builder().build());
299-
300-
customControlsView.reset();
301299
}
302300
}

java/advanced/APIDemo/app/src/main/java/com/google/android/gms/example/apidemo/CustomControlsView.java

Lines changed: 28 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,13 @@
22

33
import android.annotation.SuppressLint;
44
import android.content.Context;
5+
import android.graphics.drawable.Drawable;
56
import android.util.AttributeSet;
67
import android.view.LayoutInflater;
78
import android.view.View;
8-
import android.widget.Button;
9+
import android.widget.ImageButton;
910
import android.widget.LinearLayout;
10-
import android.widget.TextView;
11+
import androidx.core.content.ContextCompat;
1112
import com.google.android.gms.ads.MediaContent;
1213
import com.google.android.gms.ads.VideoController;
1314

@@ -17,10 +18,9 @@
1718
*/
1819
public class CustomControlsView extends LinearLayout {
1920

20-
private Button playButton;
21-
private Button muteButton;
21+
private ImageButton playButton;
22+
private ImageButton muteButton;
2223
private View controlsView;
23-
private TextView videoStatusText;
2424
private boolean isVideoPlaying;
2525

2626
public CustomControlsView(Context context) {
@@ -43,42 +43,40 @@ private void init(Context context, AttributeSet unusedAttrs, int unusedDefStyle)
4343
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
4444
inflater.inflate(R.layout.custom_video_controls, this, true);
4545

46-
videoStatusText = findViewById(R.id.tv_video_status);
4746
playButton = findViewById(R.id.btn_play);
4847
muteButton = findViewById(R.id.btn_mute);
4948
controlsView = findViewById(R.id.video_controls);
5049
controlsView.setVisibility(View.GONE);
5150
}
5251

5352
/*
54-
* Reset the custom controls view.
55-
*/
56-
public void reset() {
57-
controlsView.setVisibility(View.GONE);
58-
videoStatusText.setText("");
59-
}
60-
61-
/*
62-
* Sets up the custom controls view with the provided VideoController.
53+
* Sets up the custom controls view with the provided VideoController and mute state.
6354
*/
6455
@SuppressLint("SetTextI18n")
65-
public void setMediaContent(MediaContent mediaContent) {
56+
public void initialize(MediaContent mediaContent, final boolean muted) {
6657
controlsView.setVisibility(View.GONE);
6758
if (mediaContent.hasVideoContent()) {
68-
videoStatusText.setText("Video status: Ad contains a video asset.");
6959
configureVideoContent(mediaContent.getVideoController());
70-
} else {
71-
videoStatusText.setText("Video status: Ad does not contain a video asset.");
7260
}
61+
setMuteImage(muted);
7362
}
7463

7564
private boolean isVideoPlaying() {
7665
return isVideoPlaying;
7766
}
7867

68+
private void setMuteImage(final boolean muted) {
69+
Drawable img;
70+
if (muted) {
71+
img = ContextCompat.getDrawable(getContext(), R.drawable.video_mute);
72+
} else {
73+
img = ContextCompat.getDrawable(getContext(), R.drawable.video_unmute);
74+
}
75+
muteButton.setImageDrawable(img);
76+
}
77+
7978
private void configureVideoContent(final VideoController videoController) {
8079
if (videoController.isCustomControlsEnabled()) {
81-
muteButton.setText(videoController.isMuted() ? "Unmute" : "Mute");
8280
controlsView.setVisibility(View.VISIBLE);
8381

8482
muteButton.setOnClickListener(new View.OnClickListener() {
@@ -109,44 +107,43 @@ public void onClick(View unusedView) {
109107
@SuppressLint("SetTextI18n")
110108
@Override
111109
public void onVideoMute(final boolean muted) {
112-
videoStatusText.setText(
113-
("Video status: " + (muted ? "Video did mute" : "Video did un-mute")));
114-
muteButton.setText(muted ? "Unmute" : "Mute");
110+
setMuteImage(muted);
115111
super.onVideoMute(muted);
116112
}
117113

118114
@SuppressLint("SetTextI18n")
119115
@Override
120116
public void onVideoPause() {
121-
videoStatusText.setText("Video status: Video did pause.");
122-
playButton.setText("Play");
117+
Drawable img = ContextCompat.getDrawable(getContext(), R.drawable.video_play);
118+
playButton.setImageDrawable(img);
123119
isVideoPlaying = false;
124120
super.onVideoPause();
125121
}
126122

127123
@SuppressLint("SetTextI18n")
128124
@Override
129125
public void onVideoPlay() {
130-
videoStatusText.setText("Video status: Video did play.");
131-
playButton.setText("Pause");
126+
Drawable img = ContextCompat.getDrawable(getContext(), R.drawable.video_pause);
127+
playButton.setImageDrawable(img);
132128
isVideoPlaying = true;
129+
setMuteImage(videoController.isMuted());
133130
super.onVideoPlay();
134131
}
135132

136133
@SuppressLint("SetTextI18n")
137134
@Override
138135
public void onVideoStart() {
139-
videoStatusText.setText("Video status: Video did start.");
140-
playButton.setText("Pause");
136+
Drawable img = ContextCompat.getDrawable(getContext(), R.drawable.video_pause);
137+
playButton.setImageDrawable(img);
141138
isVideoPlaying = true;
142139
super.onVideoStart();
143140
}
144141

145142
@SuppressLint("SetTextI18n")
146143
@Override
147144
public void onVideoEnd() {
148-
videoStatusText.setText("Video status: Video playback has ended.");
149-
playButton.setText("Play");
145+
Drawable img = ContextCompat.getDrawable(getContext(), R.drawable.video_play);
146+
playButton.setImageDrawable(img);
150147
isVideoPlaying = false;
151148
super.onVideoEnd();
152149
}
Loading
Loading
Loading
Loading

java/advanced/APIDemo/app/src/main/res/layout/ad_simple_custom_template.xml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,4 +32,8 @@
3232
android:textColor="#888888"
3333
android:textStyle="italic" />
3434

35+
<FrameLayout
36+
android:id="@+id/simplecustom_video_control_holder"
37+
android:layout_width="wrap_content"
38+
android:layout_height="wrap_content" />
3539
</LinearLayout>
Lines changed: 16 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,38 +1,26 @@
11
<?xml version="1.0" encoding="utf-8"?>
22
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
3-
android:orientation="vertical" android:layout_width="match_parent"
3+
android:orientation="vertical"
4+
android:layout_width="wrap_content"
45
android:layout_height="wrap_content">
56
<LinearLayout
67
android:id="@+id/video_controls"
7-
android:layout_width="match_parent"
8+
android:layout_width="wrap_content"
89
android:layout_height="wrap_content"
9-
android:gravity="center"
10-
>
11-
<Button
10+
android:gravity="center">
11+
<ImageButton
1212
android:id="@+id/btn_play"
13-
android:layout_width="wrap_content"
14-
android:layout_height="wrap_content"
15-
android:layout_marginBottom="16dp"
16-
android:layout_marginTop="16dp"
17-
android:layout_marginRight="10dp"
18-
android:text="@string/customcontrols_view_play"/>
19-
<Button
13+
android:background="#CC000000"
14+
android:layout_width="20dp"
15+
android:layout_height="20dp"
16+
android:scaleType="centerInside"
17+
android:src="@drawable/video_play" />
18+
<ImageButton
2019
android:id="@+id/btn_mute"
21-
android:layout_width="wrap_content"
22-
android:layout_height="wrap_content"
23-
android:layout_marginBottom="16dp"
24-
android:layout_marginTop="16dp"
25-
android:layout_marginLeft="10dp"
26-
android:text="@string/customcontrols_view_mute"/>
27-
20+
android:background="#CC000000"
21+
android:layout_width="20dp"
22+
android:layout_height="20dp"
23+
android:scaleType="centerInside"
24+
android:src="@drawable/video_mute" />
2825
</LinearLayout>
29-
<TextView
30-
android:id="@+id/tv_video_status"
31-
android:layout_width="match_parent"
32-
android:layout_height="wrap_content"
33-
android:layout_marginLeft="@dimen/activity_horizontal_margin"
34-
android:layout_marginRight="@dimen/activity_horizontal_margin"
35-
android:text="@string/customcontrols_view_video_status"
36-
android:gravity="center"
37-
android:textAppearance="@style/TextAppearance.AppCompat.Medium" />
3826
</LinearLayout>

java/advanced/APIDemo/app/src/main/res/layout/fragment_gam_customcontrols.xml

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
xmlns:tools="http://schemas.android.com/tools"
33
android:layout_width="match_parent"
44
android:layout_height="match_parent"
5-
tools:context="com.google.android.gms.example.apidemo.AdManagerCustomControlsFragment">
5+
tools:context=".AdManagerCustomControlsFragment">
66

77
<LinearLayout
88
android:layout_width="match_parent"
@@ -15,13 +15,6 @@
1515
android:layout_height="wrap_content"
1616
android:layout_marginTop="16dp" />
1717

18-
<com.google.android.gms.example.apidemo.CustomControlsView
19-
android:id="@+id/custom_controls"
20-
android:layout_width="match_parent"
21-
android:layout_height="wrap_content">
22-
23-
</com.google.android.gms.example.apidemo.CustomControlsView>
24-
2518
<CheckBox
2619
android:id="@+id/cb_native"
2720
android:layout_width="wrap_content"

0 commit comments

Comments
 (0)