1

I have made an Android app, on Android 4.4.4, and I want to develop it on Android 4.0.0. I have a problem to send a service, my binder, to a fragment.

On Android 4.4.4 I use the following lines :

AddTrashFragment addTrashFragment = new AddTrashFragment();
Bundle bundle = new Bundle();
bundle.putParcelable("bitmap", bitmap2);
bundle.putString("fileName", fileName);
bundle.putBinder("binder", binder);
addTrashFragment.setArguments(bundle);

FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction().replace(R.id.relativeLayout,addTrashFragment).addToBackStack(null).commitAllowingStateLoss();

But when I try to build my project with Android 4.0.0 I have the following error : Call requires API level 18 (current min is 14): android.os.Bundle#putBinder less (Ctrl + F1)

I don't understand how to send my service, my binder, to a fragment when I try to build my project on Ice Scream Sandwich.

Onik
  • 19,396
  • 14
  • 68
  • 91
Fred37b
  • 822
  • 2
  • 10
  • 29

3 Answers3

1

Because the Bundle.putBinder() is API 18+ you'll have to do it a different way. The simplest is to have your Fragment define a callback interface which your Activity must implement:

public class MyFragment extends Fragment {
    MyFragment.Callback  cb;

    public interface Callback {
        Binder getServiceBinder();
    }
    ...

    public void onAttach(Context context) {
        try {
            cb = (MyFragment.Callback)context;
        } catch (ClassCastException e) {
            Log.e(TAG, "Activity (Context) must implement Callback");
            throw new RuntimeException();
        }
    }
}

public class MyActivity extends Activity implements MyFragment.Callback {
    private Binder  mService;
    ...

    public Binder getServiceBinder() {
        return mService;
    }
}
Larry Schiefer
  • 15,687
  • 2
  • 27
  • 33
1

The issue is happening because bundle.putBinder(Binder) was added later on API 18 only. So, in devices with API 14, that code will fail since that method does not exist on those devices.

Maybe, you can create a public method in your Fragment and call it like:

public class AddTrashFragment extends Fragment {
    private Binder binder;

    public void setBinder(Binder binder) {
        this.binder = binder;
    }
}

And in your activity, you call:

AddTrashFragment addTrashFragment = new AddTrashFragment();
Bundle bundle = new Bundle();
bundle.putParcelable("bitmap", bitmap2);
bundle.putString("fileName", fileName);
addTrashFragment.setArguments(bundle);

addTrashFragment.setBinder(binder);

OR

You can get the Binder from activity like:

public class MainAcitivity extends Activity {
    public Binder getBinder() {
        return binder;
    }
}

and in your fragment:

public AddTrashFragment extends Fragment {
    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {

        Binder binder;
        Activity activity = getActivity();
        if(activity != null && activity instanceof MainActivity)
            binder = ((MainAcitivity)activity).getBinder();
    }
}
guipivoto
  • 18,327
  • 9
  • 60
  • 75
0

You can use BundleCompat to put and get an IBinder from a Bundle.

See: BundleCompat Documentation

masterwok
  • 4,868
  • 4
  • 34
  • 41