Skip to content
This repository has been archived by the owner on Jun 8, 2024. It is now read-only.

Commit

Permalink
CheatSheet: Add tooltips for image buttons
Browse files Browse the repository at this point in the history
Signed-off-by: Fung <[email protected]>
  • Loading branch information
fython committed Aug 6, 2017
1 parent c1e8243 commit d61734c
Show file tree
Hide file tree
Showing 7 changed files with 156 additions and 3 deletions.
145 changes: 145 additions & 0 deletions mobile/src/main/java/info/papdt/express/helper/support/CheatSheet.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,145 @@
package info.papdt.express.helper.support;

import android.content.Context;
import android.content.res.Configuration;
import android.graphics.Rect;
import android.text.TextUtils;
import android.view.Gravity;
import android.view.View;
import android.widget.TextView;
import android.widget.Toast;
import info.papdt.express.helper.R;

/**
* Helper class for showing cheat sheets (tooltips) for icon-only UI elements on long-press. This is
* already default platform behavior for icon-only {@link android.app.ActionBar} items and tabs.
* This class provides this behavior for any other such UI element.
*
* <p>Based on the original action bar implementation in <a href="https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/core/java/com/android/internal/view/menu/ActionMenuItemView.java">
* ActionMenuItemView.java</a>.
*/
public class CheatSheet {
/**
* The estimated height of a toast, in dips (density-independent pixels). This is used to
* determine whether or not the toast should appear above or below the UI element.
*/
private static final int ESTIMATED_TOAST_HEIGHT_DIPS = 48;

/**
* Sets up a cheat sheet (tooltip) for the given view by setting its {@link
* android.view.View.OnLongClickListener}. When the view is long-pressed, a {@link Toast} with
* the view's {@link android.view.View#getContentDescription() content description} will be
* shown either above (default) or below the view (if there isn't room above it).
*
* @param view The view to add a cheat sheet for.
*/
public static void setup(View view) {
view.setOnLongClickListener(new View.OnLongClickListener() {
@Override
public boolean onLongClick(View view) {
return showCheatSheet(view, view.getContentDescription());
}
});
}

/**
* Sets up a cheat sheet (tooltip) for the given view by setting its {@link
* android.view.View.OnLongClickListener}. When the view is long-pressed, a {@link Toast} with
* the given text will be shown either above (default) or below the view (if there isn't room
* above it).
*
* @param view The view to add a cheat sheet for.
* @param textResId The string resource containing the text to show on long-press.
*/
public static void setup(View view, final int textResId) {
view.setOnLongClickListener(new View.OnLongClickListener() {
@Override
public boolean onLongClick(View view) {
return showCheatSheet(view, view.getContext().getString(textResId));
}
});
}

/**
* Sets up a cheat sheet (tooltip) for the given view by setting its {@link
* android.view.View.OnLongClickListener}. When the view is long-pressed, a {@link Toast} with
* the given text will be shown either above (default) or below the view (if there isn't room
* above it).
*
* @param view The view to add a cheat sheet for.
* @param text The text to show on long-press.
*/
public static void setup(View view, final CharSequence text) {
view.setOnLongClickListener(new View.OnLongClickListener() {
@Override
public boolean onLongClick(View view) {
return showCheatSheet(view, text);
}
});
}

/**
* Removes the cheat sheet for the given view by removing the view's {@link
* android.view.View.OnLongClickListener}.
*
* @param view The view whose cheat sheet should be removed.
*/
public static void remove(final View view) {
view.setOnLongClickListener(null);
}

/**
* Internal helper method to show the cheat sheet toast.
*/
private static boolean showCheatSheet(View view, CharSequence text) {
if (TextUtils.isEmpty(text)) {
return false;
}

final int[] screenPos = new int[2]; // origin is device display
final Rect displayFrame = new Rect(); // includes decorations (e.g. status bar)
view.getLocationOnScreen(screenPos);
view.getWindowVisibleDisplayFrame(displayFrame);

final Context context = view.getContext();
final int viewWidth = view.getWidth();
final int viewHeight = view.getHeight();
final int viewCenterX = screenPos[0] + viewWidth / 2;
final int screenWidth = context.getResources().getDisplayMetrics().widthPixels;
final int estimatedToastHeight = (int) (ESTIMATED_TOAST_HEIGHT_DIPS
* context.getResources().getDisplayMetrics().density);

Toast cheatSheet = Toast.makeText(context, text, Toast.LENGTH_SHORT);
int currentNightMode = context.getResources().getConfiguration().uiMode & Configuration.UI_MODE_NIGHT_MASK;
boolean isNightMode = currentNightMode == Configuration.UI_MODE_NIGHT_YES;
cheatSheet.getView().setBackgroundResource(
!isNightMode ?
android.support.v7.appcompat.R.drawable.tooltip_frame_dark :
android.support.v7.appcompat.R.drawable.tooltip_frame_light);
TextView textView = cheatSheet.getView().findViewById(android.R.id.message);
textView.setTextAppearance(context, R.style.TextAppearance_AppCompat_Body1);
textView.setTextColor(context.getResources().getColor(R.color.white_in_dark));
int dp16 = (int) ScreenUtils.dpToPx(context, 16);
textView.setPaddingRelative(dp16, 0, dp16, 0);
boolean showBelow = screenPos[1] < estimatedToastHeight;
if (showBelow) {
// Show below
// Offsets are after decorations (e.g. status bar) are factored in
cheatSheet.setGravity(Gravity.TOP | Gravity.CENTER_HORIZONTAL,
viewCenterX - screenWidth / 2,
screenPos[1] - displayFrame.top + viewHeight);
} else {
// Show above
// Offsets are after decorations (e.g. status bar) are factored in
// NOTE: We can't use Gravity.BOTTOM because when the keyboard is up
// its height isn't factored in.
cheatSheet.setGravity(Gravity.TOP | Gravity.CENTER_HORIZONTAL,
viewCenterX - screenWidth / 2,
screenPos[1] - displayFrame.top - estimatedToastHeight);
}

cheatSheet.show();
return true;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
import info.papdt.express.helper.dao.PackageDatabase;
import info.papdt.express.helper.model.BaseMessage;
import info.papdt.express.helper.model.Package;
import info.papdt.express.helper.support.CheatSheet;
import info.papdt.express.helper.support.ClipboardUtils;
import info.papdt.express.helper.support.ScreenUtils;
import info.papdt.express.helper.support.Settings;
Expand Down Expand Up @@ -97,6 +98,7 @@ public void onClick(View view) {
showNameEditDialog();
}
});
CheatSheet.setup(mFAB);
}

