Early Access SDK - cleveradssolutions/CAS-Android GitHub Wiki

Note

Please note that the new CAS 4.0.0 version is available as an early release and may have issues.

Warning

Please note that the beta repository has changed the url to https://repo.repsy.io/mvn/cleveradssolutions/beta

Changes

CAS 4.0 introduces several enhancements to streamline management and improve the stability of in-app ads:

  • Unified Management: All ad formats are now managed using a CAS ID string with the new CASAppOpen, CASInterstitial and CASRewarded ad objects. Read more about the new implementation below. Previously, this required working with a MediationManager instance.
  • Ad Type Management: Use ManagerBuilder.withAdTypes() only if you continue to use MediationManager for ad requests. For the new CASInterstitial and CASRewarded implementations, you should skip this function call.
  • Preloading and Caching: You can now preload and cache multiple instances of ads for each ad format, reducing latency and improving ad display performance.
  • Support Native Ad format: Read more about new Native Ad format implementation.
  • Single impression listener: All ad objects have OnAdImpressionListener to collect impression data via new AdContent structure. Read more below.
  • User ID Specification: The CAS.targetingOptions.userId property is now available for specifying the User ID. The previous method using ManagerBuilder.withUserID() has been deprecated.
  • Banner View Constructor: A new constructor for CASBannerView has been added that accepts a CAS ID parameter. The old constructor that accepted a MediationManager parameter is now deprecated.

Beta 9

  • Includes adapter updates from version 3.9.8.
  • Update for AppOpen, Interstitial, Rewarded:
    • The screen ad instance can now be loaded if it will only be used in ScreenAdContentCallback. Make sure to call destroy() to release application resources.
    • The screen ad instances no longer requires a context to create (context can be optionally null).
    • The load() method for screen ads is deprecated in favor of load(Context?).
    • The show(Activity?) method for screen ads no longer requires an Activity, but it is still recommended to pass an Activity when possible. The CAS SDK will attempt to determine the last created Activity of your app.

Note

Context can be null, but you may encounter a loading error if the CAS SDK is unable to determine the context for any reason. The context can be provided either via the constructor or CAS.buildManager().

  • Update for Native format:
    • CASMediaView can now have a size of WRAP_CONTENT. In this case, it will use all available space while maintaining the aspect ratio of the ad content.
    • NativeAdContent can now be set repeatedly to CASNativeView without causing an error. However, note that you should avoid situations where the same NativeAdContent is set to multiple CASNativeView instances simultaneously. Also, make sure to always call destroy() for NativeAdContent that is no longer in use, in order to release application resources.
    • The CASNativeView.setNativeAdTemplate(NativeAdContent, AdSize) method is now deprecated in favor of the new setAdTemplateSize(AdSize) method. This new method still creates a view layout with the specified size, but now you must call setNativeAd(NativeAdContent) to populate the content.

Note

Creating the view layout may cause a delay in UI rendering, so it is recommended to specify the template size once during initialization. After that, you can set different NativeAdContent for the same view without any loss in rendering performance.

  • Added automatic initialization of the Tenjin SDK when you provide the API key in the CAS SDK initialization parameters. The CAS SDK will handle the connect(), optIn(), or optOut() functions calls for Tenjin SDK.
CAS.buildManager()
   .withMediationExtras("tenjin_key", <TENJIN_SDK_KEY>)
   .build(this)
  • Fixed java.lang.ClassCastException: LayoutParams cannot be cast to MarginLayoutParams from CASNativeView.
  • Fixed a tracking issues for YsoNetwork and Yandex Ads impressions.
  • Fixed an issue where Mintegral video ads would not play in their native format.
  • Fixed an issue where Mintegral AppOpen ads could show underneath existing dialogs.
  • Fixed a rare issue where on some tablets the banner size would load in Leaderboard format instead of the normal one.
Early beta versions

Beta 8

  • Fixed an issue where Native Ads did not trigger loading callbacks.
  • Fixed a rare issue where AppOpen Ads could appear on top of Interstitial Ads.
  • Fixed a rare issue where fullscreen ads were not shown due to AdErrorCode.ALREADY_DISPLAYED.
  • Fixed display issues with CASExchange.
  • Fixed tracking issues for YsoNetwork impressions.
  • Added new ConsentFlow.Status.UNKNOWN that can only occur if CPM has not been initialized yet.
  • Added new AdErrorCode.REJECTED that occurs when the device is not supported by all services.
  • Improved CAS initialization:
    • Added new InitialConfiguration.consentFlowStatus with status of Consent Flow or UNKNOWN.
    • InitializationError.NO_CONNECTION now immediately interrupt the initialization process.
    • CAS initialization can now occur as needed during ad loading.
  • CASBannerView now has a size of (0, 0) when no ad is loaded. You can use WRAP_CONTENT for this case.
  • Optimized mediation initialization.

Beta 7

  • Includes adapter updates from version 3.9.7.
  • Fixed one of the InMobi processes.
  • Fixed potential loss of activity for showing Consent Flow when CAS initialization.
  • Improved Yandex Ads bidding requests.
  • Improved YSO Network bidding requests.
  • Optimized mediation processes.

