增加切换帐号悬浮窗
This commit is contained in:
parent
037f0f7937
commit
69834694bc
@ -16,7 +16,7 @@
|
||||
|
||||
<application
|
||||
android:allowBackup="true"
|
||||
android:icon="@mipmap/ic_launcher"
|
||||
android:icon="@drawable/icon"
|
||||
android:name=".JCApplication"
|
||||
android:label="@string/app_name"
|
||||
android:usesCleartextTraffic="true"
|
||||
|
@ -21,6 +21,9 @@ import android.widget.FrameLayout;
|
||||
import android.widget.ImageView;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.hnjc.wjtx.floatingview.FloatingMagnetView;
|
||||
import com.hnjc.wjtx.floatingview.FloatingView;
|
||||
import com.hnjc.wjtx.floatingview.MagnetViewListener;
|
||||
import com.hnjc.wjtx.util.AssetsUtil;
|
||||
import com.hnjc.wjtx.util.StorageUtil;
|
||||
import com.hnjc.wjtx.util.StringUtil;
|
||||
@ -116,12 +119,37 @@ public class MainActivity extends Activity {
|
||||
Manifest.permission.WRITE_EXTERNAL_STORAGE}, 1);
|
||||
}
|
||||
com.quicksdk.Sdk.getInstance().onCreate(this);
|
||||
FloatingView.get().add();
|
||||
FloatingView.get().listener(new MagnetViewListener() {
|
||||
@Override
|
||||
public void onRemove(FloatingMagnetView magnetView) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onClick(FloatingMagnetView magnetView) {
|
||||
|
||||
AlertDialog.Builder builder=new AlertDialog.Builder(MainActivity.this);
|
||||
builder.setTitle("提示:");
|
||||
builder.setMessage("确定切换帐号?");
|
||||
//设置确认按钮
|
||||
builder.setPositiveButton("确定", (dialog, which) -> {
|
||||
// nativeAndroid.callExternalInterface("changeAccount", "");
|
||||
com.quicksdk.User.getInstance().logout(MainActivity.this);
|
||||
});
|
||||
//设置取消按钮
|
||||
builder.setNegativeButton("取消",null);
|
||||
//显示弹框
|
||||
builder.show();
|
||||
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onStart() {
|
||||
super.onStart();
|
||||
com.quicksdk.Sdk.getInstance().onStart(this);
|
||||
FloatingView.get().attach(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -148,6 +176,7 @@ public class MainActivity extends Activity {
|
||||
protected void onStop() {
|
||||
super.onStop();
|
||||
com.quicksdk.Sdk.getInstance().onStop(this);
|
||||
FloatingView.get().detach(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -0,0 +1,29 @@
|
||||
package com.hnjc.wjtx.floatingview;
|
||||
|
||||
import android.content.Context;
|
||||
import android.support.annotation.DrawableRes;
|
||||
import android.support.annotation.LayoutRes;
|
||||
import android.support.annotation.NonNull;
|
||||
import android.widget.ImageView;
|
||||
|
||||
import com.hnjc.wjtx.R;
|
||||
|
||||
public class EnFloatingView extends FloatingMagnetView {
|
||||
|
||||
private final ImageView mIcon;
|
||||
|
||||
public EnFloatingView(@NonNull Context context) {
|
||||
this(context, R.layout.en_floating_view);
|
||||
}
|
||||
|
||||
public EnFloatingView(@NonNull Context context, @LayoutRes int resource) {
|
||||
super(context, null);
|
||||
inflate(context, resource, this);
|
||||
mIcon = findViewById(R.id.icon);
|
||||
}
|
||||
|
||||
public void setIconImage(@DrawableRes int resId){
|
||||
mIcon.setImageResource(resId);
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,210 @@
|
||||
package com.hnjc.wjtx.floatingview;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.res.Configuration;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.util.AttributeSet;
|
||||
import android.view.MotionEvent;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.FrameLayout;
|
||||
|
||||
import com.hnjc.wjtx.util.SystemUtils;
|
||||
|
||||
public class FloatingMagnetView extends FrameLayout {
|
||||
|
||||
public static final int MARGIN_EDGE = 13;
|
||||
private float mOriginalRawX;
|
||||
private float mOriginalRawY;
|
||||
private float mOriginalX;
|
||||
private float mOriginalY;
|
||||
private MagnetViewListener mMagnetViewListener;
|
||||
private static final int TOUCH_TIME_THRESHOLD = 150;
|
||||
private long mLastTouchDownTime;
|
||||
protected MoveAnimator mMoveAnimator;
|
||||
protected int mScreenWidth;
|
||||
private int mScreenHeight;
|
||||
private int mStatusBarHeight;
|
||||
private boolean isNearestLeft = true;
|
||||
private float mPortraitY;
|
||||
|
||||
public void setMagnetViewListener(MagnetViewListener magnetViewListener) {
|
||||
this.mMagnetViewListener = magnetViewListener;
|
||||
}
|
||||
|
||||
public FloatingMagnetView(Context context) {
|
||||
this(context, null);
|
||||
}
|
||||
|
||||
public FloatingMagnetView(Context context, AttributeSet attrs) {
|
||||
this(context, attrs, 0);
|
||||
}
|
||||
|
||||
public FloatingMagnetView(Context context, AttributeSet attrs, int defStyleAttr) {
|
||||
super(context, attrs, defStyleAttr);
|
||||
init();
|
||||
}
|
||||
|
||||
private void init() {
|
||||
mMoveAnimator = new MoveAnimator();
|
||||
mStatusBarHeight = SystemUtils.getStatusBarHeight(getContext());
|
||||
setClickable(true);
|
||||
// updateSize();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onTouchEvent(MotionEvent event) {
|
||||
if (event == null) {
|
||||
return false;
|
||||
}
|
||||
switch (event.getAction()) {
|
||||
case MotionEvent.ACTION_DOWN:
|
||||
changeOriginalTouchParams(event);
|
||||
updateSize();
|
||||
mMoveAnimator.stop();
|
||||
break;
|
||||
case MotionEvent.ACTION_MOVE:
|
||||
updateViewPosition(event);
|
||||
break;
|
||||
case MotionEvent.ACTION_UP:
|
||||
clearPortraitY();
|
||||
moveToEdge();
|
||||
if (isOnClickEvent()) {
|
||||
dealClickEvent();
|
||||
}
|
||||
break;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
protected void dealClickEvent() {
|
||||
if (mMagnetViewListener != null) {
|
||||
mMagnetViewListener.onClick(this);
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean isOnClickEvent() {
|
||||
return System.currentTimeMillis() - mLastTouchDownTime < TOUCH_TIME_THRESHOLD;
|
||||
}
|
||||
|
||||
private void updateViewPosition(MotionEvent event) {
|
||||
setX(mOriginalX + event.getRawX() - mOriginalRawX);
|
||||
// 限制不可超出屏幕高度
|
||||
float desY = mOriginalY + event.getRawY() - mOriginalRawY;
|
||||
if (desY < mStatusBarHeight) {
|
||||
desY = mStatusBarHeight;
|
||||
}
|
||||
if (desY > mScreenHeight - getHeight()) {
|
||||
desY = mScreenHeight - getHeight();
|
||||
}
|
||||
setY(desY);
|
||||
}
|
||||
|
||||
private void changeOriginalTouchParams(MotionEvent event) {
|
||||
mOriginalX = getX();
|
||||
mOriginalY = getY();
|
||||
mOriginalRawX = event.getRawX();
|
||||
mOriginalRawY = event.getRawY();
|
||||
mLastTouchDownTime = System.currentTimeMillis();
|
||||
}
|
||||
|
||||
protected void updateSize() {
|
||||
ViewGroup viewGroup = (ViewGroup) getParent();
|
||||
if (viewGroup != null) {
|
||||
mScreenWidth = viewGroup.getWidth() - getWidth();
|
||||
mScreenHeight = viewGroup.getHeight();
|
||||
}
|
||||
// mScreenWidth = (SystemUtils.getScreenWidth(getContext()) - this.getWidth());
|
||||
// mScreenHeight = SystemUtils.getScreenHeight(getContext());
|
||||
}
|
||||
|
||||
public void moveToEdge() {
|
||||
moveToEdge(isNearestLeft(), false);
|
||||
}
|
||||
|
||||
public void moveToEdge(boolean isLeft, boolean isLandscape) {
|
||||
float moveDistance = isLeft ? MARGIN_EDGE : mScreenWidth - MARGIN_EDGE;
|
||||
float y = getY();
|
||||
if (!isLandscape && mPortraitY != 0) {
|
||||
y = mPortraitY;
|
||||
clearPortraitY();
|
||||
}
|
||||
mMoveAnimator.start(moveDistance, Math.min(Math.max(0, y), mScreenHeight - getHeight()));
|
||||
}
|
||||
|
||||
private void clearPortraitY() {
|
||||
mPortraitY = 0;
|
||||
}
|
||||
|
||||
protected boolean isNearestLeft() {
|
||||
int middle = mScreenWidth / 2;
|
||||
isNearestLeft = getX() < middle;
|
||||
return isNearestLeft;
|
||||
}
|
||||
|
||||
public void onRemove() {
|
||||
if (mMagnetViewListener != null) {
|
||||
mMagnetViewListener.onRemove(this);
|
||||
}
|
||||
}
|
||||
|
||||
protected class MoveAnimator implements Runnable {
|
||||
|
||||
private Handler handler = new Handler(Looper.getMainLooper());
|
||||
private float destinationX;
|
||||
private float destinationY;
|
||||
private long startingTime;
|
||||
|
||||
void start(float x, float y) {
|
||||
this.destinationX = x;
|
||||
this.destinationY = y;
|
||||
startingTime = System.currentTimeMillis();
|
||||
handler.post(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
if (getRootView() == null || getRootView().getParent() == null) {
|
||||
return;
|
||||
}
|
||||
float progress = Math.min(1, (System.currentTimeMillis() - startingTime) / 400f);
|
||||
float deltaX = (destinationX - getX()) * progress;
|
||||
float deltaY = (destinationY - getY()) * progress;
|
||||
move(deltaX, deltaY);
|
||||
if (progress < 1) {
|
||||
handler.post(this);
|
||||
}
|
||||
}
|
||||
|
||||
private void stop() {
|
||||
handler.removeCallbacks(this);
|
||||
}
|
||||
}
|
||||
|
||||
private void move(float deltaX, float deltaY) {
|
||||
setX(getX() + deltaX);
|
||||
setY(getY() + deltaY);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onConfigurationChanged(Configuration newConfig) {
|
||||
super.onConfigurationChanged(newConfig);
|
||||
if (getParent() != null) {
|
||||
final boolean isLandscape = newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE;
|
||||
markPortraitY(isLandscape);
|
||||
((ViewGroup) getParent()).post(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
updateSize();
|
||||
moveToEdge(isNearestLeft, isLandscape);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private void markPortraitY(boolean isLandscape) {
|
||||
if (isLandscape) {
|
||||
mPortraitY = getY();
|
||||
}
|
||||
}
|
||||
}
|
196
app/src/main/java/com/hnjc/wjtx/floatingview/FloatingView.java
Normal file
196
app/src/main/java/com/hnjc/wjtx/floatingview/FloatingView.java
Normal file
@ -0,0 +1,196 @@
|
||||
package com.hnjc.wjtx.floatingview;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.support.annotation.DrawableRes;
|
||||
import android.support.annotation.LayoutRes;
|
||||
import android.support.v4.view.ViewCompat;
|
||||
import android.view.Gravity;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.FrameLayout;
|
||||
import android.widget.RelativeLayout;
|
||||
|
||||
import com.hnjc.wjtx.R;
|
||||
import com.hnjc.wjtx.util.EnContext;
|
||||
|
||||
import java.lang.ref.WeakReference;
|
||||
|
||||
public class FloatingView implements IFloatingView {
|
||||
|
||||
private FloatingMagnetView mEnFloatingView;
|
||||
private static volatile FloatingView mInstance;
|
||||
private WeakReference<FrameLayout> mContainer;
|
||||
@LayoutRes
|
||||
private int mLayoutId = R.layout.en_floating_view;
|
||||
@DrawableRes
|
||||
private int mIconRes = R.drawable.change_acct;
|
||||
|
||||
private ViewGroup.LayoutParams mLayoutParams = getParams();
|
||||
|
||||
private FloatingView() {
|
||||
}
|
||||
|
||||
public static FloatingView get() {
|
||||
if (mInstance == null) {
|
||||
synchronized (FloatingView.class) {
|
||||
if (mInstance == null) {
|
||||
mInstance = new FloatingView();
|
||||
}
|
||||
}
|
||||
}
|
||||
return mInstance;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView remove() {
|
||||
new Handler(Looper.getMainLooper()).post(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
if (mEnFloatingView == null) {
|
||||
return;
|
||||
}
|
||||
if (ViewCompat.isAttachedToWindow(mEnFloatingView) && getContainer() != null) {
|
||||
getContainer().removeView(mEnFloatingView);
|
||||
}
|
||||
mEnFloatingView = null;
|
||||
}
|
||||
});
|
||||
return this;
|
||||
}
|
||||
|
||||
private void ensureFloatingView() {
|
||||
synchronized (this) {
|
||||
if (mEnFloatingView != null) {
|
||||
return;
|
||||
}
|
||||
EnFloatingView enFloatingView = new EnFloatingView(EnContext.get(), mLayoutId);
|
||||
mEnFloatingView = enFloatingView;
|
||||
enFloatingView.setLayoutParams(mLayoutParams);
|
||||
enFloatingView.setIconImage(mIconRes);
|
||||
addViewToWindow(enFloatingView);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView add() {
|
||||
ensureFloatingView();
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView attach(Activity activity) {
|
||||
attach(getActivityRoot(activity));
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView attach(FrameLayout container) {
|
||||
if (container == null || mEnFloatingView == null) {
|
||||
mContainer = new WeakReference<>(container);
|
||||
return this;
|
||||
}
|
||||
if (mEnFloatingView.getParent() == container) {
|
||||
return this;
|
||||
}
|
||||
if (mEnFloatingView.getParent() != null) {
|
||||
((ViewGroup) mEnFloatingView.getParent()).removeView(mEnFloatingView);
|
||||
}
|
||||
mContainer = new WeakReference<>(container);
|
||||
container.addView(mEnFloatingView);
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView detach(Activity activity) {
|
||||
detach(getActivityRoot(activity));
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView detach(FrameLayout container) {
|
||||
if (mEnFloatingView != null && container != null && ViewCompat.isAttachedToWindow(mEnFloatingView)) {
|
||||
container.removeView(mEnFloatingView);
|
||||
}
|
||||
if (getContainer() == container) {
|
||||
mContainer = null;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingMagnetView getView() {
|
||||
return mEnFloatingView;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView icon(@DrawableRes int resId) {
|
||||
mIconRes = resId;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView customView(FloatingMagnetView viewGroup) {
|
||||
mEnFloatingView = viewGroup;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView customView(@LayoutRes int resource) {
|
||||
mLayoutId = resource;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView layoutParams(ViewGroup.LayoutParams params) {
|
||||
mLayoutParams = params;
|
||||
if (mEnFloatingView != null) {
|
||||
mEnFloatingView.setLayoutParams(params);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public FloatingView listener(MagnetViewListener magnetViewListener) {
|
||||
if (mEnFloatingView != null) {
|
||||
mEnFloatingView.setMagnetViewListener(magnetViewListener);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
private void addViewToWindow(final View view) {
|
||||
if (getContainer() == null) {
|
||||
return;
|
||||
}
|
||||
getContainer().addView(view);
|
||||
}
|
||||
|
||||
private FrameLayout getContainer() {
|
||||
if (mContainer == null) {
|
||||
return null;
|
||||
}
|
||||
return mContainer.get();
|
||||
}
|
||||
|
||||
private FrameLayout.LayoutParams getParams() {
|
||||
FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(
|
||||
RelativeLayout.LayoutParams.WRAP_CONTENT,
|
||||
RelativeLayout.LayoutParams.WRAP_CONTENT);
|
||||
params.gravity = Gravity.BOTTOM | Gravity.START;
|
||||
params.setMargins(13, params.topMargin, params.rightMargin, 500);
|
||||
return params;
|
||||
}
|
||||
|
||||
private FrameLayout getActivityRoot(Activity activity) {
|
||||
if (activity == null) {
|
||||
return null;
|
||||
}
|
||||
try {
|
||||
return (FrameLayout) activity.getWindow().getDecorView().findViewById(android.R.id.content);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
@ -0,0 +1,35 @@
|
||||
package com.hnjc.wjtx.floatingview;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.support.annotation.DrawableRes;
|
||||
import android.support.annotation.LayoutRes;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.FrameLayout;
|
||||
|
||||
public interface IFloatingView {
|
||||
|
||||
FloatingView remove();
|
||||
|
||||
FloatingView add();
|
||||
|
||||
FloatingView attach(Activity activity);
|
||||
|
||||
FloatingView attach(FrameLayout container);
|
||||
|
||||
FloatingView detach(Activity activity);
|
||||
|
||||
FloatingView detach(FrameLayout container);
|
||||
|
||||
FloatingMagnetView getView();
|
||||
|
||||
FloatingView icon(@DrawableRes int resId);
|
||||
|
||||
FloatingView customView(FloatingMagnetView viewGroup);
|
||||
|
||||
FloatingView customView(@LayoutRes int resource);
|
||||
|
||||
FloatingView layoutParams(ViewGroup.LayoutParams params);
|
||||
|
||||
FloatingView listener(MagnetViewListener magnetViewListener);
|
||||
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
package com.hnjc.wjtx.floatingview;
|
||||
|
||||
public interface MagnetViewListener {
|
||||
|
||||
void onRemove(FloatingMagnetView magnetView);
|
||||
|
||||
void onClick(FloatingMagnetView magnetView);
|
||||
}
|
31
app/src/main/java/com/hnjc/wjtx/util/EnContext.java
Normal file
31
app/src/main/java/com/hnjc/wjtx/util/EnContext.java
Normal file
@ -0,0 +1,31 @@
|
||||
package com.hnjc.wjtx.util;
|
||||
|
||||
import android.app.Application;
|
||||
|
||||
public class EnContext {
|
||||
|
||||
private static final Application INSTANCE;
|
||||
|
||||
static {
|
||||
Application app = null;
|
||||
try {
|
||||
app = (Application) Class.forName("android.app.AppGlobals").getMethod("getInitialApplication").invoke(null);
|
||||
if (app == null)
|
||||
throw new IllegalStateException("Static initialization of Applications must be on main thread.");
|
||||
} catch (final Exception e) {
|
||||
e.printStackTrace();
|
||||
try {
|
||||
app = (Application) Class.forName("android.app.ActivityThread").getMethod("currentApplication").invoke(null);
|
||||
} catch (final Exception ex) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
} finally {
|
||||
INSTANCE = app;
|
||||
}
|
||||
}
|
||||
|
||||
public static Application get() {
|
||||
return INSTANCE;
|
||||
}
|
||||
}
|
||||
|
36
app/src/main/java/com/hnjc/wjtx/util/SystemUtils.java
Normal file
36
app/src/main/java/com/hnjc/wjtx/util/SystemUtils.java
Normal file
@ -0,0 +1,36 @@
|
||||
package com.hnjc.wjtx.util;
|
||||
|
||||
import android.content.Context;
|
||||
|
||||
public class SystemUtils {
|
||||
|
||||
public static int getStatusBarHeight(Context context) {
|
||||
int result = 0;
|
||||
int resourceId = context.getResources().getIdentifier("status_bar_height", "dimen", "android");
|
||||
if (resourceId > 0) {
|
||||
result = context.getResources().getDimensionPixelSize(resourceId);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public static int getScreenWidth(Context context) {
|
||||
int screenWith = -1;
|
||||
try {
|
||||
screenWith = context.getResources().getDisplayMetrics().widthPixels;
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return screenWith;
|
||||
}
|
||||
|
||||
public static int getScreenHeight(Context context) {
|
||||
int screenHeight = -1;
|
||||
try {
|
||||
screenHeight = context.getResources().getDisplayMetrics().heightPixels;
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return screenHeight;
|
||||
}
|
||||
|
||||
}
|
BIN
app/src/main/res/drawable/change_acct.png
Normal file
BIN
app/src/main/res/drawable/change_acct.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 13 KiB |
Binary file not shown.
Before Width: | Height: | Size: 145 KiB After Width: | Height: | Size: 345 KiB |
12
app/src/main/res/layout/en_floating_view.xml
Normal file
12
app/src/main/res/layout/en_floating_view.xml
Normal file
@ -0,0 +1,12 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/icon"
|
||||
android:layout_width="50dp"
|
||||
android:layout_height="50dp"
|
||||
android:src="@drawable/change_acct" />
|
||||
|
||||
</RelativeLayout>
|
Loading…
x
Reference in New Issue
Block a user