Android SDK Implementation Guide
This is a free Software Development Kit for the Android application developers and publishers to monetize their digital mobile inventory in the blink of an eye. SmartyAds SDK integrates with SmartyAds SSP, creating one single source of offerings tailored to publishers’ needs.
Banner and rich media ads:
Size, DPI | Type | SmartyAds SDK Size Constant |
---|---|---|
320x50 | Standard Banner | kSmartyAdsAdSizeBanner |
320x100 | Large Banner | kSmartyAdsAdSizeLargeBanner |
300x250 | IAB Medium Rectangle | kSmartyAdsAdSizeIABMediumRectangle |
468x60 | IAB Full-Size Banner | kSmartyAdsAdSizeIABFullSizeBanner |
728x90 | IAB Leaderboard | kSmartyAdsAdSizeIABLeaderBoard |
Video ads:
Orientation: Landscape or Portrait
Native ads:
In accordance with the IAB specification:
The padding Property
This property adds space between the border and the content in a table.
Field | Scope | Type | Default | Description |
---|---|---|---|---|
ver | optional | string | 1.2 | Version of the Native Markup version in use. |
context | recommended | integer | - | The context in which the ad appears. See Table of Context IDs below for a list of supported context types. |
contextsubtype | optional | integer | - | A more detailed context in which the ad appears. Supported SubType IDs: 10 General or mixed content. 11 Primarily article content (which of course could include images, etc as part of the article). 12 Primarily video content. 13 Primarily audio content. 14 Primarily image content. 15 User-generated content - forums, comments, etc. 20 General social content such as a general social network. 21 Primarily email content. 22 Primarily chat/IM content. 30 Content focused on selling products, whether digital or physical. 31 Application store/marketplace. 32 Product reviews site primarily (which may sell product secondarily). 500+ To be defined by the exchange. |
plcmttype | recommended | integer | - | The design/format/layout of the ad unit being offered. Supported Placement Type IDs: 1 In the feed of content - for example as an item inside the organic feed/grid/listing/carousel. 2 In the atomic unit of the content - IE in the article page or single image page. 3 Outside the core content - for example in the ads section on the right rail, as a banner-style placement near the content, etc. 4 Recommendation widget, most commonly presented below the article content. 500+ To be defined by the exchange. |
plcmtcnt | optional | integer | 1 | The number of identical placements in this Layout. |
seq | optional | integer | 0 | 0 for the first ad, 1 for the second ad, and so on. Note this would generally NOT be used in combination with plcmtcnt - either you are auctioning multiple identical placements (in which case plcmtcnt>1, seq=0) or you are holding separate auctions for distinct items in the feed (in which case plcmtcnt=1, seq=>=1). |
assets | required | array of objects | 0 | An array of Asset Objects. Any bid response must comply with the array of elements expressed in the bid request. |
aurlsupport | optional | int | 0 | 0 Whether the supply source / impression supports returning an assets url instead of an asset object. 0 or the absence of the field indicates no such support. |
durlsupport | optional | int | 0 | Whether the supply source/ impression supports returning a dco url instead of an asset object. 0 or the absence of the field indicates no such support. |
eventtrackers | optional | array of objects | 0 | Specifies what type of event tracking is supported - see Event Trackers Request Object. |
privacy | recommended | integer | 0 | Set to 1 when the native ad supports buyer-specific privacy notice. Set to 0 (or field absent) when the native ad doesn’t support custom privacy links or if support is unknown. |
ext | optional | object | - | This object is a placeholder that may contain custom JSON agreed to by the parties to support flexibility beyond the standard defined in this specification. |
Interstitial ads:
Size, DPI | Type |
---|---|
Custom size | Full screen |
Getting Started
Just a few steps to start (to understand how user works with inventory):
- Register your account on SmartyAds Supply Side Platform.
- Confirm your registration by following the confirmation link sent via email.
- Create your first mobile inventory by clicking ‘Add Inventory’. Select Android Application in pop up.
- After your inventory reviewed and approved, you will be granted access to create placements for your inventory, and ‘Add Placement’ button should become clickable.
- Click on ‘+Banner’, add the targeting options, floor price and size of your placement, then save your changes.
- Please note the Placement ID (e.g., ID#1234) below its title. It will be used later in your code to initialize the ad container.
Requirements
SmartyAds in-app advertising SDK requires Android SDK version 16 or higher.
Installation
First way
repositories {
jcenter()
// Smarty Maven dependepcies
mavenCentral()
mavenLocal()
flatDir {
dirs '../libs'
}
maven { url "https://jitpack.io" }
maven { url "https://s3.amazonaws.com/moat-sdk-builds" }
maven { url "https://dl.bintray.com/smartyads/maven/" }
maven {
url 'https://maven.google.com/'
name 'Google'
}
}
Include SDK dependency into your Module gradle.build:
compile('com.smartyads:ad-container:0.4.5') {
transitive = true
}
- Synchronize the project with Gradle files (Gradle sync)
Alternative way
- Download aar lib from latest release: ad-container-release.aar.
- In Android studio: File -> New -> New Module and choose Import .jar/.aar Package, press next.
- File name: path to aar.
- File -> Project Structure -> {your_module_tab} -> dependencies and add just imported module as dependency.
You also need to add the following dependencies in your build.gradle file for proper SDK performance.
compile 'com.android.support:appcompat-v7:26.0.1' |
compile 'com.google.code.gson:gson:2.8.0' |
compile 'io.reactivex.rxjava2:rxandroid:2.0.1' |
compile 'io.reactivex.rxjava2:rxjava:2.1.0' |
compile 'com.squareup.retrofit2:retrofit:2.3.0' |
compile 'com.squareup.retrofit2:converter-gson:2.3.0' |
compile 'com.squareup.picasso:picasso:2.5.2' |
compile "android.arch.persistence.room:runtime:1.0.0-alpha9" |
compile "android.arch.persistence.room:rxjava2:1.0.0-alpha9" |
annotationProcessor "android.arch.persistence.room:compiler:1.0.0-alpha9" |
compile 'com.google.android.gms:play-services-ads:+' |
* Important!
Enable Multidex for your app. It will help the app to compile in case it approaches 64K DEX reference limit.
Setup App Permissions (optional)
Edit your Android manifest to include the following (optional but recommended) permissions:
<?xml version="1.0" encoding="utf-8"?> |
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.smartyads.sampleapp"> |
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <!-- Grants the SDK permission to access a more accurate location based on GPS --> |
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> <!-- Grants the SDK permission to access approximate location based on cell tower --> |
<!-- your app description --> </manifest> |
SmartyAds SDK already has the following normal permissions required by the SDK:
- <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
- <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
- <uses-permission android:name="android.permission.INTERNET" />
Setting up required parameters in strings.xml
Set the app distribution type (required by SDK) in your strings.xml file:
<integer name="distribution_type">{0|1}</integer>
where:
0 - app is free
1 - the app is a paid version
Now, add the banner_id to strings.xml
<string name="banner_id">{your_banner_id_here}</string>
Important!
Do not forget to replace the ‘your_banner_id_here’ with the placement ID from the Platform (Step 6 of the Getting Started section).
e.g, <string name="banner_id">{1234}</string>
Initializing SmartyAds SDK
Extend android.app.Application class, override #attachBaseContext(Context) method and call com.SmartyAds.Ads#init(Context) method as shown below:
public class SampleApp extends Application {
@Override
protected void attachBaseContext(Context base) {
super.attachBaseContext(base);
Ads.init(base);
}
}
Show ads by types
Show Banners
You can configure your banner ad view using XML:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:smartyads="http://schemas.android.com/apk/res-auto">
<com.smartyads.adcontainer.BannerContainer
android:id="@+id/banner_container"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
smartyads:adContainerId="@string/banner_id"
smartyads:banner_width="300dp"
smartyads:banner_height="250dp"
smartyads:refreshTime="20"
/>
</LinearLayout>
Where
- smartyads:adContainerId="@string/banner_id" - the placement ID you received
- smartyads:banner_width="300dp" - placement width
- smartyads:banner_height="250dp" - placement height
- smartyads:refreshTime="20" - Optional. Time in seconds after which the banner will expire and will be reloaded automatically. By default 20 sec.
Make sure
that xmlns:smartyads="http://schemas.android.com/apk/res-auto" was added to your root layout.
Finally, call BannerContainer#loadAd()
BannerContainer bannerContainer = (BannerContainer) findViewById(R.id.banner_container);
bannerContainer.loadAd();
There is an alternative method BannerContainer#loadAd(BannerOnLoadListener) that would be useful if you want to show a banner manually at specific time or you just want to know whether the banner was loaded successfully or not.
bannerContainer.loadAd(new BannerOnLoadListener() {
@Override
public void onSuccess() {
Log.d("YOUR_TAG","Banner succesfully loaded");
}
@Override
public void onFailure(Exception e) {
Log.e("YOUR_TAG","Cannot load ad: " + e.getMessage());
}
});
Show Interstitial
To show interstitial you just need to initialize ad container and call InterstitialAdContainer#loadAd() method as shown in example below:
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
if(savedInstanceState == null){//activity first time showing condition
new InterstitialAdContainer(this, getString(R.string.banner_id))
.interstitial.loadAd();//interstitial will be shown as soon as ad will be loaded
}
}
}
Where R.string.banner_id - your interstitial id(see #important) Note:
Also, you can use InterstitialAdContainer#loadAd(BannerOnLoadListener) method if you want to show interstitial manually at specific time.
public class MainActivity extends AppCompatActivity {
private Button showAdButton;
private InterstitialAdContainer interstitial;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
showAdButton = (Button) findViewById(R.id.show_ad);
showAdButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(interstitialContainer.isLoaded())
interstitialContainer.showAd();
}
});
interstitial = new InterstitialAdContainer(this, getString(R.string.banner_id));
interstitial.loadAd(new InterstitialListener() {
@Override
public void onSuccess() {
Log.e("YOUR_TAG", "Ad loaded");
}
@Override
public void onFailure(Exception e) {
Log.e("YOUR_TAG", "Cannot load interstitial, reason: " + e.getMessage());
}
@Override
public void closed() {
Log.d("YOUR_TAG", "Interstitial closed");
}
});
}
}
Show Vast (Video ad)
Update your AndroidManifest.xml with new permission WRITE_EXTERNAL_STORAGE
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.smartyads.sampleapp">
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <!-- Required. Allows an application to write to external storage. -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <!-- Optional. Grants the SDK permission to access a more accurate location based on GPS -->
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> <!-- Optional. Grants the SDK permission to access approximate location based on cell tower -->
<!-- your app description -->
</manifest>
The usage of VideoContainer exactly the same as the usage of InterstitialAdContainer):
public class MainActivity extends AppCompatActivity {
private Button showAdButton;
private VideoContainer videoContainer;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
showAdButton = (Button) findViewById(R.id.show_ad);
showAdButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(videoContainer.isLoaded())
videoContainer.showAd();
}
});
videoContainer = new VideoContainer(this, getString(R.string.video_container_id));
videoContainer.loadAd(new InterstitialListener() {
@Override
public void onSuccess() {
Log.e("YOUR_TAG", "Ad loaded");
}
@Override
public void onFailure(Exception e) {
Log.e("YOUR_TAG", "Cannot load interstitial, reason: " + e.getMessage());
}
@Override
public void closed() {
Log.d("YOUR_TAG", "Interstitial closed");
}
});
}
}
Show Rewarded video ad
Update your AndroidManifest.xml with new permission WRITE_EXTERNAL_STORAGE
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.smartyads.sampleapp">
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <!-- Required. Allows an application to write to external storage. -->
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <!-- Optional. Grants the SDK permission to access a more accurate location based on GPS -->
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> <!-- Optional. Grants the SDK permission to access approximate location based on cell tower -->
<!-- your app description -->
</manifest>
The usage of RewardedVideoContainer exactly the same as the usage of InterstitialAdContainer):
You could give REWARD and AMOUNT fields to RewardedVideoContainer. They will be changed to macros, if those were indicated in the links when creating rewarded video placement on SmartyAds Supply Side Platform.
public class MainActivity extends AppCompatActivity {
private Button showAdButton;
private RewardedVideoContainer rewardedVideoContainer;
private String myReward; // if you indicated REWARD macro in links
private int myAmount; // if you indicated AMOUNT macro in links
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
showAdButton = (Button) findViewById(R.id.show_ad);
showAdButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if(rewardedVideoContainer.isLoaded())
rewardedVideoContainer.showAd();
}
});
rewardedVideoContainer = new RewardedVideoContainer(this, getString(R.string.rewarded_video_container_id), myReward, myAmount);
rewardedVideoContainer.loadAd(new InterstitialListener() {
@Override
public void onSuccess() {
Log.e("YOUR_TAG", "Ad loaded");
}
@Override
public void onFailure(Exception e) {
Log.e("YOUR_TAG", "Cannot load interstitial, reason: " + e.getMessage());
}
@Override
public void closed() {
Log.d("YOUR_TAG", "Interstitial closed");
}
});
}
}
Show Native
To show native you just need to initialize ad container through Builder and call NativeAdContainer#loadAd(loadListener) method as shown in example below. You should give to a Builder all fields that you specified while creating native placement on SmartyAds Supply Side Platform.
NativeAdContainer native = NativeAdContainer.Builder(getContext(),
getContext().getString(R.string.native_placement_id))
.setTitleView(myTitleView)
.setDescriptionView(myDescriptionView)
.setSponsoredTextView(mySponsoredTextView)
.setPriceView(myPriceView)
.setImageView(myImageView)
.setCtaView(myActionButton)
// Another specified fields
.build();
native.loadAd(new NativeOnLoadListener() {
@Override public void onSuccess() {
switchLoadingState(false);
showResult("success");
}
@Override public void onFailure(Exception e) {
switchLoadingState(false);
showResult("Failure: " + e.getMessage());
}
});
Where R.string.native_placement_id - your native placement id(see #important).
Ads caching configuration
By default caching allowed for all containers (recommended option). If you want to disable ads caching use SdkConfig class as shown below:
public class SampleApp extends Application {
@Override
protected void attachBaseContext(Context base) {
super.attachBaseContext(base);
SdkConfig.getConfigBuilder(base)
.setCacheEnabled(true)
.excludeCachingFor(
getString(R.string.banner_id)
).apply();
Ads.init(base);
}
}
To disable caching for separate containers use SdkConfig.Builder#excludeCachingFor(Collection).
To disable caching for all containers use SdkConfig.Builder#setCacheEnabled(false).
Adding targeting params
Targeting params are data that are provided for the SDK that will improve ad targeting. The params are not required and can be provided if your application has such data. There are three targeting parameters types:
- Gender: male, female, other - user gender
- Year of birth - year of a user birthday
- Keywords - user interests or intents
Usage:
AdContainer adContainer = new InterstitialAdContainer(this, getString(R.string.banner_id));
...
UserKeywords userKeywords = new UserKeywords()
.addKeywords("interest 1", "interest 2")
.addKeywords(Collections.singletonList("interest 3"));
adContainer.addTargetingData(Gender.MALE)
.addTargetingData(new YearOfBirth(1990))
.addTargetingData(userKeywords);
...
adContainer.loadAd();
Rendering Problems in Android Studio
In case you got rendering problems (VerifyError) in Preview mode, add -noverify VM option to Android Studio:
- Menu Help -> Edit Custom VM Options...
- Add -noverify key
- Restart Android Studio