When TimeBar scrubbed video change position accordingly in ExoPlayer - java

I'm using StyledPlayerView for controls. I want to implement that while user moves TimeBar video also change its position simultaneously(not after user stopped scrubbing).
I know that I can use TimeBar.OnScrubListener(), but I cannot find a way to implement that method to default StyledPlayerView. Is there a way to do that? Thanks.
public class ShowTutorialFragment extends Fragment {
private ExoPlayer player;
private NavController navController;
private ImageView imageViewClose;
private StyledPlayerView videoViewTutorial;
private boolean goBackLockScreen = false;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
Bundle bundle = getArguments();
if (bundle != null && bundle.getString("whereItCame") == "LockScreen")
goBackLockScreen = true;
return inflater.inflate(R.layout.fragment_show_tutorial, container, false);
}
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
initialize(view);
setListeners();
}
#Override
public void onPause() {
super.onPause();
player.pause();
}
private void initialize(View view) {
player = new ExoPlayer.Builder(requireContext()).build();
navController = Navigation.findNavController(view);
imageViewClose = view.findViewById(R.id.image_view_close_dialog);
videoViewTutorial = view.findViewById(R.id.video_view_tutorial);
playVideo();
}
private void playVideo() {
String path = "android.resource://" + getActivity().getPackageName() + "/" + R.raw.tutorial_video;
MediaItem mediaItem = MediaItem.fromUri(path);
videoViewTutorial.setPlayer(player); // Set the media item to be played.
videoViewTutorial.setShowPreviousButton(false);
videoViewTutorial.setShowNextButton(false);
player.setMediaItem(mediaItem); // Prepare the player.
player.prepare();
player.play();
Log.i("track", "playVideo: "+ player.getTrackSelector().toString());
/* setXButtonVisible();*/
}
private void setListeners() {
imageViewClose.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
player.release();
if (goBackLockScreen) {
navController.navigate(R.id.action_showTutorialFragment_to_lockScreenFragment);
} else navController.navigate(R.id.action_showTutorialFragment_to_mainMenu);
}
});
videoViewTutorial.setOnLongClickListener(new View.OnLongClickListener() {
#Override
public boolean onLongClick(View v) {
player.pause();
videoViewTutorial.hideController();
return false;
}
});
}
}
my xml code
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/layout_fl_container"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#color/black"
android:clickable="true"
android:focusable="true"
android:orientation="vertical"
tools:context="com.atgeotech.erpintel.views.tutorial.ShowTutorialFragment">
<FrameLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_gravity="center"
>
<com.google.android.exoplayer2.ui.StyledPlayerView
android:id="#+id/video_view_tutorial"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:longClickable="true"
app:show_buffering="when_playing"
app:show_shuffle_button="true"
app:surface_type="surface_view"
tools:ignore="SpeakableTextPresentCheck" />
<ImageView
android:id="#+id/image_view_close_dialog"
android:layout_width="35dp"
android:layout_height="35dp"
android:layout_gravity="end"
android:layout_margin="8dp"
android:background="#color/faded_black"
android:clickable="true"
android:focusable="true"
android:visibility="visible"
app:srcCompat="#drawable/ic_close_dialog"
tools:ignore="SpeakableTextPresentCheck" />
</FrameLayout>

Issue which I tried to explain is that if I want to change video position during scrubbing, I must use TimeBar.OnScrubListener.onScrubMove(). In order to use this, function must access to DefaultTimeBar inside StyledPlayerView, and I did not know how to do it, yet solution is easy.
I just need to add global DefaultTimeBar variable,
private DefaultTimeBar timeBar;
then initialize it through videoViewTutorial variable
timeBar = videoViewTutorial.findViewById(R.id.exo_progress);//Solution
then I just use the listener to achieve my desired result
timeBar.addListener(new TimeBar.OnScrubListener() { //Solution
#Override
public void onScrubStart(TimeBar timeBar, long position) {
}
#Override
public void onScrubMove(TimeBar timeBar, long position) {
player.seekTo(position);
}
#Override
public void onScrubStop(TimeBar timeBar, long position, boolean canceled) {
}
});

Related

Is it possible to create a recents screen like in android for the activities of my app

