Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
明日からちょっと KotlinでAndroidが書きたくなる(かもしれない?)SAM変換と...
Search
RyotaMurohoshi
July 14, 2014
Technology
0
28
明日からちょっと KotlinでAndroidが書きたくなる(かもしれない?)SAM変換と拡張関数
2014/07/04 かわいいKotlin勉強会で行った発表の資料です
※ 元々はSlideShareで公開していた資料です。
RyotaMurohoshi
July 14, 2014
Tweet
Share
More Decks by RyotaMurohoshi
See All by RyotaMurohoshi
Unityの合同同人誌や合同商業誌を書いてる僕は感想やレビューや評価が欲しい
ryotamurohoshi
0
490
Unity 2021.1での Unityパッケージの名称変更について
ryotamurohoshi
0
680
Odin Validationはいいぞ!
ryotamurohoshi
2
910
Tilemapはいいぞ!2020 〜すごいぞ、プロジェクト専用拡張Brush〜
ryotamurohoshi
0
2.3k
Unityでも、新しいC#
ryotamurohoshi
0
1.3k
Riderはいいぞ!
ryotamurohoshi
1
3.4k
Riderのススメ〜俺はRiderここが好き〜
ryotamurohoshi
1
2.3k
Unity開発者に伝えたい.NETのこと
ryotamurohoshi
4
37k
ImportedLinqのススメ
ryotamurohoshi
0
1.3k
Other Decks in Technology
See All in Technology
4th place solution Eedi - Mining Misconceptions in Mathematics
rist
0
150
ライフステージの変化を乗り越える 探索型のキャリア選択
tenshoku_draft
1
120
役員・マネージャー・著者・エンジニアそれぞれの立場から見たAWS認定資格
nrinetcom
PRO
5
6.8k
貧民的プログラミングのすすめ
kakehashi
PRO
1
140
エンジニアのキャリアパスと、 その中で自分が大切にしていること
noteinc
3
310
Introduction to OpenSearch Project - Search Engineering Tech Talk 2025 Winter
tkykenmt
2
230
【内製開発Summit 2025】イオンスマートテクノロジーの内製化組織の作り方/In-house-development-summit-AST
aeonpeople
2
1.1k
AWSではじめる Web APIテスト実践ガイド / A practical guide to testing Web APIs on AWS
yokawasa
8
790
MIMEと文字コードの闇
hirachan
2
1.5k
職位にかかわらず全員がリーダーシップを発揮するチーム作り / Building a team where everyone can demonstrate leadership, regardless of position
madoxten
18
9.1k
データエンジニアリング領域におけるDuckDBのユースケース
chanyou0311
9
2.6k
DeepSeekとは?何がいいの? - Databricksと学ぶDeepSeek! 〜これからのLLMに備えよ!〜
taka_aki
1
180
Featured
See All Featured
Let's Do A Bunch of Simple Stuff to Make Websites Faster
chriscoyier
507
140k
Build your cross-platform service in a week with App Engine
jlugia
229
18k
How To Stay Up To Date on Web Technology
chriscoyier
790
250k
Why Our Code Smells
bkeepers
PRO
336
57k
The Myth of the Modular Monolith - Day 2 Keynote - Rails World 2024
eileencodes
21
2.5k
KATA
mclloyd
29
14k
Unsuck your backbone
ammeep
669
57k
The MySQL Ecosystem @ GitHub 2015
samlambert
250
12k
Building a Modern Day E-commerce SEO Strategy
aleyda
38
7.1k
Art, The Web, and Tiny UX
lynnandtonic
298
20k
4 Signs Your Business is Dying
shpigford
183
22k
Visualizing Your Data: Incorporating Mongo into Loggly Infrastructure
mongodb
45
9.4k
Transcript
໌͔Βͪΐͬͱ KotlinͰAndroid͕ॻ͖ͨ͘ͳΔ(͔͠Εͳ͍ʁ) SAMมͱ֦ுؔ ɹ ྄ࣨଠ 2014/7/4(ۚ))ୈ2ճ)͔Θ͍͍Kotlinษڧձ)#jkug
ಥવͰ͕࣭͢Ͱ͢ʂ
Kotlinॻ͍ͨ͜ͱ͋Δํʁ
ʮKotlin'ॻ͍ͨ͜ͱͳ͍ʯ ͬͯΠϕϯτϖʔδʹॻ͍͚ͨΕͲ ຊॻ͍ͨ͜ͱ͋Δํʁ
AndroidΞϓϦ ։ൃͨ͜͠ͱ͋Δํʁ
͋Γ͕ͱ͏͍͟͝·ͨ͠ʂ
͓લͩΕΑ • ໊લ":"྄ࣨଠ • ࣄ":"AndroidΞϓϦ։ൃ(Java)ɺUnityήʔϜ։ൃ(C#) • Twi6er":"@RyotaMurohoshi • ߘઌ":"h6p:/ /qiita.com/RyotaMurohoshi
• ڵຯ":"Kotlin,"Groovy,"C#,"Unity,"SonyͷWearable"Device
AndroidΞϓϦΛJavaͰ։ൃ͍ͯͯ͠ɺ ʮͳΜͰ͜Μͳʹͳίʔυ͕ඞཁͳΜͩʂʯ ͬͯΠϥͬͱ͢Δ͜ͱ͋Γ·ͤΜ͔ʁ
ࢲ͋Γ·͢ʂ C#ΛۀͰ͍࢝ΊͨΓͨ͠Γɺ GroovyΛ΄Μͷͪΐͬͱษڧͨ͠Βɺ ʮͳΜͰJavaɺʓʓͰ͖ͳ͍ͷʔʂʯ ͬͯɺΠϥοͱͳΓ·ͨ͠
ͦ͜ͰKotlinͰ͢Ͷʂ
໌͔Βͪΐͬͱ KotlinͰAndroid͕ॻ͖ͨ͘ͳΔ(͔͠Εͳ͍ʁ) SAMมͱ֦ுؔ ͱͯ͠ࠓLT͠·͢ʂ
͍Βͬͱ͢Δͳίʔυ̍ button.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) {
Log.v(TAG, "clicked"); } }); ͲΜͳAndroidೖॻʹࡌ͍ͬͯΔɺΞΫςΟϏςΟͰΑ͘ΈΔίʔυ KotlinͰॻ͍ͨͭͱൺΔͱɺͳͷ͕Ұྎવʂ
Kotlinͩͱ͖ͬ͢Γ button.setOnClickListener { Log.v(TAG, "clicked") }
JavaɺKotlinͦΕͧΕͷΫϦοΫϦεφʔ Kotlin button.setOnClickListener { Log.v(TAG, "clicked") } Java button.setOnClickListener(new View.OnClickListener()
{ @Override public void onClick(View v) { Log.v(TAG, "clicked!"); } });
ߦ͕͘ͳͬͨ͜ͱͰͳ͘ɺ ʮͳ෦ॻ͘ඞཁ͕ͳ͘ ຊ࣭తͳ͜ͱ͚ͩॻ͚Α͘ͳͬͨʯ ͱ͍͏ͷ͕ϛι
JavaͷίʔυΛ͏ҰݟͯΈ·͠ΐ͏ button.setOnClickListener(new View.OnClickListener() { // newҎ߱ຊ࣭͡Όͳ͍ @Override // <- ຊ࣭͡Όͳ͍
public void onClick(View v) { // <- ຊ࣭͡Όͳ͍ Log.v(TAG, "clicked!"); } // <- ຊ࣭͡Όͳ͍ }); // <- ຊ࣭͡Όͳ͍ Javaຊ࣭͡Όͳ͍෦͕ଟ͍ɻKotlinຊ࣭ͷΈΛهड़͢Ε͍͍ Kotlinͳͥ͋Μͳهड़͕Ͱ͖Δͷ͔ʁ
Single'Abstract'Method'Conversions SAMม h"p:/ /blog.jetbrains.com/kotlin/2013/08/kotlin;m6;is;here/
SAM$ΠϯλʔϑΣʔε Ұͭͷ(Single))ந(Abstract))ϝιου(Method) ΛͭΠϯλʔϑΣʔε • Runnable):)void)run() • View.OnClickListener):)void)onClick(View)v) • Response.Listener<T>):)void)onResponse(T)response)) ͳͲɺଞʹͨ͘͞Μ
SAMม ؔϦςϥϧ!">!SAMΠϯλʔϑΣʔε!ͳม KotlinͰɺSAMΠϯλʔϑΣʔεΛҾʹͱΔϝιουͰɺ Ҿͷܕͱॱংͦͯ͠ฦܕ͕Ұக͢ΔؔϦςϥϧΛ͢ͱ ΠϯλʔϑΣʔεʹมͯ͘͠ΕΔ SAMΠϯλʔϑΣʔε͕ඞཁͳॴɺؔϦςϥϧͰεοΩϦʂ
SAMมͰ͖Δྫ button.setOnClickListener( { (v : View): Unit -> Log.v(TAG, "clicked")
}) button.setOnClickListener( { v -> Log.v(TAG, "clicked")}) button.setOnClickListener{ v -> Log.v(TAG, "clicked") } button.setOnClickListener{ Log.v(TAG, "clicked") } val listener : (View) -> Unit = {v -> Log.v(TAG, "clicked") } //or val listener : (View) -> Unit = { Log.v(TAG, "click") } //or val listener = { (v : View) : Unit -> Log.v(TAG, "clicked") } button.setOnClickListener(listener)
SAMมͰ͖ͳ͍ྫ // ԼهίϯύΠϧΤϥʔ // Type mismatch val listener : View.OnClickListener
= { (v : View) : Unit -> Log.v(TAG, "clicked") } // Լه࣮ߦ࣌Τϥʔ // java.lang.ClassCastException val listener = { (v : View) : Unit -> Log.v(TAG, "clicked") } as View.OnClickListener ҾʹؔϦςϥϧΛ͞ͳ͍ͱ͍͚ͳ͍
SAMมͰແବίʔυΛແͤ͘·͢Ͷʂ ͏Ұྫ VolleyͷStringRequest
VolleyͷStringRequest0Java൛ StringRequest request = new StringRequest( "https://www.google.co.jp/", new Response.Listener<String>() {
@Override public void onResponse(String response) { Toast.makeText(getApplicationContext(), response, Toast.LENGTH_LONG).show(); } }, new Response.ErrorListener() { @Override public void onErrorResponse(VolleyError volleyError) { Toast.makeText(getApplicationContext(), "onErrorResponse", Toast.LENGTH_LONG).show(); } } ); ແବͳ෦͕ଟ͘ɺॎʹ͍ɽɽɽ
VolleyͷStringRequest0Kotlin൛ val request = StringRequest( url = "https://www.google.co.jp/", listener =
{ response -> Toast.makeText(this, response, Toast.LENGTH_LONG).show() }, errorListener = { volleyError -> Toast.makeText(this, "onErrorResponse", Toast.LENGTH_LONG).show() } ); ܕύϥʔϝʔλ͕͋ΔΠϯλʔϑΣʔεSAMมՄೳ ໊લ͖ҾͰՄಡੑΞοϓ
ͪΐͬͱGroovyΈͯΈ·͠ΐ͏ GroovySAMม͕͑ΔΑ͏Ͱ͢ɻ button.setOnClickListener { v -> Toas.makeText(this, "click", Toast.LENGTH_LONG).show() }
Groovy&2.2͔Βasԋࢉࢠ͕͍Βͳ͘ͳͬͨͦ͏Ͱ͢ɻ h"p:/ /groovy.codehaus.org/Groovy+2.2+release+notes
ͪΐͬͱGroovyΈͯΈ·͠ΐ͏ SAMΠϯλʔϑΣʔε͚ͩͰͳ͘ɺෳϝιουΛ࣋ͭΠϯλʔϑΣʔε Map+Ϋϩʔδϟʔ+asԋࢉࢠͰ͜Μͳײ͡ʹʂ viewPager.setOnPageChangeListener ([ onPageScrollStateChanged: { state -> Log.v(TAG,
state) }, onPageScrolled : { position, positionOffset, positionOffsetPixels -> /*ུ*/ }, onPageSelected : { position -> Log.v(TAG, position) } ] as ViewPager.OnPageChangeListener) h"p:/ /groovy.codehaus.org/Groovy+way+to+implement+interfaces
࣮AndroidStudioͱIntelliJͩͱ Ұ͚ͭͩϝιουΛ࣮ͨ͠ಗ໊Ϋϥε͕͍͍ײ͡ʹʂ(SAMܕ) button.setOnClickListener((v) -> {Log.v(TAG, "clicked");}); IDE্Ͱ͍͍ײ͡ͰંΓ·Εͯ·͕͢ɺ githubͱ͔ͰίʔυϦϏϡʔ͢Δͱ͖ɺ ΄Β·Εͳ͍͠ɽɽɽ h"p:/
/qiita.com/RyotaMurohoshi/items/0ce799c747d91756131a
Ҏ্ SAMมͰͨ͠ɻ
͍Βͬͱ͢Δͳίʔυ̎ ImageView imageView = (ImageView)findViewById(R.id.image_view); ͲΜͳAndroidೖॻʹࡌ͍ͬͯΔɺΞΫςΟϏςΟͰΑ͘ΈΔίʔυ ͚ΕͲʮImageViewʯͬͯͳΜͰ2ճॻ͘ඞཁ͋ΔΜʁܕਪͯ͘͠Ε͍͍ͯ͡ΌΜʂ
ͱΓ͋͑ͣܧঝ͠·͢ʁ Ac#vityΛܧঝͨ͠ΫϥεBaseAc#vityʹͯɺ͜Μͳϝιουఆٛ͢Εɺ public <T extends View> T findById(int viewId) {
return (T)findViewById(viewId); } BaseAc'vityΛߋʹܧঝͨ͠ΫϥεͰɺ͜Μͳײ͡ͰΩϟετෆཁʹͳΓ·͢Ͷ ImageView imageView = findById(R.id.image_view);
͚Ͳܧঝͬͯ • ܧঝΉ͍ͣ • ʮܧঝ͕ڐ͞ΕΔͷখֶੜ·ͰͩΑͶʯɺͩͱɽɽɽ • Ac$vityͷαϒΫϥε͍͔ͭ͋͘Δ͚Ͳɺશ෦ʹߋʹαϒΫϥε ࡞ͬͯϝιουఆٛ͢Δʁ ͪΐͬͱͳ͍͔ͳɽɽɽ
ͯ͞Ͳ͏͠·͠ΐ͏ʁ • ͳهड़͕සൃͨ͠ΓɺΑ͘͏ॲཧ͕͋Δ • Ac$vityͱ͔ʹɺϝιουΛՃ͍ͨ͠ʂ • ͚Ͳܧঝͨ͘͠ͳ͍)or)Ͱ͖ͳ͍
Extension)Funcitons ֦ுؔ h"p:/ /confluence.jetbrains.com/display/Kotlin/Extension+func=ons
Extension)Funcitons(֦ுؔ)ͱ • ܧঝͤͣʹϝιουΛՃͰ͖Δ" • ܧঝېࢭͳΫϥεʹϝιουΛՃͰ͖Δ • privateͳϝϯόʹΞΫηεͰ͖ͳ͍ • ϝιουΛΦʔόʔϥΠυͰ͖ͳ͍
Extension)Func-onsͷྫ)ఆٛଆ extensions.ktʹͯ package com.mrstar.extensions import android.app.Activity import android.view.View fun <T
: View> Activity.findById (id : Int) : T = findViewById(id) as T
Extension)Func-onsͷྫ)ར༻ଆ package com.mrstar.android_with_kotlin // ུ import com.mrstar.extensions.findById // <-
public class MainActivity() : FragmentActivity() { // <- protected override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) val textView: ImageView = findById (R.id.image_view) // <- } }
• fun$ClassName.methodName(hoge$:$Hoge)$:$Fuga"Έ͍ͨͳײ͡Ͱ ϝιουΛఆٛ͠·͢ • ఆ֦ٛͨ͠ுϝιουΛimport͠·͢ • ͦ͏͢Δͱී௨ͷϝιουͷΑ͏ʹ͑·͢ • ͜ͷྫͩͱAc+vityͷαϒΫϥε͚ͩͰͳ͘ɺ FragmentAc+vityɺAc+onBarAc+vityɺଞͷαϒΫϥεͰ͑
·͢(ܧঝͰఆٛ͢ΔͳΒɺ֤Ϋϥεʹϝιουఆ͕ٛඞཁ)
Extension)Func-onsΛ͑ɽɽɽ • ܧঝ͠ͳͯ͘ϝιουΛՃͰ͖·͢Ͷ • ͨ͘͞ΜͷΫϥεʹϝιουΛՃ͠ͳ͍͍ͯ͘Ͱ͢Ͷ • ࣗ࡞ͷϝιουͰͳهड़ΛεοΩϦͰ͖·͢Ͷʂ
ͪΐͬͱC#ΈͯΈ·͠ΐ͏ C#ʹ֦ுؔͱಉ͡Α͏ͳ֦ுϝιου͕͋Γ·͢ɻ // ఆٛଆ public static class StringExtensions { public
static string Decorate(this string str, string symbol) { return string.Format("{0}{1}{2}", symbol, str, symbol); } } //ར༻ଆ string decoratedMessage = "Hello!".Decorate("===") ͜Μͳײ͡Ͱɺsta$cͳΫϥεʹsta$cͳϝιουͱ֦ͯ͠ுϝιουΛఆٛ͠·͢ɻ
ͪΐͬͱC#ΈͯΈ·͠ΐ͏ C# • JavaͷpackageΞΫηεͷΑ͏ͳɺϝϯόΛಉ໊͡લۭ͚ؒͩʹ ެ։͢Δͱ͍͏੍ݶ͕ͳ͍ • privateͰsta.cͳೖΕࢠͷΫϥε࡞ΕΔ • ͕↑ͳΫϥεͰ֦ுϝιουΛఆٛͰ͖ͳ͍ ͜ͷΫϥεʹ͚ͩɺ͜ͷ໊લۭؒͰ͚ͩ͑Δͱ͍͏֦ுϝιουΛఆٛͰ͖ͳ͍ʂ
ҰํKotlinͰ • packageʹͦͷ໊લۭؒͱͦͷαϒ໊લۭؒݶఆͰ • ΫϥεʹprivateΞΫηεϨϕϧͰ • ؔʹϩʔΧϧؔͱͯ͠ɺϩʔΧϧείʔϓͰ Kotlinͩͱ֦ுؔΛఆٛͰ͖Δʂ
Ҏ্ ֦ுؔͰͨ͠ɻ
࣭͋Γ·͔͢ʁ
͝ਗ਼ௌ͋Γ͕ͱ͏͍͟͝·ͨ͠ʂ ɹ SAMมʹ͍ͭͯ(Qiita) h"p:/ /qiita.com/RyotaMurohoshi