package com.ioabsoftware.gameraven;
import android.annotation.SuppressLint;
import android.app.AlertDialog;
import android.app.Dialog;
import android.app.SearchManager;
import android.content.Context;
import android.content.DialogInterface;
import android.content.DialogInterface.OnClickListener;
import android.content.DialogInterface.OnShowListener;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.content.res.ColorStateList;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
import android.os.Environment;
import android.preference.PreferenceManager;
import android.support.annotation.NonNull;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.NavigationView;
import android.support.v4.view.MenuItemCompat;
import android.support.v4.widget.DrawerLayout;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.app.ActionBar;
import android.support.v7.app.ActionBarDrawerToggle;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.SearchView;
import android.text.Editable;
import android.text.TextWatcher;
import android.text.format.Time;
import android.util.Log;
import android.util.TypedValue;
import android.view.Gravity;
import android.view.HapticFeedbackConstants;
import android.view.KeyEvent;
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.view.WindowManager;
import android.view.inputmethod.InputMethodManager;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.CompoundButton;
import android.widget.CompoundButton.OnCheckedChangeListener;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.ProgressBar;
import android.widget.Spinner;
import android.widget.TextView;
import com.ioabsoftware.gameraven.db.HighlightListDBHelper;
import com.ioabsoftware.gameraven.db.HighlightedUser;
import com.ioabsoftware.gameraven.networking.NetDesc;
import com.ioabsoftware.gameraven.networking.Session;
import com.ioabsoftware.gameraven.prefs.HeaderSettings;
import com.ioabsoftware.gameraven.prefs.SettingsHighlightedUsers;
import com.ioabsoftware.gameraven.util.AccountManager;
import com.ioabsoftware.gameraven.util.DocumentParser;
import com.ioabsoftware.gameraven.util.Theming;
import com.ioabsoftware.gameraven.views.BaseRowData;
import com.ioabsoftware.gameraven.views.BaseRowData.ReadStatus;
import com.ioabsoftware.gameraven.views.MarqueeToolbar;
import com.ioabsoftware.gameraven.views.ViewAdapter;
import com.ioabsoftware.gameraven.views.rowdata.AMPRowData;
import com.ioabsoftware.gameraven.views.rowdata.BoardRowData;
import com.ioabsoftware.gameraven.views.rowdata.BoardRowData.BoardType;
import com.ioabsoftware.gameraven.views.rowdata.GameSearchRowData;
import com.ioabsoftware.gameraven.views.rowdata.HeaderRowData;
import com.ioabsoftware.gameraven.views.rowdata.MentionRowData;
import com.ioabsoftware.gameraven.views.rowdata.MessageRowData;
import com.ioabsoftware.gameraven.views.rowdata.NotifRowData;
import com.ioabsoftware.gameraven.views.rowdata.PMDetailRowData;
import com.ioabsoftware.gameraven.views.rowdata.PMRowData;
import com.ioabsoftware.gameraven.views.rowdata.TopicRowData;
import com.ioabsoftware.gameraven.views.rowdata.TopicRowData.TopicType;
import com.ioabsoftware.gameraven.views.rowdata.TrackedTopicRowData;
import com.ioabsoftware.gameraven.views.rowdata.UserDetailRowData;
import com.ioabsoftware.gameraven.views.rowview.MessageRowView;
import com.joanzapata.iconify.IconDrawable;
import com.joanzapata.iconify.fonts.MaterialCommunityIcons;
import com.joanzapata.iconify.fonts.MaterialIcons;
import com.koushikdutta.async.future.FutureCallback;
import com.koushikdutta.ion.Ion;
import org.acra.ACRA;
import org.apache.commons.lang3.StringEscapeUtils;
import org.apache.commons.lang3.math.NumberUtils;
import org.codechimp.apprater.AppRater;
import org.jetbrains.annotations.NotNull;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.nodes.TextNode;
import org.jsoup.select.Elements;
import java.io.File;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
import java.util.Set;
import java.util.TimeZone;
import de.keyboardsurfer.android.widget.crouton.Crouton;
@SuppressLint("RtlHardcoded")
public class AllInOneV2 extends AppCompatActivity implements SwipeRefreshLayout.OnRefreshListener {
public static final int SEND_PM_DIALOG = 102;
public static final int MESSAGE_ACTION_DIALOG = 103;
public static final int REPORT_MESSAGE_DIALOG = 104;
public static final int POLL_OPTIONS_DIALOG = 105;
public static final String EMPTY_STRING = "";
public static String defaultSig;
private Session session = null;
public Session getSession() {
return session;
}
private String boardID;
private String topicID;
private String messageIDForEditing;
private String postPostUrl;
private String savedPostBody;
public String getSavedPostBody() {
return savedPostBody;
}
private String savedPostTitle;
public String getSavedPostTitle() {
return savedPostTitle;
}
private static SharedPreferences settings = null;
public static SharedPreferences getSettingsPref() {
return settings;
}
private LinearLayout titleWrapper;
private EditText postTitle;
private EditText postBody;
private TextView titleCounter;
private TextView bodyCounter;
private Button postSubmitButton;
private Button postCancelButton;
private Button pollButton;
private View pollSep;
private boolean pollUse = false;
public boolean isUsingPoll() {
return pollUse;
}
private String pollTitle = EMPTY_STRING;
public String getPollTitle() {
return pollTitle;
}
private String[] pollOptions = new String[10];
public String[] getPollOptions() {
return pollOptions;
}
private int pollMinLevel = -1;
public String getPollMinLevel() {
return Integer.toString(pollMinLevel);
}
private LinearLayout postWrapper;
private SwipeRefreshLayout swipeRefreshLayout;
private ListView contentList;
private String tlUrl;
private enum PostMode {ON_BOARD, ON_TOPIC, NEW_PM}
private PostMode pMode;
private enum FavMode {ON_BOARD, ON_TOPIC}
private FavMode fMode;
private String favKey;
private Button pageLabel;
private Button firstPage, prevPage, nextPage, lastPage;
private String firstPageUrl, prevPageUrl, nextPageUrl, lastPageUrl, jumperPageUrl;
private AlertDialog.Builder jumperDialogBuilder;
private NetDesc pageJumperDesc;
private View pageJumperWrapper;
@SuppressWarnings("ConstantConditions")
public int[] getScrollerVertLoc() {
try {
int firstVis = contentList.getFirstVisiblePosition();
return new int[]{firstVis, contentList.getChildAt(0).getTop()};
} catch (NullPointerException npe) {
return new int[]{0, 0};
}
}
private static HighlightListDBHelper hlDB;
public static HighlightListDBHelper getHLDB() {
return hlDB;
}
private DrawerLayout drawerLayout;
private ActionBarDrawerToggle drawerToggle;
private Spinner accountsSpinner, notifsSpinner;
private ArrayAdapter<String> accountsAdapter, notifsAdapter;
private ArrayList<String> notifsLinks = new ArrayList<>();
private MenuItem dwrNavHeadItem, dwrPMInboxItem, dwrAMPItem;
private FloatingActionButton fab;
@SuppressLint("StaticFieldLeak")
private static AllInOneV2 me;
public static AllInOneV2 get() {
return me;
}
private Theming themingInstance;
/**
* *******************************************
* START METHODS
* ********************************************
*/
@Override
protected void onCreate(Bundle savedInstanceState) {
me = this;
settings = PreferenceManager.getDefaultSharedPreferences(this);
// get an instance of Theming to ensure values don't get GC'd
// Will they get GC'd? I have no idea. Better safe than sorry.
themingInstance = new Theming();
Theming.preInit(settings);
setTheme(Theming.theme());
Theming.init(this, settings);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
getWindow().addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
getWindow().setStatusBarColor(Theming.colorPrimaryDark());
}
super.onCreate(savedInstanceState);
setContentView(R.layout.allinonev2);
Theming.colorOverscroll(this);
AccountManager.init(this);
setSupportActionBar((MarqueeToolbar) findViewById(R.id.aioToolbar));
ActionBar aBar = getSupportActionBar();
assert aBar != null : "Action bar is null";
aBar.setDisplayHomeAsUpEnabled(true);
aBar.setDisplayShowTitleEnabled(true);
drawerLayout = (DrawerLayout) findViewById(R.id.aioDrawerLayout);
NavigationView navigationView = (NavigationView) findViewById(R.id.aioNavigationDrawer);
drawerToggle = new ActionBarDrawerToggle(this, drawerLayout, R.string.drawer_open, R.string.drawer_close);
drawerLayout.addDrawerListener(drawerToggle);
assert navigationView != null;
navigationView.setNavigationItemSelectedListener(new NavigationView.OnNavigationItemSelectedListener() {
@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
switch (item.getItemId()) {
case R.id.dwrBoardJumper:
showBoardQuickList();
break;
case R.id.dwrAMPList:
session.get(NetDesc.AMP_LIST, buildAMPLink());
break;
case R.id.dwrTrackedTopics:
session.get(NetDesc.TRACKED_TOPICS, "/user/tracked");
break;
case R.id.dwrPMInbox:
session.get(NetDesc.PM_INBOX, "/pm/");
break;
case R.id.dwrCopyCurrURL:
android.content.ClipboardManager clipboard =
(android.content.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
clipboard.setPrimaryClip(android.content.ClipData.newPlainText("simple text", session.getLastPath()));
Crouton.showText(AllInOneV2.this, "URL copied to clipboard.", Theming.croutonStyle());
break;
case R.id.dwrHighlightList:
startActivity(new Intent(AllInOneV2.this, SettingsHighlightedUsers.class));
break;
case R.id.dwrSettings:
startActivity(new Intent(AllInOneV2.this, HeaderSettings.class));
break;
case R.id.dwrExit:
AllInOneV2.this.finish();
break;
}
drawerLayout.closeDrawers();
return false;
}
});
View headerView = navigationView.getHeaderView(0);
accountsSpinner = (Spinner) headerView.findViewById(R.id.dwrHdrAccounts);
notifsSpinner = (Spinner) headerView.findViewById(R.id.dwrHdrNotifications);
accountsAdapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_item);
notifsAdapter = new ArrayAdapter<>(this, android.R.layout.simple_spinner_item);
accountsAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
notifsAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
accountsAdapter.add("No Accounts");
notifsAdapter.add("0 " + getString(R.string.notifications));
accountsSpinner.setAdapter(accountsAdapter);
notifsSpinner.setAdapter(notifsAdapter);
Menu drawerMenu = navigationView.getMenu();
dwrNavHeadItem = drawerMenu.findItem(R.id.dwrNavHeader);
dwrPMInboxItem = drawerMenu.findItem(R.id.dwrPMInbox);
dwrAMPItem = drawerMenu.findItem(R.id.dwrAMPList);
aBar.setDisplayHomeAsUpEnabled(true);
aBar.setHomeButtonEnabled(true);
if (!settings.contains("defaultAccount")) {
// settings need to be set to default
PreferenceManager.setDefaultValues(this, R.xml.prefsaccountsnotifs, false);
PreferenceManager.setDefaultValues(this, R.xml.prefsadvanced, false);
PreferenceManager.setDefaultValues(this, R.xml.prefsgeneral, false);
PreferenceManager.setDefaultValues(this, R.xml.prefstheming, false);
Editor sEditor = settings.edit();
sEditor.putString("defaultAccount", HeaderSettings.NO_DEFAULT_ACCOUNT)
.putString("timezone", TimeZone.getDefault().getID())
.apply();
}
swipeRefreshLayout = (SwipeRefreshLayout) findViewById(R.id.ptr_layout);
if (swipeRefreshLayout != null) {
swipeRefreshLayout.setEnabled(false);
swipeRefreshLayout.setColorSchemeColors(Theming.colorPrimary(), Theming.colorPrimaryDark());
swipeRefreshLayout.setOnRefreshListener(this);
}
contentList = (ListView) findViewById(R.id.aioMainList);
titleWrapper = (LinearLayout) findViewById(R.id.aioPostTitleWrapper);
postTitle = (EditText) findViewById(R.id.aioPostTitle);
postBody = (EditText) findViewById(R.id.aioPostBody);
titleCounter = (TextView) findViewById(R.id.aioPostTitleCounter);
bodyCounter = (TextView) findViewById(R.id.aioPostBodyCounter);
pageJumperWrapper = findViewById(R.id.aioHeader);
firstPage = (Button) findViewById(R.id.aioFirstPage);
firstPage.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
session.get(pageJumperDesc, firstPageUrl);
}
});
prevPage = (Button) findViewById(R.id.aioPreviousPage);
prevPage.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
session.get(pageJumperDesc, prevPageUrl);
}
});
nextPage = (Button) findViewById(R.id.aioNextPage);
nextPage.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
session.get(pageJumperDesc, nextPageUrl);
}
});
lastPage = (Button) findViewById(R.id.aioLastPage);
lastPage.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
session.get(pageJumperDesc, lastPageUrl);
}
});
pageLabel = (Button) findViewById(R.id.aioPageLabel);
pageLabel.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
jumperDialogBuilder.show();
}
});
Theming.setTextSizeBases(firstPage.getTextSize(), pageLabel.getTextSize());
postTitle.addTextChangedListener(new TextWatcher() {
@Override
public void afterTextChanged(Editable s) {
int length = StringEscapeUtils.escapeHtml4(s.toString()).length();
if (length > 70) {
String t = length + "/80";
titleCounter.setText(t);
titleCounter.setVisibility(View.VISIBLE);
} else
titleCounter.setVisibility(View.GONE);
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before,
int count) {
}
});
postBody.addTextChangedListener(new TextWatcher() {
@Override
public void afterTextChanged(Editable s) {
// GFAQs adds 13(!) characters onto bodies when they have a sig, apparently.
int length = StringEscapeUtils.escapeHtml4(s.toString()).length() + getSig().length() + 13;
if (length > 4000) {
String t = length + "\n/4096";
bodyCounter.setText(t);
bodyCounter.setVisibility(View.VISIBLE);
} else
bodyCounter.setVisibility(View.GONE);
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count,
int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before,
int count) {
}
});
postSubmitButton = (Button) findViewById(R.id.aioPostDo);
postCancelButton = (Button) findViewById(R.id.aioPostCancel);
pollButton = (Button) findViewById(R.id.aioPollOptions);
pollSep = findViewById(R.id.aioPollSep);
postWrapper = (LinearLayout) findViewById(R.id.aioPostWrapper);
if (BuildConfig.DEBUG) wtl("creating default sig");
defaultSig = "Posted with GameRaven *grver*";
if (BuildConfig.DEBUG) wtl("getting css directory");
File cssDirectory = new File(Environment.getExternalStorageDirectory().getAbsolutePath() + "/gameraven");
if (!cssDirectory.exists()) {
if (BuildConfig.DEBUG) wtl("css directory does not exist, creating");
if (cssDirectory.mkdir())
if (BuildConfig.DEBUG) wtl("css directory created");
else if (BuildConfig.DEBUG) wtl("css directory creation failed");
}
if (BuildConfig.DEBUG) wtl("starting db creation");
hlDB = new HighlightListDBHelper(this);
View foot = new View(this);
foot.setMinimumHeight(Theming.convertDPtoPX(this, 80));
contentList.addFooterView(foot);
adapterRows.add(new HeaderRowData("Loading..."));
contentList.setAdapter(viewAdapter);
fab = (FloatingActionButton) findViewById(R.id.fab);
fab.setImageDrawable(new IconDrawable(this, MaterialIcons.md_add).colorRes(R.color.white).sizeDp(24));
fab.setBackgroundTintList(new ColorStateList(
new int[][]{new int[]{}},
new int[]{Theming.colorPrimary()}));
fab.setRippleColor(Theming.colorAccent());
fab.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (pMode == PostMode.ON_BOARD)
postSetup(false);
else if (pMode == PostMode.ON_TOPIC)
postSetup(true);
else if (pMode == PostMode.NEW_PM)
pmSetup(EMPTY_STRING, EMPTY_STRING, EMPTY_STRING);
}
});
fab.setVisibility(View.GONE);
AppRater.app_launched(this);
if (BuildConfig.DEBUG) wtl("onCreate finishing");
}
@Override
protected void onPostCreate(Bundle savedInstanceState) {
super.onPostCreate(savedInstanceState);
// Sync the toggle state after onRestoreInstanceState has occurred.
drawerToggle.syncState();
}
@Override
protected void onNewIntent(Intent intent) {
if (intent.getData() != null && intent.getData().getPath() != null) {
String url = intent.getData().getPath();
NetDesc desc = Session.determineNetDesc(url);
if (desc != NetDesc.UNSPECIFIED)
session.get(desc, url);
else
Crouton.showText(this, "Page not recognized: " + url, Theming.croutonStyle());
}
}
private boolean firstResume = true;
@Override
protected void onResume() {
if (BuildConfig.DEBUG) wtl("onResume fired");
super.onResume();
swipeRefreshLayout.setEnabled(settings.getBoolean("enablePTR", false));
contentList.setFastScrollEnabled(settings.getBoolean("enableFastScroll", true));
int lastUpdateYear = settings.getInt("lastUpdateYear", 0);
int lastUpdateYearDay = settings.getInt("lastUpdateYearDay", 0);
@SuppressWarnings("deprecation") Time now = new Time();
now.setToNow();
if (lastUpdateYear != now.year || lastUpdateYearDay != now.yearDay) {
if (BuildConfig.DEBUG) wtl("checking for update");
try {
if (BuildConfig.DEBUG) wtl("my version is " + BuildConfig.VERSION_CODE);
Ion.with(this)
.load("GET", "http://ioabsoftware.com/gameraven/latest.txt")
.asString()
.setCallback(new FutureCallback<String>() {
@Override
public void onCompleted(Exception e, String result) {
if (NumberUtils.isNumber(result)) {
int netVersion = Integer.valueOf(result);
if (BuildConfig.DEBUG) wtl("net version is " + netVersion);
if (netVersion > BuildConfig.VERSION_CODE) {
AlertDialog.Builder b = new AlertDialog.Builder(AllInOneV2.this);
b.setTitle("New Version Found");
b.setMessage("Open Google Play Market to download new version? Note that although " +
"care is taken to make sure this notification only goes out once the update " +
"has spread to all Google servers, there is still a chance the update may not " +
"show up in the Play Store at first. Rest assured, there is a new version. " +
"It just hasn't reached your local Google Play server yet.");
b.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent i = new Intent(Intent.ACTION_VIEW);
i.setData(Uri.parse("market://details?id=com.ioabsoftware.gameraven"));
AllInOneV2.this.startActivity(i);
}
});
b.setNegativeButton("No", null);
b.show();
}
}
}
});
settings.edit().putInt("lastUpdateYear", now.year).putInt("lastUpdateYearDay", now.yearDay).apply();
} catch (NullPointerException e) {
e.printStackTrace();
}
}
if (Theming.updateTextScale(settings.getInt("textScale", 100) / 100f)) {
int px = TypedValue.COMPLEX_UNIT_PX;
firstPage.setTextSize(px, Theming.getScaledPJButtonTextSize());
prevPage.setTextSize(px, Theming.getScaledPJButtonTextSize());
nextPage.setTextSize(px, Theming.getScaledPJButtonTextSize());
lastPage.setTextSize(px, Theming.getScaledPJButtonTextSize());
pageLabel.setTextSize(px, Theming.getScaledPJLabelTextSize());
}
MessageRowView.setUsingAvatars(settings.getBoolean("usingAvatars", false));
accountsAdapter.clear();
accountsAdapter.addAll(AccountManager.getUsernames(this));
accountsAdapter.add(getString(R.string.log_out));
if (firstResume) {
accountsSpinner.setOnItemSelectedListener(accountsListener);
notifsSpinner.setOnItemSelectedListener(notifsListener);
}
if (session == null) {
String initUrl = null;
NetDesc initDesc = null;
if (firstResume) {
Uri uri = getIntent().getData();
if (uri != null && uri.getScheme() != null && uri.getHost() != null) {
if (uri.getScheme().equals("http") && uri.getHost().contains("gamefaqs.com")) {
initUrl = uri.getPath();
initDesc = Session.determineNetDesc(initUrl);
}
}
}
String defaultAccount = settings.getString("defaultAccount", HeaderSettings.NO_DEFAULT_ACCOUNT);
String resumeAccount = settings.getString("resumeSessionUser", HeaderSettings.NO_DEFAULT_ACCOUNT);
boolean resumeSession = settings.getBoolean("resumeSession", false);
if (firstResume && resumeSession && AccountManager.containsUser(this, resumeAccount)) {
session = new Session(this, resumeAccount, AccountManager.getPassword(this, resumeAccount), Session.RESUME_INIT_URL, NetDesc.UNSPECIFIED);
} else if (AccountManager.containsUser(this, defaultAccount)) {
if (BuildConfig.DEBUG) wtl("starting new session from onResume, logged in");
session = new Session(this, defaultAccount, AccountManager.getPassword(this, defaultAccount), initUrl, initDesc);
} else {
if (BuildConfig.DEBUG) wtl("starting new session from onResume, no login");
session = new Session(this, null, null, initUrl, initDesc);
}
} else {
if (settings.getBoolean("reloadOnResume", false)) {
if (BuildConfig.DEBUG)
wtl("session exists, reload on resume is true, refreshing page");
isRoR = true;
session.refresh();
}
}
if (!settings.contains("beenWelcomed")) {
settings.edit().putBoolean("beenWelcomed", true).apply();
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setTitle("Welcome!");
b.setMessage("Would you like to view the quick start help files? This dialog won't be shown again.");
b.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse("http://ioabsoftware.com/gameraven/quickstart.html")));
}
});
b.setNegativeButton("No", null);
b.show();
}
firstResume = false;
if (BuildConfig.DEBUG) wtl("onResume finishing");
}
@Override
protected void onStop() {
Editor e = settings.edit();
e.putBoolean("resumeSession", true);
session.addHistoryBeforeStop();
if (Session.isLoggedIn())
e.putString("resumeSessionUser", Session.getUser());
e.apply();
session.closeHistoryDB();
super.onStop();
}
@Override
protected void onRestart() {
super.onRestart();
session.openHistoryDB();
session.popHistory();
}
@Override
protected void onDestroy() {
if (BuildConfig.DEBUG) wtl("Destroying!");
Crouton.clearCroutonsForActivity(this);
if (isFinishing())
settings.edit().putBoolean("resumeSession", false).apply();
super.onDestroy();
}
private AlertDialog loginDialog;
public void showLoggingInDialog(String user) {
if (loginDialog == null) {
AlertDialog.Builder b = new AlertDialog.Builder(this);
ProgressBar spinner = new ProgressBar(this);
spinner.setIndeterminate(true);
b.setView(spinner);
loginDialog = b.create();
}
loginDialog.setTitle("Logging in as " + user + "...");
loginDialog.show();
}
public void dismissLoginDialog() {
loginDialog.dismiss();
}
private boolean needToSetNavList = true;
public void navDrawerReset() {
setMenuItemVisibility(dwrNavHeadItem, false);
needToSetNavList = true;
}
public void setNavDrawerVisibility(boolean isLoggedIn) {
setMenuItemVisibility(dwrNavHeadItem, true);
dwrNavHeadItem.getSubMenu().setGroupVisible(R.id.dwrLoggedInNav, isLoggedIn);
needToSetNavList = false;
}
@Override
public boolean onSearchRequested() {
if (searchIcon != null && searchIcon.isVisible())
MenuItemCompat.expandActionView(searchIcon);
return false;
}
public void toggleMenu() {
if (drawerLayout.isDrawerOpen(Gravity.LEFT))
drawerLayout.closeDrawers();
else
drawerLayout.openDrawer(Gravity.LEFT);
}
@Override
public boolean onKeyUp(int keyCode, @NotNull KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_MENU) {
toggleMenu();
return true;
} else {
return super.onKeyUp(keyCode, event);
}
}
@Override
public void onRefresh() {
refreshClicked(null);
}
private MenuItem refreshIcon, replyIcon, pmInboxIcon, pmOutboxIcon, addFavIcon, remFavIcon,
searchIcon, topicListIcon, sendUserPMIcon, tagUserIcon, unreadNotifsIcon, clearUnreadNotifsIcon;
/**
* Adds menu items
*/
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.main, menu);
searchIcon = menu.findItem(R.id.search).setIcon(new IconDrawable(
this, MaterialIcons.md_search).colorRes(R.color.white).actionBarSize());
unreadNotifsIcon = menu.findItem(R.id.unreadNotifs).setIcon(new IconDrawable(
this, MaterialCommunityIcons.mdi_comment_alert).colorRes(R.color.white).actionBarSize());
clearUnreadNotifsIcon = menu.findItem(R.id.clearUnreadNotifs).setIcon(new IconDrawable(
this, MaterialCommunityIcons.mdi_notification_clear_all).colorRes(R.color.white).actionBarSize());
topicListIcon = menu.findItem(R.id.topicList).setIcon(new IconDrawable(
this, MaterialIcons.md_view_list).colorRes(R.color.white).actionBarSize());
addFavIcon = menu.findItem(R.id.addFav).setIcon(new IconDrawable(
this, MaterialIcons.md_favorite_border).colorRes(R.color.white).actionBarSize());
remFavIcon = menu.findItem(R.id.remFav).setIcon(new IconDrawable(
this, MaterialIcons.md_favorite).colorRes(R.color.white).actionBarSize());
pmInboxIcon = menu.findItem(R.id.pmInbox).setIcon(new IconDrawable(
this, MaterialIcons.md_inbox).colorRes(R.color.white).actionBarSize());
pmOutboxIcon = menu.findItem(R.id.pmOutbox).setIcon(new IconDrawable(
this, MaterialCommunityIcons.mdi_outbox).colorRes(R.color.white).actionBarSize());
sendUserPMIcon = menu.findItem(R.id.sendUserPM).setIcon(new IconDrawable(
this, MaterialIcons.md_mail).colorRes(R.color.white).actionBarSize());
tagUserIcon = menu.findItem(R.id.tagUser).setIcon(new IconDrawable(
this, MaterialCommunityIcons.mdi_tag_text_outline).colorRes(R.color.white).actionBarSize());
replyIcon = menu.findItem(R.id.reply).setIcon(new IconDrawable(
this, MaterialIcons.md_reply).colorRes(R.color.white).actionBarSize());
refreshIcon = menu.findItem(R.id.refresh).setIcon(new IconDrawable(
this, MaterialIcons.md_refresh).colorRes(R.color.white).actionBarSize());
SearchView searchView = (SearchView) MenuItemCompat.getActionView(searchIcon);
if (searchView != null) {
SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
SearchView.OnQueryTextListener queryTextListener = new SearchView.OnQueryTextListener() {
public boolean onQueryTextChange(String newText) {
// just do default
return false;
}
public boolean onQueryTextSubmit(String query) {
try {
String encodedQuery = URLEncoder.encode(query, DocumentParser.CHARSET_NAME);
if (session.getLastDesc() == NetDesc.BOARD) {
if (BuildConfig.DEBUG) wtl("searching board for query");
session.get(NetDesc.BOARD, session.getLastPathWithoutData() + "?search=" + encodedQuery);
} else if (session.getLastDesc() == NetDesc.BOARD_JUMPER || session.getLastDesc() == NetDesc.GAME_SEARCH) {
if (BuildConfig.DEBUG) wtl("searching for games");
session.get(NetDesc.GAME_SEARCH, "/search/index.html?game=" + encodedQuery);
}
} catch (UnsupportedEncodingException e) {
throw new AssertionError(DocumentParser.CHARSET_NAME + " is unknown");
// shouldn't ever happen
}
return true;
}
};
searchView.setOnQueryTextListener(queryTextListener);
}
return true;
}
UserDetailRowData userDetailData;
/**
* fires when a menu option is selected
*/
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Pass the event to ActionBarDrawerToggle, if it returns
// true, then it has handled the app icon touch event
if (drawerToggle.onOptionsItemSelected(item)) {
return true;
}
// Handle item selection
switch (item.getItemId()) {
case R.id.search:
onSearchRequested();
return true;
case R.id.addFav:
AlertDialog.Builder afb = new AlertDialog.Builder(this);
afb.setNegativeButton("No", null);
final HashMap<String, List<String>> afData = new HashMap<>();
afData.put("key", Collections.singletonList(favKey));
final String afPath = session.getLastPath().replace("/boards/", "/boardaction/");
switch (fMode) {
case ON_BOARD:
afb.setTitle("Add Board to Favorites?");
afb.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
afData.put("action", Collections.singletonList("addfav"));
session.post(NetDesc.BOARD, afPath, afData);
}
});
break;
case ON_TOPIC:
afb.setTitle("Track Topic?");
afb.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
afData.put("action", Collections.singletonList("tracktopic"));
session.post(NetDesc.TOPIC, afPath, afData);
}
});
break;
}
afb.show();
return true;
case R.id.remFav:
AlertDialog.Builder rfb = new AlertDialog.Builder(this);
rfb.setNegativeButton("No", null);
final HashMap<String, List<String>> rfData = new HashMap<>();
rfData.put("key", Collections.singletonList(favKey));
final String rfPath = session.getLastPath().replace("/boards/", "/boardaction/");
switch (fMode) {
case ON_BOARD:
rfb.setTitle("Remove Board from Favorites?");
rfb.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
rfData.put("action", Collections.singletonList("remfav"));
session.post(NetDesc.BOARD, rfPath, rfData);
}
});
break;
case ON_TOPIC:
rfb.setTitle("Stop Tracking Topic?");
rfb.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
rfData.put("action", Collections.singletonList("stoptrack"));
session.post(NetDesc.TOPIC, rfPath, rfData);
}
});
break;
}
rfb.show();
return true;
case R.id.unreadNotifs:
session.get(NetDesc.NOTIFS_PAGE, NOTIFS_PAGE_LINK);
return true;
case R.id.clearUnreadNotifs:
session.get(NetDesc.NOTIFS_CLEAR, NOTIFS_CLEAR_LINK);
return true;
case R.id.topicList:
session.get(NetDesc.BOARD, tlUrl);
return true;
case R.id.pmInbox:
session.get(NetDesc.PM_INBOX, "/pm/");
return true;
case R.id.pmOutbox:
session.get(NetDesc.PM_OUTBOX, "/pm/sent");
return true;
case R.id.sendUserPM:
pmSetup(userDetailData.getName(), null, null);
return true;
case R.id.tagUser:
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setTitle("Set " + userDetailData.getName() + "'s Tag");
b.setMessage("User tags can be up to 30 characters long and cannot contain any banned words." +
"If a banned word is detected, the tag will be discarded.");
final EditText tagText = new EditText(this);
tagText.setHint(R.string.user_tag_hint);
tagText.setText(userDetailData.getTagText());
b.setView(tagText);
b.setPositiveButton("OK", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
HashMap<String, List<String>> data = new HashMap<>();
data.put("key", Collections.singletonList(userDetailData.getTagKey()));
assert tagText.getText() != null : "tagText.getText() is null";
data.put("t", Collections.singletonList(tagText.getText().toString()));
data.put("user", Collections.singletonList(userDetailData.getID()));
hideSoftKeyboard(tagText);
AllInOneV2.get().getSession().post(NetDesc.USER_TAG, Session.ROOT + "/ajax/user_tag", data);
}
});
b.show();
return true;
case R.id.reply:
pmSetup(replyTo, replySubject, EMPTY_STRING);
return true;
case R.id.refresh:
if (session.getLastPath() == null) {
if (Session.isLoggedIn()) {
if (BuildConfig.DEBUG)
wtl("starting new session from case R.id.refresh, logged in");
session = new Session(this, Session.getUser(), AccountManager.getPassword(this, Session.getUser()));
} else {
if (BuildConfig.DEBUG)
wtl("starting new session from R.id.refresh, no login");
session = new Session(this);
}
} else
session.refresh();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
private void setMenuItemVisibility(MenuItem item, boolean visible) {
if (item != null)
item.setVisible(visible);
}
private void setMenuItemEnabled(MenuItem item, boolean enabled) {
if (item != null)
item.setEnabled(enabled);
}
private void setAllMenuItemsExceptRefreshVisibility(boolean visible) {
setMenuItemVisibility(searchIcon, visible);
setMenuItemVisibility(replyIcon, visible);
setMenuItemVisibility(pmInboxIcon, visible);
setMenuItemVisibility(pmOutboxIcon, visible);
setMenuItemVisibility(sendUserPMIcon, visible);
setMenuItemVisibility(tagUserIcon, visible);
setMenuItemVisibility(addFavIcon, visible);
setMenuItemVisibility(remFavIcon, visible);
setMenuItemVisibility(topicListIcon, visible);
setMenuItemVisibility(unreadNotifsIcon, visible);
setMenuItemVisibility(clearUnreadNotifsIcon, visible);
if (visible)
fab.setVisibility(View.VISIBLE);
else
fab.setVisibility(View.GONE);
}
private void setAllMenuItemsEnabled(boolean enabled) {
setMenuItemEnabled(refreshIcon, enabled);
setMenuItemEnabled(searchIcon, enabled);
setMenuItemEnabled(replyIcon, enabled);
setMenuItemEnabled(pmInboxIcon, enabled);
setMenuItemEnabled(pmOutboxIcon, enabled);
setMenuItemEnabled(sendUserPMIcon, enabled);
setMenuItemEnabled(tagUserIcon, enabled);
setMenuItemEnabled(addFavIcon, enabled);
setMenuItemEnabled(remFavIcon, enabled);
setMenuItemEnabled(topicListIcon, enabled);
setMenuItemEnabled(unreadNotifsIcon, enabled);
setMenuItemEnabled(clearUnreadNotifsIcon, enabled);
fab.setEnabled(enabled);
}
public void setLoginName(String name) {
if (name == null)
name = getString(R.string.log_out);
accountsSpinner.setSelection(accountsAdapter.getPosition(name), false);
}
private void hideSoftKeyboard(View inputView) {
((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE)).
hideSoftInputFromWindow(inputView.getWindowToken(), 0);
}
public void postError(String msg) {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage(msg);
builder.setTitle("There was a problem with your post...");
builder.setPositiveButton("Ok", null);
builder.show();
ptrCleanup();
}
public void genError(String errorTitle, String errorMsg, String buttonText) {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setMessage(errorMsg);
builder.setTitle(errorTitle);
builder.setPositiveButton(buttonText, null);
builder.show();
ptrCleanup();
}
public void noNetworkConnection() {
genError("No Network Connection", "Couldn't establish network connection. Check your network settings, then try again.",
"Dismiss");
}
public void timeoutCleanup(NetDesc desc) {
String msg;
String title;
String posButtonText;
boolean retrySub = false;
//noinspection EnumSwitchStatementWhichMissesCases
switch (desc) {
case LOGIN_S1:
case LOGIN_S2:
title = "Login Timeout";
msg = "Login timed out, press retry to try again.";
posButtonText = "Retry";
break;
case MSG_POST_S1:
case MSG_POST_S3:
case TOPIC_POST_S1:
case TOPIC_POST_S3:
postTimeoutCleanup();
return;
default:
retrySub = true;
title = "Timeout";
msg = "Connection timed out, press retry to try again.";
posButtonText = "Retry";
break;
}
final boolean retry = retrySub;
AlertDialog.Builder b = new AlertDialog.Builder(AllInOneV2.this);
b.setTitle(title);
b.setMessage(msg);
b.setPositiveButton(posButtonText, new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
if (retry)
session.get(session.getLastAttemptedDesc(), session.getLastAttemptedPath());
else
refreshClicked(new View(AllInOneV2.this));
}
});
b.setNegativeButton("Dismiss", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
postExecuteCleanup(session.getLastDesc());
}
});
b.show();
}
private void postTimeoutCleanup() {
AlertDialog.Builder b = new AlertDialog.Builder(AllInOneV2.this);
b.setTitle("Post Timeout");
b.setMessage("Post timed out. Refresh the page to check if your post made it through. Dismissing " +
"and posting again without first checking if the post went through may result in the post " +
"being submitted twice.");
b.setPositiveButton("Refresh", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
session.get(Session.determineNetDesc(postPostUrl), postPostUrl);
}
});
b.setNeutralButton("Copy Post", null);
b.setNegativeButton("Dismiss", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
session.setLastPathAndDesc(postPostUrl, Session.determineNetDesc(postPostUrl));
ptrCleanup();
}
});
b.setCancelable(false);
final AlertDialog d = b.create();
d.setOnShowListener(new OnShowListener() {
@Override
public void onShow(DialogInterface dialog) {
d.getButton(DialogInterface.BUTTON_NEUTRAL).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
android.content.ClipboardManager clipboard =
(android.content.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
clipboard.setPrimaryClip(android.content.ClipData.newPlainText("simple text", savedPostBody));
Crouton.showText(AllInOneV2.this,
"Message body copied to clipboard.",
Theming.croutonStyle(),
(ViewGroup) v.getParent().getParent());
}
});
}
});
d.show();
}
private boolean isRoR = false;
private void postInterfaceCleanup() {
if (!isRoR && postWrapper.getVisibility() == View.VISIBLE) {
if (BuildConfig.DEBUG) wtl("postInterfaceCleanup fired --NEL");
postWrapper.setVisibility(View.GONE);
pollButton.setVisibility(View.GONE);
pollSep.setVisibility(View.GONE);
postBody.setText(null);
postTitle.setText(null);
clearPoll();
messageIDForEditing = null;
fab.setVisibility(View.VISIBLE);
hideSoftKeyboard(postBody);
if (!pageLabel.getText().toString().equals("~ 1 / 1 ~"))
pageJumperWrapper.setVisibility(View.VISIBLE);
}
}
private void ptrCleanup() {
swipeRefreshLayout.setRefreshing(false);
setAllMenuItemsEnabled(true);
if (postWrapper.getVisibility() == View.VISIBLE) {
postSubmitButton.setEnabled(true);
postCancelButton.setEnabled(true);
pollButton.setEnabled(true);
}
}
public void setAMPLinkVisible(boolean visible) {
dwrAMPItem.setVisible(visible);
}
public void preExecuteSetup(NetDesc desc) {
if (BuildConfig.DEBUG) wtl("GRAIO dPreES fired --NEL, desc: " + desc.name());
if (desc != NetDesc.MSG_POST_S1 && desc != NetDesc.TOPIC_POST_S1 && desc != NetDesc.EDIT_MSG)
postInterfaceCleanup();
swipeRefreshLayout.setRefreshing(true);
setAllMenuItemsEnabled(false);
}
/*
* *****************************************
* START HNR
* *****************************************
*/
ArrayList<BaseRowData> adapterRows = new ArrayList<>();
ViewAdapter viewAdapter = new ViewAdapter(this, adapterRows);
@SuppressLint("SetJavaScriptEnabled")
public void processContent(NetDesc desc, Document doc, String resUrl) {
if (BuildConfig.DEBUG) wtl("GRAIO hNR fired, desc: " + desc.name());
swipeRefreshLayout.setEnabled(false);
if (searchIcon != null)
searchIcon.collapseActionView();
setAllMenuItemsExceptRefreshVisibility(false);
adapterRows.clear();
boolean isDefaultAcc = Session.getUser() != null &&
Session.getUser().equals(settings.getString("defaultAccount", HeaderSettings.NO_DEFAULT_ACCOUNT));
if (BuildConfig.DEBUG) wtl("setting board, topic, message id to null");
boardID = null;
topicID = null;
messageIDForEditing = null;
Element tbody;
Element pj;
String headerTitle;
String firstPage = null;
String prevPage = null;
int[] pagesInfo = new int[]{1, 1};
String nextPage = null;
String lastPage = null;
String pagePrefix = null;
if (BuildConfig.DEBUG) wtl("checking for board quick list");
Element boardsDropdown = null;
for (Element e : doc.select("ul.masthead_mygames_subnav")) {
if (e.previousElementSibling().ownText().equals("My Boards")) {
boardsDropdown = e;
break;
}
}
if (boardsDropdown != null) {
Elements dItems = boardsDropdown.getElementsByTag("a");
boardQuickListOptions = new String[dItems.size() + 1];
boardQuickListLinks = new String[dItems.size() + 1];
boardQuickListOptions[0] = "Go to Boards Page...";
int x = 1;
for (Element e : dItems) {
boardQuickListOptions[x] = e.text();
boardQuickListLinks[x] = e.attr("href");
x++;
}
}
contentList.setDividerHeight(Theming.convertDPtoPX(this, 1));
switch (desc) {
case BOARD_JUMPER:
case LOGIN_S2:
updateHeaderNoJumper("Board Jumper", NetDesc.BOARD_JUMPER);
setMenuItemVisibility(searchIcon, true);
processBoards(doc);
break;
case BOARD_LIST:
updateHeaderNoJumper(doc.getElementsByTag("th").get(4).text(), NetDesc.BOARD_LIST);
processBoards(doc);
break;
case NOTIFS_PAGE:
settings.edit().putLong("notifsLastCheck", System.currentTimeMillis()).apply();
tbody = doc.getElementsByTag("tbody").first();
headerTitle = Session.getUser() + "'s Notifications";
updateHeaderNoJumper(headerTitle, desc);
if (tbody != null) {
for (Element row : tbody.getElementsByTag("tr")) {
Elements cells = row.children();
// [title, url] [time] [read]
Element titleLinkElem = cells.get(0).children().first();
String title = titleLinkElem.text();
String link = titleLinkElem.attr("href");
String time = cells.get(1).text();
boolean isOld = false;
if (cells.get(2).text().equals("Read"))
isOld = true;
adapterRows.add(new NotifRowData(title, time, link, isOld));
}
} else {
adapterRows.add(new HeaderRowData("You have no notifications at this time."));
}
setMenuItemVisibility(clearUnreadNotifsIcon, true);
NotifierService.notifDismiss(this);
break;
case MENTIONS_PAGE:
tbody = doc.getElementsByTag("tbody").first();
headerTitle = Session.getUser() + "'s Mentions";
updateHeaderNoJumper(headerTitle, desc);
if (tbody != null) {
for (Element row : tbody.getElementsByTag("tr")) {
Elements cells = row.children();
// [topic] [board] [user] [time]
Element topicLinkElem = cells.get(0).children().first();
String topic = topicLinkElem.text();
String link = topicLinkElem.attr("href");
String board = cells.get(1).text();
String user = cells.get(2).text();
String time = cells.get(3).text();
adapterRows.add(new MentionRowData(topic, board, user, time, link));
}
} else {
adapterRows.add(new HeaderRowData("You have no mentions at this time."));
}
break;
case PM_INBOX:
case PM_OUTBOX:
tbody = doc.getElementsByTag("tbody").first();
boolean isInbox = false;
if (desc == NetDesc.PM_INBOX)
isInbox = true;
if (isInbox)
headerTitle = Session.getUser() + "'s PM Inbox";
else
headerTitle = Session.getUser() + "'s PM Outbox";
if (tbody != null) {
pj = doc.select("ul.paginate").first();
if (pj != null) {
pagesInfo = getPageJumperInfo(pj);
if (isInbox)
pagePrefix = "/pm/?page=";
else
pagePrefix = "/pm/sent?page=";
if (pagesInfo[0] > 1) {
firstPage = pagePrefix + 0;
prevPage = pagePrefix + (pagesInfo[0] - 2);
}
if (pagesInfo[0] != pagesInfo[1]) {
nextPage = pagePrefix + pagesInfo[0];
lastPage = pagePrefix + (pagesInfo[1] - 1);
}
}
updateHeader(headerTitle, firstPage, prevPage, pagesInfo[0],
pagesInfo[1], nextPage, lastPage, pagePrefix, desc);
for (Element row : tbody.getElementsByTag("tr")) {
Elements cells = row.children();
// [icon] [sender] [subject] [time] [check]
boolean isOld = true;
if (cells.get(0).children().first().hasClass("fa-circle"))
isOld = false;
String sender = cells.get(1).text();
Element subjectLinkElem = cells.get(2).children().first();
String subject = subjectLinkElem.text();
String link = subjectLinkElem.attr("href");
String time = cells.get(3).text();
adapterRows.add(new PMRowData(subject, sender, time, link, isOld, isInbox));
}
} else {
updateHeaderNoJumper(headerTitle, desc);
adapterRows.add(new HeaderRowData("There are no private messages here at this time."));
}
fab.setVisibility(View.VISIBLE);
pMode = PostMode.NEW_PM;
if (isInbox)
setMenuItemVisibility(pmOutboxIcon, true);
else
setMenuItemVisibility(pmInboxIcon, true);
break;
case PM_INBOX_DETAIL:
case PM_OUTBOX_DETAIL:
String pmTitle = doc.select("h2.title").first().text();
String pmMessage = doc.select("div.body").first().outerHtml();
Element foot = doc.select("div.foot").first();
foot.child(1).remove();
String pmFoot = foot.outerHtml();
//Sent by: P4wn4g3 on 6/1/2013 2:15:55 PM
String footText = foot.text();
String sender = footText.substring(9, footText.indexOf(" on "));
updateHeaderNoJumper(pmTitle, desc);
if (desc == NetDesc.PM_INBOX_DETAIL) {
replyTo = sender;
if (!pmTitle.startsWith("Re: "))
replySubject = "Re: " + pmTitle;
else
replySubject = pmTitle;
setMenuItemVisibility(replyIcon, true);
}
adapterRows.add(new PMDetailRowData(sender, pmTitle, pmMessage + pmFoot));
break;
case AMP_LIST:
if (BuildConfig.DEBUG) wtl("GRAIO hNR determined this is an amp response");
tbody = doc.getElementsByTag("tbody").first();
headerTitle = Session.getUser() + "'s Active Messages";
if (doc.select("ul.paginate").size() > 1) {
pj = doc.select("ul.paginate").get(1);
if (pj != null && !pj.hasClass("user")
&& !pj.hasClass("tsort")) {
pagesInfo = getPageJumperInfo(pj);
pagePrefix = buildAMPLink() + "&page=";
if (pagesInfo[0] > 1) {
firstPage = pagePrefix + 0;
prevPage = pagePrefix + (pagesInfo[0] - 2);
}
if (pagesInfo[0] != pagesInfo[1]) {
nextPage = pagePrefix + pagesInfo[0];
lastPage = pagePrefix + (pagesInfo[1] - 1);
}
}
}
updateHeader(headerTitle, firstPage, prevPage, pagesInfo[0],
pagesInfo[1], nextPage, lastPage, pagePrefix, NetDesc.AMP_LIST);
if (!tbody.children().isEmpty()) {
for (Element row : tbody.children()) {
// [board] [read status] [title] [msg] [last post] [your last post]
Elements cells = row.children();
String board = cells.get(0).text();
Element titleLinkElem = cells.get(2).child(0);
String title = titleLinkElem.text();
String link = titleLinkElem.attr("href");
String mCount = cells.get(3).textNodes().get(0).text().trim();
Element lPostLinkElem = cells.get(4).child(1);
String lPost = lPostLinkElem.text();
String lPostLink = lPostLinkElem.attr("href");
ReadStatus status = ReadStatus.UNREAD;
String tImg = cells.get(1).child(0).className();
if (tImg.endsWith("_read"))
status = ReadStatus.READ;
else if (tImg.endsWith("_unread")) {
status = ReadStatus.NEW_POST;
lPostLink = cells.get(1).child(0).attr("href");
}
adapterRows.add(new AMPRowData(title, board, lPost, mCount, link,
lPostLink, status));
}
} else {
adapterRows.add(new HeaderRowData("You have no active messages at this time."));
}
if (BuildConfig.DEBUG) wtl("amp response block finished");
break;
case TRACKED_TOPICS:
headerTitle = Session.getUser() + "'s Tracked Topics";
updateHeaderNoJumper(headerTitle, desc);
tbody = doc.getElementsByTag("tbody").first();
if (tbody != null) {
for (Element row : tbody.children()) {
// [remove] [title] [board name] [msgs] [last [pst]
Elements cells = row.children();
int rsMod = 0;
if (cells.size() == 6)
rsMod = 1;
String removeLink = cells.get(0).child(0)
.attr("href");
String topicLink = cells.get(1 + rsMod).child(0)
.attr("href");
String topicText = cells.get(1 + rsMod).text();
String board = cells.get(2 + rsMod).text();
String msgs = cells.get(3 + rsMod).text();
String lPostLink = cells.get(4 + rsMod).child(0)
.attr("href");
String lPostText = cells.get(4 + rsMod).text();
ReadStatus status = ReadStatus.UNREAD;
if (rsMod == 1) {
String tImg = cells.get(1).child(0).className();
if (tImg.endsWith("_read"))
status = ReadStatus.READ;
else if (tImg.endsWith("_unread"))
status = ReadStatus.NEW_POST;
}
adapterRows.add(new TrackedTopicRowData(board, topicText, lPostText,
msgs, topicLink, removeLink, lPostLink, status));
}
} else {
adapterRows.add(new HeaderRowData("You have no tracked topics at this time."));
}
break;
case BOARD:
if (BuildConfig.DEBUG) wtl("GRAIO hNR determined this is a board response");
if (BuildConfig.DEBUG) wtl("setting board id");
boardID = parseBoardID(resUrl);
boolean isSplitList = false;
if (doc.getElementsByTag("th").first() != null) {
if (doc.getElementsByTag("th").first().text().equals("Board Title")) {
if (BuildConfig.DEBUG) wtl("is actually a split board list");
updateHeaderNoJumper(doc.select("h1.page-title").first().text(), NetDesc.BOARD);
processBoards(doc);
isSplitList = true;
}
}
if (!isSplitList) {
String searchQuery = EMPTY_STRING;
String searchPJAddition = EMPTY_STRING;
if (resUrl.contains("search=")) {
if (BuildConfig.DEBUG) wtl("board search url: " + resUrl);
searchQuery = resUrl.substring(resUrl.indexOf("search=") + 7);
int i = searchQuery.indexOf('&');
if (i != -1)
searchQuery = searchQuery.replace(searchQuery.substring(i), EMPTY_STRING);
searchPJAddition = "&search=" + searchQuery;
try {
searchQuery = URLDecoder.decode(searchQuery, DocumentParser.CHARSET_NAME);
} catch (UnsupportedEncodingException e) {
throw new AssertionError(DocumentParser.CHARSET_NAME + " is unknown");
// should never happen
}
}
Element headerElem = doc.getElementsByClass("page-title").first();
if (headerElem != null)
headerTitle = headerElem.text();
else
headerTitle = "GFAQs Cache Error, Board Title Not Found";
if (searchQuery.length() > 0)
headerTitle += " (search: " + searchQuery + ")";
if (doc.select("ul.paginate").size() > 1) {
pj = doc.select("ul.paginate").get(1);
if (pj != null && !pj.hasClass("user")) {
pagesInfo = getPageJumperInfo(pj);
pagePrefix = "boards/" + boardID + "?page=";
if (pagesInfo[0] > 1) {
firstPage = pagePrefix + 0 + searchPJAddition;
prevPage = pagePrefix + (pagesInfo[0] - 2) + searchPJAddition;
}
if (pagesInfo[0] != pagesInfo[1]) {
nextPage = pagePrefix + pagesInfo[0] + searchPJAddition;
lastPage = pagePrefix + (pagesInfo[1] - 1) + searchPJAddition;
if (pagesInfo[0] > pagesInfo[1]) {
session.forceNoHistoryAddition();
session.forceSkipAIOCleanup();
Crouton.showText(this, "Page count higher than page amount, going to last page...", Theming.croutonStyle());
session.get(NetDesc.BOARD, lastPage);
return;
}
}
}
}
updateHeader(headerTitle, firstPage, prevPage, pagesInfo[0], pagesInfo[1], nextPage,
lastPage, pagePrefix + searchPJAddition, NetDesc.BOARD);
setMenuItemVisibility(searchIcon, true);
if (Session.isLoggedIn()) {
Element favbtn = doc.getElementsByClass("user").first().getElementsByAttributeValueStarting("onclick", "post_click").first();
if (favbtn != null) {
String favtext = favbtn.text().toLowerCase();
String onclick = favbtn.attr("onclick");
int endPoint = onclick.lastIndexOf('\'');
int startPoint = onclick.lastIndexOf('\'', endPoint - 1) + 1;
favKey = onclick.substring(startPoint, endPoint);
fMode = FavMode.ON_BOARD;
if (favtext.contains("add to favorites"))
setMenuItemVisibility(addFavIcon, true);
else if (favtext.contains("remove favorite"))
setMenuItemVisibility(remFavIcon, true);
}
updatePostingRights(doc, false);
}
Element splitList = doc.select("p:contains(this is a split board)").first();
if (splitList != null) {
String splitListLink = splitList.child(0).attr("href");
adapterRows.add(new BoardRowData("This is a Split Board.", "Click here to return to the Split List.",
null, null, null, splitListLink, BoardType.SPLIT));
}
Element table = doc.select("table.board").first();
if (table != null && !table.select("td").first().hasAttr("colspan")) {
table.getElementsByTag("col").get(2).remove();
table.getElementsByTag("th").get(2).remove();
table.getElementsByTag("col").get(0).remove();
table.getElementsByTag("th").get(0).remove();
if (BuildConfig.DEBUG) wtl("board row parsing start");
boolean skipFirst = true;
Set<String> hlUsers = hlDB.getHighlightedUsers().keySet();
for (Element row : table.getElementsByTag("tr")) {
if (!skipFirst) {
Elements cells = row.getElementsByTag("td");
// cells = [image] [title] [author] [post count] [last post]
String tImg = cells.get(0).child(0).className();
Element titleLinkElem = cells.get(1).child(0);
String title = titleLinkElem.text();
String tUrl = titleLinkElem.attr("href");
String tc = cells.get(2).text();
Element lPostLinkElem = cells.get(4).child(0);
String lastPost = lPostLinkElem.text();
String lpUrl = lPostLinkElem.attr("href");
String mCount = cells.get(3).text();
TopicType type = TopicType.NORMAL;
if (tImg.contains("poll"))
type = TopicType.POLL;
else if (tImg.contains("sticky"))
type = TopicType.PINNED;
else if (tImg.contains("closed"))
type = TopicType.LOCKED;
else if (tImg.contains("archived"))
type = TopicType.ARCHIVED;
if (BuildConfig.DEBUG) wtl(tImg + ", " + type.name());
ReadStatus status = ReadStatus.UNREAD;
if (tImg.endsWith("_read"))
status = ReadStatus.READ;
else if (tImg.endsWith("_unread")) {
status = ReadStatus.NEW_POST;
lpUrl = cells.get(0).child(0).attr("href");
}
int hlColor = 0;
if (hlUsers.contains(tc.toLowerCase(Locale.US))) {
HighlightedUser hUser = hlDB.getHighlightedUsers().get(tc.toLowerCase(Locale.US));
hlColor = hUser.getColor();
tc += " (" + hUser.getLabel() + ")";
}
adapterRows.add(new TopicRowData(title, tc, lastPost, mCount, tUrl,
lpUrl, type, status, hlColor));
} else
skipFirst = false;
}
if (BuildConfig.DEBUG) wtl("board row parsing end");
} else {
adapterRows.add(new HeaderRowData("There are no topics at this time."));
}
}
if (BuildConfig.DEBUG) wtl("board response block finished");
break;
case TOPIC:
contentList.setDividerHeight(0);
boardID = parseBoardID(resUrl);
topicID = parseTopicID(resUrl);
tlUrl = "boards/" + boardID;
if (BuildConfig.DEBUG) wtl(tlUrl);
setMenuItemVisibility(topicListIcon, true);
Element headerElem = doc.getElementsByClass("title").first();
if (headerElem != null)
headerTitle = headerElem.text();
else
headerTitle = "GFAQs Cache Error, Title Not Found";
if (headerTitle.equals("Log In to GameFAQs")) {
headerElem = doc.getElementsByClass("title").get(1);
if (headerElem != null)
headerTitle = headerElem.text();
}
if (doc.select("ul.paginate").size() > 1) {
pj = doc.select("ul.paginate").get(1);
if (pj != null && !pj.hasClass("user")) {
pagesInfo = getPageJumperInfo(pj);
pagePrefix = "boards/" + boardID + "/" + topicID + "?page=";
if (pagesInfo[0] > 1) {
firstPage = pagePrefix + 0;
prevPage = pagePrefix + (pagesInfo[0] - 2);
}
if (pagesInfo[0] != pagesInfo[1]) {
nextPage = pagePrefix + pagesInfo[0];
lastPage = pagePrefix + (pagesInfo[1] - 1);
if (pagesInfo[0] > pagesInfo[1]) {
session.forceNoHistoryAddition();
session.forceSkipAIOCleanup();
Crouton.showText(this, "Page count higher than page amount, going to last page...", Theming.croutonStyle());
session.get(NetDesc.TOPIC, lastPage);
return;
}
}
}
}
updateHeader(headerTitle, firstPage, prevPage, pagesInfo[0],
pagesInfo[1], nextPage, lastPage, pagePrefix, NetDesc.TOPIC);
if (Session.isLoggedIn()) {
Element favbtn = doc.getElementsByClass("user").first().getElementsByAttributeValueStarting("onclick", "post_click").first();
if (favbtn != null) {
String favtext = favbtn.text().toLowerCase();
String onclick = favbtn.attr("onclick");
int endPoint = onclick.lastIndexOf('\'');
int startPoint = onclick.lastIndexOf('\'', endPoint - 1) + 1;
favKey = onclick.substring(startPoint, endPoint);
fMode = FavMode.ON_TOPIC;
if (favtext.contains("track topic"))
setMenuItemVisibility(addFavIcon, true);
else if (favtext.contains("stop tracking"))
setMenuItemVisibility(remFavIcon, true);
}
updatePostingRights(doc, true);
}
String goToThisPost = null;
if (goToUrlDefinedPost) {
if (resUrl.indexOf('#') != -1) {
goToThisPost = resUrl.substring(resUrl.indexOf('#'));
} else {
// goToUrlDefinedPost is true when there is no url defined post, oops
goToUrlDefinedPost = false;
}
}
Elements rows = doc.select("table.board").first().getElementsByTag("tr");
int rowCount = rows.size();
int msgIndex = 0;
Set<String> hlUsers = hlDB.getHighlightedUsers().keySet();
for (int x = 0; x < rowCount; x++) {
Element row = rows.get(x);
if (row.select("div.msg_deleted").isEmpty()) {
String user;
String postNum;
String postTime;
String mID = null;
String userTitles = EMPTY_STRING;
Element msgBody;
boolean canReport = false, canDelete = false, canEdit = false, canQuote = false;
Element infoBox = row.select("div.msg_infobox").first();
user = infoBox.getElementsByTag("b").first().text();
Element userInfo = infoBox.select("span.user_info").first();
if (userInfo != null)
userTitles = " " + userInfo.text();
Element userTag = infoBox.select("span.tag").first();
if (userTag != null)
userTitles += " (" + userTag.text() + ")";
postTime = infoBox.select("span.post_time").first().text();
Element number = infoBox.select("span.message_num").first();
postNum = number.text();
if (!number.children().isEmpty()) {
mID = parseMessageID(number.child(0).attr("href"));
}
msgBody = row.select("div.msg_body").first();
Element msgBelow = row.select("div.msg_below").first();
Element edited = msgBelow.select("span.edited").first();
if (edited != null)
userTitles += " (edited)";
Element belowOptions = msgBelow.select("span.options").first();
if (belowOptions != null) {
String options = belowOptions.text();
if (options.contains("report"))
canReport = true;
if (options.contains("delete"))
canDelete = true;
if (options.contains("edit"))
canEdit = true;
if (options.contains("quote"))
canQuote = true;
}
int hlColor = 0;
if (hlUsers.contains(user.toLowerCase(Locale.US))) {
HighlightedUser hUser = hlDB
.getHighlightedUsers().get(
user.toLowerCase(Locale.US));
hlColor = hUser.getColor();
userTitles += " (" + hUser.getLabel() + ")";
}
if (goToUrlDefinedPost) {
if (postNum.equals(goToThisPost))
goToThisIndex = msgIndex;
}
String avatarUrl = row.getElementsByClass("imgboxart").first().attr("src");
if (BuildConfig.DEBUG) wtl("creating messagerowdata object");
adapterRows.add(new MessageRowData(user, userTitles, avatarUrl, postNum,
postTime, msgBody, boardID, topicID, mID, hlColor, canReport, canDelete, canEdit, canQuote));
} else {
String postNum = row.select("span.message_num").first().text();
if (goToUrlDefinedPost) {
if (postNum.equals(goToThisPost))
goToThisIndex = msgIndex;
}
adapterRows.add(new MessageRowData(true, postNum));
}
msgIndex++;
}
break;
case MESSAGE_DETAIL:
updateHeaderNoJumper("Message Detail", NetDesc.MESSAGE_DETAIL);
boardID = parseBoardID(resUrl);
topicID = parseTopicID(resUrl);
String mID = parseMessageID(resUrl);
Elements msgRows = doc.select("td.msg");
adapterRows.add(new HeaderRowData("Current Version"));
MessageRowData msg;
int msgRowCount = msgRows.size();
for (int x = 0; x < msgRowCount; x++) {
if (x == 1)
adapterRows.add(new HeaderRowData("Previous Version(s)"));
Element currRow = msgRows.get(x);
Element msgInfobox = currRow.select("div.msg_infobox").first();
Element msgBody = currRow.select("div.msg_body").first();
String user = msgInfobox.getElementsByTag("b").first().text();
String postTime = msgInfobox.select("span.post_time").first().text();
msg = new MessageRowData(user, EMPTY_STRING, EMPTY_STRING,
"#" + (msgRowCount - x), postTime, msgBody, boardID, topicID,
mID, 0, false, false, false, false);
msg.disableTopClick();
adapterRows.add(msg);
}
break;
case USER_TAG:
if (BuildConfig.DEBUG) wtl("starting check for user tag success");
Element error = doc.getElementsByClass("error").first();
if (error == null) {
Crouton.showText(this, "User tag updated successfully.", Theming.croutonStyle());
} else {
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setTitle("There was an error tagging the user...");
b.setMessage("Error message from GameFAQs:\n\n" + error.text());
b.setPositiveButton("OK", null);
b.show();
}
case USER_DETAIL:
if (BuildConfig.DEBUG) wtl("starting user detail processing");
tbody = doc.select("table.board").first().getElementsByTag("tbody").first();
String name = null;
String ID = null;
String level = null;
String creation = null;
String lVisit = null;
String sig = null;
String karma = null;
String AMP = null;
String tagKey = null;
String tagText = null;
for (Element row : tbody.children()) {
String label = row.child(0).text().toLowerCase(Locale.US);
if (BuildConfig.DEBUG) wtl("user detail row label: " + label);
switch (label) {
case "user name":
name = row.child(1).text();
break;
case "user id":
ID = row.child(1).text();
break;
case "board user level":
level = row.child(1).html();
if (BuildConfig.DEBUG) wtl("set level: " + level);
break;
case "account created":
creation = row.child(1).text();
break;
case "last visit":
lVisit = row.child(1).text();
break;
case "signature":
sig = row.child(1).html();
break;
case "karma":
karma = row.child(1).text();
break;
case "active messages posted":
AMP = row.child(1).text();
break;
}
}
if (Session.isLoggedIn()) {
Element pmIcon = doc.select("i.fa-envelope").last();
if (pmIcon != null && pmIcon.attr("title").startsWith("Send a PM to"))
setMenuItemVisibility(sendUserPMIcon, true);
setMenuItemVisibility(tagUserIcon, true);
tagKey = doc.getElementsByAttributeValue("name", "key").attr("value");
tagText = doc.getElementsByAttributeValue("name", "tag_text").attr("value");
if (tagText == null) tagText = "";
}
updateHeaderNoJumper(name + "'s Details", NetDesc.USER_DETAIL);
userDetailData = new UserDetailRowData(name, ID, level, creation, lVisit, sig,
karma, AMP, tagKey, tagText, resUrl);
adapterRows.add(userDetailData);
break;
case GAME_SEARCH:
if (BuildConfig.DEBUG) wtl("GRAIO hNR determined this is a game search response");
if (BuildConfig.DEBUG) wtl("game search url: " + resUrl);
String searchQuery = resUrl.substring(resUrl.indexOf("game=") + 5);
int i = searchQuery.indexOf("&");
if (i != -1)
searchQuery = searchQuery.replace(searchQuery.substring(i), EMPTY_STRING);
int pageIndex = resUrl.indexOf("page=");
if (pageIndex != -1) {
String currPage = resUrl.substring(pageIndex + 5);
i = currPage.indexOf("&");
if (i != -1)
currPage = currPage.replace(currPage.substring(i), EMPTY_STRING);
pagesInfo[0] = Integer.parseInt(currPage) + 1;
} else {
pagesInfo[0] = 1;
}
if (pagesInfo[0] > 1) {
firstPage = "/search/index.html?game=" + searchQuery + "&page=0";
prevPage = "/search/index.html?game=" + searchQuery + "&page=" + (pagesInfo[0] - 2);
}
if (!doc.getElementsByClass("icon-angle-right").isEmpty()) {
nextPage = "/search/index.html?game=" + searchQuery + "&page=" + (pagesInfo[0]);
}
try {
headerTitle = "Searching games: " + URLDecoder.decode(searchQuery, DocumentParser.CHARSET_NAME) + EMPTY_STRING;
} catch (UnsupportedEncodingException e) {
throw new AssertionError(DocumentParser.CHARSET_NAME + " is unknown");
// should never happen
}
updateHeader(headerTitle, firstPage, prevPage, pagesInfo[0],
-1, nextPage, lastPage, pagePrefix, NetDesc.GAME_SEARCH);
setMenuItemVisibility(searchIcon, true);
Elements gameSearchTables = doc.select("table.results");
int tCount = gameSearchTables.size();
int tCounter = 0;
if (!gameSearchTables.isEmpty()) {
for (Element table : gameSearchTables) {
tCounter++;
if (tCounter < tCount)
adapterRows.add(new HeaderRowData("Best Matches"));
else
adapterRows.add(new HeaderRowData("Good Matches"));
String prevPlatform = EMPTY_STRING;
if (BuildConfig.DEBUG) wtl("board row parsing start");
for (Element row : table.getElementsByTag("tr")) {
if (row.parent().tagName().equals("tbody")) {
Elements cells = row.getElementsByTag("td");
// cells = [platform] [title] [faqs] [codes] [saves] [revs] [mygames] [q&a] [pics] [vids] [board]
String platform = cells.get(0).text();
String bName = cells.get(1).text();
String bUrl = cells.get(9).child(0).attr("href");
if (platform.codePointAt(0) == ('\u00A0')) {
platform = prevPlatform;
} else {
prevPlatform = platform;
}
adapterRows.add(new GameSearchRowData(bName, platform, bUrl));
}
}
if (BuildConfig.DEBUG) wtl("board row parsing end");
}
} else {
adapterRows.add(new HeaderRowData("No results."));
}
if (BuildConfig.DEBUG) wtl("game search response block finished");
break;
default:
if (BuildConfig.DEBUG) wtl("GRAIO hNR determined response type is unhandled");
getSupportActionBar().setTitle("Page unhandled - " + resUrl);
break;
}
Element pmInboxLink = doc.select("i.fa-envelope").first();
String pmButtonLabel = getString(R.string.pm_inbox);
if (pmInboxLink != null) {
pmButtonLabel += " " + ((TextNode) pmInboxLink.nextSibling()).text();
}
dwrPMInboxItem.setTitle(pmButtonLabel);
Element notifsObject = doc.select("span.notifications").first();
notifsAdapter.clear();
notifsLinks.clear();
notifsLinks.add("filler");
String count = "0";
if (notifsObject != null) {
count = notifsObject.child(0).text();
if (count.equals("1"))
count = count + " " + getString(R.string.notification);
else
count = count + " " + getString(R.string.notifications);
notifsAdapter.add(count);
Elements notifsLines = notifsObject.getElementsByTag("li");
notifsLines.remove(notifsLines.size() - 1);
for (Element e : notifsLines) {
notifsAdapter.add(e.text());
notifsLinks.add(e.select("a").first().attr("href"));
}
notifsAdapter.add("View All");
notifsLinks.add(NOTIFS_PAGE_LINK);
notifsAdapter.add("Clear All");
notifsLinks.add(NOTIFS_CLEAR_LINK);
setMenuItemVisibility(unreadNotifsIcon, true);
} else {
notifsAdapter.add(count + " " + getString(R.string.notifications));
notifsAdapter.add("View All");
notifsLinks.add(NOTIFS_PAGE_LINK);
setMenuItemVisibility(unreadNotifsIcon, false);
}
notifsAdapter.notifyDataSetChanged();
swipeRefreshLayout.setEnabled(settings.getBoolean("enablePTR", false));
viewAdapter.notifyDataSetChanged();
if (consumeGoToUrlDefinedPost() && !Session.applySavedScroll) {
contentList.post(new Runnable() {
@Override
public void run() {
contentList.setSelection(goToThisIndex);
}
});
} else if (Session.applySavedScroll) {
contentList.post(new Runnable() {
@Override
public void run() {
contentList.setSelectionFromTop(Session.savedScrollVal[0], Session.savedScrollVal[1]);
Session.applySavedScroll = false;
}
});
} else {
contentList.post(new Runnable() {
@Override
public void run() {
contentList.setSelectionAfterHeaderView();
}
});
}
if (swipeRefreshLayout.isRefreshing())
swipeRefreshLayout.setRefreshing(false);
if (BuildConfig.DEBUG) wtl("GRAIO hNR finishing");
}
/*
* ********************************
* END HNR
* ********************************
*/
private void processBoards(Document pRes) {
Elements homeTables = pRes.select("table.board");
boolean skippedFirst = false;
for (Element row : homeTables.first().getElementsByTag("tr")) {
if (skippedFirst) {
if (row.hasClass("head")) {
adapterRows.add(new HeaderRowData(row.text()));
} else {
// [title + link] [topics] [msgs] [last post]
Elements cells = row.children();
Element titleCell = cells.get(0);
String lvlReq = EMPTY_STRING;
if (!titleCell.textNodes().isEmpty())
lvlReq = titleCell.textNodes().get(0).toString();
String title = titleCell.child(0).text() + lvlReq;
String boardDesc = null;
if (titleCell.children().size() > 2)
boardDesc = titleCell.child(2).text();
String link = titleCell.select("a").first().attr("href");
if (link.isEmpty())
link = null;
String tCount = null;
String mCount = null;
String lPost = null;
BoardType bvt;
if (cells.size() > 3) {
tCount = cells.get(1).text();
mCount = cells.get(2).text();
lPost = cells.get(3).text();
bvt = BoardType.NORMAL;
} else
bvt = BoardType.SPLIT;
adapterRows.add(new BoardRowData(title, boardDesc, lPost, tCount, mCount, link, bvt));
}
} else {
skippedFirst = true;
}
}
}
private int[] getPageJumperInfo(Element pj) {
int[] i = new int[]{1, 1};
if (pj != null && !pj.hasClass("user") && !pj.hasClass("tsort")) {
String currPage, pageCount;
int x = 0;
String pjText = pj.child(x).text();
while (pjText.contains("First") || pjText.contains("Previous")) {
x++;
pjText = pj.child(x).text();
}
// Page [dropdown] of 4
// Page 1 of 3
if (pj.getElementsByTag("select").isEmpty()) {
int ofIndex = pjText.indexOf(" of ");
currPage = pjText.substring(5, ofIndex); // "Page ".length = 5
int pageCountEnd = pjText.length();
pageCount = pjText.substring(ofIndex + 4, pageCountEnd);
} else {
currPage = pj.select("option[selected=selected]").first().text();
pageCount = pj.getElementsByTag("option").last().text();
}
i[0] = Integer.parseInt(currPage);
i[1] = Integer.parseInt(pageCount);
}
return i;
}
private void updatePostingRights(Document pRes, boolean onTopic) {
if (onTopic) {
if (pRes.getElementsByClass("user").first().text().contains("Post New Message")) {
fab.setVisibility(View.VISIBLE);
pMode = PostMode.ON_TOPIC;
}
} else {
if (pRes.getElementsByClass("user").first().text().contains("New Topic")) {
fab.setVisibility(View.VISIBLE);
pMode = PostMode.ON_BOARD;
}
}
}
public void postExecuteCleanup(NetDesc desc) {
if (BuildConfig.DEBUG)
wtl("GRAIO dPostEC --NEL, desc: " + (desc == null ? "null" : desc.name()));
if (needToSetNavList) {
setNavDrawerVisibility(Session.isLoggedIn());
}
ptrCleanup();
if (desc == NetDesc.BOARD || desc == NetDesc.TOPIC)
postInterfaceCleanup();
if (isRoR)
isRoR = false;
setLoginName(Session.getUser());
System.gc();
}
private boolean goToUrlDefinedPost = false;
private int goToThisIndex = 0;
public void enableGoToUrlDefinedPost() {
goToUrlDefinedPost = true;
}
private boolean consumeGoToUrlDefinedPost() {
boolean temp = goToUrlDefinedPost;
goToUrlDefinedPost = false;
return temp;
}
private void updateHeader(String titleIn, String firstPageIn, String prevPageIn, int currPage,
int pageCount, String nextPageIn, String lastPageIn,
String jumperPageIn, NetDesc desc) {
if (pageCount == 1) {
updateHeaderNoJumper(titleIn, desc);
return;
}
assert getSupportActionBar() != null;
getSupportActionBar().setTitle(titleIn);
if (currPage == -1) {
pageJumperWrapper.setVisibility(View.GONE);
pageLabel.setText("~ 1 / 1 ~");
} else {
pageJumperWrapper.setVisibility(View.VISIBLE);
pageJumperDesc = desc;
if (firstPageIn != null) {
firstPageUrl = firstPageIn;
firstPage.setEnabled(true);
} else {
firstPage.setEnabled(false);
}
if (prevPageIn != null) {
prevPageUrl = prevPageIn;
prevPage.setEnabled(true);
} else {
prevPage.setEnabled(false);
}
if (nextPageIn != null) {
nextPageUrl = nextPageIn;
nextPage.setEnabled(true);
} else {
nextPage.setEnabled(false);
}
if (lastPageIn != null) {
lastPageUrl = lastPageIn;
lastPage.setEnabled(true);
} else {
lastPage.setEnabled(false);
}
if (pageCount != -1) {
jumperPageUrl = jumperPageIn;
final String[] items = new String[pageCount];
for (int x = 0; x < pageCount; x++) {
items[x] = String.valueOf(x + 1);
}
if (jumperDialogBuilder == null) {
jumperDialogBuilder = new AlertDialog.Builder(this);
jumperDialogBuilder.setTitle("Select a page...");
}
jumperDialogBuilder.setItems(items, new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
int x = jumperPageUrl.indexOf("?page=") + 6;
if (x == 5) // -1 + 6 = 5, when "?page=" is not found
x = jumperPageUrl.indexOf("&page=") + 6;
String go = jumperPageUrl.substring(0, x) + which + jumperPageUrl.substring(x);
if (BuildConfig.DEBUG) wtl("jumper dialog url: " + go);
session.get(pageJumperDesc, go);
}
});
pageLabel.setEnabled(true);
String t = "~ " + currPage + " / " + pageCount + " ~";
pageLabel.setText(t);
} else {
pageLabel.setEnabled(false);
String t = currPage + " / ???";
pageLabel.setText(t);
}
}
}
private void updateHeaderNoJumper(String title, NetDesc desc) {
updateHeader(title, null, null, -1, -1, null, null, null, desc);
}
private MessageRowView clickedMsg;
private String quoteSelection;
public void messageMenuClicked(MessageRowView msg) {
clickedMsg = msg;
quoteSelection = clickedMsg.getSelection();
//noinspection deprecation
showDialog(MESSAGE_ACTION_DIALOG);
}
private void editPostSetup(String msg, String msgID) {
postBody.setText(msg);
messageIDForEditing = msgID;
postSetup(true);
}
private void quoteSetup(String user, String msg) {
if (BuildConfig.DEBUG) wtl("quoteSetup fired");
String quotedMsg = "<cite>" + user + " posted...</cite>\n" + "<quote>" + msg + "</quote>\n";
int start = Math.max(postBody.getSelectionStart(), 0);
int end = Math.max(postBody.getSelectionEnd(), 0);
assert postBody.getText() != null : "postBody.getText() is null";
postBody.getText().replace(Math.min(start, end), Math.max(start, end), quotedMsg);
if (postWrapper.getVisibility() != View.VISIBLE)
postSetup(true);
else
postBody.setSelection(Math.min(start, end) + quotedMsg.length());
if (BuildConfig.DEBUG) wtl("quoteSetup finishing");
}
private void postSetup(boolean postingOnTopic) {
findViewById(R.id.aioHTMLScroller).scrollTo(0, 0);
pageJumperWrapper.setVisibility(View.GONE);
fab.setVisibility(View.GONE);
postSubmitButton.setEnabled(true);
postCancelButton.setEnabled(true);
if (postingOnTopic) {
titleWrapper.setVisibility(View.GONE);
postBody.requestFocus();
assert postBody.getText() != null : "postBody.getText() is null";
postBody.setSelection(postBody.getText().length());
} else {
titleWrapper.setVisibility(View.VISIBLE);
if (Session.userHasAdvancedPosting()) {
pollButton.setEnabled(true);
pollButton.setVisibility(View.VISIBLE);
pollSep.setVisibility(View.VISIBLE);
}
postTitle.requestFocus();
}
postWrapper.setVisibility(View.VISIBLE);
postPostUrl = session.getLastPath();
if (postPostUrl.contains("#"))
postPostUrl = postPostUrl.substring(0, postPostUrl.indexOf('#'));
}
public void postCancel(View view) {
if (BuildConfig.DEBUG) wtl("postCancel fired --NEL");
if (settings.getBoolean("confirmPostCancel", false)) {
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setMessage("Cancel this post?");
b.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
postInterfaceCleanup();
}
});
b.setNegativeButton("No", null);
b.show();
} else
postInterfaceCleanup();
}
public void postPollOptions(View view) {
//noinspection deprecation
showDialog(POLL_OPTIONS_DIALOG);
}
public void postDo(View view) {
if (BuildConfig.DEBUG) wtl("postDo fired");
if (settings.getBoolean("confirmPostSubmit", false)) {
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setMessage("Submit this post?");
b.setPositiveButton("Yes", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
postSubmit();
}
});
b.setNegativeButton("No", null);
b.show();
} else
postSubmit();
}
private void postSubmit() {
assert postBody.getText() != null : "postBody.getText() is null";
assert postTitle.getText() != null : "postTitle.getText() is null";
if (titleWrapper.getVisibility() == View.VISIBLE) {
if (BuildConfig.DEBUG) wtl("posting on a board");
// posting on a board
String path = Session.ROOT + "/boards/post?board=" + boardID;
int i = path.indexOf('-');
path = path.substring(0, i);
if (BuildConfig.DEBUG) wtl("post path: " + path);
savedPostBody = postBody.getText().toString();
if (BuildConfig.DEBUG) wtl("saved post body: " + savedPostBody);
savedPostTitle = postTitle.getText().toString();
if (BuildConfig.DEBUG) wtl("saved post title: " + savedPostTitle);
if (BuildConfig.DEBUG) wtl("sending topic");
postSubmitButton.setEnabled(false);
pollButton.setEnabled(false);
postCancelButton.setEnabled(false);
if (pollUse)
path += "&poll=1";
session.get(NetDesc.TOPIC_POST_S1, path);
} else {
// posting on a topic
if (BuildConfig.DEBUG) wtl("posting on a topic");
String path = Session.ROOT + "/boards/post?board=" + boardID + "&topic=" + topicID;
if (messageIDForEditing != null)
path += "&message=" + messageIDForEditing;
if (BuildConfig.DEBUG) wtl("post path: " + path);
savedPostBody = postBody.getText().toString();
if (BuildConfig.DEBUG) wtl("saved post body: " + savedPostBody);
if (BuildConfig.DEBUG) wtl("sending post");
postSubmitButton.setEnabled(false);
postCancelButton.setEnabled(false);
if (messageIDForEditing != null)
session.get(NetDesc.EDIT_MSG, path);
else
session.get(NetDesc.MSG_POST_S1, path);
}
}
/**
* creates dialogs
*/
@SuppressWarnings("deprecation")
@Override
protected Dialog onCreateDialog(int id) {
Dialog dialog = null;
switch (id) {
case SEND_PM_DIALOG:
dialog = createSendPMDialog();
break;
case MESSAGE_ACTION_DIALOG:
dialog = createMessageActionDialog();
break;
case REPORT_MESSAGE_DIALOG:
dialog = createReportMessageDialog();
break;
case POLL_OPTIONS_DIALOG:
dialog = createPollOptionsDialog();
break;
}
return dialog;
}
private Dialog createPollOptionsDialog() {
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setTitle("Poll Options");
LayoutInflater inflater = getLayoutInflater();
@SuppressLint("InflateParams")
final View v = inflater.inflate(R.layout.polloptions, null);
b.setView(v);
b.setCancelable(false);
final EditText[] options = new EditText[10];
assert v != null : "v is null";
final CheckBox poUse = (CheckBox) v.findViewById(R.id.poUse);
final EditText poTitle = (EditText) v.findViewById(R.id.poTitle);
options[0] = (EditText) v.findViewById(R.id.po1);
options[1] = (EditText) v.findViewById(R.id.po2);
options[2] = (EditText) v.findViewById(R.id.po3);
options[3] = (EditText) v.findViewById(R.id.po4);
options[4] = (EditText) v.findViewById(R.id.po5);
options[5] = (EditText) v.findViewById(R.id.po6);
options[6] = (EditText) v.findViewById(R.id.po7);
options[7] = (EditText) v.findViewById(R.id.po8);
options[8] = (EditText) v.findViewById(R.id.po9);
options[9] = (EditText) v.findViewById(R.id.po10);
final Spinner minLevel = (Spinner) v.findViewById(R.id.poMinLevel);
poUse.setOnCheckedChangeListener(new OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
poTitle.setEnabled(isChecked);
for (int x = 0; x < 10; x++)
options[x].setEnabled(isChecked);
}
});
for (int x = 0; x < 10; x++)
options[x].setText(pollOptions[x]);
minLevel.setSelection(pollMinLevel);
poTitle.setText(pollTitle);
poUse.setChecked(pollUse);
b.setPositiveButton("Save", new OnClickListener() {
@Override
@SuppressWarnings("ConstantConditions")
public void onClick(DialogInterface dialog, int which) {
pollUse = poUse.isChecked();
pollTitle = poTitle.getText().toString();
pollMinLevel = minLevel.getSelectedItemPosition();
for (int x = 0; x < 10; x++) {
pollOptions[x] = options[x].getText().toString();
}
}
});
b.setNegativeButton("Cancel", null);
b.setNeutralButton("Clear", new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
clearPoll();
}
});
Dialog dialog = b.create();
dialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
public void onDismiss(DialogInterface dialog) {
//noinspection deprecation
removeDialog(POLL_OPTIONS_DIALOG);
}
});
return dialog;
}
private void clearPoll() {
pollUse = false;
pollTitle = EMPTY_STRING;
for (int x = 0; x < 10; x++)
pollOptions[x] = EMPTY_STRING;
pollMinLevel = -1;
}
private String reportCode;
private Dialog createReportMessageDialog() {
AlertDialog.Builder reportMsgBuilder = new AlertDialog.Builder(this);
reportMsgBuilder.setTitle("Report Message");
final String[] reportOptions;
if (clickedMsg.getPostNum().equals("1"))
reportOptions = getResources().getStringArray(R.array.msgReportReasonsWithOffTopic);
else
reportOptions = getResources().getStringArray(R.array.msgReportReasons);
reportMsgBuilder.setItems(reportOptions, new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
reportCode = getResources().getStringArray(R.array.msgReportCodes)[which];
/*
<form action="https://www.gamefaqs.com/features/board_mark/pick.php" method="post">
<input type="hidden" name="b" value="848">
<input type="hidden" name="t" value="71881473">
<input type="hidden" name="m" value="821951056">
<input type="hidden" name="r" value="8">
<input type="hidden" name="rt" value="Testing">
<input type="hidden" name="i" value="0">
<input type="hidden" name="key" value="[session key]">
<input type="submit">
</form>
*/
HashMap<String, List<String>> markData = new HashMap<>();
markData.put("b", Collections.singletonList(boardID));
markData.put("t", Collections.singletonList(topicID));
markData.put("m", Collections.singletonList(clickedMsg.getMessageID()));
markData.put("r", Collections.singletonList(reportCode));
markData.put("rt", Collections.singletonList(EMPTY_STRING));
markData.put("i", Collections.singletonList("0"));
markData.put("key", Collections.singletonList(session.getSessionKey()));
session.post(NetDesc.MSG_MARK, "/features/board_mark/pick.php", markData);
// session.get(NetDesc.MARKMSG_S1, clickedMsg.getMessageDetailLink());
}
});
reportMsgBuilder.setNegativeButton("Cancel", null);
Dialog dialog = reportMsgBuilder.create();
dialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
public void onDismiss(DialogInterface dialog) {
//noinspection deprecation
removeDialog(REPORT_MESSAGE_DIALOG);
}
});
return dialog;
}
private Dialog createMessageActionDialog() {
AlertDialog.Builder msgActionBuilder = new AlertDialog.Builder(this);
LayoutInflater inflater = getLayoutInflater();
@SuppressLint("InflateParams")
final View v = inflater.inflate(R.layout.msgaction, null);
msgActionBuilder.setView(v);
msgActionBuilder.setTitle("Message Actions");
ArrayList<String> listBuilder = new ArrayList<>();
if (clickedMsg.getMessageID() != null) {
if (clickedMsg.isEdited())
listBuilder.add("View Previous Version(s)");
else
listBuilder.add("Message Detail");
}
if (clickedMsg.canQuote())
listBuilder.add("Quote");
if (clickedMsg.canEdit())
listBuilder.add("Edit");
if (clickedMsg.canDelete())
listBuilder.add("Delete");
if (clickedMsg.canReport())
listBuilder.add("Report");
listBuilder.add("Highlight User");
listBuilder.add("User Details");
assert v != null : "v is null";
ListView lv = (ListView) v.findViewById(R.id.maList);
final LinearLayout wrapper = (LinearLayout) v.findViewById(R.id.maWrapper);
ArrayAdapter<String> adapter = new ArrayAdapter<>(this, android.R.layout.simple_list_item_1);
adapter.addAll(listBuilder);
lv.setAdapter(adapter);
lv.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
String selected = (String) parent.getItemAtPosition(position);
assert selected != null : "selected is null";
switch (selected) {
case "View Previous Version(s)":
case "Message Detail":
session.get(NetDesc.MESSAGE_DETAIL, clickedMsg.getMessageDetailLink());
break;
case "Quote":
String msg = (quoteSelection != null ? quoteSelection : clickedMsg.getMessageForQuoting());
quoteSetup(clickedMsg.getUser(), msg);
break;
case "Edit":
editPostSetup(clickedMsg.getMessageForEditing(), clickedMsg.getMessageID());
break;
case "Delete":
HashMap<String, List<String>> delData = new HashMap<>();
delData.put("action", Collections.singletonList("delete"));
delData.put("key", Collections.singletonList(session.getSessionKey()));
session.post(NetDesc.MSG_DELETE,
clickedMsg.getMessageDetailLink().replace("/boards/", "/boardaction/"), delData);
break;
case "Report":
//noinspection deprecation
showDialog(REPORT_MESSAGE_DIALOG);
break;
case "Highlight User":
HighlightedUser user = hlDB.getHighlightedUsers().get(clickedMsg.getUser().toLowerCase(Locale.US));
HighlightListDBHelper.showHighlightUserDialog(AllInOneV2.this, user, clickedMsg.getUser(), null);
break;
case "User Details":
session.get(NetDesc.USER_DETAIL, clickedMsg.getUserDetailLink());
break;
default:
Crouton.showText(AllInOneV2.this, "not recognized: " + selected, Theming.croutonStyle());
break;
}
//noinspection deprecation
dismissDialog(MESSAGE_ACTION_DIALOG);
}
});
msgActionBuilder.setNegativeButton("Cancel", null);
Dialog dialog = msgActionBuilder.create();
dialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
public void onDismiss(DialogInterface dialog) {
//noinspection deprecation
removeDialog(MESSAGE_ACTION_DIALOG);
}
});
dialog.setOnShowListener(new OnShowListener() {
@Override
public void onShow(DialogInterface dialog) {
if (quoteSelection != null)
Crouton.showText(AllInOneV2.this, "Selected text prepped for quoting.", Theming.croutonStyle(), wrapper);
}
});
return dialog;
}
private LinearLayout pmSending;
private Dialog createSendPMDialog() {
AlertDialog.Builder b = new AlertDialog.Builder(this);
LayoutInflater inflater = getLayoutInflater();
@SuppressLint("InflateParams")
final View v = inflater.inflate(R.layout.sendpm, null);
b.setView(v);
b.setTitle("Send Private Message");
b.setCancelable(false);
assert v != null : "v is null";
final EditText to = (EditText) v.findViewById(R.id.spTo);
final EditText subject = (EditText) v.findViewById(R.id.spSubject);
final EditText message = (EditText) v.findViewById(R.id.spMessage);
pmSending = (LinearLayout) v.findViewById(R.id.spFootWrapper);
to.setText(savedTo);
subject.setText(savedSubject);
message.setText(savedMessage);
b.setPositiveButton("Send", null);
b.setNegativeButton("Cancel", null);
final AlertDialog d = b.create();
d.setOnShowListener(new OnShowListener() {
@Override
@SuppressWarnings("ConstantConditions")
public void onShow(DialogInterface dialog) {
d.getButton(AlertDialog.BUTTON_POSITIVE).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String toContent = to.getText().toString();
String subjectContent = subject.getText().toString();
String messageContent = message.getText().toString();
if (toContent.length() > 0) {
if (subjectContent.length() > 0) {
if (messageContent.length() > 0) {
savedTo = toContent;
savedSubject = subjectContent;
savedMessage = messageContent;
pmSending.setVisibility(View.VISIBLE);
session.get(NetDesc.PM_SEND_S1, "/pm/new");
} else
Crouton.showText(AllInOneV2.this,
"The message can't be empty.",
Theming.croutonStyle(),
(ViewGroup) to.getParent());
} else
Crouton.showText(AllInOneV2.this,
"The subject can't be empty.",
Theming.croutonStyle(),
(ViewGroup) to.getParent());
} else
Crouton.showText(AllInOneV2.this,
"The recipient can't be empty.",
Theming.croutonStyle(),
(ViewGroup) to.getParent());
}
});
}
});
d.setOnDismissListener(new DialogInterface.OnDismissListener() {
public void onDismiss(DialogInterface dialog) {
pmSending = null;
//noinspection deprecation
removeDialog(SEND_PM_DIALOG);
}
});
return d;
}
private String[] boardQuickListOptions;
private String[] boardQuickListLinks;
private void showBoardQuickList() {
if (boardQuickListOptions != null && boardQuickListOptions.length > 1) {
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setTitle("My Boards");
b.setNegativeButton("Cancel", null);
b.setItems(boardQuickListOptions, new OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
if (which == 0) {
session.get(NetDesc.BOARD_JUMPER, "/boards");
} else session.get(NetDesc.BOARD, boardQuickListLinks[which]);
}
});
drawerLayout.closeDrawers();
b.show();
} else session.get(NetDesc.BOARD_JUMPER, "/boards");
}
private String replyTo, replySubject;
public String savedTo, savedSubject, savedMessage;
public void pmSetup(String toIn, String subjectIn, String messageIn) {
if (toIn != null && !toIn.equals("null"))
savedTo = toIn;
else
savedTo = EMPTY_STRING;
if (subjectIn != null && !subjectIn.equals("null"))
savedSubject = subjectIn;
else
savedSubject = EMPTY_STRING;
if (messageIn != null && !messageIn.equals("null"))
savedMessage = messageIn;
else
savedMessage = EMPTY_STRING;
try {
savedTo = URLDecoder.decode(savedTo, DocumentParser.CHARSET_NAME);
savedSubject = URLDecoder.decode(savedSubject, DocumentParser.CHARSET_NAME);
savedMessage = URLDecoder.decode(savedMessage, DocumentParser.CHARSET_NAME);
} catch (UnsupportedEncodingException e) {
throw new AssertionError(DocumentParser.CHARSET_NAME + " is unknown");
// should never happen
}
//noinspection deprecation
showDialog(SEND_PM_DIALOG);
}
public void pmCleanup(boolean wasSuccessful, String error) {
if (wasSuccessful) {
Crouton.showText(this, "PM sent.", Theming.croutonStyle());
((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE)).
hideSoftInputFromWindow(pmSending.getWindowToken(), 0);
//noinspection deprecation
dismissDialog(SEND_PM_DIALOG);
} else {
Crouton.showText(this, error, Theming.croutonStyle(), (ViewGroup) pmSending.getParent());
pmSending.setVisibility(View.GONE);
}
}
public void refreshClicked(View view) {
if (BuildConfig.DEBUG) wtl("refreshClicked fired --NEL");
if (view != null)
view.performHapticFeedback(HapticFeedbackConstants.VIRTUAL_KEY);
if (session.getLastPath() == null) {
if (Session.isLoggedIn()) {
if (BuildConfig.DEBUG) wtl("starting new session from refreshClicked, logged in");
session = new Session(this, Session.getUser(), AccountManager.getPassword(this, Session.getUser()));
} else {
if (BuildConfig.DEBUG) wtl("starting new session from refreshClicked, no login");
session = new Session(this);
}
} else
session.refresh();
}
public String getSig() {
String sig = EMPTY_STRING;
if (session != null) {
if (Session.isLoggedIn())
sig = settings.getString("customSig" + Session.getUser(), EMPTY_STRING);
}
if (sig.length() == 0)
sig = settings.getString("customSig", EMPTY_STRING);
if (sig.length() == 0)
sig = defaultSig;
return sig.replace("*grver*", BuildConfig.VERSION_NAME);
}
private static long lastNano = 0;
public static void wtl(String msg) {
if (BuildConfig.DEBUG) {
long currNano = System.nanoTime();
msg = msg.replaceAll("\\\\n", "(nl)");
long elapsed;
if (lastNano == 0)
elapsed = 0;
else
elapsed = currNano - lastNano;
elapsed = elapsed / 1000000;
if (elapsed > 100)
Log.w("logger", "time since previous log was over 100 milliseconds");
lastNano = System.nanoTime();
msg = elapsed + "// " + msg;
Log.d("logger", msg);
}
}
public void tryCaught(String url, String desc, Throwable e, String source) {
if (!BuildConfig.DEBUG) {
ACRA.getErrorReporter().putCustomData("URL", url);
ACRA.getErrorReporter().putCustomData("NetDesc", desc);
ACRA.getErrorReporter().putCustomData("Page Source", StringEscapeUtils.escapeJava(source));
ACRA.getErrorReporter().putCustomData("Last Attempted Path", session.getLastAttemptedPath());
ACRA.getErrorReporter().putCustomData("Last Attempted Desc", session.getLastAttemptedDesc().toString());
ACRA.getErrorReporter().handleException(e);
} else {
Log.e("tryCaught", "", e);
}
}
private String parseBoardID(String url) {
if (BuildConfig.DEBUG) wtl("parseBoardID fired");
// board example: https://www.gamefaqs.com/boards/400-current-events
String boardUrl = url.substring(Session.ROOT.length() + 8);
int i = boardUrl.indexOf('/');
if (i != -1) {
String replacer = boardUrl.substring(i);
boardUrl = boardUrl.replace(replacer, EMPTY_STRING);
}
i = boardUrl.indexOf('?');
if (i != -1) {
String replacer = boardUrl.substring(i);
boardUrl = boardUrl.replace(replacer, EMPTY_STRING);
}
i = boardUrl.indexOf('#');
if (i != -1) {
String replacer = boardUrl.substring(i);
boardUrl = boardUrl.replace(replacer, EMPTY_STRING);
}
if (BuildConfig.DEBUG) wtl("boardID: " + boardUrl);
return boardUrl;
}
private String parseTopicID(String url) {
if (BuildConfig.DEBUG) wtl("parseTopicID fired");
// topic example: https://www.gamefaqs.com/boards/400-current-events/64300205
String topicUrl = url.substring(url.indexOf('/', Session.ROOT.length() + 8) + 1);
int i = topicUrl.indexOf('/');
if (i != -1) {
String replacer = topicUrl.substring(i);
topicUrl = topicUrl.replace(replacer, EMPTY_STRING);
}
i = topicUrl.indexOf('?');
if (i != -1) {
String replacer = topicUrl.substring(i);
topicUrl = topicUrl.replace(replacer, EMPTY_STRING);
}
i = topicUrl.indexOf('#');
if (i != -1) {
String replacer = topicUrl.substring(i);
topicUrl = topicUrl.replace(replacer, EMPTY_STRING);
}
if (BuildConfig.DEBUG) wtl("topicID: " + topicUrl);
return topicUrl;
}
private String parseMessageID(String url) {
if (BuildConfig.DEBUG) wtl("parseMessageID fired");
String msgID = url.substring(url.lastIndexOf('/') + 1);
if (BuildConfig.DEBUG) wtl("messageIDForEditing: " + msgID);
return msgID;
}
@Override
public void onBackPressed() {
if (searchIcon != null && searchIcon.isActionViewExpanded()) {
searchIcon.collapseActionView();
} else if (drawerLayout.isDrawerOpen(Gravity.LEFT)) {
drawerLayout.closeDrawers();
} else if (postWrapper.getVisibility() == View.VISIBLE) {
postCancel(postCancelButton);
} else {
if (session != null && session.canGoBack()) {
if (BuildConfig.DEBUG) wtl("back pressed, history exists, going back");
session.goBack(false);
} else {
if (BuildConfig.DEBUG) wtl("back pressed, no history, exiting app");
finish();
}
}
}
public static String buildAMPLink() {
return "/user/messages?lp=" + settings.getString("ampSortOption", "-1");
}
public void htmlButtonClicked(View view) {
String tag = (String) view.getTag();
String open = "<" + tag + ">";
String close = "</" + tag + ">";
int start = Math.max(postBody.getSelectionStart(), 0);
int end = Math.max(postBody.getSelectionEnd(), 0);
String insert;
if (start != end)
insert = open + postBody.getText().subSequence(start, end) + close;
else
insert = open + close;
postBody.getText().replace(Math.min(start, end), Math.max(start, end), insert, 0, insert.length());
}
public void processNotif(String text, String url) {
if (url.equals(NOTIFS_CLEAR_LINK)) {
session.get(NetDesc.NOTIFS_CLEAR, url);
}
else if (Session.determineNetDesc(url) == NetDesc.UNSPECIFIED) {
final String deets = "Notif Text: " + text + "\n" +
"Notif Link: " + url;
AlertDialog.Builder b = new AlertDialog.Builder(this);
b.setMessage("You found a notification that is currently unsupported. Good job! " +
"The details of the notification are below. Press OK to copy the details " +
"to the clipboard and be taken to correct topic to report this.\n" +
"\n" +
deets);
b.setPositiveButton("OK", new OnClickListener() {
@Override
public void onClick(DialogInterface dialogInterface, int i) {
android.content.ClipboardManager clipboard =
(android.content.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
clipboard.setPrimaryClip(android.content.ClipData.newPlainText("simple text", deets));
session.get(NetDesc.TOPIC, "/boards/1177-gameraven-development-and-discussion/75010049");
}
});
b.setNegativeButton("Dismiss", null);
b.show();
} else {
session.get(Session.determineNetDesc(url), url);
}
}
private AdapterView.OnItemSelectedListener accountsListener = new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
final String currUser = Session.getUser();
String selUser = accountsAdapter.getItem(position);
if (selUser.equals(getString(R.string.log_out)) && currUser != null)
if (session.hasNetworkConnection())
session = new Session(AllInOneV2.this);
else {
noNetworkConnection();
setLoginName(currUser);
}
else {
if (!selUser.equals(currUser) && !selUser.equals(getString(R.string.log_out)))
if (session.hasNetworkConnection())
session = new Session(AllInOneV2.this,
selUser,
AccountManager.getPassword(AllInOneV2.this, selUser),
session.getLastPath(),
session.getLastDesc());
else {
noNetworkConnection();
setLoginName(currUser);
}
}
drawerLayout.closeDrawers();
}
@Override
public void onNothingSelected(AdapterView<?> parent) {
// do nothing
}
};
private static final String NOTIFS_CLEAR_LINK = "/ajax/notification_clear_all";
private static final String NOTIFS_PAGE_LINK = "/user/notifications";
private AdapterView.OnItemSelectedListener notifsListener = new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
if (position > 0) {
toggleMenu();
notifsSpinner.setSelection(0);
processNotif((String) parent.getItemAtPosition(position), notifsLinks.get(position));
}
}
@Override
public void onNothingSelected(AdapterView<?> adapterView) {
// do nothing
}
};
}