Kotlin Android memulai Aktivitas baru


104

Saya ingin memulai aktivitas lain di Android tetapi saya mendapatkan kesalahan ini:

Harap tentukan permintaan konstruktor; classifier 'Page2' tidak memiliki objek pendamping

setelah membuat instance Intentkelas. Apa yang harus saya lakukan untuk memperbaiki kesalahan tersebut? Kode saya:

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
    }

    fun buTestUpdateText2 (view: View) {
        val changePage = Intent(this, Page2) 
        // Error: "Please specify constructor invocation; 
        // classifier 'Page2' does not have a companion object"

        startActivity(changePage)
    }

}

@BakaWaii halaman itu tidak ada lagi.
Scre

Jawaban:


179

Untuk memulai Activitydi java yang kami tulis Intent(this, Page2.class), pada dasarnya Anda harus mendefinisikan Contextdi parameter pertama dan kelas tujuan di parameter kedua. Menurut Intentmetode dalam kode sumber -

 public Intent(Context packageContext, Class<?> cls)

Seperti yang Anda lihat, kita harus memasukkan Class<?>tipe dalam parameter kedua.

Dengan menulis Intent(this, Page2)kami tidak pernah menentukan kami akan lulus kelas, kami mencoba untuk mengirimkan classjenis yang tidak dapat diterima.

Gunakan ::class.javayang merupakan alternatif .classdi kotlin. Gunakan kode di bawah ini untuk memulaiActivity

Intent(this, Page2::class.java)

Contoh -

val intent = Intent(this, NextActivity::class.java)
// To pass any data to next activity
intent.putExtra("keyIdentifier", value)
// start your next activity
startActivity(intent)

4
Tahu mengapa mereka mengubahnya menjadi ::class.javabukan .class? Pendekatan Kotlin sangat rumit, dibandingkan dengan Java.
Mr-IDE

3
@ Mr-IDE classmengembalikan Kotlin KClass, tetapi Android mengharapkan Java Class<...>, karena itulah .javapropertinya.
kirbyfan64sos

34

Cukup Anda dapat memulai Activitydi KOTLINdengan menggunakan metode sederhana ini,

val intent = Intent(this, SecondActivity::class.java)
intent.putExtra("key", value)
startActivity(intent)

1
Anda tidak perlu menggunakan metode putExtra untuk memulai aktivitas baru.
ShadeToD

@ShadeToD Ya! Tidak perlu menggunakan putExtrametode. Saya baru saja menambahkannya untuk nilai kelulusan saat memulai yang baruActivity
Gowtham Subramaniam

31

Untuk memulai Aktivitas baru,

startActivity(Intent(this@CurrentClassName,RequiredClassName::class.java)

Jadi ubah kode Anda menjadi:

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
    }

    fun buTestUpdateText2 (view: View) {
        startActivity(Intent(this@MainActivity,ClassName::class.java))

        // Also like this 

        val intent = Intent(this@MainActivity,ClassName::class.java)
        startActivity(intent)
    }

2
ini @ Aktivitas sama dengan Java's Activity.this :)
leoelstin

12

Anda biasanya dapat menyederhanakan spesifikasi parameter BlahActivity::class.javadengan menentukan fungsi generik yang direifikasi sebaris.

inline fun <reified T: Activity> Context.createIntent() =
    Intent(this, T::class.java)

Karena itu memungkinkan Anda melakukannya

startActivity(createIntent<Page2>()) 

Atau bahkan lebih sederhana

inline fun <reified T: Activity> Activity.startActivity() {
    startActivity(createIntent<T>()) 
} 

Jadi sekarang

startActivity<Page2>() 

Sebagai pemula di kotlin, bagaimana Anda akan menanam nomor variabel (atau tidak ada) dari putExtra () dengan itu?
Scre

1
Anda dapat mengatur inline fun <reified T: Activity> Context.createIntent(vararg extras: Pair<String, Any?>) = Intent(this, T::class.java).apply { putExtras(bundleOf(*extras)) }alih - alih apa yang saya katakan dan itu akan berfungsi (dengan asumsi Anda memiliki bundleOfdari android-ktx atau anko)
EpicPandaForce

10

Anda harus memberikan argumen kedua untuk tipe kelas. Anda juga bisa membuatnya sedikit lebih rapi seperti di bawah ini.

startActivity(Intent(this, Page2::class.java).apply {
    putExtra("extra_1", value1)
    putExtra("extra_2", value2)
    putExtra("extra_3", value3)
})

7

Coba ini

val intent = Intent(this, Page2::class.java)
startActivity(intent)

6

Ini adalah aktivitas utama saya di mana saya mengambil nama pengguna dan kata sandi dari edit teks dan pengaturan ke maksud

class MainActivity : AppCompatActivity() {
val userName = null
val password = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
button.setOnClickListener {
    val intent = Intent(this@MainActivity,SecondActivity::class.java);
    var userName = username.text.toString()
    var password = password_field.text.toString()
    intent.putExtra("Username", userName)
    intent.putExtra("Password", password)
    startActivity(intent);
 }
}

Ini adalah aktivitas kedua saya di mana saya harus menerima nilai dari aktivitas utama

override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_second)
var strUser: String = intent.getStringExtra("Username")
var strPassword: String = intent.getStringExtra("Password")
user_name.setText("Seelan")
passwor_print.setText("Seelan")
}

4

Ini karena Page2kelas Anda tidak memiliki objek pendamping yang mirip dengan staticdi Java sehingga untuk menggunakan kelas Anda. Untuk melewatkan kelas Anda sebagai argumen Intent, Anda harus melakukan sesuatu seperti ini

