内容简介:首先,如果要实现Activity与其他的Fragment之间实现通信,那么这个Fragment需要拥有一个独立的Layout文件,以便重用,并且以代码添加的方式出现在Activity中。这么做的好处在于我们可以把相关的业务逻辑写在这个Fragment中,减少它所依附的Activity中的代码。在官方文档中,建议我们在实现Fragment与其他Activity/Fragment通信的时候使用ViewModel,在
首先,如果要实现Activity与其他的Fragment之间实现通信,那么这个Fragment需要拥有一个独立的Layout文件,以便重用,并且以代码添加的方式出现在Activity中。
这么做的好处在于我们可以把相关的业务逻辑写在这个Fragment中,减少它所依附的Activity中的代码。
在官方文档中,建议我们在实现Fragment与其他Activity/Fragment通信的时候使用ViewModel,在 ViewModel 存储我们的模型数据,通过在我们想要建立联系的Fragment与Activity中共享这个 ViewModel 实现数据通信(其中一个Fragment/Activity更新了 ViewModel ,其他关联了此 ViewModel 的Fragment/Activity也会变化)。
不过我们今天不说通过 ViewModel 的方式,感兴趣的同学可以通过官方文档看看。我们来说说通过 Interface 来实现Activity与其他的Fragment之间的通信。这种方式与使用 ViewModel 比起来,需要我们做更多的工作。
2,准备工作:将Fragment添加到Activity
在Fragment与Activity产生交互之前,需要先让他们 '连接'到一起。
(1) 新建一个项目,主活动是 MainActivity ,我们将它的布局改成如下 :
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity"
android:id="@+id/fragment_container">
</FrameLayout>
复制代码
主活动布局中只有一个FrameLayout,并为它指定一个id 。
(2) 创建一个Fragment
public class BFragment extends Fragment {
@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_b_layout, container, false);
Button sendMsgBtn = rootView.findViewById(R.id.send_msg_btn);
sendMsgBtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//发送消息给Activity
}
});
return rootView;
}
}
复制代码
并为这个Fragment创建一个布局文件 fragment_b_layout.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent"
android:layout_height="match_parent">
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="BUTTON"
android:id="@+id/send_msg_btn"/>
</RelativeLayout>
复制代码
Fragment布局中只有一个Button,我们将实现通过点击Button,将Fragment中的数据传到Activity中。
(3),将Fragment显示到Activity上
这里需要借助 FragmentManager 来管理Fragment,并且将Fragment显示在Activity上。
public class MainActivity extends AppCompatActivity{
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
FragmentManager fm = getSupportFragmentManager();
FragmentTransaction transaction = fm.beginTransaction();
Fragment fragment = fm.findFragmentById(R.id.fragment_container);
if (fragment == null) {
fragment = new BFragment();
transaction.add(R.id.fragment_container, fragment);
transaction.commit();
}
}
}
复制代码
OK,准备做完了,现在运行一下,页面应该是这样的 :
3,实现通信
(1),定义接口
我们在BFragment中,定义一个接口,
public class BFragment extends Fragment {
...
Callback mCallback;
public interface Callback{
public void onBtnClickListener(String str);
}
public void setCallback(Callback callback) {
mCallback = callback;
}
....
}
复制代码
接口中只有一个方法,并且有一个String 类型的参数。
为button,设置一个点击事件: 当点击按钮时,调用接口的方法:
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
...
sendMsgBtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (mCallback != null ) {
mCallback.onBtnClickListener("我来自fragment B");
}
}
});
...
}
复制代码
我们将想要传递给Activity的数据传入接口方法中。
(2),实现接口
我们让 MainActivity 实现刚刚在BFragment中定义的接口 Callback , 并且调用 BFragment的 setCallback(Callback callback),因为MainActivity类实现了 Callback 接口,所以参数可以传入MainActivity本身。
在实现 Callback 的 onBtnClickListener(String str) 方法中,我们弹出含有信息的 toast.
public class MainActivity extends AppCompatActivity implements BFragment.Callback{
...
@Override
public void onBtnClickListener(String str) {
Toast.makeText(this, str, Toast.LENGTH_SHORT).show();
}
...
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
...//省略刚刚写过的代码
if (fragment == null) {
fragment = new BFragment();
((BFragment) fragment).setCallback(this);
transaction.add(R.id.fragment_container, fragment);
transaction.commit();
}
}
}
复制代码
运行,看效果:
正如我们预想的那样,我们在点击 Fragment中的 Button,成功使 Activity产生一个Toast,作为响应,并且能够得到传过去的字符串数据。
(完~)
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
猜你喜欢:- APUE 学习笔记——进程间通信
- 操作系统学习笔记-7:进程通信
- Vue笔记(六)——Vue组件通信&Vuex
- 间歇性笔记--Vue组件间通信传值的各种方式
- 面试官:如果让你设计一个消息中间件,如何将其网络通信性能优化10倍以上?【石杉的架构笔记】
- 网络通信2:TCP简单通信
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Coming of Age in Second Life
Tom Boellstorff / Princeton University Press / 2008-04-21 / USD 29.95
The gap between the virtual and the physical, and its effect on the ideas of personhood and relationships, is the most interesting aspect of Boellstorff's analysis... Boellstorff's portrayal of a virt......一起来看看 《Coming of Age in Second Life》 这本书的介绍吧!