jetpack組件-----聲明式UI:Compose(一):簡單實(shí)現(xiàn)一個界面

最近一直在準(zhǔn)備軟考,天天在看教學(xué)視頻,這不后天就要考試了,我報的是軟件設(shè)計師,說說我對軟考的理解吧,軟考高級我不知道,就中級而言,非常符合中國的應(yīng)試性教育??嫉亩己軓V,但沒有一樣?xùn)|西考的精,我學(xué)了那么長時間,知識儲備已經(jīng)有了,考試應(yīng)付足夠了,但我覺得我可能永遠(yuǎn)沒有機(jī)會把這些只是應(yīng)用到實(shí)際中。扯多了,回歸正題。
我第一次聽說compose是在逛Android大牛講堂的時候,大佬說這會成為以后UI的主流框架,就很好奇到底是什么樣的東西能夠動搖xml那么多年的老大哥位置,還一直被谷歌力推,下面就讓我們來一步步走近它。
參看文章:Android開發(fā)者平臺

什么是compose

先看官方的解釋:
Jetpack Compose 是一個適用于 Android 的新式聲明性界面工具包。Compose 提供聲明性 API,讓您可在不以命令方式改變前端視圖的情況下呈現(xiàn)應(yīng)用界面,從而使編寫和維護(hù)應(yīng)用界面變得更加容易。此術(shù)語需要一些解釋說明,它的含義對應(yīng)用設(shè)計非常重要。
這里我就官方解釋給出自己的理解,不以命令方式改變前端視圖來呈現(xiàn)應(yīng)用界面,其實(shí)就是叫我們摒棄命令式UI,來使用Compose這種聲明式UI。那為什么要這樣做呢?
我們的傳統(tǒng)式UI在繪制界面上都是重新生成整個視圖,如果我們從服務(wù)器拿到一條數(shù)據(jù)需要適配給多個視圖,那更新起來會很麻煩,甚至出現(xiàn)忘記去更改數(shù)據(jù)的情況,Compose可以避免這種情況,當(dāng)然,這是后話了。還有一個原因是傳統(tǒng)命令式UI需要重新繪制視圖,從頭到尾重新渲染,這會導(dǎo)致消耗資源大,速度慢,而Compose做的只是在概念上從頭開始重新生成整個屏幕,實(shí)際上只執(zhí)行必要的更改。這就是他相比較于xml的優(yōu)勢所在。

compose的簡單使用

Compose的使用需要下載Android studio的Fox及以上版本,然后new一個compose的新工程,選擇Empty Compose Activity


image.png

基本代碼如下:

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            ComposeDemo2Theme {
                // A surface container using the 'background' color from the theme
                Surface(color = MaterialTheme.colors.background) {
                    Greeting("Android")
                }
            }
        }
    }
}

@Composable
fun Greeting(name: String) {
    Text(text = "Hello $name!")
}

@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemo2Theme {
        Greeting("Android")
    }
}

我們可以看到很多不一樣的東西,首先看到兩個注解@compose和@Preview,@compose注解表示此注釋可告知 Compose 編譯器:此函數(shù)旨在將數(shù)據(jù)轉(zhuǎn)換為界面。也就是說帶有@conpose注解的函數(shù)都是編寫界面的函數(shù),通常我們叫它可組合函數(shù)。
對于@Preview注解看看官方的解釋:
Android Studio 允許您在 IDE 中預(yù)覽可組合函數(shù),無需將應(yīng)用安裝到 Android 設(shè)備或模擬器中??山M合函數(shù)必須為任何參數(shù)提供默認(rèn)值。因此,您無法直接預(yù)覽 MessageCard() 函數(shù),而是需要創(chuàng)建另一個名為 PreviewMessageCard() 的函數(shù),由該函數(shù)使用適當(dāng)?shù)膮?shù)調(diào)用 MessageCard()。請在 @Composable 上方添加 @Preview 注解。
就是@Preview注解的函數(shù)編寫的界面會展示在預(yù)覽區(qū)中。和實(shí)際效果不一定相同。
比如上述代碼改成

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            ComposeDemo2Theme {
                // A surface container using the 'background' color from the theme
                Surface(color = MaterialTheme.colors.background) {
                    Greeting("蒙奇.D.路飛")
                }
            }
        }
    }
}

