0

FIXED

I outsourced the Bluetooth scanning to a separate thread which was a failure. :D Having fixed this the code now works. Thanks for all support!

ORIGINAL QUESTION

I'm having troubles with exchanging dynamically added fragments (I use the support library and my minimal API version is 8 (Android 2.2)). In my XML which can be seen below file I have a FrameLayout which contains the fragment.

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin"
    tools:context=".BluetoothConnectionManager">

    <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:id="@+id/frmlFragmentContainer"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"/>

    <android.support.v7.widget.Toolbar
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:id="@+id/tbBottom"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:minHeight="?attr/actionBarSize"
        android:background="@color/hafnertec"
        android:layout_alignParentBottom="true">

        <RelativeLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content">
            <TextView android:id="@+id/lblMode"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@string/lblMode"
                android:layout_centerInParent="true"/>
            <ImageButton android:id="@+id/btnRefresh"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:src="@drawable/ic_action_refresh"
                android:layout_alignParentRight="true"
                android:layout_centerHorizontal="true"
                android:layout_centerVertical="true"
                android:layout_alignRight="@id/lblMode"
                android:clickable="false"
                android:longClickable="false"
                android:onClick="updateData"/>
        </RelativeLayout>

    </android.support.v7.widget.Toolbar>

</RelativeLayout>

For exchanging the fragments i use a SupportFragmentManager. Furthermore, I also instantiate the two fragments in the onCreate() method. In addition, the fragment for discovering Bluetooth devices is added to the frame layout which works fine.

@Override
protected void onCreate(Bundle savedInstanceState)
{
    ...
    // fetch a FragmentManager used for exchanging the fragments
    this.fmFragmentExchanger = this.getSupportFragmentManager();
    this.btDiscoveryFragment = new BluetoothDiscoveryFragment();
    this.btConnectorFragment = new BluetoothConnectorFragment();

    if (this.findViewById(R.id.frmlFragmentContainer) != null)
    {
        this.fmFragmentExchanger.beginTransaction().add(R.id.frmlFragmentContainer, this.btDiscoveryFragment).disallowAddToBackStack().commit();
    }
    ...
}

Moreover, I've taken care that the fragments extend the Fragment class provided by the support library:

import android.support.v4.app.Fragment;
public class BluetoothDiscoveryFragment extends Fragment implements ...
{
    // see: https://developer.android.com/training/basics/fragments/creating.html
    @Override
    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, Nullable Bundle savedInstanceState)
    {
        return inflater.inflate(R.layout.fragment_connection_bluetooth_device, container, false);
    }

Here is my code for exchanging the fragments:

this.fmFragmentExchanger.beginTransaction().replace(R.id.frmlFragmentContainer, this.btConnectorFragment).disallowAddToBackStack().commit();

The class for discovering Bluetooth devices makes use of a BroadcastReceiver which is "connected" with the activity. On stopping the discovery process or when it has finished I unregister this BroadcastReceiver.

However, on exchanging the fragments nothing happens and after some time I get an error caused by SIGABRT:

12-31 15:09:51.621    9790-9795/com.hafnertec.afdbluetooth I/dalvikvm﹕ Wrote stack traces to '/data/anr/traces.txt'
12-31 15:09:53.945    9790-9790/com.hafnertec.afdbluetooth A/libc﹕ Fatal signal 6 (SIGABRT) at 0x000001bd (code=0), thread 9790 (ec.afdbluetooth)

Here you can see the file /data/anr/traces.txt: trace file

I'm running the tests on a Samsung Galaxy S I9000 with Android 4.4.4 (CM SNAPSHOT M12). During the activity's onCreate() method I add the btDiscoveryFragment instance which works fine:

this.fmFragmentExchanger.beginTransaction().add(R.id.frmlFragmentContainer, this.btDiscoveryFragment).disallowAddToBackStack().commit();

Furthermore, adding the instance btConnectorFragment using .add() works. However, it logically causes the btConnectorFragment to be overlayed over the btDiscoveryFragment.

Lukas
  • 756
  • 7
  • 20

1 Answers1

1

I think you have a typo, causing btDiscoveryFragment to be null:

this.fmFragmentExchanger = this.getSupportFragmentManager();
//add this line
this.btDiscoveryFragment = new BluetoothDiscoveryFragment();
//remove this duplicated line
//this.btConnectorFragment = new BluetoothConnectorFragment();
this.btConnectorFragment = new BluetoothConnectorFragment();
Sam Dozor
  • 40,335
  • 6
  • 42
  • 42
  • oh, it was just an error in your question? did you fix the code in your app too? ;) – Sam Dozor Dec 31 '14 at 17:26
  • In my application the code has been right regarding this error. I forgot to mention that I add the fragment btDiscoveryFragment during the activity's onCreate() method which works fine. I have updated my question. – Lukas Jan 01 '15 at 11:36