I am trying to make an Activity which will hold all the recents screen in my app not in the android device.
The idea it is to create the recents view like in android.
I do not have for the moment an idea how to do that. I have searched in the official site of android but didn't get what I want.
I have some activities which there is declared WebView and I want to take title, url and the view of that Url and to save to show at VisualHistory.
The design I am able to do I have achieved but I do not know how to show the recents screen or views.
The color of the background should based from url.
If someone don't understand something let me know.
Below you can find a photo which will show what I am trying to do, I have copied this photo from another app.
I have planned these steps to follow to achieve that.
In the Pojo.class and in db it is not defined the image which will be shown in the cardview because I do not know how to achieve that.
I want the background which for the moment in blue to be depended from the url color. Is it any way to get the color of the url ?
Create a POJO.class
Create a DB which will hold this data
Create an Adapter
Create a Fragment
I have a Log here which shows me the items.
[VisualHistoryItem{id=109, title='Wikipedia, the free encyclopedia', url='https://en.m.wikipedia.org/w/index.php?title=Main_Page'}, VisualHistoryItem{id=112, title='', url='https://mail.google.com/'}, VisualHistoryItem{id=113, title='Gmail – kostenloser Speicherplatz und E-Mails von Google', url='https://www.google.com/intl/de/gmail/about/#'}]
This saves a visual history item.
mVisualHistory.setUrl(url);
mVisualHistory.setTitle(view.getTitle());
Bitmap topass= getSnapshoot.takeScreenShot(BookmarkActivity.this);
try {
String filename = mVisualHistory.getId()+".png";
FileOutputStream stream = BookmarkActivity.this.openFileOutput(filename, Context.MODE_PRIVATE);
topass.compress(Bitmap.CompressFormat.PNG, 100, stream);
stream.close();
topass.recycle();
} catch (Exception e) {
e.printStackTrace();
}
mVisualRepository.insertNoteTask(mVisualHistory);
I have created an Activity code is below.
public class ActivityTabs extends AppCompatActivity implements View.OnClickListener {
private PopupMenu mPopupMenu;
private FrameLayout settings;
private FrameLayout frameLayout;
private LinearLayout linearLayout;
private ImageView incognito;
private TextView textOfHistory;
#RequiresApi(api = Build.VERSION_CODES.LOLLIPOP)
protected void onCreate(#Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_tabs);
findViewById(R.id.vgGoMain).setOnClickListener(this);
findViewById(R.id.vgAdd).setOnClickListener(this);
settings = findViewById(R.id.vgSettingsHis);
linearLayout = findViewById(R.id.layoutEmptyVisHistory);
settings.setOnClickListener(this);
textOfHistory = findViewById(R.id.tvEmptyHistory);
FragmentVisualHistoryVertical newFragment = new FragmentVisualHistoryVertical();
getSupportFragmentManager().beginTransaction().add(R.id.frameLayoutVisHistory, newFragment).commit();
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.frameLayoutVisHistory, newFragment)
.commit();
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.vgGoMain:
finish();
return;
case R.id.vgAdd:
Intent intent = new Intent(this, ActivitySearchEngine.class);
startActivity(intent);
finish();
return;
case R.id.vgSettingsHis:
showMenuSettings();
return;
default:
break;
}
}
public void showMenuSettings() {
mPopupMenu = new PopupMenu(this, settings);
final MenuInflater menuInflater = mPopupMenu.getMenuInflater();
menuInflater.inflate(R.menu.history_settings, mPopupMenu.getMenu());
mPopupMenu.show();
}
}
And this is the XML for this Activity.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#color/historyEmptyBack"
android:gravity="center_horizontal"
android:orientation="vertical">
<FrameLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<FrameLayout
android:id="#+id/frameLayoutVisHistory"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:paddingBottom="#dimen/bottomPanelHeight"></FrameLayout>
<LinearLayout
android:id="#+id/layoutEmptyVisHistory"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:visibility="gone">
<TextView
android:id="#+id/tvEmptyHistoryTitle"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:layout_marginTop="#dimen/common_24dp"
android:gravity="center_horizontal"
android:lineSpacingExtra="3.0sp"
android:text="#string/VHVEmptyTite"
android:textColor="#color/historyEmptyTitle"
android:textSize="22.0sp" />
<FrameLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_marginBottom="48.0dip"
android:layout_weight="1.0">
<LinearLayout
android:id="#+id/horizontalEmpty"
style="#style/LayoutEmptySmile"
android:layout_width="#dimen/visual_history_element_width"
android:layout_height="#dimen/visual_history_element_height"
android:orientation="vertical">
<ImageView
style="#style/EmptyHistorySmile"
android:src="#drawable/vh_smile_gray" />
<TextView
style="#style/EmptyHistoryText"
android:layout_marginTop="#dimen/common_16dp"
android:gravity="center_horizontal"
android:paddingLeft="#dimen/common_16dp"
android:paddingRight="#dimen/common_16dp"
android:text="#string/VHVEmptyDesc" />
</LinearLayout>
<LinearLayout
android:id="#+id/verticalEmpty"
style="#style/LayoutEmptySmile"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginLeft="#dimen/common_24dp"
android:layout_marginRight="#dimen/common_24dp"
android:orientation="horizontal"
android:paddingLeft="#dimen/common_16dp"
android:paddingTop="#dimen/common_16dp"
android:paddingRight="#dimen/common_16dp"
android:paddingBottom="#dimen/common_16dp">
<ImageView
style="#style/EmptyHistorySmile"
android:src="#drawable/vh_smile_gray" />
<TextView
style="#style/EmptyHistoryText"
android:layout_width="wrap_content"
android:gravity="left"
android:paddingLeft="#dimen/common_16dp"
android:text="#string/VHVEmptyDesc" />
</LinearLayout>
<LinearLayout
android:id="#+id/layoutIncognito"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:paddingBottom="#dimen/bottomPanelHeight"
android:visibility="visible">
<LinearLayout
android:id="#+id/layoutEmptyDesc"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_marginTop="#dimen/common_16dp"
android:gravity="center"
android:orientation="vertical">
<ImageView
android:id="#+id/ivEmptyHistory"
android:layout_width="#dimen/history_private"
android:layout_height="#dimen/history_private"
android:src="#drawable/incognito_icon_history" />
<TextView
android:id="#+id/tvEmptyHistory"
style="#style/EmptyHistoryText"
android:layout_marginTop="#dimen/common_16dp"
android:gravity="center_horizontal"
android:paddingLeft="#dimen/common_16dp"
android:paddingRight="#dimen/common_16dp"
android:text="#string/SVSearchPrivateMode"
android:textColor="#color/historyTextColor"
android:textSize="#dimen/common_18sp" />
</LinearLayout>
</LinearLayout>
</FrameLayout>
</LinearLayout>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:background="#color/historyEmptyBack"
android:gravity="bottom"
android:orientation="vertical"
android:paddingLeft="2.0dip"
android:paddingRight="2.0dip">
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="center_vertical"
android:orientation="horizontal">
<LinearLayout style="#style/VisHistoryMenuSideLayout">
<FrameLayout
android:id="#+id/vgGoMain"
style="#style/VisHistoryFrLayoutMenu"
android:paddingRight="14.0dip">
<TextView
style="#style/VisHistoryTvMenu"
android:text="#string/VHVHomeBarButtonItemTitle" />
</FrameLayout>
<View style="#style/VisHistoryEmptyView" />
</LinearLayout>
<FrameLayout
android:id="#+id/vgAdd"
style="#style/VisHistoryFrLayoutMenu">
<ImageView
style="#style/VisHistoryMenuIv"
android:scaleX="0.8"
android:scaleY="0.8"
android:src="#drawable/newtab_button" />
</FrameLayout>
<LinearLayout style="#style/VisHistoryMenuSideLayout">
<View style="#style/VisHistoryEmptyView" />
<FrameLayout
android:id="#+id/vgTrash"
style="#style/VisHistoryFrLayoutMenu">
<ImageView
style="#style/VisHistoryMenuIv"
android:scaleX="1.3"
android:scaleY="1.3"
android:src="#drawable/trash" />
</FrameLayout>
<View style="#style/VisHistoryEmptyView" />
<FrameLayout
android:id="#+id/vgSettingsHis"
style="#style/VisHistoryFrLayoutMenu"
android:paddingLeft="0.0dip"
android:paddingRight="0.0dip">
<android.support.v7.widget.AppCompatImageView
style="#style/VisHistoryMenuIv"
android:layout_gravity="right"
app:srcCompat="#drawable/ic_dots_vertical"
tools:ignore="VectorDrawableCompat" />
</FrameLayout>
</LinearLayout>
</LinearLayout>
</LinearLayout>
</FrameLayout>
</LinearLayout>
This is another Fragment
Here will show of the list
public class FragmentVisualHistoryVertical extends FragmentVisualHistory implements VisualRecyclerAdapter.OnVisualHistoryItemListener {
public View paramView;
private VisualRecyclerAdapter mVisualHistoryRecyclerAdapter;
private RecyclerView mRecyclerView;
private VisualHistoryRepository getmNoteRepository;
private ArrayList<VisualHistoryItem> mVisualHistoryItems = new ArrayList<>();
#Override
public void onAttach(Context context) {
super.onAttach(context);
mContext = context;
}
#Nullable
#Override
public View onCreateView(#NonNull LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
paramView = inflater.inflate(R.layout.fragment_vis_history_vertical, container, false);
mRecyclerView = paramView.findViewById(R.id.rvWebHistory);
initRecyclerView();
getmNoteRepository = new VisualHistoryRepository(getActivity());
retrieveVisualHistory();
return paramView;
}
private void initRecyclerView(){
LinearLayoutManager linearLayoutManager = new LinearLayoutManager(getActivity());
mRecyclerView.setLayoutManager(linearLayoutManager);
linearLayoutManager.setReverseLayout(true);
new ItemTouchHelper(itemTouchHelperCallback).attachToRecyclerView(mRecyclerView);
mVisualHistoryRecyclerAdapter = new VisualRecyclerAdapter(mVisualHistoryItems, this, mContext);
DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(mRecyclerView.getContext(),
linearLayoutManager.getOrientation());
mRecyclerView.addItemDecoration(dividerItemDecoration);
mRecyclerView.setAdapter(mVisualHistoryRecyclerAdapter);
}
private void retrieveVisualHistory() {
getmNoteRepository.retrieveVisualHistoryTask().observe(this, new Observer<List<VisualHistoryItem>>() {
#Override
public void onChanged(#Nullable List<VisualHistoryItem> item) {
if(mVisualHistoryItems.size() > 0){
mVisualHistoryItems.clear();
}
if(item != null){
mVisualHistoryItems.addAll(item);
}
mVisualHistoryRecyclerAdapter.notifyDataSetChanged();
}
});
}
#Override
public void onItemClicked(int position) {
}
private void deleteNote(VisualHistoryItem item) {
mVisualHistoryItems.remove(item);
mVisualHistoryRecyclerAdapter.notifyDataSetChanged();
getmNoteRepository.deleteVisualHistoryTask(item);
}
ItemTouchHelper.SimpleCallback itemTouchHelperCallback = new ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.RIGHT) {
#Override
public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
return false;
}
#Override
public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) {
deleteNote(mVisualHistoryItems.get(viewHolder.getAdapterPosition()));
}
};
}
This is the XML.
<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.RecyclerView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:aapt="http://schemas.android.com/aapt" android:id="#+id/rvWebHistory" android:layout_width="match_parent" android:layout_height="match_parent"/>
This is the room db
#Database(entities = {VisualHistoryItem.class}, version = 1)
public abstract class VisualHistoryDB extends RoomDatabase {
private static final String DATABASE_NAME = "visualHistory_db";
private static VisualHistoryDB instance;
public static VisualHistoryDB getInstance(final Context context) {
if (instance == null) {
instance = Room.databaseBuilder(
context.getApplicationContext(),
VisualHistoryDB.class,
DATABASE_NAME
).build();
}
return instance;
}
public abstract VisualHistoryDao getVisualHistoryDao();
}
The room db Dao
#Dao
public interface VisualHistoryDao {
#Insert
long[] insertVisualHistory(VisualHistoryItem... visualHistoryItems);
#Query("SELECT * FROM visualHistory")
LiveData<List<VisualHistoryItem>> getVisualHistory();
#Delete
int delete(VisualHistoryItem... visualHistoryItems);
}
This is the pojo.class
#Entity(tableName = "visualHistory")
public class VisualHistoryItem implements Parcelable {
#PrimaryKey(autoGenerate = true)
private int id;
#ColumnInfo(name = "title")
private String title;
#ColumnInfo(name = "url")
private String url;
public VisualHistoryItem(int id, String title, String url) {
this.id = id;
this.title = title;
this.url = url;
}
#Ignore
public VisualHistoryItem() {
}
protected VisualHistoryItem(Parcel in) {
id = in.readInt();
title = in.readString();
url = in.readString();
}
public static final Creator<VisualHistoryItem> CREATOR = new Creator<VisualHistoryItem>() {
#Override
public VisualHistoryItem createFromParcel(Parcel in) {
return new VisualHistoryItem(in);
}
#Override
public VisualHistoryItem[] newArray(int size) {
return new VisualHistoryItem[size];
}
};
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
#Override
public String toString() {
return "VisualHistoryItem{" +
"id=" + id +
", title='" + title + '\'' +
", url='" + url + '\'' +
'}';
}
#Override
public int describeContents() {
return 0;
}
#Override
public void writeToParcel(Parcel parcel, int flags) {
parcel.writeInt(id);
parcel.writeString(title);
parcel.writeString(url);
}
}
And this is the Adapter.
public class VisualRecyclerAdapter extends RecyclerView.Adapter<VisualRecyclerAdapter.ViewHolder> {
private ArrayList<VisualHistoryItem> mVisualHistoryItem = new ArrayList<>();
private OnVisualHistoryItemListener mItemListener;
private final Context context;
public VisualRecyclerAdapter(ArrayList<VisualHistoryItem> mVisualHistoryItem, OnVisualHistoryItemListener mItemListener, Context context) {
this.context = context;
this.mVisualHistoryItem = mVisualHistoryItem;
this.mItemListener = mItemListener;
}
#NonNull
#Override
public ViewHolder onCreateViewHolder(#NonNull ViewGroup viewGroup, int i) {
View view = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.fragment_visual_history, viewGroup, false);
return new ViewHolder(view, mItemListener);
}
#Override
public void onBindViewHolder(#NonNull ViewHolder viewHolder, int i) {
Resources res = viewHolder.itemView.getContext().getResources();
viewHolder.visFragmentMain.setBackgroundColor(res.getColor(R.color.blue_text));
viewHolder.tvPageUrl.setText(mVisualHistoryItem.get(i).getUrl());
viewHolder.tvPageName.setText(mVisualHistoryItem.get(i).getTitle());
Bitmap bmp = null;
String filename = mVisualHistoryItem.get(i).getId()+".png";
try {
FileInputStream is = context.openFileInput(filename);
bmp = BitmapFactory.decodeStream(is);
is.close();
} catch (Exception e) {
e.printStackTrace();
}
if (bmp!=null) {
BitmapDrawable ob = new BitmapDrawable(context.getResources(), bmp);
viewHolder.ivVisualHistory.setBackground(ob);
}
}
#Override
public int getItemCount() {
return mVisualHistoryItem.size();
}
public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
ImageView ivVisualHistory;
OnVisualHistoryItemListener itemListener;
TextView tvPageName, tvPageUrl;
RelativeLayout visFragmentMain;
CardView cardView;
public ViewHolder(#NonNull View itemView, OnVisualHistoryItemListener mItemListener) {
super(itemView);
itemListener = mItemListener;
ivVisualHistory = itemView.findViewById(R.id.ivVisualHistory);
visFragmentMain = itemView.findViewById(R.id.visFragmentMain);
tvPageName = itemView.findViewById(R.id.tvPageName);
tvPageUrl = itemView.findViewById(R.id.tvPageUrl);
cardView = itemView.findViewById(R.id.cardView);
}
#Override
public void onClick(View v) {
itemListener.onItemClicked(getAdapterPosition());
}
}
public interface OnVisualHistoryItemListener {
void onItemClicked(int position);
}
}
This is what I am trying to achieve.
This is my actual view.
Well you can get the favicon of the website and use the Palette class of android explained here to get the prominent color of the url and if you want to get the snapshot you can save the snapshot and save instance data before launching another activity. To take snapshot you can use takesnapshot meathod after creating util class, code as follows:
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.Rect;
import android.view.View;
class Util {
static Bitmap takeScreenShot(Activity activity) {
View view = activity.getWindow().getDecorView();
view.setDrawingCacheEnabled(true);
view.buildDrawingCache();
Bitmap b1 = view.getDrawingCache();
Rect frame = new Rect();
activity.getWindow().getDecorView().getWindowVisibleDisplayFrame(frame);
int statusBarHeight = frame.top;
//Find the screen dimensions to create bitmap in the same size.
int width = activity.getWindowManager().getDefaultDisplay().getWidth();
int height = activity.getWindowManager().getDefaultDisplay().getHeight();
Bitmap b = Bitmap.createBitmap(b1, 0, statusBarHeight, width, height - statusBarHeight);
view.destroyDrawingCache();
return b;
}
}
in your activity use it to save it to png file as follows:
Bitmap topass=Util.takeScreenShot(this);
try {
//Write file
String filename = "bitmap.png";
FileOutputStream stream = this.openFileOutput(filename, Context.MODE_PRIVATE);
topass.compress(Bitmap.CompressFormat.PNG, 100, stream);
//Cleanup
stream.close();
topass.recycle();
} catch (Exception e) {
e.printStackTrace();
}
Instead of using name "bitmap.png" use your "id.png"(String.valueof(id)+".png") as you have put int "id" name in your db. You can save screenshot of every activity with its id and whenever you build the cardview of it, show the screenshot by the name of "id.png". To show screenshot, you can use
Bitmap bmp = null;
String filename = String.valueof(getId())+".png";
try {
FileInputStream is = this.openFileInput(filename);
bmp = BitmapFactory.decodeStream(is);
is.close();
} catch (Exception e) {
e.printStackTrace();
}
if(bmp!=null)
{
ConstraintLayout cl =findViewById(R.id.shopbk); //it can be your any view
BitmapDrawable ob = new BitmapDrawable(getResources(), bmp);
cl.setBackground(ob); /* you should use glide here to show bitmap drawable as your preview will be very small as compared to screenshot actual size*/
}
and as far as getting the color (you said the link is not working) is concerned you can get firstly the bitmap using
try {
URL url = new URL("http://..somepath url../favicon.ico");
Bitmap image = BitmapFactory.decodeStream(url.openConnection().getInputStream());
} catch(IOException e) {
System.out.println(e);
}
and then use palette to extract the color using
Palette.generateAsync(image, new Palette.PaletteAsyncListener() {
public void onGenerated(Palette palette) {
// Do something with colors...
}
});
for this you will need to implement one dependancy
dependencies {
...
compile 'com.android.support:palette-v7:21.0.+'
}

