Начать действие с фрагмента

91

У меня есть 2 фрагмента с кнопкой на обоих фрагментах. Когда я нажимаю кнопку, я хочу начать новое действие. Но я не могу заставить его работать.

Ошибка, которую я получаю: ОШИБКА здесь: Несоответствие типов: невозможно преобразовать из mFragmentFavorite в Fragment

Что я делаю не так?

MyFragmentPagerAdapter

import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;

public class MyFragmentPagerAdapter extends FragmentPagerAdapter{

    final int PAGE_COUNT = 3;

    /** Constructor of the class */
    public MyFragmentPagerAdapter(FragmentManager fm) {
        super(fm);
    }

    /** This method will be invoked when a page is requested to create */
    @Override
    public Fragment getItem(int arg0) {

        switch(arg0){

        case 0:
            return new FavoriteActivity();
                    //ERROR: Type mismatch: cannot convert from FavoriteActivity to Fragment


        case 1:
            return new SettingsActivity();


        default:
            return null;

        }       
    }

    /** Returns the number of pages */
    @Override
    public int getCount() {
        return PAGE_COUNT;
    }
}

Любимое занятие

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.Button;

public class FavoriteActivity extends Activity{

    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View v = inflater.inflate(R.layout.main_favorite, container, false);


        OnClickListener listnr=new OnClickListener() {
            @Override
            public void onClick(View v) {
                  Intent i= new Intent("aFavorite");
                  startActivity(i);
            }
        };

          Button btn =(Button) v.findViewById(R.id.mainFavorite);
          btn.setOnClickListener(listnr);

          return v;
    }
}

Если FavoriteActivity расширяет фрагменты, ошибка исчезла, но затем я получаю сообщение об ошибке, findViewById(R.id.mainFavorite);и ошибка

Метод findViewById (int) не определен для типа FavoriteActivity

РЕДАКТИРОВАТЬ:

Когда я нажимаю кнопку во фрагменте, чтобы начать действие, приложение вылетает, это мой логарифм

03-18 16:01:23.985: E/AndroidRuntime(1985): FATAL EXCEPTION: main
03-18 16:01:23.985: E/AndroidRuntime(1985): android.content.ActivityNotFoundException: No Activity found to handle Intent { act=FavoriteActivityList }
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.app.Instrumentation.checkStartActivityResult(Instrumentation.java:1569)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.app.Instrumentation.execStartActivity(Instrumentation.java:1420)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.app.Activity.startActivityForResult(Activity.java:3446)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.app.Activity.startActivityForResult(Activity.java:3407)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.support.v4.app.FragmentActivity.startActivityFromFragment(FragmentActivity.java:826)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.support.v4.app.Fragment.startActivity(Fragment.java:838)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at com.example.spui.FavoriteActivity$1.onClick(FavoriteActivity.java:24)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.view.View.performClick(View.java:4211)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.view.View$PerformClick.run(View.java:17267)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.os.Handler.handleCallback(Handler.java:615)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.os.Handler.dispatchMessage(Handler.java:92)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.os.Looper.loop(Looper.java:137)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at android.app.ActivityThread.main(ActivityThread.java:4898)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at java.lang.reflect.Method.invokeNative(Native Method)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at java.lang.reflect.Method.invoke(Method.java:511)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1006)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:773)
03-18 16:01:23.985: E/AndroidRuntime(1985):     at dalvik.system.NativeStart.main(Native Method)
mXX
источник
3
Возможно, вам стоит не расширять FragmentActivity, а Fragment?
промежуток времени
1
Ну, например, вы не используете Fragments. По крайней мере, нет в опубликованном вами коде.
adneal

Ответы:

247

mFragmentFavoriteв вашем коде - это FragmentActivityне то же самое, что Fragment. Вот почему вы получаете несоответствие типов. Кроме того, вы никогда не должны обращаться newк ним, так Activityкак это не лучший способ начать.

Если вы хотите запустить новый экземпляр mFragmentFavorite, вы можете сделать это через файл Intent.

От Fragment:

Intent intent = new Intent(getActivity(), mFragmentFavorite.class);
startActivity(intent);

Из Activity

Intent intent = new Intent(this, mFragmentFavorite.class);
startActivity(intent);

Если вы хотите , чтобы начать aFavoriteвместо , mFragmentFavoriteто вам нужно только изменить их имена в созданном Intent.

