从片段调用活动方法

     2023-02-19     119

关键词:

【中文标题】从片段调用活动方法【英文标题】:Call an activity method from a fragment 【发布时间】:2012-09-21 12:05:18 【问题描述】:

尝试从片段调用我的活动中的方法。我希望片段提供方法数据并在方法返回时获取数据。我想实现类似于调用静态方法,但不使用静态,因为它会在活动中产生问题。

对 Fragment 不熟悉,所以我需要一个简单的教学解释!

谢谢!

【问题讨论】:

【参考方案1】:

从片段到活动:

((YourActivityClassName)getActivity()).yourPublicMethod();

从活动到片段:

FragmentManager fm = getSupportFragmentManager();

//if you added fragment via layout xml
YourFragmentClass fragment = (YourFragmentClass)fm.findFragmentById(R.id.your_fragment_id);
fragment.yourPublicMethod();

如果您通过代码添加片段并在添加片段时使用tag 字符串,请改用findFragmentByTag

YourFragmentClass fragment = (YourFragmentClass)fm.findFragmentByTag("yourTag");

【讨论】:

要小心,因为如果演员表不起作用会发生意想不到的事情......:S 为了避免演员阵容问题,请使用:Activity act = getActivity(); if (act instanceof YourActivityClassName) ((YourActivityClassName) act).yourPublicMethod(); 投射 Activity 是糟糕的设计和不安全的。 Fragment 不限于特定的 Activity。 Fragments 意味着可以在任何 Activity 中重复使用和设置。如果我有 5 个活动使用相同的片段怎么办? Marco 的答案是正确的,也是片段间和 Activity-Fragment 通信的良好实践。 @Kay 不一定。片段可以用作任何更大活动的“片段”。例如,创建响应式 UI。我很少使用相同的片段并将其附加到不同的活动主机。【参考方案2】:

您可能应该尝试将片段与活动分离,以防您想在其他地方使用它。您可以通过创建您的活动实现的接口来做到这一点。

所以你会定义一个如下所示的接口:

例如,假设您想给活动一个字符串并让它返回一个整数:

public interface MyStringListener
    public Integer computeSomething(String myString);

这可以在片段或单独的文件中定义。

然后您将让您的活动实现该接口。

public class MyActivity extends FragmentActivity implements MyStringListener

  @Override
  public Integer computeSomething(String myString)
   /** Do something with the string and return your Integer instead of 0 **/ 
   return 0;
  


然后在您的片段中,您将有一个 MyStringListener 变量,您将在片段的 onAttach(Activity activity) 方法中设置侦听器。

public class MyFragment 

        private MyStringListener listener;

        @Override
        public void onAttach(Context context) 
            super.onAttach(context);
            try 
                listener = (MyStringListener) context;
             catch (ClassCastException castException) 
                /** The activity does not implement the listener. */
            
        

    

编辑(17.12.2015):onAttach(Activity activity) is deprecated, use onAttach(Context context) instead, it works as intended

第一个答案肯定有效,但它将您当前的片段与主机活动结合起来。如果您想在另一个活动中使用它,将片段与主机活动分离,这是一种很好的做法。

【讨论】:

对于其他人来说,虽然公认的答案显然确实有效,但从设计的角度来看,这是更好、更安全的方法。 这个答案在代码设计方面要好得多。如果 Activity 被错误地投射,它也不会导致崩溃 +1 但我不会在 onAttach 中使用 try-catch。让它失败。如果监听器是可选的(也就是说,失败是不合适的),在片段中添加一个 set/addListener 方法。 对面通讯请见:developer.android.com/training/basics/fragments/…。使用片段的接口(这也是执行片段->活动通信的安全方法,如上所述),如果您想根据片段->活动采取行动,您也可以从您的活动中调用片段中的方法通讯。 我认为 MyFragment 覆盖 onDetach 并将侦听器设置为 null 以避免内存泄漏也很重要。【参考方案3】:

对于 Kotlin 开发人员

(activity as YourActivityClassName).methodName()

对于 Java 开发人员

((YourActivityClassName) getActivity()).methodName();

【讨论】:

如果我们运行这段代码,它会在 kotlin 中出错。还有其他方法吗? 当我运行它时。我得到 ActivityClass 的空值,我认为这不是在 kotlin 中执行此操作的正确方法,即使没有错误。或者可能是一个错误? @JakeGarbo 正确的方式,否则 12 人没有投票给它。第二件事有时 getActivity() 返回 null 检查那些关于 SO 的问题。【参考方案4】:

