적응형 스티키 배너
앱 화면의 상단 또는 하단에 배치되어 자동으로 업데이트되는 작은 광고입니다. 주요 앱 콘텐츠와 겹치지 않으며 게임 앱에서 자주 사용됩니다.
적응형 스티키 배너는 각 장치에서 광고 크기를 최적화하여 최대 효율성을 제공합니다. 이 광고 유형은 개발자가 허용 가능한 최대 광고 너비를 설정할 수 있게 하지만, 최적의 광고 크기는 여전히 자동으로 결정됩니다. 적응형 스티키 배너의 높이는 화면 높이의 15%를 초과해서는 안 됩니다.
표시 예

이 가이드는 Android 앱에 적응형 스티키 배너를 통합하는 방법을 보여줍니다. 코드 예시와 지침 외에도 형식별 권장 사항 및 추가 리소스에 대한 링크가 포함되어 있습니다.
사전 준비
- 빠른 시작에 설명된 SDK 통합 단계를 수행하세요.
- 광고 SDK를 미리 초기화하세요.
- 최신 Yandex Mobile Ads SDK 버전을 사용하고 있는지 확인하세요. 중재를 사용하는 경우, 최신 통합 빌드 버전을 실행하고 있는지도 확인하세요.
실행
적응형 스티키 배너 통합을 위한 주요 단계:
- 배너 광고를 표시하기 위한 보기를 생성 및 구성합니다.
- 콜백 메서드 리스너를 등록합니다.
- 광고를 로드합니다.
- Adfox를 사용하는 경우 추가 설정을 전달합니다.
적응형 스티키 배너 통합의 특징
-
Yandex Mobile Ads SDK 메서드에 대한 모든 호출은 메인 스레드에서 이루어져야 합니다.
-
onAdFailedToLoad()
콜백에서 오류가 발생한 경우, 새로운 광고를 다시 로드하려고 시도하지 마세요. 다른 옵션이 없는 경우, 광고 로드 재시도 횟수를 제한하세요. 이렇게 하면 제한이 발생할 때 지속적인 실패 요청과 연결 문제를 방지할 수 있습니다. -
적응형 스티키 배너는 사용 가능한 모든 너비를 사용할 때 가장 잘 작동합니다. 대부분의 경우에는 장치 화면의 전체 너비에 해당합니다. 앱에 적용 가능한 모든 패딩과 안전한 디스플레이 영역을 포함해야 합니다.
-
광고의 크기를 가져오려면 광고 컨텍스트와 광고 컨테이너의 사용 가능한 너비를 인수로 받아들이는
BannerAdSize.stickySize(context, adWidth)
메서드를 사용하세요. -
BannerAdSize.stickySize(context, adWidth)
메서드를 사용하여 계산된BannerAdSize
객체는 동일한 장치에 대한 일정한 광고 너비와 높이 값을 포함합니다. 특정 장치에서 앱의 레이아웃을 테스트하면 광고 크기가 일관됨을 확신할 수 있습니다. -
적응형 스티키 배너의 높이는 화면 높이의 15%를 초과해서는 안 되며, 최소 50dp여야 합니다.
앱 레이아웃에 광고 보기 추가
배너 광고를 표시하려면 앱 레이아웃에 BannerAdView
을 추가해야 합니다. 프로그래매틱 방식으로, 또는 XML 파일을 사용하여 수행할 수 있습니다.
앱 화면 레이아웃에 BannerAdView
추가 예시:
# activity.xml
...
<com.yandex.mobile.ads.banner.BannerAdView
android:id="@+id/banner"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintBottom_toBottomOf="parent" />
...
또한 프로그래매틱 방식으로 BannerAdView
객체를 생성할 수 있습니다.
val bannerAd = BannerAdView(this)
final BannerAdView bannerAd = new BannerAdView(this);
광고 로드 및 렌더링
BannerAdView
를 생성하여 앱 화면에 추가하면 광고를 로드해야 합니다. 적응형 스티키 배너를 로드하기 전에 각 장치에 대한 광고 크기도 계산해야 합니다.
이는 SDK API( BannerAdSize.stickySize(context, adWidth)
)를 통해 자동으로 수행됩니다.
인수로 컨텍스트 및 광고 컨테이너의 최대 허용 너비를 전달하세요. 장치 화면의 전체 너비 또는 상위 컨테이너의 너비를 사용하는 것이 좋습니다. 앱에 사용 가능한 모든 패딩과 안전한 디스플레이 영역을 포함해야 합니다.
private val adSize: BannerAdSize
get() {
// 광고 컨테이너의 패딩을 고려하여 광고의 너비를 계산합니다.
var adWidthPixels = binding.adContainerView.width
if (adWidthPixels == 0) {
// 광고가 배치되지 않은 경우 기본적으로 전체 화면 너비로 설정합니다
adWidthPixels = resources.displayMetrics.widthPixels
}
val adWidth = (adWidthPixels / resources.displayMetrics.density).roundToInt()
return BannerAdSize.stickySize(this, adWidth)
}
@NonNull
private BannerAdSize getAdSize() {
final DisplayMetrics displayMetrics = getResources().getDisplayMetrics();
// 광고 컨테이너의 패딩을 고려하여 광고의 너비를 계산합니다.
int adWidthPixels = mBinding.adContainerView.getWidth();
if (adWidthPixels == 0) {
// 광고가 배치되지 않은 경우 기본적으로 전체 화면 너비로 설정합니다
adWidthPixels = displayMetrics.widthPixels;
}
final int adWidth = Math.round(adWidthPixels / displayMetrics.density);
return BannerAdSize.stickySize(this, adWidth);
}
광고 로드에는 Activity 컨텍스트와 Partner Interface(adUnitId)의 광고 배치 ID가 필요합니다.
광고가 로드되거나 로드에 실패할 때 알림을 전송하고, 적응형 스티키 배너의 수명 주기를 추적하려면 BannerAdView
클래스 객체에 대한 BannerAdEventListener
콜백 메서드 리스너를 설정하세요.
요청에 사용자 관심사, 컨텍스트 앱 데이터, 위치 세부 정보 또는 기타 데이터를 전달함으로써 AdRequest.Builder()
를 통해 광고 요청 매개변수를 확장할 수 있습니다. 요청에 추가적인 컨텍스트 데이터를 제공하면 광고 품질을 크게 향상할 수 있습니다. 광고 타겟팅 섹션에서 자세한 내용을 확인하세요.
다음 예시는 적응형 스티키 배너를 로드하는 방법을 보여줍니다. 성공적으로 로드된 후는 배너가 자동으로 표시됩니다.
class StickyBannerAdActivity : AppCompatActivity(R.layout.activity_sticky_banner_ad) {
private var bannerAd: BannerAdView? = null
private lateinit var binding: ActivityStickyBannerAdBinding
private val adSize: BannerAdSize
get() {
// 광고 컨테이너의 패딩을 고려하여 광고의 너비를 계산합니다.
var adWidthPixels = binding.adContainerView.width
if (adWidthPixels == 0) {
// 광고가 배치되지 않은 경우 기본적으로 전체 화면 너비로 설정합니다
adWidthPixels = resources.displayMetrics.widthPixels
}
val adWidth = (adWidthPixels / resources.displayMetrics.density).roundToInt()
return BannerAdSize.stickySize(this, adWidth)
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityStickyBannerAdBinding.inflate(layoutInflater)
setContentView(binding.root)
// adContainerView 크기를 기준으로 배너를 로드하기 때문에
// 이 보기가 배치될 때까지 기다려야 너비를 가져올 수 있습니다
binding.adContainerView.viewTreeObserver.addOnGlobalLayoutListener(object :
ViewTreeObserver.OnGlobalLayoutListener {
override fun onGlobalLayout() {
binding.adContainerView.viewTreeObserver.removeOnGlobalLayoutListener(this);
bannerAd = loadBannerAd(adSize)
}
})
}
private fun loadBannerAd(adSize: BannerAdSize): BannerAdView {
return binding.banner.apply {
setAdSize(adSize)
setAdUnitId("your-ad-unit-id")
setBannerAdEventListener(object : BannerAdEventListener {
override fun onAdLoaded() {
// 활동이 파기된 후에 이 콜백이 발생하면
// destroy를 호출하고 반환해야 하며 그렇지 않으면 메모리가 누출될 수 있습니다.
// `isDestroyed`는 Activity의 메서드입니다.
if (isDestroyed) {
bannerAd?.destroy()
return
}
}
override fun onAdFailedToLoad(adRequestError: AdRequestError) {
// AdRequestError로 광고를 로드하는 데 실패했습니다.
// onAdFailedToLoad() 메서드에서 새 광고를 로드하려는 시도는 권장되지 않습니다.
}
override fun onAdClicked() {
// 광고에 대한 클릭이 기록될 때 호출됩니다.
}
override fun onLeftApplication() {
// 사용자가 광고를 클릭한 후 애플리케이션을 종료하려고 할 때(예: 브라우저로 이동) 호출됩니다.
}
override fun onReturnedToApplication() {
// 클릭 후 사용자가 애플리케이션으로 돌아왔을 때 호출됩니다.
}
override fun onImpression(impressionData: ImpressionData?) {
// 광고에 대한 노출이 기록될 때 호출됩니다.
}
})
loadAd(
AdRequest.Builder()
// 여기서 AdRequest.Builder 클래스의 메서드를 사용하여 개별 옵션 설정을 지정할 수 있습니다.
.build()
)
}
}
}
public class StickyBannerAdActivity extends AppCompatActivity {
@Nullable
private BannerAdView mBannerAd = null;
private ActivityStickyBannerAdBinding mBinding;
public StickyBannerAdActivity() {
super(R.layout.activity_sticky_banner_ad);
}
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mBinding = ActivityStickyBannerAdBinding.inflate(getLayoutInflater());
setContentView(mBinding.getRoot());
// adContainerView 크기를 기준으로 배너를 로드하기 때문에
// 이 보기가 배치될 때까지 기다려야 너비를 가져올 수 있습니다
mBinding.adContainerView.getViewTreeObserver().addOnGlobalLayoutListener(
new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
mBinding.adContainerView.getViewTreeObserver().removeOnGlobalLayoutListener(this);
mBannerAd = loadBannerAd(getAdSize());
}
}
);
}
@NonNull
private BannerAdSize getAdSize() {
final DisplayMetrics displayMetrics = getResources().getDisplayMetrics();
// 광고 컨테이너의 패딩을 고려하여 광고의 너비를 계산합니다.
int adWidthPixels = mBinding.adContainerView.getWidth();
if (adWidthPixels == 0) {
// 광고가 배치되지 않은 경우 기본적으로 전체 화면 너비로 설정합니다
adWidthPixels = displayMetrics.widthPixels;
}
final int adWidth = Math.round(adWidthPixels / displayMetrics.density);
return BannerAdSize.stickySize(this, adWidth);
}
@NonNull
private BannerAdView loadBannerAd(@NonNull final BannerAdSize adSize) {
final BannerAdView bannerAd = mBinding.banner;
bannerAd.setAdSize(adSize);
bannerAd.setAdUnitId("your-ad-unit-id");
bannerAd.setBannerAdEventListener(new BannerAdEventListener() {
@Override
public void onAdLoaded() {
// 활동이 파기된 후에 이 콜백이 발생하면
// destroy를 호출하고 반환해야 하며 그렇지 않으면 메모리가 누출될 수 있습니다.
// `isDestroyed`는 Activity의 메서드입니다.
if (isDestroyed() && mBannerAd != null) {
mBannerAd.destroy();
}
}
@Override
public void onAdFailedToLoad(@NonNull final AdRequestError adRequestError) {
// AdRequestError로 광고를 로드하는 데 실패했습니다.
// onAdFailedToLoad() 메서드에서 새 광고를 로드하려는 시도는 권장되지 않습니다.
}
@Override
public void onAdClicked() {
// 광고에 대한 클릭이 기록될 때 호출됩니다.
}
@Override
public void onLeftApplication() {
// 사용자가 광고를 클릭한 후 애플리케이션을 종료하려고 할 때(예: 브라우저로 이동) 호출됩니다.
}
@Override
public void onReturnedToApplication() {
// 클릭 후 사용자가 애플리케이션으로 돌아왔을 때 호출됩니다.
}
@Override
public void onImpression(@Nullable ImpressionData impressionData) {
// 광고에 대한 노출이 기록될 때 호출됩니다.
}
});
final AdRequest adRequest = new AdRequest.Builder()
// 여기서 AdRequest.Builder 클래스의 메서드를 사용하여 개별 옵션 설정을 지정할 수 있습니다.
.build();
bannerAd.loadAd(adRequest);
return bannerAd;
}
}
리소스 릴리스
콜백 메서드가 Activity 수명 주기 종료 후 호출된 경우, 광고 객체에 대한 destroy()
함수를 호출하여 리소스를 릴리스하세요.
private fun loadBannerAd(adSize: BannerAdSize): BannerAdView {
return binding.banner.apply {
setBannerAdEventListener(object : BannerAdEventListener {
override fun onAdLoaded() {
// 활동이 훼손된 후에 이 콜백이 발생하면
// destroy를 호출하고 반환해야 하며 그렇지 않으면 메모리가 누출될 수 있습니다.
// `isDestroyed`는 Activity의 메서드입니다.
if (isDestroyed) {
bannerAd?.destroy()
return
}
}
...
})
...
}
}
@NonNull
private BannerAdView loadBannerAd(@NonNull final BannerAdSize adSize) {
final BannerAdView bannerAd = mBinding.banner;
bannerAd.setBannerAdEventListener(new BannerAdEventListener() {
@Override
public void onAdLoaded() {
// 활동이 훼손된 후에 이 콜백이 발생하면
// destroy를 호출하고 반환해야 하며 그렇지 않으면 메모리가 누출될 수 있습니다.
// `isDestroyed`는 Activity의 메서드입니다.
if (isDestroyed() && mBannerAd != null) {
mBannerAd.destroy();
}
}
...
});
...
return bannerAd;
}
적응형 스티키 배너 통합 테스트
광고 테스트를 위한 데모 광고 단위 사용
적응형 스티키 배너 통합 및 앱 자체를 테스트하기 위해 테스트 광고를 사용하는 것이 좋습니다.
모든 광고 요청에 대해 테스트 광고가 반환되도록 보장하기 위해 특별한 데모 광고 배치 ID를 생성했습니다. 광고 통합을 확인하는 데 사용하세요.
데모 adUnitId: demo-banner-yandex
.
Важно
앱을 스토어에 게시하기 전에 데모 광고 배치 ID를 Partner Interface에서 가져온 실제 ID로 교체해야 합니다.
사용 가능한 데모 광고 배치 ID 목록은 테스트용 데모 광고 단위 섹션에서 찾을 수 있습니다.
광고 통합 테스트
SDK의 내장 분석기를 사용하여 적응형 스티키 배너 통합을 확인할 수 있습니다.
이 도구는 광고가 제대로 통합되었는지 확인하고 로그에 상세한 보고서를 출력합니다. 보고서를 보려면 Android 앱 디버깅을 위한 Logcat 도구에서 "YandexAds" 키워드를 검색하세요.
adb logcat -v brief '*:S YandexAds'
통합에 성공하면 다음 메시지가 표시됩니다.
adb logcat -v brief '*:S YandexAds'
mobileads$ adb logcat -v brief '*:S YandexAds'
I/YandexAds(13719): [Integration] Ad type banner was integrated successfully
배너 광고 통합에 문제가 있는 경우, 문제에 대한 상세한 보고서와 해결 방법에 대한 권장 사항을 받게 됩니다.
추가 리소스
-
GitHub 링크.