Android:试图在片段之间传递数据的问题

时间:2014-08-27 13:41:03

标签: java android xml android-fragments

我试图将一些数据从ListFragment传递到另一个Fragment。列表显示正常,但是当我单击列表中的某个项目时,没有任何反应,并且日志中没有任何内容显示错误。我是android / java开发的新手,并尝试围绕不同的概念(活动,片段,捆绑等)。来自iOS / Objective C世界,我看到了在视图和视图之间传递数据所涉及的概念的相似之处。但我想我还没有完全理解android的概念。

无论如何,片段和布局如下。有人可以帮我看看我哪里出错吗?非常感谢。

main(fragment_ehschedule.xml)和列表视图(schedule_info.xml)的布局:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="fill_parent" 
 android:layout_height="fill_parent" 
 android:orientation="vertical">

 <EditText android:id="@+id/myFilter" 
  android:layout_width="match_parent"
  android:layout_height="wrap_content" 
  android:ems="10" 
  android:hint="@string/some_hint">
  <requestFocus />
 </EditText>

 <ListView android:id="@android:id/list" 
  android:layout_width="fill_parent"
  android:layout_height="fill_parent" />

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout 
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical"
    android:id="@+id/frameLayout"
    android:padding="6dip" >

<LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical" >

        <TextView
            android:id="@+id/textViewSessionTime"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textStyle="bold"
            android:paddingTop="10dip"
            android:paddingBottom="10dip"
            android:text="sessiontime" />

        <TextView
            android:id="@+id/textViewScheduleDate"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:text="scheduledate"
            android:textAppearance="?android:attr/textAppearanceSmall"
            android:textStyle="bold" />

        <TextView
            android:id="@+id/textViewSessionName"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textStyle="bold"
            android:text="sessionname"
            android:textAppearance="?android:attr/textAppearanceMedium" />

    </LinearLayout>

</FrameLayout>

片段详细信息(fragment_ehschedule_detail.xml)的布局如下:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  android:orientation="vertical"
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:padding="10dp">

  <TextView android:id="@+id/sessionname_label"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textSize="25dip"
            android:textStyle="bold"
            android:paddingTop="10dip"
            android:paddingBottom="10dip"
            android:textColor="#43bd00"/>

  <TextView android:id="@+id/scheduledate_label"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textColor="#acacac"/>

  <TextView android:id="@+id/sessiontime_label"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:textStyle="bold"/>

</LinearLayout>