private void setUpData() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
import info.papdt.express.helper.R;
import info.papdt.express.helper.dao.PackageDatabase;
import info.papdt.express.helper.model.Package;
import info.papdt.express.helper.support.CheatSheet;
import info.papdt.express.helper.support.PushUtils;
import info.papdt.express.helper.support.Settings;
import info.papdt.express.helper.ui.common.AbsActivity;
Expand Down Expand Up @@ -95,6 +96,7 @@ public void onClick(View view) {
startActivityForResult(intent, REQUEST_ADD);
}
});
CheatSheet.setup(fab);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import android.view.View;
import android.view.ViewGroup;
import info.papdt.express.helper.R;
import info.papdt.express.helper.support.CheatSheet;
import info.papdt.express.helper.support.ClipboardUtils;
import info.papdt.express.helper.ui.DetailsActivity;
import me.drakeet.multitype.ItemViewBinder;
Expand Down Expand Up @@ -78,6 +79,7 @@ public boolean onLongClick(View v) {
itemView.getResources()
.getString(R.string.list_package_show_toggle_desc)
);
CheatSheet.setup(button);
}
button.setVisibility(View.VISIBLE);
button.setOnClickListener(new View.OnClickListener() {
Expand Down
6 changes: 3 additions & 3 deletions mobile/src/main/res/layout/item_list_details_info_normal.xml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingEnd="16dp"
android:paddingEnd="24dp"
android:gravity="center_vertical"
android:orientation="horizontal"
android:foreground="?attr/selectableItemBackground"
Expand Down Expand Up @@ -38,8 +38,8 @@
</LinearLayout>

<android.support.v7.widget.AppCompatImageButton
android:layout_width="48dp"
android:layout_height="48dp"
android:layout_width="36dp"
android:layout_height="36dp"
android:id="@+id/btn_action"
android:background="?attr/selectableItemBackgroundBorderless"
android:visibility="gone"
Expand Down
1 change: 1 addition & 0 deletions mobile/src/main/res/values-night/colors.xml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
<color name="dark_theme_translucent_app_bar">#4F000000</color>

<color name="black_in_light">@android:color/white</color>
<color name="white_in_dark">@color/grey_900</color>

<color name="colorAccentDark">@color/indigo_accent_200</color>

Expand Down
1 change: 1 addition & 0 deletions mobile/src/main/res/values/colors.xml
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@
<color name="dark_theme_translucent_app_bar">#4F000000</color>

<color name="black_in_light">@android:color/black</color>
<color name="white_in_dark">@android:color/white</color>

<color name="colorAccentDark">@color/pink_900</color>

Expand Down

0 comments on commit d61734c

Please sign in to comment.