Login
Welcome
Login

Standard integration

On this page


Teads inRead format ads are located within a scrollable content in your app. This format champion the user experience with viewable and non-intrusive advertising.

This documentation shows you how to integrate inRead ads into an app. In addition to code snippets and instructions, it also includes information about ad view settings and additional resources.

Important

Before going further, please make sure that prerequisitesprerequisites have been fulfilled.

If you are using a WebView to display content, please refer to the Webview dedicated integration documentationWebview dedicated integration documentation.

Sample App on GitHub

Placement ID for tests

In order to ease integration iterations and testing, a test placement is specifically configured to always deliver an ad. You can use the test Placement ID (PID for short) during your testing phase. 

⚠️Please make sure this PID is no longer used in your production version, this may lead to a suspension of your Teads account. 

Test PIDs

  • 84242 - Landscape creatives only
  • 127546 - Vertical creatives only
  • 127547 - Square creatives only
  • 128779 - Carousel creatives only
  • 128780 - All creative size & formats (for adView resize testing)

Implementation

The example below is using the landscape PID  

Add the view to the layout

<?xml version="1.0" encoding="utf-8"?>
    <ScrollView
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <TextView
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:text="@string/lorem_medium"/>

            <FrameLayout
                android:id="@+id/adContainer"
                android:layout_width="match_parent"
                android:layout_height="wrap_content">

                <tv.teads.sdk.android.InReadAdView
                    android:id="@+id/teads_ad_view"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    app:teads_pid="84242"/>

            </FrameLayout>

            <TextView
              android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:text="@string/lorem_medium"/>
        </LinearLayout>
    </ScrollView>

Please note the following attributes:

  • app:teads_pid - Set this to the placement id (example includes the test PID)
  • app:teads_maxHeight - Sets the maximum height that the ad can take once expanded
  • app:teads_autoload - Requests an ad once the view is inflated (works only with layout_height:wrap_content)
  • app:teads_debug - Enable debug log ( ⚠️ Don't forget to remove this option before deploying)
  1. Add the TFAInReadAdView to the storyboard:

  2. Then create a outlet of the teadsAdView:

Note

If you don't want to use the storyboard you can add the TFAInReadAdView programmatically as it inherits from UIView. Next, set the TFAAdDelegate. You just need to set the self.teadsAdView.delegate to self and integrate all the required delegates:

self.adView = TFAInReadAdView(withPid: 84242, andDelegate: self)

Load an ad

Once InReadAdView is in place, the next step is to load an ad. Here's an example:

import tv.teads.sdk.android.InReadAdView; 

public class MainActivity extends AppCompatActivity {
private InReadAdView mAdView;

protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);

mAdView = findViewById(R.id.teads_ad_view);
mAdView.load();
}
}
import TeadsSDK
override func viewDidLoad() {
super.viewDidLoad()
self.teadsAdView.delegate = self
self.teadsAdView.load()
}

If you need some options you can first create teadsAdSettings:

let teadsAdSettings = TeadsAdSettings(build: { (settings) in
settings.enableDebug()
})
self.teadsAdView.load(teadsAdSettings: teadsAdSettings)

Ad Resizing

⚠️ Some creatives like VPAIDs may ask for a resize after the initialization of the ad View.

No action is required if the height constraint of the ad view (and its parent) is set to "wrap_content".

In the other case, it is mandatory to manually adapt the size of the Ad container.

The SDK will warn you that the creative need another resize to be correctly displayed.

Use onRatioUpdated to listen to resize updates at any time.

Don't hesitate to test PIDs listed above to make sure this part works well.

public void onRatioUpdated(float adRatio) {
//Should be override to be listened
}

⚠️ Some creatives like VPAIDs may ask for a resize after the initialization of the ad View.

The mandatory delegate below will help you to adapt the size of the Ad container.

The SDK will warn you that the creative need another resize to be correctly displayed.

Please use the test PIDs listed above to make sure this part works well.

public func didUpdateRatio(_ ad: TFAAdView, ratio: CGFloat) {
resizeTeadsAd(adRatio: ratio) //custom method resizing teadsAdView
 }

Exposing the ParentViewController

⚠️ Some user interactions like clicking an ad will provoke the load of an SFSafariViewController where web content can be displayed.

This action requires to properly identify the topViewController in order to base the SFSafariViewController on.

This step is optional but might be necessary especially for ChildViewController architectures.


Please Implement the optional function below on TFAAdDelegate in order to expose the topViewController when the ad wants to display website content (Click to action).

MyViewController: UIViewController, TFAAdDelegate {
... func adBrowserWillOpen(_ ad: TFAAdView) -> UIViewController? {
return self
}
}

Request App Tracking Transparency authorization (iOS 14+)

iOS 14 introduced App Tracking Transparency

Please see here how to implement it.

Event monitoring

The SDK provides a listener to monitor events during the ad life cycle and help you customize the ad experience in your apps.