主视图(EhallSchedFragment2.java)的类文件如下:

 public class EhallSchedFragment2 extends ListFragment{

     public static String strDate = null;

     private SQLiteDB sqlite_obj;
     private SimpleCursorAdapter dataAdapter;

      @Override
      public View onCreateView(LayoutInflater inflater, ViewGroup container,
                 Bundle savedInstanceState) {
             super.onCreateView(inflater, container, savedInstanceState);
             final View v = inflater.inflate(R.layout.fragment_ehschedule, container, false);

    sqlite_obj = new SQLiteDB(getActivity());

    sqlite_obj.open();

    Cursor cursor = sqlite_obj.fetchAllSchedules();

     // The desired columns to be bound
     String[] columns = new String[] {
       SQLiteDB.KEY_SCHEDULEDATE,
       SQLiteDB.KEY_SESSIONNAME,
       SQLiteDB.KEY_SESSIONTIME,
       SQLiteDB.KEY_DESC
     };

     // the XML defined views which the data will be bound to
     int[] to = new int[] { 
       R.id.textViewScheduleDate,
       R.id.textViewSessionName,
       R.id.textViewSessionTime,
       R.id.textViewDesc,
     };

     // create the adapter using the cursor pointing to the desired data 
     //as well as the layout information
     dataAdapter = new SimpleCursorAdapter(
             getActivity(), R.layout.schedule_info, 
               cursor, 
               columns, 
               to,
               0);

     ListView listView = (ListView)v. findViewById(android.R.id.list);
     // Assign adapter to ListView
     listView.setAdapter(dataAdapter);

     listView.setOnItemClickListener(new OnItemClickListener() {
       @Override
       public void onItemClick(AdapterView<?> listView, View view, 
         int position, long id) {
       // Get the cursor, positioned to the corresponding row in the result set
       Cursor cursor = (Cursor) listView.getItemAtPosition(position);

       String exHallScheduleDate = 
                cursor.getString(cursor.getColumnIndexOrThrow("scheduleDate"));
       String exHallSessionName = 
                        cursor.getString(cursor.getColumnIndexOrThrow("sessionName"));
       String exHallSessionTime = 
                        cursor.getString(cursor.getColumnIndexOrThrow("sessionTime"));

       EhallSchedDetailFragment2 myDetailFragment = new EhallSchedDetailFragment2();

       Bundle bundle = new Bundle();

       bundle.putString("scheduleDate", exHallScheduleDate);
       bundle.putString("sessionName", exHallSessionName);
       bundle.putString("sessionTime", exHallSessionTime);

           myDetailFragment.setArguments(bundle);

           FragmentManager fragmentManager = getFragmentManager();

            myDetailFragment.setArguments(bundle);
            FragmentTransaction transaction = fragmentManager.beginTransaction();
            transaction.replace(R.id.frameLayout, myDetailFragment);
            transaction.remove(EhallSchedFragment2.this);

           /*
                * Add this transaction to the back stack. 
                * This means that the transaction will be remembered after it is 
                * committed, and will reverse its operation when later popped off 
                * the stack.
           */
               transaction.addToBackStack(null);

               transaction.commit();

       }
      });


     EditText myFilter = (EditText)v. findViewById(R.id.myFilter);
      myFilter.addTextChangedListener(new TextWatcher() {

       public void afterTextChanged(Editable s) {
       }

       public void beforeTextChanged(CharSequence s, int start, 
         int count, int after) {
       }

       public void onTextChanged(CharSequence s, int start, 
         int before, int count) {
        dataAdapter.getFilter().filter(s.toString());
       }
      });

      dataAdapter.setFilterQueryProvider(new FilterQueryProvider() {
             public Cursor runQuery(CharSequence constraint) {
                 return sqlite_obj.fetchScheduleByDate(constraint.toString());
             }
         });

    return v;
}

}

详情视图(EhallSchedDetailFragment2.java)的类文件如下:

 public class EhallSchedDetailFragment2 extends Fragment {

TextView scheduleDateDetail;
TextView sessionNameDetail;
TextView sessionTimeDetail;

@Override
  public View onCreateView(LayoutInflater inflater, ViewGroup container,
    Bundle savedInstanceState) {
   View view = inflater.inflate(R.layout.fragment_ehschedule_detail, null);

   scheduleDateDetail = (TextView)view.findViewById(R.id.scheduledate_label);
   sessionNameDetail = (TextView)view.findViewById(R.id.sessionname_label);
   sessionTimeDetail = (TextView)view.findViewById(R.id.sessiontime_label);

       Bundle bundle = getArguments();
          if(bundle != null){
           String schedDateDet = bundle.getString("scheduleDate");
           scheduleDateDetail.setText(schedDateDet);

           String sessNameDet = bundle.getString("sessionName");
           sessionNameDetail.setText(sessNameDet);

           String sessTimeDet = bundle.getString("sessionTime");
           sessionTimeDetail.setText(sessTimeDet);
          }
          return view;
}

}

2 个答案:

答案 0 :(得分:1)

你基本上需要四件事才能得到你需要的东西:

  1. 你需要你的片段 - 称之为FragmentA
  2. 然后在该片段内或其自己的类文件中定义一个接口。此接口将具有一个必须调用以通知活动的方法。
  3. 然后在您的活动中,您实现界面并覆盖上面步骤2中的方法。
  4. 要通知FragmentB,您真正需要做的就是在步骤3中覆盖的方法中调用其方法。
  5. 如上所述,您不应直接在片段之间进行通信。以下是有关如何执行上述所有步骤的详细分步教程:

    Communicating between Fragments and Activities

    我希望这有助于您解决或接近解决问题。

答案 1 :(得分:0)

如果您使用的是ListFragment,则可以执行以下操作:

 @Override
 public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);
    mListView = getListView();
    SetClicklListener(mListView);  
  }
 public void SetClicklListener(ListView listView){
    listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
        public void onItemClick(AdapterView<?> parent, View view,
        int position, long id) {
            //Here you can catch the clicked item
        }
    });
}