Pantrix UI

Page Scaffold

Bir uygulamanın kabuğunun içindeki bir ekran: başında başlığı ve yapabildikleri, altında gösterdiği; kabuğun bar'larından, klavyeden ve pencerenin kenarlarından uzakta. Bir uygulama kabuğunu bir kez bir PantrixScaffold ile kurar, gezinmesi dar pencerede altta, geniş pencerede yanda; her ekranını bununla.

import com.pantrixui.components.container.page.PantrixPageScaffold

Örnekler

Bir yönetim sayfası

Bir yönetim panelinin siparişler sayfası. titlePlacement = PageTitlePlacement.Adaptive: kartın seçicisinde "Geniş"e geç, başlık ve eylemler içeriğin başına iner ve bar kalkar; "Dar"da bar'dadırlar ve eylemler ikonlara döner. "Arşivle"nin ikonu yoktur: dar sayfada "…" menüsündedir. Basılan eylemin anahtarı sayfanın içinde yazar.

var pressed by rememberSaveable { mutableStateOf<String?>(null) }
PageExampleFrame {
    PantrixPageScaffold(
        title = "Siparişler",
        subtitle = "12 açık",
        actions = listOf(
            PageAction(key = "new", label = "Yeni sipariş", icon = PantrixIcons.Plus, primary = true),
            PageAction(key = "export", label = "Dışa aktar", icon = PantrixIcons.Download),
            PageAction(key = "archive", label = "Arşivle")
        ),
        onAction = { pressed = it },
        header = {
            PantrixText("Son 30 günün siparişleri", color = PantrixTheme.colors.textSecondary)
        },
        titlePlacement = PageTitlePlacement.Adaptive,
        tagKey = "orders"
    ) {
        PantrixText(pressed?.let { "Son basılan: $it" } ?: "Henüz bir eyleme basılmadı")
        repeat(5) { index ->
            PantrixCard(modifier = Modifier.fillMaxWidth().padding(top = 8.dp)) {
                PantrixText("Sipariş #${1040 + index}", modifier = Modifier.padding(16.dp))
            }
        }
    }
}

@Composable
private fun PageExampleFrame(content: @Composable () -> Unit) {
    PantrixSurface(
        modifier = Modifier.fillMaxWidth().height(PAGE_EXAMPLE_HEIGHT),
        border = PantrixTheme.colors.divider
    ) {
        Box { content() }
    }
}

private val PAGE_EXAMPLE_HEIGHT = 420.dp

Bar'ın altında sekmeler, kendi kayan bir liste

Sekmeler bar'ın altında durur (stickyHeader), liste kendisi kayar (scroll = PageScroll.None) ve sayfanın bıraktığı payı contentPadding ile alır: son satırı payın içinde, kenar boşluğu satırların içinde. Listeyi kaydır: çizgi sekmelerin altında belirir. Geri düğmesine basınca alt başlık sayar.

var tab by rememberSaveable { mutableIntStateOf(0) }
var backs by rememberSaveable { mutableIntStateOf(0) }
val tabs = listOf(TabItem("Tümü"), TabItem("Satışta"), TabItem("Tükendi"))
PageExampleFrame {
    PantrixPageScaffold(
        title = "Ürünler",
        subtitle = if (backs == 0) null else "Geri'ye $backs kez basıldı",
        onBack = { backs++ },
        stickyHeader = { PantrixTabs(tabs = tabs, selectedIndex = tab, onSelect = { tab = it }, tagKey = "stock") },
        scroll = PageScroll.None,
        tagKey = "products"
    ) {
        LazyColumn(contentPadding = contentPadding, verticalArrangement = Arrangement.spacedBy(12.dp)) {
            items(List(20) { "${tabs[tab].label}: ürün ${it + 1}" }) { product -> PantrixText(product) }
        }
    }
}

@Composable
private fun PageExampleFrame(content: @Composable () -> Unit) {
    PantrixSurface(
        modifier = Modifier.fillMaxWidth().height(PAGE_EXAMPLE_HEIGHT),
        border = PantrixTheme.colors.divider
    ) {
        Box { content() }
    }
}