@Composable
fun Greeting(name: String) {
    Text(text = "Hello $name!")
}

@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemo2Theme {
        Greeting("Android")
    }
}

我們可以看到在setContent中調(diào)用的和在預(yù)覽函數(shù)中調(diào)用的Greeting函數(shù)傳的參數(shù)不一樣,所以預(yù)覽視圖和實(shí)際運(yùn)行界面也不一樣
預(yù)覽視圖:


image.png

實(shí)際界面截圖:


Screenshot_2021-11-04-15-33-19-904_com.example.co.jpg

那要怎么讓他們統(tǒng)一呢,很簡單,我們只需要在setContent里面也調(diào)用預(yù)覽函數(shù)就可以了,如下:

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            DefaultPreview()
        }
    }
}

@Composable
fun Greeting(name: String) {
    Text(text = "Hello $name!")
}

@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemo2Theme {
        Greeting("蒙奇.D.路飛")
    }
}

這樣預(yù)覽效果和實(shí)際效果就是一樣的了。

compose實(shí)現(xiàn)簡單布局

我們以官方給出的簡單demo為例:比如我們要創(chuàng)建這樣一個視圖:


image.png

首先在布局里面添加三個文本:

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            DefaultPreview()
        }
    }
}

@Composable
fun message(name: String, othername: String, phone: Long) {
        Text(text = "綽號:$othername", fontSize = 14.sp)
        Text(text = "電話號碼:$phone", fontSize = 14.sp)
        Text(text = "姓名: $name!", fontSize = 14.sp)
}


@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemoTheme {
            message(name = "張志平", othername = "大帥比", phone = 110)
    }
}

效果如圖所示:


image.png

我們會發(fā)現(xiàn)重疊在了一起,這時候使用Cloumn可以使他們豎直排序

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            DefaultPreview()
        }
    }
}

@Composable
fun message(name: String, othername: String, phone: Long) {
    Column {
        Text(text = "綽號:$othername", fontSize = 14.sp)
        Text(text = "電話號碼:$phone", fontSize = 14.sp)
        Text(text = "姓名: $name!", fontSize = 14.sp)
    }
}


@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemoTheme {
        message(name = "張志平", othername = "大帥比", phone = 110)
    }
}

如圖:


image.png

接下來添加圖片,圖片與文字水平,使用Row

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            DefaultPreview()
        }
    }
}

@Composable
fun message(name: String, othername: String, phone: Long) {
    Column {
        Text(text = "綽號:$othername", fontSize = 14.sp)
        Text(text = "電話號碼:$phone", fontSize = 14.sp)
        Text(text = "姓名: $name!", fontSize = 14.sp)
    }
}


@Preview(showBackground = true)
@Composable
fun DefaultPreview() {
    ComposeDemoTheme {
        Row(modifier = Modifier.padding(all = 8.dp)) {
            Image(
                painter = painterResource(id = R.drawable.tx),
                contentDescription = "聯(lián)系人照片",
                modifier = Modifier
                    .size(60.dp)
                    .scale(1.0F),
                contentScale = ContentScale.FillBounds
            )
            Spacer(modifier = Modifier.width(8.dp))
            message(name = "張志平", othername = "大帥比", phone = 110)
        }
    }
}

圖片如圖所示:


image.png

到此,一個compose的簡單例子就完成了,可能里面有些方法和寫法大家會覺得很不熟悉,建議點(diǎn)進(jìn)去看一下源碼,我也是看著源碼寫的,源碼的注釋已經(jīng)很清楚了,不會看的兄弟們一定要學(xué)著去看,其實(shí)很簡單,不要自己把自己勸退,比如Image()里面的構(gòu)造參數(shù),怎么調(diào)大小,怎么調(diào)比例,都是在源碼里面可以找到的,后續(xù)我會逐漸深入地去了解它,也會寫出文章和大家交流。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容