val changePage = Intent(this, Page2::class.java)

4

Dari aktivitas ke aktivitas

val intent = Intent(this, YourActivity::class.java)
startActivity(intent)

Dari fragmen ke aktivitas

val intent = Intent(activity, YourActivity::class.java)
startActivity(intent)

4

Nah, menurut saya 2 cara ini menjadi yang paling sederhana dari semua hasil:

Cara # 1:

accoun_btn.setOnClickListener {
            startActivity(Intent(this@MainActivity, SecondActivity::class.java))
        }

Cara # 2: (Dengan cara yang umum)

    accoun_btn.setOnClickListener {
        startActivity<SecondActivity>(this)
    }

    private inline fun <reified T> startActivity(context: Context) {
            startActivity(Intent(context, T::class.java))
        }

Sampel


1
val intentAct: Intent = Intent(this@YourCurrentActivity, TagentActivity::class.java)
startActivity(intentAct)

1

Saya memiliki masalah serupa, saya mulai menulis aplikasi saya di Kotlin, setelah saya menulis ulang salah satu aktivitas saya, saya ingin melihat apakah ada masalah, masalahnya adalah saya tidak yakin bagaimana cara mengirim maksud dari file java ke kotlin mengajukan.

Dalam hal ini saya membuat fungsi statis di kotlin (objek pendamping), fungsi ini mendapatkan konteks (dari aktivitas saat ini) dan mengembalikan maksud baru saat menggunakan konteks saat ini (konteks "java") saat menggunakan kelas kotlin (" :: class.java ").

Ini kode saya:

 //this code will be in the kotlin activity - SearchActivity
 companion object {

    fun newIntent(context: Context): Intent {
        return Intent(context, SearchActivity::class.java)
    }
}

    //this is how you call SearchActivity from MainActivity.java
Intent searchIntent = SearchActivity.Companion.newIntent(this);
startActivity(searchIntent);

Jika Anda menambahkan @JvmStaticke newIntentmetode Anda, Anda dapat memanggilnya dari java tanpa Companionbagian.
Wirling

0

Detail

  • Android Studio 3.1.4
  • Versi Kotlin: 1.2.60

Langkah 1. Aplikasi ()

Dapatkan tautan ke konteks aplikasi Anda

class MY_APPLICATION_NAME: Application() {

    companion object {
        private lateinit var instance: MY_APPLICATION_NAME
        fun getAppContext(): Context = instance.applicationContext
    }

    override fun onCreate() {
        instance = this
        super.onCreate()
    }

}

Langkah 2. Tambahkan objek Router

object Router {
    inline fun <reified T: Activity> start() {
         val context =  MY_APPLICATION_NAME.getAppContext()
         val intent = Intent(context, T::class.java)
         context.startActivity(intent)
    }
}

Pemakaian

// You can start activity from any class: form Application, from any activity, from any fragment and other  
Router.start<ANY_ACTIVITY_CLASS>()

0

Ingatlah untuk menambahkan aktivitas yang ingin Anda tampilkan, ke Anda AndroidManifest.xmljuga :-) Itu adalah masalah saya.


0

Bagaimana dengan ini untuk mempertimbangkan enkapsulasi?

Sebagai contoh:


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_contents)

        val title = intent.getStringExtra(EXTRA_TITLE) ?: EXTRA_TITLE_DEFAULT

        supportFragmentManager.beginTransaction()
            .add(R.id.frame_layout_fragment, ContentsFragment.newInstance())
            .commit()
    }

    // Omit...

    companion object {

        private const val EXTRA_TITLE = "extra_title"
        private const val EXTRA_TITLE_DEFAULT = "No title"

        fun newIntent(context: Context, title: String): Intent {
            val intent = Intent(context, ContentsActivity::class.java)
            intent.putExtra(EXTRA_TITLE, title)
            return intent
        }
    }

0

Anda dapat menggunakan file Kotlin dan Java dalam aplikasi Anda.

Untuk beralih di antara dua file, pastikan Anda memberinya <action android: name = "" yang unik di AndroidManifest.xml, seperti ini:

            <activity android:name=".MainActivityKotlin">
                <intent-filter>
                    <action android:name="com.genechuang.basicfirebaseproject.KotlinActivity"/>
                    <category android:name="android.intent.category.DEFAULT" />
                    <action android:name="android.intent.action.MAIN" />
                    <category android:name="android.intent.category.LAUNCHER" />
                </intent-filter>
            </activity>
            <activity
                android:name="com.genechuang.basicfirebaseproject.MainActivityJava"
                android:label="MainActivityJava" >
                <intent-filter>
                    <action android:name="com.genechuang.basicfirebaseproject.JavaActivity" />
                    <category android:name="android.intent.category.DEFAULT" />
                </intent-filter>
            </activity>

Kemudian di MainActivity.kt (file Kotlin) Anda, untuk memulai Aktivitas yang ditulis di Java, lakukan ini:

       val intent = Intent("com.genechuang.basicfirebaseproject.JavaActivity")
        startActivity(intent)

Di MainActivityJava.java (file Java) Anda, untuk memulai Aktivitas yang ditulis di Kotlin, lakukan ini:

       Intent mIntent = new Intent("com.genechuang.basicfirebaseproject.KotlinActivity");
        startActivity(mIntent);

0

cara sederhana lain untuk menavigasi ke aktivitas lain adalah

Intent(this, CodeActivity::class.java).apply {
                    startActivity(this)
                }

1
Mohon pertimbangkan untuk menjelaskan kode Anda dan bagaimana itu akan membantu, sehingga orang lain dapat memperoleh manfaat dari ini.
Amit Verma
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.