Java tutorial
/** * ******************************************************************************* * Copyright 2015 Tom Praschan * <p/> * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * <p/> * http://www.apache.org/licenses/LICENSE-2.0 * <p/> * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * ****************************************************************************** */ package de.tap.easy_xkcd.fragments.comics; import android.app.AlertDialog; import android.app.ProgressDialog; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.graphics.Bitmap; import android.net.Uri; import android.os.AsyncTask; import android.os.Bundle; import android.support.design.widget.Snackbar; import android.support.v4.content.FileProvider; import android.support.v4.view.ViewPager; import android.support.v7.widget.Toolbar; import android.view.LayoutInflater; import android.view.Menu; import android.view.MenuInflater; import android.view.MenuItem; import android.view.View; import android.view.ViewGroup; import android.widget.TextView; import android.widget.Toast; import com.bumptech.glide.Glide; import com.bumptech.glide.load.engine.DiskCacheStrategy; import com.bumptech.glide.request.target.GlideDrawableImageViewTarget; import com.nbsp.materialfilepicker.ui.FilePickerActivity; import com.tap.xkcd_reader.R; import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.FileWriter; import java.io.IOException; import java.io.InputStreamReader; import java.util.Arrays; import java.util.Random; import java.util.Stack; import de.tap.easy_xkcd.Activities.CustomFilePickerActivity; import de.tap.easy_xkcd.Activities.MainActivity; import de.tap.easy_xkcd.database.DatabaseManager; import de.tap.easy_xkcd.utils.Comic; import de.tap.easy_xkcd.utils.OfflineComic; import uk.co.senab.photoview.PhotoView; public class FavoritesFragment extends ComicFragment { public int[] favorites; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, final Bundle savedInstanceState) { View v = inflateLayout(R.layout.pager_layout, inflater, container, savedInstanceState); if (((MainActivity) getActivity()).getProgressDialog() != null) { ((MainActivity) getActivity()).getProgressDialog().dismiss(); } pager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override public void onPageSelected(int position) { favoriteIndex = position; try { //Update the ActionBar Subtitle if (prefHelper.subtitleEnabled() && ((MainActivity) getActivity()).getCurrentFragment() == R.id.nav_favorites) ((MainActivity) getActivity()).getToolbar() .setSubtitle(String.valueOf(favorites[position])); getActivity().invalidateOptionsMenu(); } catch (NullPointerException e) { e.printStackTrace(); } } @Override public void onPageScrollStateChanged(int state) { } @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } }); if (savedInstanceState != null) { favoriteIndex = savedInstanceState.getInt(LAST_FAV); getActivity().invalidateOptionsMenu(); } new updateFavorites().execute(); return v; } public class updateFavorites extends AsyncTask<Integer, Integer, Void> { @Override protected Void doInBackground(Integer... pos) { favorites = databaseManager.getFavComics(); for (int i = 0; i < favorites.length; i++) comicMap.put(i, new OfflineComic(favorites[i], getActivity(), ((MainActivity) getActivity()).getPrefHelper())); return null; } @Override protected void onPostExecute(Void v) { adapter = new FavoritesPagerAdapter(getActivity(), 0); pager.setAdapter(adapter); pager.setCurrentItem(favoriteIndex); Toolbar toolbar = ((MainActivity) getActivity()).getToolbar(); if (prefHelper.subtitleEnabled() && ((MainActivity) getActivity()).getCurrentFragment() == R.id.nav_favorites) toolbar.setSubtitle(String.valueOf(favorites[favoriteIndex])); animateToolbar(); } } private class FavoritesPagerAdapter extends ComicAdapter { public FavoritesPagerAdapter(Context context, int count) { super(context, count); } @Override public int getCount() { return comicMap.size(); } @Override public Object instantiateItem(ViewGroup container, final int position) { View itemView = setupPager(container, position); final PhotoView pvComic = (PhotoView) itemView.findViewById(R.id.ivComic); final TextView tvAlt = (TextView) itemView.findViewById(R.id.tvAlt); final TextView tvTitle = (TextView) itemView.findViewById(R.id.tvTitle); tvAlt.setText(prefHelper.getAlt(favorites[position])); tvTitle.setText(prefHelper.getTitle(favorites[position])); if (getGifId(favorites[position] - 1) != 0) Glide.with(getActivity()).load(getGifId(favorites[position] - 1)) .into(new GlideDrawableImageViewTarget(pvComic)); else pvComic.setImageBitmap(((OfflineComic) comicMap.get(position)).getBitmap()); if (Arrays.binarySearch(mContext.getResources().getIntArray(R.array.large_comics), favorites[favoriteIndex]) >= 0) pvComic.setMaximumScale(7.0f); container.addView(itemView); return itemView; } } @Override public boolean onOptionsItemSelected(MenuItem item) { switch (item.getItemId()) { case R.id.action_alt: return setAltText(true); case R.id.delete_favorites: return deleteAllFavorites(); case R.id.action_favorite: return modifyFavorites(); case R.id.action_share: return shareComic(false); case R.id.action_random: return getRandomComic(); case R.id.action_explain: return explainComic(favorites[favoriteIndex]); case R.id.action_browser: return openComicInBrowser(favorites[favoriteIndex]); case R.id.action_trans: return showTranscript(comicMap.get(favoriteIndex).getTranscript()); case R.id.export_import_favorites: return exportImportFavorites(); case R.id.action_thread: return DatabaseManager.showThread(comicMap.get(favorites[favoriteIndex]).getComicData()[0], getActivity(), false); } return super.onOptionsItemSelected(item); } private boolean exportImportFavorites() { AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); builder.setItems(R.array.export_import_dialog, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { switch (which) { case 0: exportFavorites(); break; case 1: if (prefHelper.isOnline(getActivity()) || prefHelper.fullOfflineEnabled()) getActivity().startActivityForResult( new Intent(getActivity(), CustomFilePickerActivity.class), 2); else Toast.makeText(getActivity(), getResources().getString(R.string.no_connection), Toast.LENGTH_SHORT).show(); break; } } }); builder.create().show(); return true; } public void importFavorites(Intent intent) { String filePath = intent.getStringExtra(FilePickerActivity.RESULT_FILE_PATH); try { File file = new File(filePath); InputStreamReader inputStreamReader = new InputStreamReader(new FileInputStream(file)); BufferedReader bufferedReader = new BufferedReader(inputStreamReader); String line; Stack<Integer> newFavorites = new Stack<>(); while ((line = bufferedReader.readLine()) != null) { String[] numberTitle = line.split(" - "); int number = Integer.parseInt(numberTitle[0]); if (Arrays.binarySearch(favorites, number) < 0) { newFavorites.push(number); databaseManager.setFavorite(number, true); if (number <= ((MainActivity) getActivity()).getDatabaseManager().getHighestInDatabase()) ((MainActivity) getActivity()).getDatabaseManager().setFavorite(number, true); } if (!prefHelper.fullOfflineEnabled()) { new DownloadImageTask(newFavorites).execute(); } } } catch (Exception e) { e.printStackTrace(); Toast.makeText(getActivity(), "Import failed", Toast.LENGTH_SHORT).show(); } } private class DownloadImageTask extends AsyncTask<Void, Void, Void> { private Bitmap mBitmap; private Stack<Integer> favStack; private ProgressDialog progress; public DownloadImageTask(Stack<Integer> stack) { favStack = stack; } @Override protected void onPreExecute() { progress = new ProgressDialog(getActivity()); progress.setTitle(getResources().getString(R.string.loading_comics)); progress.setCancelable(false); progress.show(); } @Override protected Void doInBackground(Void... dummy) { while (!favStack.isEmpty()) { try { int num = favStack.pop(); Comic comic = new Comic(num, getActivity()); mBitmap = Glide.with(getActivity()).load(comic.getComicData()[2]).asBitmap() .diskCacheStrategy(DiskCacheStrategy.SOURCE).into(-1, -1).get(); saveComic(num, mBitmap); prefHelper.addTitle(comic.getComicData()[0], num); prefHelper.addAlt(comic.getComicData()[1], num); } catch (Exception e) { e.printStackTrace(); } } return null; } @Override protected void onPostExecute(Void dummy) { progress.dismiss(); Toast.makeText(getActivity(), getResources().getString(R.string.pref_import_success), Toast.LENGTH_SHORT).show(); refresh(); } } private void exportFavorites() { //Export the full favorites list as text StringBuilder sb = new StringBuilder(); String newline = System.getProperty("line.separator"); for (int i = 0; i < favorites.length; i++) { sb.append(favorites[i]).append(" - "); sb.append(prefHelper.getTitle(favorites[i])); sb.append(newline); } try { File sdCard = prefHelper.getOfflinePath(); File dir = new File(sdCard.getAbsolutePath() + "/easy xkcd"); File file = new File(dir, "favorites.txt"); FileWriter writer = new FileWriter(file); writer.append(sb.toString()); writer.flush(); writer.close(); //Provide option to send to any app that accepts text/plain content Intent sendIntent = new Intent(Intent.ACTION_SEND); sendIntent.setType("text/plain"); Uri uri = FileProvider.getUriForFile(getActivity(), "de.tap.easy_xkcd.fileProvider", file); sendIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); sendIntent.putExtra(Intent.EXTRA_STREAM, uri); startActivity(Intent.createChooser(sendIntent, getResources().getString(R.string.pref_export))); } catch (IOException e) { e.printStackTrace(); Toast.makeText(getActivity(), "Export failed", Toast.LENGTH_SHORT).show(); } } private boolean deleteAllFavorites() { new android.support.v7.app.AlertDialog.Builder(getActivity()).setMessage(R.string.delete_favorites_dialog) .setPositiveButton(R.string.dialog_yes, new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int which) { final int[] fav = databaseManager.getFavComics(); databaseManager.removeAllFavorites(); MenuItem mBrowser = ((MainActivity) getActivity()).getNavView().getMenu() .findItem(R.id.nav_browser); ((MainActivity) getActivity()).selectDrawerItem(mBrowser, false, false); if (!prefHelper.fullOfflineEnabled()) for (int i : fav) getActivity().deleteFile(String.valueOf(i)); Toast toast = Toast.makeText(getActivity(), R.string.favorites_cleared, Toast.LENGTH_SHORT); toast.show(); } }).setNegativeButton(R.string.dialog_cancel, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { } }).setCancelable(true).show(); return true; } public class DeleteImageTask extends AsyncTask<Integer, Integer, Void> { int number; @Override protected Void doInBackground(Integer... pos) { number = pos[0]; if (!MainActivity.fullOffline) getActivity().deleteFile(String.valueOf(pos[0])); databaseManager.setFavorite(pos[0], false); return null; } @Override protected void onPostExecute(Void v) { if (databaseManager.noFavorites()) { //If there are no favorites left, show ComicBrowserFragment MenuItem mBrowser = ((MainActivity) getActivity()).getNavView().getMenu() .findItem(R.id.nav_browser); ((MainActivity) getActivity()).selectDrawerItem(mBrowser, false, false); return; } refresh(); } } private boolean modifyFavorites() { final int mRemoved = favorites[favoriteIndex]; final Bitmap mRemovedBitmap = ((OfflineComic) comicMap.get(favoriteIndex)).getBitmap(); final String mAlt = prefHelper.getAlt(favorites[favoriteIndex]); final String mTitle = prefHelper.getTitle(favorites[favoriteIndex]); new DeleteImageTask().execute(mRemoved); View.OnClickListener oc = new View.OnClickListener() { @Override public void onClick(View v) { databaseManager.setFavorite(mRemoved, true); if (mRemoved <= ((MainActivity) getActivity()).getDatabaseManager().getHighestInDatabase()) ((MainActivity) getActivity()).getDatabaseManager().setFavorite(mRemoved, true); saveComic(mRemoved, mRemovedBitmap); prefHelper.addTitle(mTitle, mRemoved); prefHelper.addAlt(mAlt, mRemoved); refresh(); } }; Snackbar.make(((MainActivity) getActivity()).getFab(), R.string.snackbar_remove, Snackbar.LENGTH_LONG) .setAction(R.string.snackbar_undo, oc).show(); return true; } public boolean shareComic(boolean fromPermission) { if (fromPermission || prefHelper.shareImage()) { shareComicImage(getURI(comicMap.get(favoriteIndex).getComicNumber()), comicMap.get(favoriteIndex)); return true; } AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); builder.setItems(R.array.share_dialog, new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { switch (which) { case 0: shareComicImage(getURI(comicMap.get(favoriteIndex).getComicNumber()), comicMap.get(favoriteIndex)); break; case 1: shareComicUrl(comicMap.get(favoriteIndex)); break; } } }); AlertDialog alert = builder.create(); alert.show(); return true; } @Override public void onPrepareOptionsMenu(Menu menu) { /*menu.findItem(R.id.action_latest).setVisible(false); menu.findItem(R.id.action_search).setVisible(false); menu.findItem(R.id.action_boomark).setVisible(false); menu.findItem(R.id.action_overview).setVisible(false); menu.findItem(R.id.delete_favorites).setVisible(true); menu.findItem(R.id.export_import_favorites).setVisible(true); MenuItem fav = menu.findItem(R.id.action_favorite); fav.setIcon(R.drawable.ic_action_favorite); fav.setTitle(R.string.action_favorite_remove);*/ //If the FAB is visible, hide the random comic menu item if (((MainActivity) getActivity()).getFab().getVisibility() == View.GONE) { menu.findItem(R.id.action_random).setVisible(true); } else { menu.findItem(R.id.action_random).setVisible(false); } } @Override public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) { inflater.inflate(R.menu.menu_favorites_fragment, menu); menu.findItem(R.id.action_search).setVisible(false); super.onCreateOptionsMenu(menu, inflater); } public boolean getRandomComic() { //get a random number and update the pager if (favorites.length > 1) { Random rand = new Random(); Integer number = rand.nextInt(favorites.length); while (number.equals(favoriteIndex)) { number = rand.nextInt(favorites.length); } pager.setCurrentItem(number); } return true; } public void refresh() { //Updates favorite list, pager and alt TextView comicMap.clear(); if (!databaseManager.noFavorites()) { if (favoriteIndex == databaseManager.getFavComics().length) favoriteIndex--; new updateFavorites().execute(); } } public void updatePager() { } }