在我了解更多片段的工作原理后更新。每个片段都属于一个父活动。所以只需使用:

getActivity().whatever

从片段内部。这是一个更好的答案,因为您避免了多余的演员表。如果您无法使用此解决方案避免演员阵容,请使用以下解决方案。

============

你要做的就是投射到外部活动

((MainActivity) getActivity()).Method();

创建一个新实例会混淆 android 框架并且它无法识别它。 另见:

https://***.com/a/12014834/1984636

https://***.com/a/2042829/1984636

【讨论】:

【参考方案5】:

虽然我完全喜欢 Marco 的回答,但我认为公平地指出,您也可以使用基于发布/订阅的框架来实现相同的结果,例如,如果您使用事件总线,您可以执行以下操作

片段:

EventBus.getDefault().post(new DoSomeActionEvent()); 

活动:

 @Subscribe
onSomeActionEventRecieved(DoSomeActionEvent doSomeActionEvent)
//Do something


【讨论】:

【参考方案6】:

在 kotlin 中,您可以从片段中调用活动方法,如下所示:

var mainActivity: MainActivity = activity as MainActivity
        mainActivity.showToast() //Calling show toast method of activity

【讨论】:

【参考方案7】:

感谢@BIJAY_JHA 和@Manaus。我使用 Kotlin 版本来调用我的 signIn() 方法,该方法位于 Activity 中并且我从 Fragment 调用。我在 Android 中使用导航架构,因此侦听器接口模式不在片段中:

 (activity as MainActivity).signIn() 

【讨论】:

【参考方案8】:

我是这样做的:

首先制作界面

interface NavigationInterface 
    fun closeActivity()

接下来确保活动实现接口并覆盖接口方法

class NotesActivity : AppCompatActivity(), NavigationInterface 

    override fun onCreate(savedInstanceState: Bundle?) 
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_notes)
        setSupportActionBar(findViewById(R.id.toolbar))
    

    override fun closeActivity() 
        this.finish()
    

然后确保在片段中创建接口监听器

private lateinit var navigationInterface: NavigationInterface

override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
): View? 
    //establish interface communication
    activity?.let 
        instantiateNavigationInterface(it)
    
    // Inflate the layout for this fragment
    return inflater.inflate(R.layout.fragment_notes_info, container, false)


private fun instantiateNavigationInterface(context: FragmentActivity) 
    navigationInterface = context as NavigationInterface

然后你可以像这样拨打电话:

view.findViewById<Button>(R.id.button_second).setOnClickListener 
    navigationInterface.closeActivity()

【讨论】:

【参考方案9】:

要通过片段访问在 Activity 中声明的函数,请使用接口,如 marco 的回答所示。

如果您没有标签或 id,则可以通过您的 Activity 访问在 Fragment 中声明的函数

private void setupViewPager(ViewPager viewPager) 
    //fragmentOne,fragmentTwo and fragmentThree are all global variables
    fragmentOne= new FragmentOne();
    fragmentTwo= new FragmentTwo();
    fragmentThree = new FragmentThree();

    viewPagerAdapteradapter = new ViewPagerAdapter(getSupportFragmentManager());
    viewPagerAdapteradapter.addFragment(fragmentOne, "Frag1");
    viewPagerAdapteradapter.addFragment(fragmentTwo, "Frag2");
    viewPagerAdapteradapter.addFragment(fragmentThree, "Frag3");

    //viewPager has to be instantiated when you create the activity:
    //ViewPager viewPager = (ViewPager)findViewById(R.id.pager);
    //setupViewPager(viewPager);
    //Where R.id.pager is the id of the viewPager defined in your activity's xml page.

    viewPager.setAdapter(viewPagerAdapteradapter);


    //frag1 and frag2 are also global variables
    frag1 = (FragmentOne)viewPagerAdapteradapter.mFragmentList.get(0);
    frag2 = (FragmentTwo)viewPagerAdapteradapter.mFragmentList.get(1);;


    //You can use the variable fragmentOne or frag1 to access functions declared in FragmentOne



这是 ViewpagerAdapterClass

    class ViewPagerAdapter extends FragmentPagerAdapter 
    public final List<Fragment> mFragmentList = new ArrayList<>();
    private final List<String> mFragmentTitleList = new ArrayList<>();

    public ViewPagerAdapter(FragmentManager manager) 
        super(manager);
    

    @Override
    public Fragment getItem(int position) 
        return mFragmentList.get(position);
    

    @Override
    public int getCount() 
        return mFragmentList.size();
    

    public void addFragment(Fragment fragment, String title) 
        mFragmentList.add(fragment);
        mFragmentTitleList.add(title);
    

    @Override
    public CharSequence getPageTitle(int position) 
        return mFragmentTitleList.get(position);
    