private val PAGE_EXAMPLE_HEIGHT = 420.dp

Büyük başlık ve bir liste

Bir listenin sayfası: PantrixLazyPageScaffold. Satırlar göründükçe kurulur; header listenin ilk satırıdır. largeTitle = true: başlık bar'ın altında büyük yazılır, liste kaydıkça bar'a çıkar. trailing bar'ın sonuna uygulamanın kendi düğmesini koyar. width = PageWidth.Content: okunan bir liste geniş pencerede temanın içerik genişliğinde kalır.

PageExampleFrame {
    PantrixLazyPageScaffold(
        title = "Gelen kutusu",
        trailing = {
            PantrixIconButton(PantrixIcons.Search, contentDescription = "Ara", onClick = {}, tagKey = "search")
        },
        header = { PantrixText("4 okunmamış ileti", color = PantrixTheme.colors.textSecondary) },
        largeTitle = true,
        width = PageWidth.Content,
        verticalArrangement = Arrangement.spacedBy(12.dp),
        tagKey = "inbox"
    ) {
        items(List(30) { "İleti ${it + 1}" }) { message -> PantrixText(message) }
    }
}

@Composable
private fun PageExampleFrame(content: @Composable () -> Unit) {
    PantrixSurface(
        modifier = Modifier.fillMaxWidth().height(PAGE_EXAMPLE_HEIGHT),
        border = PantrixTheme.colors.divider
    ) {
        Box { content() }
    }
}

private val PAGE_EXAMPLE_HEIGHT = 420.dp

Kabuğun içinde, kendi ölçüleriyle

Kabuğun içinde bir sayfa: PantrixScaffold'un alt bar'ı var, sayfa onun payını kendisi okur ve son satırını bar'ın üstünde bırakır. padding verilmese de odur (LocalPantrixScaffoldPadding.current); burada açıkça yazılı. style sayfanın kenar boşluğunu ve bölümlerin arasını değiştirir.

PageExampleFrame {
    PantrixScaffold(
        bottomBar = { insets ->
            PantrixSurface(modifier = Modifier.fillMaxWidth().padding(insets).height(56.dp)) {
                PantrixText("Alt bar", modifier = Modifier.align(Alignment.Center))
            }
        }
    ) {
        PantrixPageScaffold(
            title = "Ayarlar",
            header = { PantrixText("Kenar boşluğu 24 dp, bölümlerin arası 8 dp") },
            padding = LocalPantrixScaffoldPadding.current,
            style = PageScaffoldStyle(horizontalPadding = 24.dp, sectionGap = 8.dp),
            tagKey = "settings"
        ) {
            repeat(12) { index -> PantrixText("Ayar ${index + 1}", modifier = Modifier.padding(vertical = 8.dp)) }
        }
    }
}

@Composable
private fun PageExampleFrame(content: @Composable () -> Unit) {
    PantrixSurface(
        modifier = Modifier.fillMaxWidth().height(PAGE_EXAMPLE_HEIGHT),
        border = PantrixTheme.colors.divider
    ) {
        Box { content() }
    }
}

private val PAGE_EXAMPLE_HEIGHT = 420.dp

Pencerenin başlığı

Pencerenin başlığı bir sayfa olmadan da verilir: PantrixWindowTitle ekranın adını, LocalPantrixWindowTitleFormat onu pencereye nasıl yazacağını söyler. Anahtarı aç: web'de sekmenin, masaüstünde pencerenin başlığı "Raporlar — Yönetim" olur; kapatınca bu sayfanınki geri gelir. Android'de ve iOS'ta kullanıcıya görünen bir pencere başlığı yoktur.

var named by rememberSaveable { mutableStateOf(false) }
PantrixSwitchButton(
    checked = named,
    onCheckedChange = { named = it },
    label = "Pencereye \"Raporlar\" adını ver",
    tagKey = "window_title"
)
if (named) {
    CompositionLocalProvider(LocalPantrixWindowTitleFormat provides PantrixWindowTitleFormat { "$it — Yönetim" }) {
        PantrixWindowTitle("Raporlar")
    }
}

API

title

