Show a Frame
Render a server-driven frame in your Android or iOS app.
A frame is an embeddable, server-driven UI unit rendered natively at runtime. Frames are not limited to full screens. You can embed one anywhere in your existing app:
| Use case | Example |
|---|---|
| Full screen | Replace an entire Composable or SwiftUI view with a frame |
| Card | Drop a frame into a Column row or a SwiftUI HSack item |
| Dialog / Alert | Show a frame inside a Dialog |
| Bottom sheet | Embed a frame in a bottomSheet |
| Section / Banner | Render a frame as a partial section inside a larger screen |
NativeblocksFrame is just a Composable / SwiftUI view. Place it anywhere you would place any other UI component. The route tells it which frame definition to fetch and render.
Scaffold
Before rendering any frame you can call getScaffold to fetch the scaffold model from the server. The scaffold returns registered frames. Use it to drive your initial navigation instead of hardcoding a route.
class MainViewModel : ViewModel() {
fun loadScaffold() {
viewModelScope.launch {
NativeblocksManager.getInstance().getScaffold()
.onSuccess { scaffold ->
scaffold.frames
}
.onFailure { Log.e("Nativeblocks", "scaffold failed", it) }
}
}
}
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val viewModel: MainViewModel by viewModels()
setContent {
MyAppTheme {
LaunchedEffect(Unit) { viewModel.loadScaffold() }
NativeblocksFrame(
route = viewModel.startRoute,
routeArguments = hashMapOf(),
loading = { NativeblocksLoading() },
error = { msg -> NativeblocksError(message = msg) }
)
}
}
}
}
setContent {
NativeblocksFrame(
route = "/",
routeArguments = hashMapOf(),
loading = { NativeblocksLoading() },
error = { message -> NativeblocksError(message = message) }
)
}
Parameters
| Parameter | Description |
|---|---|
route | The route key registered via the CLI (e.g. /home, /profile) |
routeArguments | Runtime values injected into the frame (user ID, locale, flags) |
loading | UI shown while the frame is fetching |
error | UI shown if the frame fails to load |
Passing Route Arguments
Route arguments let you inject dynamic values into a frame at render time. They can be read at runtime to conditionally show blocks or populate data:
NativeblocksFrame(
route = "/profile",
routeArguments = hashMapOf(
"userId" to "abc123",
"tab" to "orders"
),
loading = { NativeblocksLoading() },
error = { message -> NativeblocksError(message = message) }
)
Full Example
A single-Activity app using Jetpack Compose Navigation to render different frames per destination.
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.material3.Scaffold
import androidx.navigation.compose.NavHost
import androidx.navigation.compose.composable
import androidx.navigation.compose.rememberNavController
import io.nativeblocks.core.api.NativeblocksFrame
import io.nativeblocks.core.api.NativeblocksLoading
import io.nativeblocks.core.api.NativeblocksError
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent {
MyAppTheme {
val navController = rememberNavController()
Scaffold { padding ->
NavHost(
navController = navController,
startDestination = "home",
modifier = Modifier.padding(padding)
) {
composable("home") {
NativeblocksFrame(
route = "/home",
routeArguments = hashMapOf(),
loading = { NativeblocksLoading() },
error = { msg -> NativeblocksError(message = msg) }
)
}
composable("profile/{userId}") { backStackEntry ->
val userId = backStackEntry.arguments?.getString("userId") ?: ""
NativeblocksFrame(
route = "/profile",
routeArguments = hashMapOf("userId" to userId),
loading = { NativeblocksLoading() },
error = { msg -> NativeblocksError(message = msg) }
)
}
composable("settings") {
NativeblocksFrame(
route = "/settings",
routeArguments = hashMapOf(),
loading = { NativeblocksLoading() },
error = { msg -> NativeblocksError(message = msg) }
)
}
}
}
}
}
}
}