1 /* 2 * Copyright (C) 2015 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.menu; 18 19 import android.content.Context; 20 import android.graphics.Bitmap; 21 import android.support.annotation.Nullable; 22 import android.text.TextUtils; 23 import android.util.AttributeSet; 24 import android.util.Log; 25 import android.view.View; 26 import android.widget.ImageView; 27 import android.widget.ProgressBar; 28 import android.widget.TextView; 29 import com.android.tv.MainActivity; 30 import com.android.tv.R; 31 import com.android.tv.data.Program; 32 import com.android.tv.data.api.Channel; 33 import com.android.tv.parental.ParentalControlSettings; 34 import com.android.tv.util.images.ImageLoader; 35 import java.util.Objects; 36 37 /** A view to render channel card. */ 38 public class ChannelCardView extends BaseCardView<ChannelsRowItem> { 39 private static final String TAG = MenuView.TAG; 40 private static final boolean DEBUG = MenuView.DEBUG; 41 42 private final int mCardImageWidth; 43 private final int mCardImageHeight; 44 45 private ImageView mImageView; 46 private TextView mChannelNumberNameView; 47 private ProgressBar mProgressBar; 48 private Channel mChannel; 49 private Program mProgram; 50 private String mPosterArtUri; 51 private final MainActivity mMainActivity; 52 ChannelCardView(Context context)53 public ChannelCardView(Context context) { 54 this(context, null); 55 } 56 ChannelCardView(Context context, AttributeSet attrs)57 public ChannelCardView(Context context, AttributeSet attrs) { 58 this(context, attrs, 0); 59 } 60 ChannelCardView(Context context, AttributeSet attrs, int defStyle)61 public ChannelCardView(Context context, AttributeSet attrs, int defStyle) { 62 super(context, attrs, defStyle); 63 mCardImageWidth = getResources().getDimensionPixelSize(R.dimen.card_image_layout_width); 64 mCardImageHeight = getResources().getDimensionPixelSize(R.dimen.card_image_layout_height); 65 mMainActivity = (MainActivity) context; 66 } 67 68 @Override onFinishInflate()69 protected void onFinishInflate() { 70 super.onFinishInflate(); 71 mImageView = (ImageView) findViewById(R.id.image); 72 mImageView.setBackgroundResource(R.color.channel_card); 73 mChannelNumberNameView = (TextView) findViewById(R.id.channel_number_and_name); 74 mProgressBar = (ProgressBar) findViewById(R.id.progress); 75 } 76 77 @Override onBind(ChannelsRowItem item, boolean selected)78 public void onBind(ChannelsRowItem item, boolean selected) { 79 if (DEBUG) { 80 Log.d( 81 TAG, 82 "onBind(channelName=" 83 + item.getChannel().getDisplayName() 84 + ", selected=" 85 + selected 86 + ")"); 87 } 88 updateChannel(item); 89 updateProgram(); 90 super.onBind(item, selected); 91 } 92 updateChannel(ChannelsRowItem item)93 private void updateChannel(ChannelsRowItem item) { 94 if (!item.getChannel().equals(mChannel)) { 95 mChannel = item.getChannel(); 96 mChannelNumberNameView.setText(mChannel.getDisplayText()); 97 mChannelNumberNameView.setVisibility(VISIBLE); 98 } 99 } 100 updateProgram()101 private void updateProgram() { 102 ParentalControlSettings parental = mMainActivity.getParentalControlSettings(); 103 if (parental.isParentalControlsEnabled() && mChannel.isLocked()) { 104 setText(R.string.program_title_for_blocked_channel); 105 mProgram = null; 106 } else { 107 Program currentProgram = 108 mMainActivity.getProgramDataManager().getCurrentProgram(mChannel.getId()); 109 if (!Objects.equals(currentProgram, mProgram)) { 110 mProgram = currentProgram; 111 if (mProgram == null || TextUtils.isEmpty(mProgram.getTitle())) { 112 setTextViewEnabled(false); 113 setText(R.string.program_title_for_no_information); 114 } else { 115 setTextViewEnabled(true); 116 setText(mProgram.getTitle()); 117 } 118 } 119 } 120 if (mProgram == null) { 121 mProgressBar.setVisibility(GONE); 122 setPosterArt(null); 123 } else { 124 // Update progress. 125 mProgressBar.setVisibility(View.VISIBLE); 126 long startTime = mProgram.getStartTimeUtcMillis(); 127 long endTime = mProgram.getEndTimeUtcMillis(); 128 long currTime = System.currentTimeMillis(); 129 if (currTime <= startTime) { 130 mProgressBar.setProgress(0); 131 } else if (currTime >= endTime) { 132 mProgressBar.setProgress(100); 133 } else { 134 mProgressBar.setProgress( 135 (int) (100 * (currTime - startTime) / (endTime - startTime))); 136 } 137 // Update image. 138 if (!parental.isParentalControlsEnabled() 139 || !parental.isRatingBlocked(mProgram.getContentRatings())) { 140 setPosterArt(mProgram.getPosterArtUri()); 141 } 142 } 143 } 144 createProgramPosterArtCallback( ChannelCardView cardView, final Program program)145 private static ImageLoader.ImageLoaderCallback<ChannelCardView> createProgramPosterArtCallback( 146 ChannelCardView cardView, final Program program) { 147 return new ImageLoader.ImageLoaderCallback<ChannelCardView>(cardView) { 148 @Override 149 public void onBitmapLoaded(ChannelCardView cardView, @Nullable Bitmap posterArt) { 150 if (posterArt == null 151 || cardView.mProgram == null 152 || program.getChannelId() != cardView.mProgram.getChannelId() 153 || program.getChannelId() != cardView.mChannel.getId()) { 154 return; 155 } 156 cardView.updatePosterArt(posterArt); 157 } 158 }; 159 } 160 161 private void setPosterArt(String posterArtUri) { 162 if (!TextUtils.equals(mPosterArtUri, posterArtUri)) { 163 mPosterArtUri = posterArtUri; 164 if (posterArtUri == null 165 || !mProgram.loadPosterArt( 166 getContext(), 167 mCardImageWidth, 168 mCardImageHeight, 169 createProgramPosterArtCallback(this, mProgram))) { 170 mImageView.setImageResource(R.drawable.ic_recent_thumbnail_default); 171 mImageView.setForeground(null); 172 } 173 } 174 } 175 176 private void updatePosterArt(Bitmap posterArt) { 177 mImageView.setImageBitmap(posterArt); 178 mImageView.setForeground(getContext().getDrawable(R.drawable.card_image_gradient)); 179 } 180 } 181