NullPointerException запуск Firebase Auth UI с активности Kotlin - PullRequest
0 голосов
/ 09 июля 2019

У меня было Java-приложение для Android с androidx навигацией (панель поддержки + ящик навигации), и оно запускало Firebase UI , чтобы войти в систему. Затем я решил перенести код Activity в Kotlin, используя конвертер AS и некоторая ручная работа по настройке навигации.

Несмотря на мои усилия, он все еще ломается с этим стеком

E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.gabrielcalero.familytree, PID: 20260
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.gabrielcalero.familytree/com.firebase.ui.auth.KickoffActivity}: java.lang.NullPointerException: Attempt to invoke super method 'void androidx.fragment.app.FragmentActivity.onPanelClosed(int, android.view.Menu)' on a null object reference
    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2793)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2864)
    at android.app.ActivityThread.-wrap12(ActivityThread.java)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1567)
    at android.os.Handler.dispatchMessage(Handler.java:102)
    at android.os.Looper.loop(Looper.java:156)
    at android.app.ActivityThread.main(ActivityThread.java:6524)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:941)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:831)
 Caused by: java.lang.NullPointerException: Attempt to invoke super method 'void androidx.fragment.app.FragmentActivity.onPanelClosed(int, android.view.Menu)' on a null object reference
    at androidx.appcompat.app.AppCompatActivity.onPanelClosed(AppCompatActivity.java:505)
    at androidx.lifecycle.LiveData.observe(LiveData.java:172)
    at com.firebase.ui.auth.KickoffActivity.onCreate(KickoffActivity.java:35)
    at android.app.Activity.performCreate(Activity.java:6910)
    at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1123)
    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2746)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2864) 
    at android.app.ActivityThread.-wrap12(ActivityThread.java) 
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1567) 
    at android.os.Handler.dispatchMessage(Handler.java:102) 
    at android.os.Looper.loop(Looper.java:156) 
    at android.app.ActivityThread.main(ActivityThread.java:6524) 
    at java.lang.reflect.Method.invoke(Native Method) 
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:941) 
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:831) 

Странная вещь в том, что после стека исключение onPanelClosed, что означает, что super равно нулю. Как это возможно?

@Override
public void onPanelClosed(int featureId, Menu menu) {
    super.onPanelClosed(featureId, menu);
}

ОБНОВЛЕНИЕ: вот код активности

package com.gabrielcalero.familytree.ui
import android.content.Intent
import android.os.Bundle
import android.view.MenuItem
import android.widget.ImageView
import android.widget.TextView
import androidx.appcompat.app.AppCompatActivity
import androidx.navigation.NavController
import androidx.navigation.findNavController
import androidx.navigation.ui.AppBarConfiguration
import androidx.navigation.ui.setupWithNavController
import com.firebase.ui.auth.AuthUI
import com.gabrielcalero.familytree.R
import com.gabrielcalero.familytree.ServiceLocator
import com.gabrielcalero.familytree.entity.Constants
import com.gabrielcalero.familytree.ui.picasso.CropCircleTransformation
import com.google.android.material.navigation.NavigationView
import com.google.firebase.auth.FirebaseAuth
import com.squareup.picasso.Picasso
import kotlinx.android.synthetic.main.activity_main.*
import java.util.*

class MainActivity : AppCompatActivity(), NavigationView.OnNavigationItemSelectedListener, FirebaseAuth.AuthStateListener {

private var mUserPicture: ImageView? = null
private var mUserNameTextView: TextView? = null
private var mAuth: FirebaseAuth? = null

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

    mUserPicture = navView.getHeaderView(0).findViewById(R.id.picture)
    mUserNameTextView = navView.getHeaderView(0).findViewById(R.id.display_name)

    mAuth = FirebaseAuth.getInstance().apply { addAuthStateListener { this } }

    launchSignInUI()
}

override fun onStart() {
    super.onStart()
    updateLoggedInUser()
}

