From 86e69f2856b3255f502a53e6c0ba3dcc1da4c618 Mon Sep 17 00:00:00 2001 From: Christophe Beyls Date: Fri, 21 Feb 2014 00:04:49 +0100 Subject: [PATCH] Scroll to the source event in TrackScheduleListFragment when navigating up from EventDetailsActivity. Also select the source event by default in dual-pane mode. --- .../activities/EventDetailsActivity.java | 1 + .../activities/TrackScheduleActivity.java | 9 ++- .../fragments/TrackScheduleListFragment.java | 65 ++++++++++++++++--- 3 files changed, 65 insertions(+), 10 deletions(-) diff --git a/src/be/digitalia/fosdem/activities/EventDetailsActivity.java b/src/be/digitalia/fosdem/activities/EventDetailsActivity.java index d368f85..633ea67 100644 --- a/src/be/digitalia/fosdem/activities/EventDetailsActivity.java +++ b/src/be/digitalia/fosdem/activities/EventDetailsActivity.java @@ -69,6 +69,7 @@ public class EventDetailsActivity extends ActionBarActivity implements LoaderCal Intent upIntent = new Intent(this, TrackScheduleActivity.class); upIntent.putExtra(TrackScheduleActivity.EXTRA_DAY, event.getDay()); upIntent.putExtra(TrackScheduleActivity.EXTRA_TRACK, event.getTrack()); + upIntent.putExtra(TrackScheduleActivity.EXTRA_FROM_EVENT_ID, event.getId()); upIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); finish(); diff --git a/src/be/digitalia/fosdem/activities/TrackScheduleActivity.java b/src/be/digitalia/fosdem/activities/TrackScheduleActivity.java index a576775..9f0dbff 100644 --- a/src/be/digitalia/fosdem/activities/TrackScheduleActivity.java +++ b/src/be/digitalia/fosdem/activities/TrackScheduleActivity.java @@ -27,6 +27,8 @@ public class TrackScheduleActivity extends ActionBarActivity implements TrackSch public static final String EXTRA_DAY = "day"; public static final String EXTRA_TRACK = "track"; + // Optional extra used as a hint for up navigation from an event + public static final String EXTRA_FROM_EVENT_ID = "from_event_id"; private Day day; private Track track; @@ -51,7 +53,12 @@ public class TrackScheduleActivity extends ActionBarActivity implements TrackSch TrackScheduleListFragment trackScheduleListFragment; FragmentManager fm = getSupportFragmentManager(); if (savedInstanceState == null) { - trackScheduleListFragment = TrackScheduleListFragment.newInstance(day, track); + long fromEventId = extras.getLong(EXTRA_FROM_EVENT_ID, -1L); + if (fromEventId != -1L) { + trackScheduleListFragment = TrackScheduleListFragment.newInstance(day, track, fromEventId); + } else { + trackScheduleListFragment = TrackScheduleListFragment.newInstance(day, track); + } fm.beginTransaction().add(R.id.schedule, trackScheduleListFragment).commit(); } else { trackScheduleListFragment = (TrackScheduleListFragment) fm.findFragmentById(R.id.schedule); diff --git a/src/be/digitalia/fosdem/fragments/TrackScheduleListFragment.java b/src/be/digitalia/fosdem/fragments/TrackScheduleListFragment.java index 77a9455..670ea79 100644 --- a/src/be/digitalia/fosdem/fragments/TrackScheduleListFragment.java +++ b/src/be/digitalia/fosdem/fragments/TrackScheduleListFragment.java @@ -39,12 +39,15 @@ public class TrackScheduleListFragment extends ListFragment implements LoaderCal } private static final int EVENTS_LOADER_ID = 1; + private static final String ARG_DAY = "day"; private static final String ARG_TRACK = "track"; + private static final String ARG_FROM_EVENT_ID = "from_event_id"; private TrackScheduleAdapter adapter; private Callbacks listener; private boolean selectionEnabled = false; + private boolean isListAlreadyShown = false; public static TrackScheduleListFragment newInstance(Day day, Track track) { TrackScheduleListFragment f = new TrackScheduleListFragment(); @@ -55,12 +58,32 @@ public class TrackScheduleListFragment extends ListFragment implements LoaderCal return f; } + public static TrackScheduleListFragment newInstance(Day day, Track track, long fromEventId) { + TrackScheduleListFragment f = new TrackScheduleListFragment(); + Bundle args = new Bundle(); + args.putParcelable(ARG_DAY, day); + args.putParcelable(ARG_TRACK, track); + args.putLong(ARG_FROM_EVENT_ID, fromEventId); + f.setArguments(args); + return f; + } + @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); adapter = new TrackScheduleAdapter(getActivity()); setListAdapter(adapter); + + if (savedInstanceState != null) { + isListAlreadyShown = savedInstanceState.getBoolean("isListAlreadyShown"); + } + } + + @Override + public void onSaveInstanceState(Bundle outState) { + super.onSaveInstanceState(outState); + outState.putBoolean("isListAlreadyShown", isListAlreadyShown); } @Override @@ -79,7 +102,7 @@ public class TrackScheduleListFragment extends ListFragment implements LoaderCal private void notifyEventSelected(int position) { if (listener != null) { - listener.onEventSelected(position, (position == -1) ? null : adapter.getItem(position)); + listener.onEventSelected(position, (position == ListView.INVALID_POSITION) ? null : adapter.getItem(position)); } } @@ -114,23 +137,27 @@ public class TrackScheduleListFragment extends ListFragment implements LoaderCal final int count = adapter.getCount(); int checkedPosition = getListView().getCheckedItemPosition(); if ((checkedPosition == ListView.INVALID_POSITION) || (checkedPosition >= count)) { - if (count > 0) { - // Select the first item if any - getListView().setItemChecked(0, true); - checkedPosition = 0; - } else { - // No result, nothing selected - checkedPosition = -1; + // There is no current valid selection, use the default one + checkedPosition = getDefaultPosition(); + if (checkedPosition != ListView.INVALID_POSITION) { + getListView().setItemChecked(checkedPosition, true); } } // Ensure the current selection is visible - if (checkedPosition != -1) { + if (checkedPosition != ListView.INVALID_POSITION) { setSelection(checkedPosition); } // Notify the parent of the current selection to synchronize its state notifyEventSelected(checkedPosition); + + } else if (!isListAlreadyShown) { + int position = getDefaultPosition(); + if (position != ListView.INVALID_POSITION) { + setSelection(position); + } } + isListAlreadyShown = true; } // The list should now be shown. @@ -141,6 +168,26 @@ public class TrackScheduleListFragment extends ListFragment implements LoaderCal } } + /** + * @return The default position in the list, or -1 if the list is empty + */ + private int getDefaultPosition() { + final int count = adapter.getCount(); + if (count == 0) { + return ListView.INVALID_POSITION; + } + long fromEventId = getArguments().getLong(ARG_FROM_EVENT_ID, -1L); + if (fromEventId != -1L) { + // Look for the source event in the list and return its position + for (int i = 0; i < count; ++i) { + if (adapter.getItemId(i) == fromEventId) { + return i; + } + } + } + return 0; + } + @Override public void onLoaderReset(Loader loader) { adapter.swapCursor(null);