这个答案适合像我这样的菜鸟。祝你有美好的一天。

【讨论】:

【参考方案10】:

这是来自 Fragment 类...

((KidsStoryDashboard)getActivity()).values(title_txt,bannerImgUrl);

来自活动类的代码...

 public void values(String title_txts, String bannerImgUrl) 
    if (!title_txts.isEmpty()) 

//Do something to set text 
    
    imageLoader.displayImage(bannerImgUrl, htab_header_image, doption);

【讨论】:

【参考方案11】:

我一直在寻找最好的方法来做到这一点,因为并非我们要调用的每个方法都位于具有相同 Activity Parent 的 Fragment 中。

在你的片段中

public void methodExemple(View view)

        // your code here

        Toast.makeText(view.getContext(), "Clicked clicked",Toast.LENGTH_LONG).show();
    

在你的活动中

new ExempleFragment().methodExemple(context); 

【讨论】:

【参考方案12】:

我已经尝试了这个线程中显示的所有方法,但没有一个对我有用,试试这个。它对我有用。

((MainActivity) getContext().getApplicationContext()).Method();

【讨论】:

【参考方案13】:
((your_activity) getActivity).method_name()

your_activity 是您的活动名称,method_name() 是您要调用的方法的名称。

【讨论】:

【参考方案14】:

Kotlin 试试

class DataForm : Fragment() 
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) 
        Tasks(this).getData()
    

    fun getResponse(response: String) 
        // code
    


class Tasks(private val context: Any) 
    fun getData() 

        val getContext = (context as DataForm).activity
        val getFragment = (context as DataForm)

        val responseListener = Response.Listener<String>  response ->
            getFragment.getResponse(response)
        

        val errorListener = Response.ErrorListener  error ->
            error.printStackTrace();
        

        val stringRequest = StringRequest(Request.Method.GET, url, responseListener, errorListener)
        Volley.newRequestQueue(getContext).add(stringRequest)
    

【讨论】:

我喜欢这个,因为它消除了孩子对父母的知识水平。片段不应该直接调用父方法。【参考方案15】:

((YourActivityName)getActivity()).functionName();

例如:((SessionActivity)getActivity()).changeFragment();

注意:类名应该是公开的

【讨论】:

【参考方案16】:

从片段到活动:

((YourActivityClassName)requireActivity()).yourPublicMethod();

【讨论】:

【参考方案17】:

从各自的片段中调用活动方法的最佳方式

(activity as YourActivity).activtiyMethod()

从您的活动中使用此行。例如

假设您有 Activity A 和方法 add() 以及您的片段 ABC,并且您想从片段 ABC 调用方法 add,

(activity as A).add()

【讨论】:

如何从主要活动中调用片段方法

】如何从主要活动中调用片段方法【英文标题】:Howtocallfragmentmethodfrommainactivity【发布时间】:2016-06-1507:31:12【问题描述】:我在片段类中有方法。我想从主要活动中调用该方法,但我不想使用FragmentById(或)FragmentByTag。我的... 查看详情

从活动中调用片段方法

】从活动中调用片段方法【英文标题】:Callingfragmentmethodfromactivity【发布时间】:2013-10-2011:36:41【问题描述】:我的项目ViewPage中有一个带有两个片段(FragmentView1和FragmentView2)。这是我的ViewPageMainActivity,它有一个带有菜单的Act... 查看详情

从活动调用片段方法时出现空指针异常

】从活动调用片段方法时出现空指针异常【英文标题】:nullpointerexceptionwhencallingfragmentmethodsfromactivity【发布时间】:2013-01-1602:37:36【问题描述】:我有一个片段活动,它通过以下方式调用其他片段:FragmentView1f=(FragmentView1)this.get... 查看详情

如何从android中的活动调用片段方法?

】如何从android中的活动调用片段方法?【英文标题】:Howtocallafragmentmethodfromanactivityinandroid?【发布时间】:2016-10-1105:45:36【问题描述】:我的主活动上有一个选项卡式视图和一个浮动操作按钮。每当我单击浮动操作按钮时,我... 查看详情

如何从活动中调用片段方法?

】如何从活动中调用片段方法?【英文标题】:Howtocallfragmentsmethodfromactivity?【发布时间】:2021-12-2301:25:38【问题描述】:我希望每个人都做得很好,我是一名初学者级别的Android开发人员,我正在制作一个计数器Android应用程序,... 查看详情