Show empty view when data set is empty in recyclerview

I have a recyclerview which shows multiple cardviews with items. In the recyclerview, I have a popup menu to delete that current cardview.
When the dataset is empty I would like to show an empty view. Something with an image and text saying "empty" I have tried some online examples. No success.
My layout is a cardview(card_view_row.xml) is a simple view with a cardview that shows a few items.
Here is my recyclerview
public class AlarmRecyclerViewAdapter extends
RecyclerView.Adapter<AlarmRecyclerViewAdapter.DataObjectHolder> {
private ArrayList<Alarm> mDataset;
private static AlarmRecyclerViewAdapter.MyClickListener myClickListener;
private AlarmDataAccess dataAccess;
private Alarm alarm;
private int switchOn = 1;
private int switchOff = 0;
private static Context context;
private PopupMenu popupMenu;
public static class DataObjectHolder extends RecyclerView.ViewHolder
implements View
.OnClickListener {
TextView label;
TextView dateTime;
TextView label2;
TextView textViewLabel;
TextView gender;
TextView daysofweek;
Switch aSwitch;
ImageView trash;
public DataObjectHolder(View itemView) {
super(itemView);
dateTime = (TextView) itemView.findViewById(R.id.textView2);
label = (TextView) itemView.findViewById(R.id.textView);
label2 =(TextView) itemView.findViewById(R.id.textView3);
aSwitch = (Switch)itemView.findViewById(R.id.switchButton);
trash = (ImageView)itemView.findViewById(R.id.imageTrash);
gender = (TextView)itemView.findViewById(R.id.textViewGender);
daysofweek = (TextView)itemView.findViewById(R.id.textViewDays);
textViewLabel = (TextView)itemView.findViewById(R.id.textViewLabel);
itemView.setOnClickListener(this);
}
#Override
public void onClick(View v) {
myClickListener.onItemClick(getAdapterPosition(), v);
}
}
public void setOnItemClickListener(AlarmRecyclerViewAdapter.MyClickListener myClickListener) {
this.myClickListener = myClickListener;
}
public AlarmRecyclerViewAdapter(ArrayList<Alarm> myDataset, Context context2) {
mDataset = myDataset;
context = context2;
}
#Override
public AlarmRecyclerViewAdapter.DataObjectHolder onCreateViewHolder(ViewGroup parent,
int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.card_view_row, parent, false);
AlarmRecyclerViewAdapter.DataObjectHolder dataObjectHolder = new AlarmRecyclerViewAdapter.DataObjectHolder(view);
return dataObjectHolder;
}
#Override
public void onBindViewHolder(final AlarmRecyclerViewAdapter.DataObjectHolder holder, final int position) {
boolean status = false;
int gender;
alarm = new Alarm();
dataAccess = new AlarmDataAccess(context);
dataAccess.open();
holder.label.setText(mDataset.get(position).getHourOfDay() + ":" + mDataset.get(position).getMinute() + " " + mDataset.get(position).getTimeSet());
holder.textViewLabel.setText(mDataset.get(position).getLabel());
gender = mDataset.get(position).getGender();
if(gender == 0){
holder.gender.setText("Male voice");
}else{
holder.gender.setText("Female voice");
}
holder.daysofweek.setText(mDataset.get(position).getDays());
holder.label2.setText("" + mDataset.get(position).getAffirmationName());
holder.trash.setImageResource(R.drawable.menu2);
if( mDataset.get(position).getStatus() == 0){
status = false;
}else {
status = true;
}
holder.aSwitch.setChecked(status);
holder.aSwitch.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
#Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
if (buttonView.isPressed()) {
if (isChecked) {
mDataset.get(position).setStatus(switchOn);
} else {
mDataset.get(position).setStatus(switchOff);
}
alarm.setId(mDataset.get(position).getId());
alarm.setStatus(mDataset.get(position).getStatus());
dataAccess.updateStatus(alarm);
}
}
});
holder.trash.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
popupMenu = new PopupMenu(AlarmRecyclerViewAdapter.context, v);
popupMenu.inflate(R.menu.popup_menu);
popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
#Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.edit:
long selectedAlarmId = mDataset.get(position).getId();
Intent intent = new Intent(AlarmRecyclerViewAdapter.context, EditAlarmActivity.class);
intent.putExtra("id", selectedAlarmId);
intent.putExtra("Edit", "FromEdit");
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK|Intent.FLAG_ACTIVITY_NEW_TASK);
AlarmRecyclerViewAdapter.context.startActivity(intent);
return true;
case R.id.delete:
long id = mDataset.get(position).getId();
mDataset.remove(position);
notifyItemRemoved(position);
notifyItemRangeChanged(position, mDataset.size());
dataAccess.deleteAlarm(id);
return true;
}
return false;
}
});
popupMenu.show();
}
});
}
public void deleteItem(int index) {
mDataset.remove(index);
notifyItemRemoved(index);
}
#Override
public int getItemCount() {
return mDataset.size();
}
}
My recyclerview is inside a fragment view
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/fragment_place">
<ImageButton
android:id="#+id/add_button"
android:layout_width="48dp"
android:layout_height="48dp"
android:layout_gravity="end|bottom"
android:tint="#color/icon"
android:elevation="12dp"
android:background="#drawable/oval_ripple"
tools:backgroundTint="#96ceb4"
android:src="#android:drawable/ic_input_add"
android:layout_alignParentTop="true"
android:layout_alignParentStart="true"
android:layout_marginStart="12dp"
android:layout_marginTop="14dp" />
<android.support.v7.widget.RecyclerView
android:id="#+id/my_recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:scrollbars="vertical"
android:layout_below="#+id/add_button"
android:layout_centerHorizontal="true"
android:layout_marginTop="16dp" />
</RelativeLayout>
Is there a way to detect if the data set is empty to show an empty view with text saying empty or something? I need this done inside recyclerview since I am deleting items inside there.
EDIT
I finally figured out how to do it. I am posting this incase anyone else has the same problem.
http://akbaribrahim.com/empty-view-for-androids-recyclerview/
For my personal use I use this trick :
I use two LinearLayout, one with my RecyclerView and another with a simple TextView saying "Empty". Both are in the same parent view.
<LinearLayout
android:id="#+id/linearContent"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:visibility="invisible">
<android.support.v7.widget.RecyclerView
android:id="#+id/my_recycler_view"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:scrollbars="vertical" />
</LinearLayout>
<LinearLayout
android:id="#+id/linearEmpty"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:id="#+id/textEmpty"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_marginTop="30dp"
android:text="#string/dialog_no_result"
android:textColor="#color/cardview_dark_background" />
</LinearLayout>
And when I update my list of item I call this method :
if (linearContent != null && linearEmpty != null) {
if (mListItems.isEmpty()) {
linearContent.setVisibility(View.GONE);
linearEmpty.setVisibility(View.VISIBLE);
textEmpty.setVisibility(View.VISIBLE);
} else {
linearContent.setVisibility(View.VISIBLE);
linearEmpty.setVisibility(View.GONE);
textEmpty.setVisibility(View.GONE);
}
}
Then I use the same layout, but just change the visibility of some objects.
Hope it help.