Beta 5

  • Includes adapter updates from version 3.9.5.
  • Fixed crash from CASExchange adapter.
  • Fixed some internal bugs.

Beta 4

  • Fixed YSO Network adapter.
  • Fixed NullPointerException from IronSource adapter.
  • Fixed ActivityNotFoundException from CASExchange adapter.
  • Fixed an issue where SDK automatic initialization would complete incorrectly.
  • Fixed an issue where ads would fail to load when multiple CAS IDs were used.
  • Optimized some internal processes.

Beta 3

  • Includes adapter updates from version 3.9.4.
  • Fixed internal critical bugs in mediation.
  • Optimized some internal processes.
  • The NativeAdContentCallback.onAdFailedToShow function renamed to onNativeAdFailedToShow.
  • Added new adapter for YSO Network. Contact our manager if you want to try a new ad network. To integrate, you need to add a new repository to project settings:
maven {  
    name = "YSOAdsRepo"  
    url = "https://ysonetwork.s3.eu-west-3.amazonaws.com/sdk/android"  
    content { it.includeGroup("com.ysocorp") }  
}

And include the adapter to build:

cas {
    adapters {
        ysoNetwork = true
    }
}

Beta 2

  • Fixed some internal exceptions.
  • Added CASMediaView.imageScaleType property.
  • Added CASNativeLoader.isStartVideoMuted property.
  • Added Native Ads support from more ad sources.
  • Added App Open Ads support from more ad sources.

Integration

In addition to the lines described in the Add Maven repositories section, please add the beta maven repository to your settings.gradle file.

pluginManagement {  
    repositories {  
        ...  
        maven {  
            name = "CASBetaRepo"  
            url = "https://repo.repsy.io/mvn/cleveradssolutions/beta"  
        }  
    }
}

dependencyResolutionManagement {  
    repositories {  
        ...
        maven {  
            name = "CASBetaRepo"  
            url = "https://repo.repsy.io/mvn/cleveradssolutions/beta"  
            content { it.includeGroup("com.cleveradssolutions") }  
        }
    }
}

Note

pluginManagement.repositories can also be defined in the root-level build.gradle file within buildscript.repositories.

Continue with Plugin integration, using the beta version in app-level build.gradle:

plugins {
    id("com.cleveradssolutions.gradle-plugin") version "4.0.0-beta9"
}

cas {
    ...
}

CAS ID

In most cases, a casId is the same as your application package name.

val casId = BuildConfig.APPLICATION_ID

Initialize Ads

You can skip the manual call for ad initialization, and then the SDK will automatically perform the initialization before the first ad load. However, if it's important for you to change the configuration or listen to states of the Consent Flow, make sure to initialize it at least once before the first ad load.

override fun onCreate() {  
    super.onCreate()
    
    CAS.buildManager()  
        .withManagerId(casId)
        .withTestAdMode(BuildConfig.DEBUG)
        .withConsentFlow(  
            ConsentFlow(isEnabled = true)  
                .withDismissListener {  
                    Log.d(TAG, "Consent flow dismissed")  
                }  
        )  
        .withCompletionListener {  
            if (it.error == null) {  
                Log.d(TAG, "Ads initialized")  
            } else {  
                Log.d(TAG, "Ads initialization failed: " + it.error)  
            }  
        }  
        .build(this)
}

Important

Use ManagerBuilder.withAdTypes() only if you continue to use MediationManager for ad requests. For the new CASInterstitial and CASRewarded implementations, you should skip this function call.

Autoload Ad mode

If enabled, the ad will automatically load new content when the current ad is dismissed or completed. Additionally, it will automatically retry loading the ad if an error occurs during the loading process.

(Deprecated) Previously, you used settings to choose between automatic or manual loading modes.

CAS.settings.loadingMode = LoadingManagerMode.Manual

With the update to CAS 4.0, you can now configure automatic loading individually for each ad object. Below is an example of using the isAutoloadEnabled property and the default value for each ad format.

bannerView.isAutoloadEnabled = CAS.settings.loadingMode != LoadingManagerMode.Manual

interstitialAd.isAutoloadEnabled = false
rewardedAd.isAutoloadEnabled = false
appOpenAd.isAutoloadEnabled = false

The CASNativeLoader does not have an autoload ad mode.

OnAdImpressionListener (new)

A functional interface for listening to ad impression events.

val impressionListener = OnAdImpressionListener { ad: AdContent ->  
    // Called when an ad impression occurs.  
}

Each ad format has an onImpressionListener property within the ad object for registering a listener.

AdContent (new)

The deprecated AdImpression (AdStatusHandler) has been replaced by the new AdContent data structure, which contains information about the loaded/displayed ad. You can access AdContent using OnAdImpressionListener, ScreenAdContentCallback, or NativeAdContentCallback.

