In-App Native Display Integration
This guide shows how to render NotifyVisitors Native Displays (a.k.a. in-app nudges/cards) inside your Android app using the notifyvisitors-nudges SDK. You’ll add the SDK, drop a NotifyVisitorsNativeDisplay view into your layout, load content by property_id (configured in the NotifyVisitors panel), and handle a callback to size the container.
1. Add Dependencies
Add the base SDK and the nudges module to your app module’s build.gradle:
dependencies {
implementation "com.notifyvisitors.notifyvisitors:notifyvisitors:v5.6.0"
implementation "com.notifyvisitors.nudges:notifyvisitors-nudges:v0.0.8"
}
Make sure the core notifyvisitors SDK is initialized the way your workspace expects (usually in Application#onCreate), before loading a native display.
2. Imports
Import the following statements:
import com.notifyvisitors.nudges.NotifyVisitorsNativeDisplay;
import com.notifyvisitors.notifyvisitors.interfaces.OnNudgeUiCompletion;
import com.notifyvisitors.notifyvisitors.NotifyVisitorsApi;
import com.notifyvisitors.nudges.NotifyVisitorsNativeDisplay
import com.notifyvisitors.notifyvisitors.interfaces.OnNudgeUiCompletion
import com.notifyvisitors.notifyvisitors.NotifyVisitorsApi
3. Code Implementation
Instantiate the view with an Activity context (not the Application context), add it to a container, and call loadContent(property_id) to fetch/render the configured native display.
NotifyVisitorsNativeDisplay nativeCardUI = new NotifyVisitorsNativeDisplay(activityContext);
nativeCardUI.loadContent(property_id_as_string);
val nativeCardUI = NotifyVisitorsNativeDisplay(activityContext)
nativeCardUI.loadContent(property_id_as_string)
Parameter:
property_id(String): Must exactly match the ID configured for the native display in the NotifyVisitors panel. Treat it as the unique key for the content you want to render (e.g.,"home","paywall_banner","promo_card_q3").
4. Handling the Completion Callback
When the UI finishes rendering, the SDK invokes a completion callback. On success, it returns a JSON payload that typically contains a size object with the rendered height/width so you can adjust your container.
NotifyVisitorsApi.getInstance(activityContext).nudgeUiFinalized(new OnNudgeUiCompletion() {
@Override
public void onFinish(org.json.JSONObject info) {
// Called when the native display finishes rendering.
// Example payload (may vary):
// {
// "success": true,
// "size": { "height": "180", "width": "match_parent" }
// }
}
});
NotifyVisitorsApi.getInstance(activityContext).nudgeUiFinalized(object : OnNudgeUiCompletion {
override fun onFinish(info: org.json.JSONObject) {
// Handle success + size info here
}
})
5. Example
This example:
- Adds the native display view into a
LinearLayoutcontainer. - Loads the
"home"property. - Listens for the callback and dynamically updates the parent’s height on the main thread.
LinearLayout parentView = findViewById(R.id.parent_view);
NotifyVisitorsNativeDisplay nativeCardUI = new NotifyVisitorsNativeDisplay(this /* activityContext */);
parentView.addView(nativeCardUI);
// Start loading content configured as "home" in the dashboard
nativeCardUI.loadContent("home");
// Listen for completion and resize
NotifyVisitorsApi.getInstance(this).nudgeUiFinalized(new OnNudgeUiCompletion() {
@Override
public void onFinish(org.json.JSONObject info) {
android.util.Log.d("App", "NUDGE INFO >> " + info);
android.os.Handler h = new android.os.Handler(android.os.Looper.getMainLooper());
h.post(() -> {
try {
org.json.JSONObject size = info.optJSONObject("size");
if (size != null) {
// Height may be provided as a string
String heightStr = size.optString("height", "");
if (!heightStr.isEmpty()) {
int finalHeight = Integer.parseInt(heightStr);
ViewGroup.LayoutParams params = parentView.getLayoutParams();
params.height = finalHeight;
parentView.setLayoutParams(params);
android.util.Log.d("App", "Updated parent height to: " + finalHeight);
}
}
} catch (Exception e) {
android.util.Log.e("App", "Failed to update height", e);
}
});
}
});
val parentView = findViewById<LinearLayout>(R.id.parent_view)
val nativeCardUI = NotifyVisitorsNativeDisplay(this /* activityContext */)
parentView.addView(nativeCardUI)
// Start loading content configured as "home" in the dashboard
nativeCardUI.loadContent("home")
// Listen for completion and resize
NotifyVisitorsApi.getInstance(this).nudgeUiFinalized { info ->
android.util.Log.d("App", "NUDGE INFO >> $info")
val h = android.os.Handler(android.os.Looper.getMainLooper())
h.post {
try {
val size = info.optJSONObject("size")
if (size != null) {
val heightStr = size.optString("height", "")
if (heightStr.isNotEmpty()) {
val finalHeight = heightStr.toInt()
val params = parentView.layoutParams
params.height = finalHeight
parentView.layoutParams = params
android.util.Log.d("App", "Updated parent height to: $finalHeight")
}
}
} catch (e: Exception) {
android.util.Log.e("App", "Failed to update height", e)
}
}
}
6. Layout Recommendations
XML container example
<!-- res/layout/activity_main.xml -->
<LinearLayoutandroid:id="@+id/parent_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"/>
Tips
- Start with
wrap_contentand let the callback size the container precisely. - Avoid hardcoded widths/heights inside your native display container unless you have a fixed design.
- If the content supports dynamic updates (A/B variations, different images), always rely on the callback to finalize the size.
Further Reading
Knowledge base: Creating In-App Native Displays with NotifyVisitors (use cases, targeting, activation, troubleshooting)
Updated about 23 hours ago