Android fragments strangely disappears when tag is set

I've two types of Fragment in PageView. The first one is TextFragment containing TextView and having set tag on it. The other ones are ImageFragments containing ImageView and having no tag. Images are loaded asynchronously from asset folder.
The problem is that the second (and sometimes also some other) fragment does not show the content or the content appears just for a while and then disappears. When I remove/comment the line where the tag is set, everything starts to work perfectly.
Do you know how to have the fragment appear correctly even with the tag set?
Here is the code (using appcompat). Keep in mind that the tag is needed (in my app) although it's not queried here in the code.
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/activity_main"
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="example.com.testfragment.MainActivity">
<android.support.v4.view.ViewPager
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/core_pager"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</RelativeLayout>
MainActivity.java
public class MainActivity extends AppCompatActivity {
private static final String TEXTFR_TAG = "TEXTFR_TAG";
static final String MYDATAFOLDER = "mydata";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ViewPager viewPager = (ViewPager) findViewById(R.id.core_pager);
final String[] imgs = getImages();
viewPager.setAdapter(new FragmentStatePagerAdapter(getSupportFragmentManager()) {
#Override
public int getCount() {
return imgs.length + 1;
}
#Override
public Fragment getItem(int position) {
switch (position) {
case 0:
return TextFragment.newInstance(getSupportFragmentManager(), TEXTFR_TAG);
default:
return ImageFragment.newInstance(imgs[position - 1]);
}
}
});
}
private String[] getImages() {
try {
return this.getAssets().list(MYDATAFOLDER);
} catch (IOException e) {
return new String[0];
}
}
}
fragment_text.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#android:color/darker_gray">
<TextView android:layout_width="match_parent" android:layout_height="match_parent"
android:id="#+id/textfragment_textview"/>
</LinearLayout>
TextFragment.java
public class TextFragment extends Fragment {
public TextFragment() {
}
static TextFragment newInstance(FragmentManager fragmentManager, String tag) {
TextFragment instance = new TextFragment();
fragmentManager
.beginTransaction()
.replace(R.id.core_pager, instance, tag) // <--- REMOVING THIS FIXES THE PROBLEM
.commit();
return instance;
}
#Override
public View onCreateView(final LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View root = inflater.inflate(R.layout.fragment_text, container, false);
((TextView)root.findViewById(R.id.textfragment_textview)).setText("SOME TEXT");
return root;
}
}
fragment_image.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#android:color/white">
<ImageView android:layout_width="match_parent" android:layout_height="match_parent"
android:id="#+id/imagefragment_imageview"/>
</LinearLayout>
ImageFragment.java
public class ImageFragment extends Fragment {
private static final String ARG_IMG = "ARG_IMG";
public ImageFragment() {
}
static ImageFragment newInstance(String imagePath) {
ImageFragment instance = new ImageFragment();
Bundle args = new Bundle();
args.putString(ARG_IMG, imagePath);
instance.setArguments(args);
return instance;
}
#Override
public View onCreateView(final LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_image, container, false);
}
#Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
if(view == null) {
return;
}
final Bundle args = getArguments();
final ImageView iv = (ImageView) view.findViewById(R.id.imagefragment_imageview);
new AsyncTask<Void, Void, Drawable>() {
#Override
protected Drawable doInBackground(Void... voids) {
String imgFile = args.getString(ARG_IMG);
try {
Context context = getContext().getApplicationContext();
return Drawable.createFromStream(context.getAssets().open(MainActivity.MYDATAFOLDER + '/' + imgFile), null);
} catch (Exception e) {
Log.e("MyAPP", "Error: ", e);
}
return null;
}
#Override
protected void onPostExecute(Drawable drawable) {
if(drawable != null) {
iv.setImageDrawable(drawable);
} else {
Log.d("MyAPP", "No drawable");
}
}
}.execute();
}
}