mAdView.setListener(new TeadsListener() {
@Override
public void onAdLoaded(float adRatio) {
//When the ad request has been made and it receive a successfull response.
//If the auto expand is disabled, the slot should be open here following the given ratio
}

@Override
public void onAdFailedToLoad(AdFailedReason adFailedReason) {
//When the SDK doesn't succeed to get an ad, following code error:
//ERROR_NOSLOT = 1
//ERROR_NETWORK = 2
//ERROR_NOTFILLED = 3 //when our ad server didn't found an ad for your placement
//ERROR_BAD_RESPONSE = 4
//ERROR_VASTERROR = 5
//ERROR_USERID_MISSING = 6
}

@Override
public void onAdDisplayed() {
//Notify that the ad is displayed
}

@Override
public void closeAd() {
//Ask to close the ad if the {@link AdSettings#autoExpandDisabled} is disable. Otherwise, it notify
//that the view will close by itself.
}

@Override
public void onError(String message) {
//When an error shows up, the player fail to play a video or an exception occured in the SDK.
}

@Override
public void onAdPlaybackChange(@PlayerConstants.PlaybackState int state) {
super.onAdPlaybackChange(state);

switch (state) {
case PlayerConstants.LOADED:
case PlayerConstants.STARTED:
case PlayerConstants.RESUMED:
case PlayerConstants.PAUSED:
case PlayerConstants.IMPRESSION:
case PlayerConstants.PROGRESS:
case PlayerConstants.FIRST_QUARTILE:
case PlayerConstants.MID_POINT:
case PlayerConstants.THIRD_QUARTILE:
case PlayerConstants.COMPLETE:
case PlayerConstants.STOPPED:
case PlayerConstants.MUTED:
case PlayerConstants.UNMUTED:
default:
// ...
break;
}
}
});

self.teadsAdView.delegate = self

func didReceiveAd(_ ad: TFAAdView, adRatio: CGFloat) {
//Called when you get an ad with its ratio
}

func didFailToReceiveAd(_ ad: TFAAdView, adFailReason: AdFailReason) {
//Called when you don't get an ad with adFailReason object that contains the error code and the error's string
//Be sure to close your slot when this happen
}

func adError(_ ad: TeadsAdView, errorMessage: String) {
//When an error shows up, the player fail to play a video or an exception occured in the SDK.
}

func adClose(_ ad: TFAAdView, userAction: Bool) {
//The `adClose` delegate method will be called in three cases:
//- the ad has an autoclose option when it is over
//- the user closes the ad
//- there is an error and the ad should close
}

Reset and clean

Use the reset method before each new load in order to call a new ad with the same InReadAdView instance.

mAdView.reset()

To avoid potentials leaks, don't forget to clean the InReadAdView when your activity is destroyed.

@Override
public void onDestroy() {
super.onDestroy();
mAdView.clean();
}

Use the reset method before each new load in order to call a new ad with the same TeadsAdView instance.

self.teadsAdView.reset()

If your class is deinit you can clean the TeadsAdView:

deinit {
self.teadsAdView = nil
}

Brand Safety and web content URL

⚠️ BrandSafety is a key feature for advertisers, Fillrate could be impacted if Brand Safety analysis is not enabled

The categorization is done on the fly with a 3rd party partner called Grapeshot. The analysis can only be done on a web page which is a problem for inApp content. The Teads inApp SDK can bypass this limitation by providing the Web equivalent URL to Grapeshot where the analysis can still be done.

In most cases, a web equivalent to the inApp content is available, especially News and article Apps. It is important to communicate that web URL  (https://....) to the Teads inApp SDK so that Brand Safety analysis could be enabled.

adView.load(new AdSettings.Builder()
.pageUrl("https://example.com/article1")
.build())
self.teadsAdView.load(TeadsAdSettings(build: { (settings) in
settings.pageUrl("https://example.com/article1")
}))

Best practices

  • You need to be sure that the InReadAdView is in the view hierarchy, where you want to display the ad (even with a height of 0 in case you have no ad). It will allow us to get accurate stats and optimize your revenue.
  • Ensure Brand Safety is enabled.
  • Ensure you comply with GDPR.
  • Be sure to close the ad slot when adClose is called.
  • Adapt your slot size with the adRatio you receive from the didReceiveAd and didUpdateRatio callbacks.
  • Ensure Brand Safety is enabled. 
  • Make sure you comply with GDPR.

Options

If you want to load an ad from your activity side, you can set the following option:

AdSettings.Builder adSettingsBuilder = new AdSettings.Builder();
  • adSettingsBuilder.enableDebug(); - Enable all Teads SDK Log for debugging purpose (such as webviews inspector chrome://inspect).
  • adSettingsBuilder.disableAutoExpand(); - Disable the auto expand and collapse on the ad view. You will have responsability to manage the ad size (see the TeadsListener)
  • adSettingsBuilder.hideBrowserUrl(); - Hide the website url in the internal browser only. The url is visible by default.
  • adSettingsBuilder.pageUrl(articleUrl); - The publisher http page url that matches the content where Teads Ad will be loaded into.
  • adSettingsBuilder.useLightEndscreen(); - When the ad playback is finished, we display an endscreen with light color (Dark color by default).
  • adSettingsBuilder.toolbarBackgroundColor(int color); - Set the toolbar background color on the browser.
  • adSettingsBuilder.userConsent(String subjectToGDPR, String consent); - The user consent following the IAB specifications.

Once you have set your adSettingBuilder you can build it in your load request:

adView.load(adSettingBuilder.build());

If you want to load an ad from your class, you can set the following option:

let teadsAdSettings = TeadsAdSettings(build: { (settings) in
settings.enableDebug()
})
  • TeadsAdSettings.enableDebug() - Enable all Teads SDK Log for debugging purpose.
  • TeadsAdSettings.pageUrl(_ articleUrl: String) - The publisher http page url that matches the content where Teads Ad will be loaded into.
  • adSettingsBuilder.userConsent(subjectToGDPR: String, consent: String) - The user consent following the IAB specifications.
  • adSettingsBuilder.disableBatteryMonitoring() - disable automatically set UIDevice.current.isBatteryMonitoringEnabled

Archive known issues

As we are using a FAT framework it sometimes causes an issue when you try to archive (the simulator file is in the framework).

This article gives a deeper explanation of the issue and provides a script that can help you fix it.

Did you find it helpful? Yes No

Send feedback
Sorry we couldn't be helpful. Help us improve this article with your feedback.