Activity 和 Fragment 通过 xml Button 内部的方法进行通信
Acitivity and Fragment communication by a method inside xml Button
我正在尝试使用 Navigation Drawer Activity 恢复我的应用程序,但在旧版本中使用简单 activity 我有一些对话框从用户那里获取数据并在内部管理它 activity.
现在我有了碎片,从用户那里取回数据时遇到了一些问题。
我的第一个问题:
MainActivity 包含 4 个 Fragment,其中一个在 XML 中有很多使用 onClick 方法的按钮。
使用 Activity 所有工作都没有问题,但使用 Fragments 我无法声明 onClick xml!
的方法
第二个问题是onClick的方法用startActivityForResult调用DialogActivity然后用on[=39取回数据=]结果。
我将 onClick 的方法移动到包含片段的 MainActivity 中,但是当它使用 startActivityForResult 启动 Dialog 时,片段中的 onActivityResult 不会被调用。
我尝试将它移动到 Activity 内,并将接收到的数据传递给带有接口的片段,但我在 Drawable style = setButtonColor(color);
在 onActivityResult[=15 内运行 Drawable style = setButtonColor(color);
时出错=]
执行此操作的最佳方法是什么?
最好删除 DialogActivity 并使用 DialogFragment 在没有 startActivityForResult 和 onActivityResult?
的情况下取回数据
这是我需要适应新片段图形的代码
<Button
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/new_button"
android:id="@+id/m12"
android:onClick="addMateria"
android:background="@drawable/buttons"
android:singleLine="true"
android:textSize="12sp"
android:layout_column="2" />
onClick的方法
public void addMateria(View v){
/* Prendo il nome della risorsa cosi nel ricompilare il progetto non perdo *
* tutti i riferimenti ai bottoni salvati nel database */
clickedButtonViewId = getResources().getResourceEntryName(v.getId());
//StartActivityForResult perche mi aspetto la materia inserita dall'altra activity
Intent myIntent = new Intent(MainActivity.this, DialogAddMateria.class);
startActivityForResult(myIntent, 1);
//onStop();
}
以及我如何取回数据
//Take back data from ActivityAddMateria
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if(requestCode == 1) {
if (resultCode == Activity.RESULT_OK) {
MySQLiteHelper db = new MySQLiteHelper(getActivity());
Toast.makeText(getContext(), "DENTRO ACTIVITYRESULT",
Toast.LENGTH_LONG).show();
//Cambio subito il Button
int resId = getResources().getIdentifier(clickedButtonViewId, "id", getActivity().getPackageName());
final Button clickedtextView = (Button) getActivity().findViewById(resId);
String result = data.getStringExtra("result"); //Take the materia from Dialog
int color = data.getIntExtra("color", 1); //Take the color from Dialog
//Controllo se il Button è già presente nel db se presente aggiorno se non presente inserisco
boolean modifica = db.Exists(clickedButtonViewId);
//Se voglio ripristinare il bottone di default
if (color == getResources().getColor(R.color.blue_orario)) {
//Ripristino la grafica di Default
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
clickedtextView.setText("New");
//Se la materia è nel database la cancello
if (modifica) {
db.deleteSingleMateria(clickedButtonViewId);
}
} else {
//Quando inserisco un normale bottone colorato
if (!modifica) {
//Materia da inserire in un nuovo spazio
db.addMateriaToDb(new Materia(clickedButtonViewId, result, color));
} else {
//Materia già presente nel Button quindi aggiorno la materia
db.updateMateria(new Materia(clickedButtonViewId, result, color));
Toast.makeText(getContext(), "Materia modificata!",
Toast.LENGTH_LONG).show();
}
//Inserisco la materia nel DB dei voti_media
db.addMateriaVotiFromOrario(new MaterieVoti(result, 0.0));
clickedtextView.setText(result);
//clickedtextView.setBackgroundColor(color);
//clickedtextView.getBackground().setColorFilter(color, PorterDuff.Mode.MULTIPLY);
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
}
}
if (resultCode == Activity.RESULT_CANCELED) {
//Nessuna materia inserita
}
}
}//onActivityResult
我对Fragments不熟悉,做我需要的东西有些困难,如果有人能告诉我怎么做,或者建议改变onClick和方法,Fragment和方法之间的通信,我在这里!
这个问题被问了很多次,activity 和片段之间的通信可以通过多种方式完成,比如在 bundle 中传递数据,根据 and using EventBus also, see 答案解释了单例模式,我已经解释了每一个关于如何做到这一点,如果您想了解更多信息,请发表评论。
官方文档是here
已全部添加到 MainActivity:
在Fragment的xml中调用的方法,如果按下按钮startActivityForResult,从用户那里获取数据。
之后我在 MainActivity 中编写了 onActivityResult,当取回数据时将其保存到 DB 中并修改 Fragment 中按钮的样式。
包含 Fragments 的 MainAcitivty
public void addMateria(View v){
/* Prendo il nome della risorsa cosi nel ricompilare il progetto non perdo *
* tutti i riferimenti ai bottoni salvati nel database */
clickedButtonViewId = getResources().getResourceEntryName(v.getId());
//StartActivityForResult perche mi aspetto la materia inserita dall'altra activity
Intent myIntent = new Intent(MainActivity.this, DialogAddMateria.class);
startActivityForResult(myIntent, 1);
//onStop();
}
//Take back data from ActivityAddMateria
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if(requestCode == 1) {
if (resultCode == Activity.RESULT_OK) {
MySQLiteHelper db = new MySQLiteHelper(this);
//Cambio subito il Button
int resId = getResources().getIdentifier(clickedButtonViewId, "id", getPackageName());
final Button clickedtextView = (Button) findViewById(resId);
String result = data.getStringExtra("result"); //Take the materia from Dialog
int color = data.getIntExtra("color", 1); //Take the color from Dialog
//Controllo se il Button è già presente nel db se presente aggiorno se non presente inserisco
boolean modifica = db.Exists(clickedButtonViewId);
//Se voglio ripristinare il bottone di default
if (color == getResources().getColor(R.color.blue_orario)) {
//Ripristino la grafica di Default
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
clickedtextView.setText("...");
//Se la materia è nel database la cancello
if (modifica) {
db.deleteSingleMateria(clickedButtonViewId);
}
} else {
//Quando inserisco un normale bottone colorato
if (!modifica) {
//Materia da inserire in un nuovo spazio
db.addMateriaToDb(new Materia(clickedButtonViewId, result, color));
} else {
//Materia già presente nel Button quindi aggiorno la materia
db.updateMateria(new Materia(clickedButtonViewId, result, color));
Toast.makeText(MainActivity.this, "Materia modificata!",
Toast.LENGTH_LONG).show();
}
//Inserisco la materia nel DB dei voti_media
db.addMateriaVotiFromOrario(new MaterieVoti(result, 0.0));
clickedtextView.setText(result);
//clickedtextView.setBackgroundColor(color);
//clickedtextView.getBackground().setColorFilter(color, PorterDuff.Mode.MULTIPLY);
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
}
}
if (resultCode == Activity.RESULT_CANCELED) {
//Nessuna materia inserita
}
}
}//onActivityResult
片段简单检查数据是否在数据库中并更新视图
List<Materia> materia;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View view = inflater.inflate(R.layout.orario_view, container, false);
MySQLiteHelper db = new MySQLiteHelper(getActivity());
//Get all materie inside database
materia = db.getAllMaterie();
//change all TextView inputed from user
if(materia.isEmpty()){
//do nothing
}else {
for (Materia mat : materia) {
//Change all the Button with values stored inside the database
int resId = getResources().getIdentifier(mat.getID(), "id", getActivity().getPackageName());
Button changedButton = (Button) view.findViewById(resId);
changedButton.setText(mat.getMateria());
changedButton.setTypeface(null, Typeface.BOLD);
Drawable style = setButtonColor(mat.getColor());
changedButton.setBackground(style);
}
}
return view;
}
我正在尝试使用 Navigation Drawer Activity 恢复我的应用程序,但在旧版本中使用简单 activity 我有一些对话框从用户那里获取数据并在内部管理它 activity.
现在我有了碎片,从用户那里取回数据时遇到了一些问题。
我的第一个问题: MainActivity 包含 4 个 Fragment,其中一个在 XML 中有很多使用 onClick 方法的按钮。 使用 Activity 所有工作都没有问题,但使用 Fragments 我无法声明 onClick xml!
的方法第二个问题是onClick的方法用startActivityForResult调用DialogActivity然后用on[=39取回数据=]结果。 我将 onClick 的方法移动到包含片段的 MainActivity 中,但是当它使用 startActivityForResult 启动 Dialog 时,片段中的 onActivityResult 不会被调用。
我尝试将它移动到 Activity 内,并将接收到的数据传递给带有接口的片段,但我在 Drawable style = setButtonColor(color);
在 onActivityResult[=15 内运行 Drawable style = setButtonColor(color);
时出错=]
执行此操作的最佳方法是什么? 最好删除 DialogActivity 并使用 DialogFragment 在没有 startActivityForResult 和 onActivityResult?
的情况下取回数据这是我需要适应新片段图形的代码
<Button
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/new_button"
android:id="@+id/m12"
android:onClick="addMateria"
android:background="@drawable/buttons"
android:singleLine="true"
android:textSize="12sp"
android:layout_column="2" />
onClick的方法
public void addMateria(View v){
/* Prendo il nome della risorsa cosi nel ricompilare il progetto non perdo *
* tutti i riferimenti ai bottoni salvati nel database */
clickedButtonViewId = getResources().getResourceEntryName(v.getId());
//StartActivityForResult perche mi aspetto la materia inserita dall'altra activity
Intent myIntent = new Intent(MainActivity.this, DialogAddMateria.class);
startActivityForResult(myIntent, 1);
//onStop();
}
以及我如何取回数据
//Take back data from ActivityAddMateria
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if(requestCode == 1) {
if (resultCode == Activity.RESULT_OK) {
MySQLiteHelper db = new MySQLiteHelper(getActivity());
Toast.makeText(getContext(), "DENTRO ACTIVITYRESULT",
Toast.LENGTH_LONG).show();
//Cambio subito il Button
int resId = getResources().getIdentifier(clickedButtonViewId, "id", getActivity().getPackageName());
final Button clickedtextView = (Button) getActivity().findViewById(resId);
String result = data.getStringExtra("result"); //Take the materia from Dialog
int color = data.getIntExtra("color", 1); //Take the color from Dialog
//Controllo se il Button è già presente nel db se presente aggiorno se non presente inserisco
boolean modifica = db.Exists(clickedButtonViewId);
//Se voglio ripristinare il bottone di default
if (color == getResources().getColor(R.color.blue_orario)) {
//Ripristino la grafica di Default
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
clickedtextView.setText("New");
//Se la materia è nel database la cancello
if (modifica) {
db.deleteSingleMateria(clickedButtonViewId);
}
} else {
//Quando inserisco un normale bottone colorato
if (!modifica) {
//Materia da inserire in un nuovo spazio
db.addMateriaToDb(new Materia(clickedButtonViewId, result, color));
} else {
//Materia già presente nel Button quindi aggiorno la materia
db.updateMateria(new Materia(clickedButtonViewId, result, color));
Toast.makeText(getContext(), "Materia modificata!",
Toast.LENGTH_LONG).show();
}
//Inserisco la materia nel DB dei voti_media
db.addMateriaVotiFromOrario(new MaterieVoti(result, 0.0));
clickedtextView.setText(result);
//clickedtextView.setBackgroundColor(color);
//clickedtextView.getBackground().setColorFilter(color, PorterDuff.Mode.MULTIPLY);
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
}
}
if (resultCode == Activity.RESULT_CANCELED) {
//Nessuna materia inserita
}
}
}//onActivityResult
我对Fragments不熟悉,做我需要的东西有些困难,如果有人能告诉我怎么做,或者建议改变onClick和方法,Fragment和方法之间的通信,我在这里!
这个问题被问了很多次,activity 和片段之间的通信可以通过多种方式完成,比如在 bundle 中传递数据,根据
官方文档是here
已全部添加到 MainActivity:
在Fragment的xml中调用的方法,如果按下按钮startActivityForResult,从用户那里获取数据。
之后我在 MainActivity 中编写了 onActivityResult,当取回数据时将其保存到 DB 中并修改 Fragment 中按钮的样式。
包含 Fragments 的 MainAcitivty
public void addMateria(View v){
/* Prendo il nome della risorsa cosi nel ricompilare il progetto non perdo *
* tutti i riferimenti ai bottoni salvati nel database */
clickedButtonViewId = getResources().getResourceEntryName(v.getId());
//StartActivityForResult perche mi aspetto la materia inserita dall'altra activity
Intent myIntent = new Intent(MainActivity.this, DialogAddMateria.class);
startActivityForResult(myIntent, 1);
//onStop();
}
//Take back data from ActivityAddMateria
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if(requestCode == 1) {
if (resultCode == Activity.RESULT_OK) {
MySQLiteHelper db = new MySQLiteHelper(this);
//Cambio subito il Button
int resId = getResources().getIdentifier(clickedButtonViewId, "id", getPackageName());
final Button clickedtextView = (Button) findViewById(resId);
String result = data.getStringExtra("result"); //Take the materia from Dialog
int color = data.getIntExtra("color", 1); //Take the color from Dialog
//Controllo se il Button è già presente nel db se presente aggiorno se non presente inserisco
boolean modifica = db.Exists(clickedButtonViewId);
//Se voglio ripristinare il bottone di default
if (color == getResources().getColor(R.color.blue_orario)) {
//Ripristino la grafica di Default
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
clickedtextView.setText("...");
//Se la materia è nel database la cancello
if (modifica) {
db.deleteSingleMateria(clickedButtonViewId);
}
} else {
//Quando inserisco un normale bottone colorato
if (!modifica) {
//Materia da inserire in un nuovo spazio
db.addMateriaToDb(new Materia(clickedButtonViewId, result, color));
} else {
//Materia già presente nel Button quindi aggiorno la materia
db.updateMateria(new Materia(clickedButtonViewId, result, color));
Toast.makeText(MainActivity.this, "Materia modificata!",
Toast.LENGTH_LONG).show();
}
//Inserisco la materia nel DB dei voti_media
db.addMateriaVotiFromOrario(new MaterieVoti(result, 0.0));
clickedtextView.setText(result);
//clickedtextView.setBackgroundColor(color);
//clickedtextView.getBackground().setColorFilter(color, PorterDuff.Mode.MULTIPLY);
Drawable style = setButtonColor(color);
clickedtextView.setBackground(style);
}
}
if (resultCode == Activity.RESULT_CANCELED) {
//Nessuna materia inserita
}
}
}//onActivityResult
片段简单检查数据是否在数据库中并更新视图
List<Materia> materia;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View view = inflater.inflate(R.layout.orario_view, container, false);
MySQLiteHelper db = new MySQLiteHelper(getActivity());
//Get all materie inside database
materia = db.getAllMaterie();
//change all TextView inputed from user
if(materia.isEmpty()){
//do nothing
}else {
for (Materia mat : materia) {
//Change all the Button with values stored inside the database
int resId = getResources().getIdentifier(mat.getID(), "id", getActivity().getPackageName());
Button changedButton = (Button) view.findViewById(resId);
changedButton.setText(mat.getMateria());
changedButton.setTypeface(null, Typeface.BOLD);
Drawable style = setButtonColor(mat.getColor());
changedButton.setBackground(style);
}
}
return view;
}