Can't see any entry in RecyclerView

I've created a RecyclerView in Android Studio like in an other fragment. The problem is that all is working for the first look but after creating a row object and stating the app I can't see any entries. I've did this RecyclerView the the same way as my old one which works great.. I've searched a lot but I can find the error.
This is my fragment xml:
<android.support.v4.widget.SwipeRefreshLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/training_swiperefresh"
android:layout_width="match_parent"
android:layout_height="match_parent">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="#+id/trainingtTitle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:layout_marginTop="0dp"
android:layout_marginBottom="16dp"
android:textStyle="bold"
android:textColor="#color/colorPrimary"
android:text="#string/trainingTitle" />
<android.support.v7.widget.RecyclerView
android:id="#+id/training_recycler_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:scrollbars="vertical"
android:layout_below="#+id/trainingtTitle" />
</RelativeLayout>
</android.support.v4.widget.SwipeRefreshLayout>
This is the row-layout for the RecyclerView:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content"
android:layout_width="match_parent"
android:focusable="true"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:clickable="true"
android:background="?android:attr/selectableItemBackground"
android:orientation="vertical">
<!-- Plan icon -->
<ImageView
android:id="#+id/planImage"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_centerVertical="true"
android:layout_alignParentStart="true"
android:layout_marginRight="8dp"
android:layout_marginTop="1dp"
android:layout_marginBottom="1dp"
android:contentDescription="Icon"
android:src="#drawable/ic_menu_train" />
<!-- Plan title -->
<TextView
android:id="#+id/planTitle"
android:textColor="#color/colorBlack"
android:layout_width="match_parent"
android:layout_marginLeft="40dp"
android:layout_marginRight="40dp"
android:layout_marginTop="14dp"
android:textSize="16dp"
android:layout_height="wrap_content" />
<!-- Plan type -->
<TextView
android:id="#+id/planType"
android:layout_below="#id/planTitle"
android:layout_marginLeft="40dp"
android:layout_marginRight="40dp"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<!-- Plan date -->
<TextView
android:id="#+id/planDate"
android:layout_width="match_parent"
android:layout_below="#id/planType"
android:layout_marginLeft="42dp"
android:layout_marginRight="40dp"
android:layout_marginBottom="14dp"
android:layout_height="wrap_content" />
<!-- Plan view -->
<ImageView
android:id="#+id/planView"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_alignParentEnd="true"
android:layout_centerVertical="true"
android:layout_marginTop="1dp"
android:layout_marginBottom="1dp"
android:contentDescription="Icon"
android:src="#drawable/ic_menu_show" />
<View
android:layout_width="fill_parent"
android:layout_height="1dip"
android:layout_below="#id/planDate"
android:layout_marginLeft="42dp"
android:background="#DCDCDC" />
</RelativeLayout>
This is my Fragment where I call the Adapter:
public class TrainingFragment extends Fragment {
private OnFragmentInteractionListener mListener;
// Variables for Recycler View
private List<Plans> planList = new ArrayList<>();
private RecyclerView trainingRecyclerView;
private PlansAdapter pAdapter;
public TrainingFragment() {
// Required empty public constructor
}
//Change the title in action bar
public void onResume() {
super.onResume();
String titleString = getResources().getString(R.string.title_activity_navigation_drawer_training);
// Set title bar
((NavigationDrawerActivity) getActivity())
.setActionBarTitle(titleString);
}
public static TrainingFragment newInstance() {
TrainingFragment fragment = new TrainingFragment();
return fragment;
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// Menü bekannt geben, dadurch kann Fragment Menü-Events verarbeiten
setHasOptionsMenu(true);
}
//Fragment XML geben, sowie als Menü setzen
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.menu.menu_training, menu);
// Declare ImageView and Animation for rotation animation
MenuItem reloadButton = (MenuItem) menu.findItem(R.id.menu_reloadbutton);
final Animation rotation = AnimationUtils.loadAnimation(getActivity(), R.anim.animation_rotate);
//if (reloadButton != null) {
// //reloadButton.setImageResource(R.drawable.ic_menu_reloadentry);
// reloadButton.getActionView().setOnClickListener(new View.OnClickListener() {
// #Override
// public void onClick(View view) {
// rotation.setRepeatCount(Animation.INFINITE);
// view.startAnimation(rotation);
// }
// });
//}
}
//AddEntry click abfangen und verarbeiten
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Wir prüfen, ob Menü-Element mit der ID "action_daten_aktualisieren"
// ausgewählt wurde und geben eine Meldung aus
int id = item.getItemId();
if (id == R.id.menu_reloadbutton) {
// Text ausgeben
//Toast.makeText(getActivity(), "Liste aktualisieren gedrückt!", Toast.LENGTH_LONG).show();
return true;
}
return super.onOptionsItemSelected(item);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View view = inflater.inflate(R.layout.fragment_training, container, false);
// Get Refresh Layout
SwipeRefreshLayout swipeRefreshLayout = (SwipeRefreshLayout) view.findViewById(R.id.training_swiperefresh);
// Change color for the refresh layout
swipeRefreshLayout.setColorSchemeColors(Color.rgb(99, 195, 195));
trainingRecyclerView = (RecyclerView) view.findViewById(R.id.training_recycler_view);
pAdapter = new PlansAdapter(planList, getContext());
RecyclerView.LayoutManager pLayoutManager = new LinearLayoutManager(getActivity().getApplicationContext());
trainingRecyclerView.setLayoutManager(pLayoutManager);
trainingRecyclerView.setItemAnimator(new DefaultItemAnimator());
trainingRecyclerView.setAdapter(pAdapter);
preparePlansData();
return view;
}
private void preparePlansData() {
// Set plan data
Plans plan = new Plans("ABC-Bestellung", "Muskelaufbau", "Datum: 21.04.1997");
// Add Object to list
planList.add(plan);
plan = new Plans("test", "tttt", "ttttt");
planList.add(plan);
// Notify data changes
pAdapter.notifyDataSetChanged();
}
// TODO: Rename method, update argument and hook method into UI event
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
#Override
public void onAttach(Context context) {
super.onAttach(context);
}
#Override
public void onStart() {
super.onStart();
try {
mListener = (OnFragmentInteractionListener) getActivity();
} catch (ClassCastException e) {
throw new ClassCastException(getActivity().toString()
+ " must implement OnFragmentInteractionListener");
}
}
#Override
public void onDetach() {
super.onDetach();
mListener = null;
}
/**
* This interface must be implemented by activities that contain this
* fragment to allow an interaction in this fragment to be communicated
* to the activity and potentially other fragments contained in that
* activity.
* <p>
* See the Android Training lesson <a href=
* "http://developer.android.com/training/basics/fragments/communicating.html"
* >Communicating with Other Fragments</a> for more information.
*/
public interface OnFragmentInteractionListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
}
This is my Adapter:
public class PlansAdapter extends RecyclerView.Adapter<PlansAdapter.MyPlanHolder> {
private List<Plans> planList;
private final Context customContext;
public class MyPlanHolder extends RecyclerView.ViewHolder {
public TextView planTitle, planType, planDate;
public MyPlanHolder(View view) {
super(view);
planTitle = (TextView) view.findViewById(R.id.planTitle);
planType = (TextView) view.findViewById(R.id.planType);
planDate = (TextView) view.findViewById(R.id.planDate);
}
}
public PlansAdapter(List<Plans> planList, Context customContext) {
this.planList = planList;
this.customContext = customContext;
}
#Override
public MyPlanHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.plans_list_row, parent, false);
return new MyPlanHolder(itemView);
}
#Override
public void onBindViewHolder(MyPlanHolder holder, int position) {
final Plans plan = planList.get(position);
holder.planTitle.setText(plan.getPlanTitle());
holder.planType.setText(plan.getPlanType());
holder.planDate.setText(plan.getPlanDate());
}
#Override
public int getItemCount() {
return 0;
}
}
And finaly my object class for the elements:
public class Plans {
private String planTitle, planType, planDate;
public Plans(String planTitle, String planType, String planDate) {
this.planTitle = planTitle;
this.planType = planType;
this.planDate = planDate;
}
public void setPlanTitle(String planTitle) {
this.planTitle = planTitle;
}
public String getPlanTitle() {
return planTitle;
}
public void setPlanType(String planType) {
this.planType = planType;
}
public String getPlanType() {
return planType;
}
public void setPlanDate(String planDate) {
this.planDate = planDate;
}
public String getPlanDate() {
return planDate;
}
}
I hope that you can find the issue.
Inside Adapter's getItemCount() method you are returning 0 as size of list.You should change it as return planList.size()
Your code is fine except in your adapter you are returning 0 in getItemCount() method.
Here's the updated code :
public class PlansAdapter extends RecyclerView.Adapter<PlansAdapter.MyPlanHolder> {
private List<Plans> planList;
private final Context customContext;
public class MyPlanHolder extends RecyclerView.ViewHolder {
public TextView planTitle, planType, planDate;
public MyPlanHolder(View view) {
super(view);
planTitle = (TextView) view.findViewById(R.id.planTitle);
planType = (TextView) view.findViewById(R.id.planType);
planDate = (TextView) view.findViewById(R.id.planDate);
}
}
public PlansAdapter(List<Plans> planList, Context customContext) {
this.planList = planList;
this.customContext = customContext;
}
#Override
public MyPlanHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View itemView = LayoutInflater.from(parent.getContext())
.inflate(R.layout.plans_list_row, parent, false);
return new MyPlanHolder(itemView);
}
#Override
public void onBindViewHolder(MyPlanHolder holder, int position) {
final Plans plan = planList.get(position);
holder.planTitle.setText(plan.getPlanTitle());
holder.planType.setText(plan.getPlanType());
holder.planDate.setText(plan.getPlanDate());
}
#Override
public int getItemCount() {
return planList.size();
}
}