从片段中调用父母的活动

】从片段中调用父母的活动【英文标题】:Callparent\'sactivityfromafragment【发布时间】:2012-12-3012:40:31【问题描述】:如果我在Fragment中,我如何调用父母的活动?【问题讨论】:通过调用getActivity()只需调用getActivity();我做到了。但... 查看详情

从活动中调用片段事件

】从活动中调用片段事件【英文标题】:Callfragmenteventsfromactivity【发布时间】:2011-07-0915:58:51【问题描述】:所以,我让我的片段中的事件传递给活动,那么我该如何做才能让活动轮流通知片段B做某事。当片段A单击列表项时,... 查看详情

从意图活动访问片段方法(代码片段)

我有一个片段,我从片段开始一个活动。现在我想从新活动中的片段调用一个方法。我试图使用接口,但似乎我不能,因为我不在片段中创建一个新活动的对象,让它调用setListener()。我正在使用意图启动新活动。我无法找到如... 查看详情

从片段开始活动

】从片段开始活动【英文标题】:StartingActivityFromFragment【发布时间】:2016-03-3111:18:47【问题描述】:我有两个AsyncTask(FetchDataFromApi,FetchDataFromDb),它们都有一个“onPostExecute”方法的实现,每个都通过调用passDataToDetailedActivity... 查看详情

从 dialogfragment 调用 onBackPressed 完成活动

...布时间】:2022-01-0700:16:13【问题描述】:我有一个对话框片段,上面有一个关闭按钮。这个对话框是从两个不同的活动中调用的。一种将其用作简单片段,另一种用作对话片段。在它的onClick方法中,我调用了requireAct 查看详情

从 JobIntentService 调用活动方法

】从JobIntentService调用活动方法【英文标题】:CallinganactivitymethodfromaJobIntentService【发布时间】:2020-03-1921:12:17【问题描述】:我想在onHandleWork的for循环中调用一个非静态方法。我怎样才能做到这一点?@OverrideprotectedvoidonHandleWork(@... 查看详情

从 FirebaseMessagingService 类调用活动类方法

】从FirebaseMessagingService类调用活动类方法【英文标题】:CallingactivityclassmethodfromFirebaseMessagingServiceclass【发布时间】:2016-12-1109:34:45【问题描述】:如何从fcm服务调用活动类方法。我已经尝试过这种方式CallingactivityclassmethodfromServ... 查看详情

Android:从片段调用活动

】Android:从片段调用活动【英文标题】:Android:CallingActivityfromFragment【发布时间】:2012-09-2004:50:42【问题描述】:我在活动中使用片段。我正在使用MediaRecorder进行录音。我有一个活动的两个部分。第一个本身将列出记录文件的... 查看详情

如何从活动中调用服务的方法?

】如何从活动中调用服务的方法?【英文标题】:HowtocallmethodsofaServicefromactivity?【发布时间】:2011-06-1805:05:51【问题描述】:我只是想从我的活动中调用本地服务的方法。我该怎么做?【问题讨论】:【参考方案1】:这是一个... 查看详情

从android中的活动调用片段

】从android中的活动调用片段【英文标题】:Callfragmentfromactivityinandroid【发布时间】:2014-09-0123:32:14【问题描述】:我目前正在处理使用过的片段中的项目。但是在这里,当我从Fragment调用活动类时,它运行良好。我要做的是在Bac... 查看详情

如何从另一个活动中调用片段

】如何从另一个活动中调用片段【英文标题】:Howtocallafragmentfromanotheractivity【发布时间】:2015-06-1722:21:16【问题描述】:我想从另一个扩展ActionBarActivity或Activity的活动中调用片段我想让它像有意图地从另一个活动中打开一个活... 查看详情

从活动访问片段时Android罕见的NPE

】从活动访问片段时Android罕见的NPE【英文标题】:AndroidrareNPEwhenaccessingfragmentfromactivity【发布时间】:2020-07-1112:39:33【问题描述】:我在Android中有一个包含框架布局的活动。其中一个框架布局是用片段膨胀的。在片段的onResume()... 查看详情

android - 从活动调用完成会破坏托管片段吗?

】android-从活动调用完成会破坏托管片段吗?【英文标题】:android-doescallingfinishfromactivitydestroyhostedfragment?【发布时间】:2014-10-1408:35:21【问题描述】:我有一个托管“片段B”的“活动A”。请确认如果我调用A.finish()则“片段B”... 查看详情