Name Type Description
format AdFormat Gets the format of the ad that is shown. See new AdFormat enum.
sourceName String Gets the display name of the mediated network that purchased the impression.
sourceId Int Gets the ID of the mediated network that purchased the impression. See new AdSourceId constants.
sourceUnitId String Gets the Ad Unit ID from the mediated network that purchased the impression.
creativeId String? Gets the Creative ID associated with the ad, if available. May be null. You can use this ID to report creative issues to the Ad review team.
revenue Double Gets the revenue generated from the impression, in USD. The revenue value may be either estimated or exact, depending on the precision specified by revenuePrecision.
revenuePrecision Int Gets the precision type of the revenue field. See new AdRevenuePrecision constants.
impressionDepth Int Gets the total number of impressions across all ad formats for the current user, across all sessions.
revenueTotal Double Gets the accumulated value of user ad revenue in USD from all ad format impressions.

Native Ad (new)

Read more about new Native Ad format implementation.

ScreenAdContentCallback (new)

A abstract class for handling events related to screen ad content.

val screenCallback = object : ScreenAdContentCallback(){  
    override fun onAdLoaded(ad: AdContent) {  
        // Called when the ad content has been successfully loaded.  
    }  
    override fun onAdFailedToLoad(format: AdFormat, error: AdError) {  
        // Called when the ad content fails to load.  
    }  
    override fun onAdFailedToShow(format: AdFormat, error: AdError) {  
        // Called when the ad content fails to show.  
    }  
    override fun onAdShowed(ad: AdContent) {  
        // Called when the ad content is successfully shown.  
    }  
    override fun onAdClicked(ad: AdContent) {  
        // Called when the ad content is clicked by the user.  
    }  
    override fun onAdDismissed(ad: AdContent) {  
        // Called when the ad content is dismissed.  
    }  
}

App Open Ad

The App Open Ad format has been newly implemented in the com.cleveradssolutions.sdk.screen.CASAppOpen class.

// Can be initialized along with the activity.
val appOpenAd = CASAppOpen(casId)

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    // Optionally, you can register listeners.
    appOpenAd.contentCallback = screenCallback
    appOpenAd.onImpressionListener = impressionListener
}

override fun onResume() {  
    super.onResume()  
    if (appOpenAd.isLoaded) {
        appOpenAd.show(this)
    } else {
        appOpenAd.load(this)
    }
}

override fun onDestroy() {
    appOpenAd.destroy()
    super.onDestroy()  
}

Interstitial Ad

The Interstitial Ad format has been newly implemented in the com.cleveradssolutions.sdk.screen.CASInterstitial class.

// Can be initialized along with the activity.
val interstitialAd = CASInterstitial(casId)

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    // Optionally, you can register listeners.
    interstitialAd.contentCallback = screenCallback
    interstitialAd.onImpressionListener = impressionListener

    interstitialAd.isAutoloadEnabled = false // Disabled by default
}

fun loadInterstitialAd() {
    if (interstitialAd.isAutoloadEnabled == false) {
        interstitialAd.load(this)
    }
}

// Not mandatory, but you can check the ad loaded
fun isInterstitialAdLoaded(): Boolean {
    return interstitialAd.isLoaded
}

fun showInterstitialAd() {
    interstitialAd.show(this)
}

override fun onDestroy() {
    interstitialAd.destroy()
    super.onDestroy()  
}

Minimum interval between Interstitial ads

Attempting to show a new ad within this interval after the previous ad has closed will result in a call to ScreenAdContentCallback.onAdFailedToShow with AdErrorCode.NOT_PASSED_INTERVAL. By default, this interval is set to 0 seconds, or it uses the global CAS.settings.interstitialInterval value.

interstitialAd.minInterval = 0

App Return Ad

Automatic display of App Return Ads is available for CASAppOpen and CASInterstitial. To enable this feature, use the isAutoshowEnabled property. Note that the ad must be ready for display at the time of returning to the app. Disabled by default.

appOpenAd.isAutoshowEnabled = true
interstitialAd.isAutoshowEnabled = true

Rewarded Ad

The Interstitial Ad format has been newly implemented in the `com.cleveradssolutions.sdk.screen.CASRewarded class.

// Can be initialized along with the activity.
val rewardedAd = CASRewarded(casId)

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    // Optionally, you can register listeners.
    rewardedAd.contentCallback = screenCallback
    rewardedAd.onImpressionListener = impressionListener

    rewardedAd.isAutoloadEnabled = false // Disabled by default
}

fun loadRewardedAd() {
    if (rewardedAd.isAutoloadEnabled == false) {
        rewardedAd.load(this)
    }
}

// Not mandatory, but you can check the ad loaded
fun isRewardedAdLoaded(): Boolean {
    return rewardedAd.isLoaded
}

fun showRewardedAd() {
    rewardedAd.show(this) { ad: AdContent ->
        // Called when a user earns a reward from the ad.
    }
}

override fun onDestroy() {
    rewardedAd.destroy()
    super.onDestroy()  
}

AdError

  • The AdError.message provides more detailed error information. There can be multiple detailed messages for a single error code.
  • All error code constants moved from AdError to AdErrorCode.
  • New errors have been added: AdErrorCode.TIMEOUT and AdErrorCode.NOT_INITIALIZED.
⚠️ **GitHub.com Fallback** ⚠️