Кроме того, я рекомендую изменить имена классов, чтобы они были более точными. Называть что-то mFragmentFavoriteнеправильно, потому что это вообще не a Fragment. Кроме того, объявления классов в Java обычно начинаются с заглавной буквы. Было бы хорошо, если бы ваш класс FavoriteActivityбыл более точным и соответствовал языковым соглашениям. Вам также потребуется переименовать файл в FavoriteActivity.java, если вы решите это сделать, поскольку Java требует, чтобы имена классов соответствовали имени файла.

ОБНОВИТЬ

Кроме того, похоже, что вы на самом деле хотели mFragmentFavoriteбыть a Fragmentвместо a в FragmentActivityзависимости от вашего использования onCreateView. Если вы хотите mFragmentFavoriteбыть, Fragmentизмените следующую строку кода:

public class mFragmentFavorite extends FragmentActivity{

Вместо этого сделайте следующее:

public class mFragmentFavorite extends Fragment {
Майкл Сели
источник
Ладно, обновлю код в первом посте. Но я не совсем понимаю mContextReference. Я
обновлю
Это пример ссылки на файл Fragmentили файл Activity. Если вы используете код внутри одного из этих классов, вы можете просто заменить его mContextReferenceна getActivity()for Fragmentили thisfor Activityв первой и thisвторой строке. Я обновлю ответ, чтобы он был более ясным.
Майкл Сели,
Хорошо, я обновил вопрос, добавив лучшие имена и совет, который вы мне дали. Сейчас я постараюсь реализовать ваше предложение, чтобы заставить его работать. Спасибо за помощь
mXX
Да, я снова изменил его на Fragment, но я получаю сообщение об ошибке на btn, чтобы найти идентификатор «Метод findViewById (int) не определен для типа FavoriteActivity»
mXX
2
Если вы сделаете это, Fragmentто измените findViewByIdна v.findViewById. Здесь нетfindViewById функции, Fragmentпоэтому вы должны getViewсначала позвонить, а затем позвонить findViewByIdпо этому поводу. Однако в вашем случае у вас уже есть свое представление, onCreateViewи это будет ваша переменная v.
Майкл Сели
21

Вы должны использовать getActivity()для запуска действий из фрагментов

Intent intent = new Intent(getActivity(), mFragmentFavorite.class);
startActivity(intent);

Кроме того, вы должны называть классы заглавными буквами: MFragmentActivityвместо mFragmentActivity.

лжец
источник
4

Если вы используете getActivity (), вы должны убедиться, что вызывающая активность уже добавлена . Если в этом случае активность не была добавлена, вы можете получить null при вызове getActivity ()

в таких случаях getContext () безопасно

тогда код для запуска активности будет немного изменен, например,

Intent intent = new Intent(getContext(), mFragmentFavorite.class);
startActivity(intent);

Activity, Service и Application расширяют класс ContextWrapper, поэтому вы можете использовать это или getContext () или getApplicationContext () вместо первого аргумента.

Джаякришнан
источник
«Если вы используете getActivity (), вы должны убедиться, что вызывающая активность уже добавлена». Что эта строка означает для новичка?
Палак Джайн
@PalakJain Это означает, что состояние активности (от активного до уничтоженного) продолжает меняться в зависимости от x причин. Действие должно быть в активном состоянии, когда вы что-либо с ним выполняете. Действие находится в активном состоянии, если его время жизни находится между onResume и onPause.
Джаякришнан
Что ж, в этом есть смысл. Благодарность!
Palak Jain
3

Я использую это в своем фрагменте.

Button btn1 = (Button) thisLayout
            .findViewById(R.id.btnDb1);

    btn1.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            // TODO Auto-generated method stub
            Intent intent = new Intent(getActivity(), otherActivity.class);
            ((MainActivity) getActivity()).startActivity(intent);

        }
    });

    return thisLayout;
}
Сара Закизаде
источник
0

Возможно, вам придется заменить getActivity () на MainActivity.this для тех, у кого есть проблемы с этим.

ADL
источник
0

Начать новое действие из фрагмента:

Intent intent = new Intent(getActivity(), TargetActivity.class);
startActivity(intent);

Начать новое занятие из занятия:

Intent intent = new Intent(this, TargetActivity.class);
startActivity(intent);
Абхай Бхусари
источник
0

с Kotlin я выполняю этот код:

requireContext().startActivity<YourTargetActivity>()

Александр Колесник
источник
Когда я пробую этот код, я получаю:None of the following functions can be called with the arguments supplied. startActivity(Intent!) defined in android.content.Context startActivity(Intent!, Bundle?) defined in android.content.Context
Тим
@Tim Вам, вероятно, понадобится Android KTX для работы кода.
Эдрик