• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2 * Copyright (C) 2016 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License
15 */
16 
17 package com.android.tv.dvr.ui.list;
18 
19 import android.annotation.TargetApi;
20 import android.database.ContentObserver;
21 import android.media.tv.TvContract.Programs;
22 import android.net.Uri;
23 import android.os.Build;
24 import android.os.Bundle;
25 import android.os.Handler;
26 import android.os.Looper;
27 import android.support.v17.leanback.widget.ClassPresenterSelector;
28 import android.transition.Fade;
29 import android.view.LayoutInflater;
30 import android.view.View;
31 import android.view.ViewGroup;
32 
33 import com.android.tv.ApplicationSingletons;
34 import com.android.tv.R;
35 import com.android.tv.TvApplication;
36 import com.android.tv.data.ChannelDataManager;
37 import com.android.tv.data.Program;
38 import com.android.tv.dvr.DvrDataManager.SeriesRecordingListener;
39 import com.android.tv.dvr.EpisodicProgramLoadTask;
40 import com.android.tv.dvr.SeriesRecording;
41 import com.android.tv.dvr.ui.list.SchedulesHeaderRowPresenter.SeriesRecordingHeaderRowPresenter;
42 
43 import java.util.List;
44 
45 /**
46  * A fragment to show the list of series schedule recordings.
47  */
48 @TargetApi(Build.VERSION_CODES.N)
49 public class DvrSeriesSchedulesFragment extends BaseDvrSchedulesFragment {
50     private static final String TAG = "DvrSeriesSchedulesFragment";
51     /**
52      * The key for series recording whose scheduled recording list will be displayed.
53      */
54     public static final String SERIES_SCHEDULES_KEY_SERIES_RECORDING =
55             "series_schedules_key_series_recording";
56     /**
57      * The key for programs belong to the series recording whose scheduled recording
58      * list will be displayed.
59      */
60     public static final String SERIES_SCHEDULES_KEY_SERIES_PROGRAMS =
61             "series_schedules_key_series_programs";
62 
63     private ChannelDataManager mChannelDataManager;
64     private SeriesRecording mSeriesRecording;
65     private List<Program> mPrograms;
66     private EpisodicProgramLoadTask mProgramLoadTask;
67 
68     private final SeriesRecordingListener mSeriesRecordingListener =
69             new SeriesRecordingListener() {
70                 @Override
71                 public void onSeriesRecordingAdded(SeriesRecording... seriesRecordings) { }
72 
73                 @Override
74                 public void onSeriesRecordingRemoved(SeriesRecording... seriesRecordings) {
75                     for (SeriesRecording r : seriesRecordings) {
76                         if (r.getId() == mSeriesRecording.getId()) {
77                             getActivity().finish();
78                             return;
79                         }
80                     }
81                 }
82 
83                 @Override
84                 public void onSeriesRecordingChanged(SeriesRecording... seriesRecordings) {
85                     for (SeriesRecording r : seriesRecordings) {
86                         if (r.getId() == mSeriesRecording.getId()
87                                 && getRowsAdapter() instanceof SeriesScheduleRowAdapter) {
88                             ((SeriesScheduleRowAdapter) getRowsAdapter())
89                                     .onSeriesRecordingUpdated(r);
90                             return;
91                         }
92                     }
93                 }
94             };
95 
96     private final ContentObserver mContentObserver =
97             new ContentObserver(new Handler(Looper.getMainLooper())) {
98                 @Override
99                 public void onChange(boolean selfChange, Uri uri) {
100                     super.onChange(selfChange, uri);
101                     executeProgramLoadingTask();
102                 }
103             };
104 
105     private final ChannelDataManager.Listener mChannelListener = new ChannelDataManager.Listener() {
106         @Override
107         public void onLoadFinished() { }
108 
109         @Override
110         public void onChannelListUpdated() {
111             executeProgramLoadingTask();
112         }
113 
114         @Override
115         public void onChannelBrowsableChanged() { }
116     };
117 
DvrSeriesSchedulesFragment()118     public DvrSeriesSchedulesFragment() {
119         setEnterTransition(new Fade(Fade.IN));
120     }
121 
122     @Override
onCreate(Bundle savedInstanceState)123     public void onCreate(Bundle savedInstanceState) {
124         Bundle args = getArguments();
125         if (args != null) {
126             mSeriesRecording = args.getParcelable(SERIES_SCHEDULES_KEY_SERIES_RECORDING);
127             mPrograms = args.getParcelableArrayList(SERIES_SCHEDULES_KEY_SERIES_PROGRAMS);
128         }
129         super.onCreate(savedInstanceState);
130         ApplicationSingletons singletons = TvApplication.getSingletons(getContext());
131         singletons.getDvrDataManager().addSeriesRecordingListener(mSeriesRecordingListener);
132         mChannelDataManager = singletons.getChannelDataManager();
133         mChannelDataManager.addListener(mChannelListener);
134         getContext().getContentResolver().registerContentObserver(Programs.CONTENT_URI, true,
135                 mContentObserver);
136     }
137 
138     @Override
onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)139     public View onCreateView(LayoutInflater inflater, ViewGroup container,
140             Bundle savedInstanceState) {
141         onProgramsUpdated();
142         return super.onCreateView(inflater, container, savedInstanceState);
143     }
144 
onProgramsUpdated()145     private void onProgramsUpdated() {
146         ((SeriesScheduleRowAdapter) getRowsAdapter()).setPrograms(mPrograms);
147         if (mPrograms == null || mPrograms.isEmpty()) {
148             showEmptyMessage(R.string.dvr_series_schedules_empty_state);
149         } else {
150             hideEmptyMessage();
151         }
152     }
153 
154     @Override
onDestroy()155     public void onDestroy() {
156         if (mProgramLoadTask != null) {
157             mProgramLoadTask.cancel(true);
158             mProgramLoadTask = null;
159         }
160         getContext().getContentResolver().unregisterContentObserver(mContentObserver);
161         mChannelDataManager.removeListener(mChannelListener);
162         TvApplication.getSingletons(getContext()).getDvrDataManager()
163                 .removeSeriesRecordingListener(mSeriesRecordingListener);
164         super.onDestroy();
165     }
166 
167     @Override
onCreateHeaderRowPresenter()168     public SchedulesHeaderRowPresenter onCreateHeaderRowPresenter() {
169         return new SeriesRecordingHeaderRowPresenter(getContext());
170     }
171 
172     @Override
onCreateRowPresenter()173     public ScheduleRowPresenter onCreateRowPresenter() {
174         return new SeriesScheduleRowPresenter(getContext());
175     }
176 
177     @Override
onCreateRowsAdapter(ClassPresenterSelector presenterSelector)178     public ScheduleRowAdapter onCreateRowsAdapter(ClassPresenterSelector presenterSelector) {
179         return new SeriesScheduleRowAdapter(getContext(), presenterSelector, mSeriesRecording);
180     }
181 
182     @Override
getFirstItemPosition()183     protected int getFirstItemPosition() {
184         if (mSeriesRecording != null
185                 && mSeriesRecording.getState() == SeriesRecording.STATE_SERIES_STOPPED) {
186             return 0;
187         }
188         return super.getFirstItemPosition();
189     }
190 
executeProgramLoadingTask()191     private void executeProgramLoadingTask() {
192         if (mProgramLoadTask != null) {
193             mProgramLoadTask.cancel(true);
194         }
195         mProgramLoadTask = new EpisodicProgramLoadTask(getContext(), mSeriesRecording) {
196             @Override
197             protected void onPostExecute(List<Program> programs) {
198                 mPrograms = programs;
199                 onProgramsUpdated();
200             }
201         };
202         mProgramLoadTask.setLoadCurrentProgram(true)
203                 .setLoadDisallowedProgram(true)
204                 .setLoadScheduledEpisode(true)
205                 .setIgnoreChannelOption(true)
206                 .execute();
207     }
208 }