所謂 DSL 領域?qū)S谜Z言(Domain Specified Language/ DSL),其基本思想是“求專不求全”,不像通用目的語言那樣目標范圍涵蓋一切軟件問題,而是專門針對某一特定問題的計算機語言。
為奈曼等地區(qū)用戶提供了全套網(wǎng)頁設計制作服務,及奈曼網(wǎng)站建設行業(yè)解決方案。主營業(yè)務為成都做網(wǎng)站、網(wǎng)站設計、奈曼網(wǎng)站設計,以傳統(tǒng)方式定制建設網(wǎng)站,并提供域名空間備案等一條龍服務,秉承以專業(yè)、用心的態(tài)度為用戶提供真誠的服務。我們深信只要達到每一位用戶的要求,就會得到認可,從而選擇與我們長期合作。這樣,我們也可以走得更遠!
Kotlin DSL 定義:使用 Kotlin 語言開發(fā)的,解決特定領域問題,具備獨特代碼結(jié)構(gòu)的 API 。
DSL(domain specific language),即領域?qū)S谜Z言:專門解決某一特定問題的計算機語言,比如大家耳熟能詳?shù)?SQL 和正則表達式。使用DSL的編程風格,可以讓程序更加簡單干凈、直觀簡潔。當然,我們也可以創(chuàng)建自己的 DSL。相對于傳統(tǒng)的 API, DSL 更加富有表現(xiàn)力、更符合人類語言習慣。
如果為解決某一特定領域問題就創(chuàng)建一套獨立的語言,開發(fā)成本和學習成本都很高,因此便有了內(nèi)部 DSL 的概念。所謂內(nèi)部 DSL,便是使用通用編程語言來構(gòu)建 DSL,比如,Kotlin DSL。
常見的 DSL 在很多領域都能看到,例如:
通用編程語言(如 Java、Kotlin、Android等),往往提供了全面的庫來幫助開發(fā)者開發(fā)完整的應用程序,而 DSL 只專注于某個領域,比如 SQL 僅支持數(shù)據(jù)庫的相關處理,而正則表達式只用來檢索和替換文本,我們無法用 SQL 或者正則表達式來開發(fā)一個完整的應用。
無論是通用編程語言,還是領域?qū)S谜Z言,最終都是要通過 API 的形式向開發(fā)者呈現(xiàn)。良好的、優(yōu)雅的、整潔的、一致的 API 風格是每個優(yōu)秀開發(fā)者的追求,而 DSL 往往具備獨特的代碼結(jié)構(gòu)和一致的代碼風格。
Anko 是一個 DSL (Domain-Specific Language), 它是 JetBrains 出品的,用 Kotlin 開發(fā)的安卓框架。它主要的目的是用來替代以前 XML 的方式來使用代碼生成 UI 布局。
Anko 中, 不需要繼承其他奇怪的類,只要標準的 Activity, Fragment,F(xiàn)ragmentActivity 或者其他任意的類
首先, 在使用 Anko 的 DSL 的類中導入 org.jetbrains.anko.* .
DSL 可以在 onCreate()中使用:
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
verticalLayout {
padding = dip(30)
editText {
hint = "Name"
textSize = 24f
}
editText {
hint = "Password"
textSize = 24f
}
button("Login") {
textSize = 26f
}
}
}
不需要顯示的調(diào)用 setContentView(R.layout.something), Anko 自動為 Activity(只會對Activity)進行 set content view
padding, hint 和 textSize 是 擴展屬性. 大多數(shù) View 具有這些屬性,允許使用 text = “Some text” 代替 setText(“Some text”).
verticalLayout (一個豎直方向的 LinearLayout), editText 和 button
擴展函數(shù). 這些函數(shù)存在與ANdroid 框架中的大部View中, Activities, Fragments ( android.support 包中的) 甚至 Context同樣適用.
如果有一個 Context 實例, 可以寫出下面的DSL結(jié)構(gòu):
val name = with(myContext) {
editText {
hint = "Name"
}
}
變量 name 成為了 EditText類型.
你可能注意到了,前面 button 方法接了一個字符串參數(shù),這樣的Helper方法同樣使用與 TextView, EditText, Button , ImageView.
如果你不需要 View 其他的屬性,你可以省略 {} 直接寫 button(“Ok”) 或只有 button():
verticalLayout {
button("Ok")
button("Cancel")
}
在父布局中布局控件可能需要使用 LayoutParams.xml 中長這樣:
Anko 中, 在 View 的后面使用 lparams 來實現(xiàn)類似與 xml 的 LayoutParams。
linearLayout {
button("Login") {
textSize = 26f
}.lparams(width = wrapContent) {
horizontalMargin = dip(5)
topMargin = dip(10)
}
}
如果指定了 lparams,但是沒有指定 width 或者 height, 默認是 WRAP_CONTENT,但是你可以自己通過使用 named arguments指定.
注意下面一些方便的屬性:
使用 Anko 之后,可以用代碼實現(xiàn)布局,并且 button 還綁定了點擊事件。
verticalLayout {
var title = editText {
id = R.id.todo_title
hintResource = R.string.title_hint
}
button {
textResource = R.string.add_todo
onClick { view -> {
// do something here
title.text = "Foo"
}
}
}
}
可以看到 DSL 的一個主要優(yōu)點在于,它需要很少的時間即可理解和傳達某個領域的詳細信息。
override fun onCreate(savedInstanceState: Bundle?) {
? super.onCreate(savedInstanceState)
? verticalLayout {
? ? ? padding = dip(30)
? ? ? editText {
? ? ? ? hint = "Name"
? ? ? ? textSize = 24f
? ? ? }
? ? ? editText {
? ? ? ? hint = "Password"
? ? ? ? textSize = 24f
? ? ? }
? ? ? button("Login") {
? ? ? ? textSize = 26f
? ? ? }
? }
}
alert("Hi, I'm Roy", "Have you tried turning it off and on again?") {
yesButton { toast("Oh…") }
noButton {}
}.show()
doAsync {
// Long background task
uiThread {
result.text = "Done"
}
}
關于我
更多信息可以點擊+關于我 , 非常希望和大家一起交流 , 共同進步