Bir uygulamanın kabuğunun içindeki bir ekran: başında başlığı ve yapabildikleri, altında gösterdiği; kabuğun bar'larından, klavyeden ve pencerenin kenarlarından uzakta. Bir uygulama kabuğunu bir kez bir PantrixScaffold ile kurar, gezinmesi dar pencerede altta, geniş pencerede yanda; her ekranını bununla.

ParametreTürVarsayılanNe olduğu
titleStringsayfanın adı: bar'ında ya da başlığında, ekran okuyucu için adı ve pencereninki.
modifierModifierModifiersayfanın modifier'ı.
subtitleString?nullbaşlığın altında bir satır, bir sayı ya da bir durum; yoksa null.
onBack(() -> Unit)?nullsayfanın geri döndüğü yer, bar'ının geri düğmesi olarak; dönülecek bir yer yoksa null. Sistemin geri hareketini, bir el hareketini ya da bir tuşu uygulamanın gezinmesi dinler.
actionsList<PageAction>emptyList()sayfanın yapabildikleri, en çok kullanılan başta: yere göre dizilir, geri kalanı bir menüdedir. Her birinin aralarında kendine ait bir anahtarı vardır.
onAction(key: String) -> Unit{}basılan eylemin anahtarını alır.
trailing(@Composable RowScope.() -> Unit)?nulleylemlerin ardında her zaman duran, bir satırda: uygulamanın kendi düğmeleri.
header(@Composable () -> Unit)?nullbaşlığın altında, içeriğin üstünde duran ve onlarla kayan.
stickyHeader(@Composable () -> Unit)?nullbar'ın altında duran ve sayfa kayarken orada kalan.
titlePlacementPageTitlePlacementPageTitlePlacement.Barbaşlığın her genişlikte bar'da mı, geniş bir sayfada içerikte mi olduğu.
largeTitleBooleanfalsebar'ın başlığının altında büyük yazılmış durup durmadığı ve sayfa kaydıkça bar'a çıkıp çıkmadığı.
widthPageWidthPageWidth.Fullsayfanın gösterdiğinin genişliği: sayfanınki ya da temanın içerik genişliği.
scrollPageScrollPageScroll.Pagesayfanın mı kaydığı, yoksa içeriğinin mi kendisi kaydığı.
paddingPaddingValuesLocalPantrixScaffoldPadding.currentsayfanın kenarlarında uzak durduğu: verilmezse çevreleyen scaffold'un payı.
stylePageScaffoldStyle?nullsayfanın geometrisi, temanınkinin üstünde.
tagKeyString?nullsayfanın otomasyon anahtarı, her dilde aynı: sayfanın ve parçalarının etiketlendiği, tuttuklarının TestScope'u ve show olayının ait olduğu sayfa.
content@Composable PageScaffoldScope.() -> Unitsayfanın gösterdiği, bir sütunda; PageScroll.None ile bırakacağı payı PageScaffoldScope.contentPadding olarak alır.

PageScaffoldStyle

PantrixPageScaffold'un geometrisi: sayfanın tuttuklarının çevresindeki ve parçalarının arasındaki yer.

ParametreTürVarsayılanNe olduğu
horizontalPaddingDpDp.UnspecifiedSayfanın yanlarıyla tuttukları arasındaki yer, scaffold'un payından sonra: verilmezse belirsizdir, yani temanın sayfa kenar boşluğudur.
verticalPaddingDpDp.UnspecifiedSayfanın tuttuklarının üstündeki ve altındaki yer: Android'de ve iOS'ta 16dp, masaüstünde ve web'de 24dp.
sectionGapDpDp.UnspecifiedSayfanın başlığı, üst kısmı ve içeriği arasındaki yer: Android'de ve iOS'ta 16dp, masaüstünde ve web'de 24dp.
actionGapDpDp.UnspecifiedSayfanın iki eylemi arasındaki ve eylemlerle yanlarındaki arasındaki yer: 8dp.
topBarTopBarStyle?nullSayfanın bar'ının kendi geometrisi, temanınkinin üstünde. Bu bir yer vermedikçe bar'ın başlığı horizontalPadding'den başlar.

Erişilebilirlik