Fragment.requireArguments()导致android应用崩溃



我学习如何在Google codelabs上制作android应用程序。现在我在做这个(https://developer.android.com/codelabs/kotlin-android-training-start-external-activity#3)。

我遵循课程的任务。但是当我点击一个按钮导航到一个片段时,我的应用程序在android Studio的android虚拟设备上崩溃了。

代码在这里

/*
* Copyright 2018, The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
*     http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.example.android.navigation
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.databinding.DataBindingUtil
import androidx.fragment.app.Fragment
import androidx.navigation.findNavController
import com.example.android.navigation.databinding.FragmentGameBinding
class GameFragment : Fragment() {
data class Question(
val text: String,
val answers: List<String>)
// The first answer is the correct one.  We randomize the answers before showing the text.
// All questions must have four answers.  We'd want these to contain references to string
// resources so we could internationalize. (Or better yet, don't define the questions in code...)
private val questions: MutableList<Question> = mutableListOf(
Question(text = "What is Android Jetpack?",
answers = listOf("All of these", "Tools", "Documentation", "Libraries")),
Question(text = "What is the base class for layouts?",
answers = listOf("ViewGroup", "ViewSet", "ViewCollection", "ViewRoot")),
Question(text = "What layout do you use for complex screens?",
answers = listOf("ConstraintLayout", "GridLayout", "LinearLayout", "FrameLayout")),
Question(text = "What do you use to push structured data into a layout?",
answers = listOf("Data binding", "Data pushing", "Set text", "An OnClick method")),
Question(text = "What method do you use to inflate layouts in fragments?",
answers = listOf("onCreateView()", "onActivityCreated()", "onCreateLayout()", "onInflateLayout()")),
Question(text = "What's the build system for Android?",
answers = listOf("Gradle", "Graddle", "Grodle", "Groyle")),
Question(text = "Which class do you use to create a vector drawable?",
answers = listOf("VectorDrawable", "AndroidVectorDrawable", "DrawableVector", "AndroidVector")),
Question(text = "Which one of these is an Android navigation component?",
answers = listOf("NavController", "NavCentral", "NavMaster", "NavSwitcher")),
Question(text = "Which XML element lets you register an activity with the launcher activity?",
answers = listOf("intent-filter", "app-registry", "launcher-registry", "app-launcher")),
Question(text = "What do you use to mark a layout for data binding?",
answers = listOf("<layout>", "<binding>", "<data-binding>", "<dbinding>"))
)

lateinit var currentQuestion: Question
lateinit var answers: MutableList<String>
private var questionIndex = 0
private val numQuestions = Math.min((questions.size + 1) / 2, 3)
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?): View? {
// Inflate the layout for this fragment
val binding = DataBindingUtil.inflate<FragmentGameBinding>(
inflater, R.layout.fragment_game, container, false)
// Shuffles the questions and sets the question index to the first question.
randomizeQuestions()
// Bind this fragment class to the layout
binding.game = this
// Set the onClickListener for the submitButton
binding.submitButton.setOnClickListener @Suppress("UNUSED_ANONYMOUS_PARAMETER")
{ view: View ->
val checkedId = binding.questionRadioGroup.checkedRadioButtonId
// Do nothing if nothing is checked (id == -1)
if (-1 != checkedId) {
var answerIndex = 0
when (checkedId) {
R.id.secondAnswerRadioButton -> answerIndex = 1
R.id.thirdAnswerRadioButton -> answerIndex = 2
R.id.fourthAnswerRadioButton -> answerIndex = 3
}
// The first answer in the original question is always the correct one, so if our
// answer matches, we have the correct answer.
if (answers[answerIndex] == currentQuestion.answers[0]) {
questionIndex++
// Advance to the next question
if (questionIndex < numQuestions) {
currentQuestion = questions[questionIndex]
setQuestion()
binding.invalidateAll()
} else {
// We've won!  Navigate to the gameWonFragment.
view.findNavController()
.navigate(GameFragmentDirections.actionGameFragmentToGameWonFragment(numQuestions, questionIndex))
}
} else {
// Game over! A wrong answer sends us to the gameOverFragment.
view.findNavController().navigate(GameFragmentDirections.actionGameFragmentToGameOverFragment())
}
}
}
val requireArgs = requireArguments()
val args = GameWonFragmentArgs.fromBundle(requireArgs)
Toast.makeText(context, "NumCorrect: ${args.numCorrect}, NumQuestions: ${args.numQuestions}", Toast.LENGTH_LONG).show()
return binding.root
}
// randomize the questions and set the first question
private fun randomizeQuestions() {
questions.shuffle()
questionIndex = 0
setQuestion()
}
// Sets the question and randomizes the answers.  This only changes the data, not the UI.
// Calling invalidateAll on the FragmentGameBinding updates the data.
private fun setQuestion() {
currentQuestion = questions[questionIndex]
// randomize the answers into a copy of the array
answers = currentQuestion.answers.toMutableList()
// and shuffle them
answers.shuffle()
(activity as AppCompatActivity).supportActionBar?.title = getString(R.string.title_android_trivia_question, questionIndex + 1, numQuestions)
}
}

以上代码在这里发生致命异常。

val requireArgs = requireArguments()

堆栈跟踪在这里。

E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.android.navigation, PID: 5761
java.lang.IllegalStateException: Fragment GameFragment{11178cb} (b2ef6b6f-1bdd-4395-8590-7386740263fb) id=0x7f0800ff} does not have any arguments.
at androidx.fragment.app.Fragment.requireArguments(Fragment.java:679)
at com.example.android.navigation.GameFragment.onCreateView(GameFragment.kt:115)
at androidx.fragment.app.Fragment.performCreateView(Fragment.java:2698)
at androidx.fragment.app.FragmentStateManager.createView(FragmentStateManager.java:320)
at androidx.fragment.app.FragmentManager.moveToState(FragmentManager.java:1187)
at androidx.fragment.app.FragmentManager.addAddedFragments(FragmentManager.java:2224)
at androidx.fragment.app.FragmentManager.executeOpsTogether(FragmentManager.java:1997)
at androidx.fragment.app.FragmentManager.removeRedundantOperationsAndExecute(FragmentManager.java:1953)
at androidx.fragment.app.FragmentManager.execPendingActions(FragmentManager.java:1849)
at androidx.fragment.app.FragmentManager$4.run(FragmentManager.java:413)
at android.os.Handler.handleCallback(Handler.java:789)
at android.os.Handler.dispatchMessage(Handler.java:98)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6541)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:240)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:767)

我已经在Stackoverflow或Google上搜索过了,但我还没有找到。

不像你的GameWonFragment, GameFragment从来没有被分配任何参数。

没有参数的片段将导致requireArguments()在访问时崩溃。

相关内容

  • 没有找到相关文章