private fun updateLoggedInUser() {
    val currentUser = mAuth!!.currentUser
    if (currentUser == null) {
        mUserPicture!!.setImageResource(R.drawable.anonymous)
        mUserNameTextView!!.text = getString(R.string.not_logged_in)
        navView.menu.findItem(R.id.signout).isVisible = false
        navView.menu.findItem(R.id.signin).isVisible = true
        navView.menu.findItem(R.id.personFragment).isEnabled = false
        navView.menu.findItem(R.id.peopleListFragment).isEnabled = false
    } else {
        // show signout
        mUserNameTextView!!.text = currentUser.displayName
        Picasso.with(this)
                .load(currentUser.photoUrl)
                .placeholder(R.drawable.anonymous)
                .error(R.drawable.anonymous)
                .transform(CropCircleTransformation())
                .resize(resources.getDimension(R.dimen.profile_picture_width).toInt(),
                        resources.getDimension(R.dimen.profile_picture_height).toInt())
                .into(mUserPicture)
        navView.menu.findItem(R.id.signout).isVisible = true
        navView.menu.findItem(R.id.signin).isVisible = false
        navView.menu.findItem(R.id.personFragment).isEnabled = true
        navView.menu.findItem(R.id.peopleListFragment).isEnabled = true
    }
}

private fun setupNavigation() {
    setSupportActionBar(toolbar)

    supportActionBar!!.setDisplayShowHomeEnabled(true)
    supportActionBar!!.setDisplayHomeAsUpEnabled(true)

    val navController : NavController = findNavController(R.id.nav_host_fragment)
    val appBarConfiguration = AppBarConfiguration(navController.graph, drawerLayout)
    toolbar.setupWithNavController(navController, appBarConfiguration)
    navView.setupWithNavController(navController)
    navView.setNavigationItemSelectedListener(this)
}

private fun launchSignInUI() {
    // Choose authentication providers
    val providers = Arrays.asList(
            AuthUI.IdpConfig.EmailBuilder().build(),
            AuthUI.IdpConfig.GoogleBuilder().build())

    // Create and launch sign-in intent
    startActivityForResult(
            AuthUI.getInstance()
                    .createSignInIntentBuilder()
                    .setAvailableProviders(providers)
                    .setLogo(R.drawable.logo)
                    .build(),
            Constants.REQUEST_CODE_SIGN_IN)
}


override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
    super.onActivityResult(requestCode, resultCode, data)
    //updateLoggedInUser()
}

override fun onNavigationItemSelected(menuItem: MenuItem): Boolean {
    val navController = findNavController(R.id.nav_host_fragment)
    when (menuItem.itemId) {
        R.id.signout -> signout()
        R.id.signin -> launchSignInUI()
        R.id.personFragment -> {
            navController.popBackStack(R.id.peopleListFragment, false)
            navController.navigate(R.id.personFragment)
            drawerLayout?.closeDrawers()
            return true
        }
        else -> {
            navController.popBackStack(R.id.peopleListFragment, false)
            drawerLayout?.closeDrawers()
            return true
        }
    }
    drawerLayout?.closeDrawers()
    return true
}

private fun signout() {
    val navController = findNavController(R.id.nav_host_fragment)

    AuthUI.getInstance()
            .signOut(this)
            .addOnCompleteListener {
                navView.menu.findItem(R.id.signout).isVisible = false
                navController.popBackStack(R.id.peopleListFragment, false)
            }

}

override fun onAuthStateChanged(firebaseAuth: FirebaseAuth) {
    ServiceLocator.getRepository(application).setCurrentUserId(firebaseAuth.uid)
    updateLoggedInUser()
}

}

1 Ответ

0 голосов
/ 10 июля 2019

Проблема была в преобразовании Java в Kotlin. В этом случае я исправил это, удалив неиспользованную зависимость

implementation "androidx.core:core-ktx:+"

Думаю, когда я закончу преобразование всех классов Java, мне придется заменить все зависимости androidx на их -ktx-аналог

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...