FrameLayout does not match_parent

I am using fragNav and bottombar plugin. I am trying to make a fullscreen fragment through a FrameLayout. By default, those plugins came with an actionBar which i delete in my theme with "Theme.AppCompat.Light.NoActionBar". But Once i did this there is still a white bar on top on my screen. When i look at hierarchyView it appears that my FrameLayout is not matching the parent but all my xml are setup with match_parent width and height..
MainActivity.java
public class MainActivity extends AppCompatActivity {
private BottomBar mBottomBar;
private FragNavController fragNavController;
private final int TAB_FIRST = FragNavController.TAB1;
private final int TAB_SECOND = FragNavController.TAB2;
private final int TAB_THIRD = FragNavController.TAB3;
private final int TAB_FOURTH = FragNavController.TAB4;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
List<Fragment> fragments = new ArrayList<>(4);
fragments.add(FirstFragment.newInstance(0));
fragments.add(SecondFragment.newInstance(0));
fragments.add(ThirdFragment.newInstance(0));
fragments.add(FourthFragment.newInstance(0));
fragNavController = new FragNavController(getSupportFragmentManager(), R.id.container, fragments);
//BottomBar menu
mBottomBar = BottomBar.attach(this, savedInstanceState);
mBottomBar.setItems(R.menu.bottombar_menu);
mBottomBar.setOnMenuTabClickListener(new OnMenuTabClickListener() {
#Override
public void onMenuTabSelected(#IdRes int menuItemId) {
//switch between tabs
switch (menuItemId) {
case R.id.bottomBarItemOne:
fragNavController.switchTab(TAB_FIRST);
break;
case R.id.bottomBarItemSecond:
fragNavController.switchTab(TAB_SECOND);
break;
case R.id.bottomBarItemThird:
fragNavController.switchTab(TAB_THIRD);
break;
case R.id.bottomBarItemFourth:
fragNavController.switchTab(TAB_FOURTH);
break;
}
}
#Override
public void onMenuTabReSelected(#IdRes int menuItemId) {
if (menuItemId == R.id.bottomBarItemOne) {
fragNavController.clearStack();
}
}
});
}
#Override
public void onBackPressed () {
if (fragNavController.getCurrentStack().size() > 1) {
fragNavController.pop();
} else {
super.onBackPressed();
}
}
#Override
protected void onSaveInstanceState (Bundle outState){
super.onSaveInstanceState(outState);
// Necessary to restore the BottomBar's state, otherwise we would
// lose the current tab on orientation change.
mBottomBar.onSaveInstanceState(outState);
}
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
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"
tools:context=".MainActivity"
android:id="#+id/container"
android:background="#color/black">
</FrameLayout>
FirstFragment.java
public class FirstFragment extends Fragment {
public class SwipeDeckAdapter extends BaseAdapter {
private List<String> data;
private Context context;
public SwipeDeckAdapter(List<String> data, Context context) {
this.data = data;
this.context = context;
}
#Override
public int getCount() {
return data.size();
}
#Override
public Object getItem(int position) {
return data.get(position);
}
#Override
public long getItemId(int position) {
return position;
}
#Override
public View getView(final int position, View convertView, ViewGroup parent) {
View v = convertView;
if(v == null){
LayoutInflater inflater = getActivity().getLayoutInflater();
// normally use a viewholder
v = inflater.inflate(R.layout.card_view, parent, false);
}
((TextView) v.findViewById(R.id.textView2)).setText(data.get(position));
v.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String item = (String)getItem(position);
Log.i("MainActivity", item);
}
});
return v;
}
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_home,container,false);
final SwipeDeck cardStack = (SwipeDeck) view.findViewById(R.id.swipe_deck);
cardStack.setHardwareAccelerationEnabled(true);
Button btn = (Button) view.findViewById(R.id.undobutton);
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
cardStack.swipeTopCardLeft(180);
}
});
Button btn2 = (Button) view.findViewById(R.id.joinbutton);
btn2.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
cardStack.swipeTopCardRight(180);
}
});
final ArrayList<String> testData = new ArrayList<>();
testData.add("0");
testData.add("1");
testData.add("2");
testData.add("3");
testData.add("4");
final SwipeDeckAdapter adapter = new SwipeDeckAdapter(testData, getActivity() );
cardStack.setAdapter(adapter);
cardStack.setEventCallback(new SwipeDeck.SwipeEventCallback() {
#Override
public void cardSwipedLeft(int position) {
Log.i("MainActivity", "card was swiped left, position in adapter: " + position);
}
#Override
public void cardSwipedRight(int position) {
Log.i("MainActivity", "card was swiped right, position in adapter: " + position);
}
#Override
public void cardsDepleted() {
Log.i("MainActivity", "no more cards");
}
#Override
public void cardActionDown() {
Log.i("MainActivity", "Down");
} ;
#Override
public void cardActionUp() {
Log.i("MainActivity", "Up");
};
});
return view;
}
public static FirstFragment newInstance(int index) {
FirstFragment f = new FirstFragment();
Bundle args = new Bundle();
args.putInt("index", index);
f.setArguments(args);
return f;
}
}
fragment_first.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:background="#color/black"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="#dimen/activity_vertical_margin"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
tools:context="io.MainActivity"
android:fitsSystemWindows="true">
<com.daprlabs.cardstack.SwipeLinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:swipedeck="http://schemas.android.com/apk/res-auto"
android:id="#+id/framelayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:weightSum="10">
<com.daprlabs.cardstack.SwipeDeck
android:id="#+id/swipe_deck"
android:layout_weight="8"
android:layout_width="match_parent"
android:layout_height="0dp"
swipedeck:card_spacing="0dp"
swipedeck:max_visible="3"
swipedeck:render_above="true"
swipedeck:rotation_degrees="15"
swipedeck:opacity_end="0.33">
</com.daprlabs.cardstack.SwipeDeck>
<RelativeLayout
android:id="#+id/rl"
android:layout_weight="2"
android:layout_width="match_parent"
android:layout_height="0dp">
<RelativeLayout
android:id="#+id/container"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true">
<Button
android:id="#+id/undobutton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Undo"
android:onClick="onClick"/>
<Button
android:id="#+id/joinbutton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toRightOf="#id/undobutton"
android:text="Join"
android:onClick="onClick"/>
</RelativeLayout>
</RelativeLayout>
</com.daprlabs.cardstack.SwipeLinearLayout>
In your parent RelativeLayout in fragment_first can you remove the android:fitsSystemWindows="true", I think that may be the cause of the issue.

Categories