多点触摸初步实现

This commit is contained in:
lihongwei 2025-04-27 16:04:58 +08:00
parent 3f6fb462ee
commit 21e5cd7902
6 changed files with 247 additions and 161 deletions

View File

@ -19,12 +19,10 @@ import java.util.ArrayList;
import java.util.List; import java.util.List;
public class AutoClickService extends AccessibilityService { public class AutoClickService extends AccessibilityService {
private final List<Point> multiClickPoints = new ArrayList<>();
private static final String TAG = "AutoClickService"; private static final String TAG = "AutoClickService";
private static AutoClickService instance; private static AutoClickService instance;
private final List<Point> multiClickPositions = new ArrayList<>(); private final List<Point> moreClickPositions = new ArrayList<>();
private int currentClickIndex = 0; private int currentClickIndex = 0;
private static final long MIN_CLICK_INTERVAL = 40; private static final long MIN_CLICK_INTERVAL = 40;
@ -70,14 +68,15 @@ public class AutoClickService extends AccessibilityService {
public void setClickPosition(float x, float y) { public void setClickPosition(float x, float y) {
Point constrained = ViewUtils.constrainToScreen(x, y, screenWidth, screenHeight); Point constrained = ViewUtils.constrainToScreen(x, y, screenWidth, screenHeight);
this.moreClickPositions.clear();
this.clickX = constrained.x; this.clickX = constrained.x;
this.clickY = constrained.y; this.clickY = constrained.y;
logDebug("设置单点点击位置: 原始 (" + x + ", " + y + ") -> 修正 (" + clickX + ", " + clickY + ")"); logDebug("设置单点点击位置: 原始 (" + x + ", " + y + ") -> 修正 (" + clickX + ", " + clickY + ")");
} }
public void setMultiClickPositions(List<Point> positions) { public void setMoreClickPositions(List<Point> positions) {
this.multiClickPositions.clear(); this.moreClickPositions.clear();
this.multiClickPositions.addAll(positions); this.moreClickPositions.addAll(positions);
logDebug("设置多点点击位置: " + positions.size() + " 个点"); logDebug("设置多点点击位置: " + positions.size() + " 个点");
} }
@ -101,10 +100,11 @@ public class AutoClickService extends AccessibilityService {
public void startClicking() { public void startClicking() {
if (!isClicking) { if (!isClicking) {
if (multiClickPositions.isEmpty() && (clickX == 0 && clickY == 0)) { if (moreClickPositions.isEmpty() && (clickX == 0 && clickY == 0)) {
Log.w(TAG, "无有效点击位置,忽略开始点击"); Log.w(TAG, "无有效点击位置,忽略开始点击");
return; return;
} }
isClicking = true; isClicking = true;
currentClickIndex = 0; currentClickIndex = 0;
logDebug("开始自动点击"); logDebug("开始自动点击");
@ -130,19 +130,20 @@ public class AutoClickService extends AccessibilityService {
return; return;
} }
// 决定使用单点还是多点点击
Point clickPoint; Point clickPoint;
if (!multiClickPositions.isEmpty()) { int flashIndex = -1; // 新增变量控制闪烁哪个点
// 多点点击模式
clickPoint = multiClickPositions.get(currentClickIndex); if (!moreClickPositions.isEmpty()) {
currentClickIndex = (currentClickIndex + 1) % multiClickPositions.size(); // 多点模式取当前索引的点
clickPoint = moreClickPositions.get(currentClickIndex);
flashIndex = currentClickIndex; // 标记当前点击的是第几个点
} else { } else {
// 单点点击模式 // 单点模式
clickPoint = new Point(clickX, clickY); clickPoint = new Point(clickX, clickY);
} }
logDebug("执行点击: (" + clickPoint.x + ", " + clickPoint.y + ")"); logDebug("执行点击: (" + clickPoint.x + ", " + clickPoint.y + ")");
flashTouchFeedback(); flashTouchFeedback(flashIndex);
Path path = new Path(); Path path = new Path();
path.moveTo(clickPoint.x, clickPoint.y); path.moveTo(clickPoint.x, clickPoint.y);
@ -155,7 +156,14 @@ public class AutoClickService extends AccessibilityService {
@Override @Override
public void onCompleted(GestureDescription gestureDescription) { public void onCompleted(GestureDescription gestureDescription) {
logDebug("点击完成"); logDebug("点击完成");
if (isClicking) { if (isClicking) {
if (!moreClickPositions.isEmpty()) {
// 多点模式下一个触摸点
currentClickIndex = (currentClickIndex + 1) % moreClickPositions.size();
logDebug("当前点击点" + currentClickIndex);
}
// 安排下一次点击无论是单点还是多点
handler.postDelayed(() -> performClick(), clickInterval); handler.postDelayed(() -> performClick(), clickInterval);
} }
} }
@ -163,15 +171,21 @@ public class AutoClickService extends AccessibilityService {
@Override @Override
public void onCancelled(GestureDescription gestureDescription) { public void onCancelled(GestureDescription gestureDescription) {
Log.e(TAG, "点击被取消"); Log.e(TAG, "点击被取消");
if (isClicking) { if (isClicking) {
if (!moreClickPositions.isEmpty()) {
currentClickIndex = (currentClickIndex + 1) % moreClickPositions.size();
}
// 点击取消也继续循环
handler.postDelayed(() -> performClick(), clickInterval + 300); handler.postDelayed(() -> performClick(), clickInterval + 300);
} }
} }
}, null); }, null);
} }
private void flashTouchFeedback() { private void flashTouchFeedback(int index) {
Intent intent = new Intent("com.auto.autoclicker.FLASH_TOUCH_POINT"); Intent intent = new Intent("com.auto.autoclicker.FLASH_TOUCH_POINT");
intent.putExtra("index", index); // 带上当前点击点的index
LocalBroadcastManager.getInstance(this).sendBroadcast(intent); LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
} }

View File

@ -54,11 +54,12 @@ public class FloatingViewManager {
private WindowManager.LayoutParams singleControlBarParams; private WindowManager.LayoutParams singleControlBarParams;
private WindowManager.LayoutParams moreControlBarParams; private WindowManager.LayoutParams moreControlBarParams;
private boolean isMoreClicking = false;
private float touchPointX = 500; private float touchPointX = 500;
private float touchPointY = 500; private float touchPointY = 500;
private boolean isClicking = false; private boolean isClicking = false;
private boolean isFloatingViewsShown = false;
private long lastToggleTime = 0; private long lastToggleTime = 0;
@ -80,7 +81,8 @@ public class FloatingViewManager {
@Override @Override
public void onReceive(Context context, Intent intent) { public void onReceive(Context context, Intent intent) {
if ("com.auto.autoclicker.FLASH_TOUCH_POINT".equals(intent.getAction())) { if ("com.auto.autoclicker.FLASH_TOUCH_POINT".equals(intent.getAction())) {
flashTouchPoint(); int index = intent.getIntExtra("index", -1); // 默认是-1
flashTouchPoint(index);
} }
} }
}, new IntentFilter("com.auto.autoclicker.FLASH_TOUCH_POINT")); }, new IntentFilter("com.auto.autoclicker.FLASH_TOUCH_POINT"));
@ -108,21 +110,11 @@ public class FloatingViewManager {
initMoreTouchPointView(); initMoreTouchPointView();
initMoreControlBar(); initMoreControlBar();
if (moreTouchPointViews.size() == moreTouchPointParams.size()) {
for (int i = 0; i < moreTouchPointViews.size(); i++) {
windowManager.addView(moreTouchPointViews.get(i), moreTouchPointParams.get(i));
}
} else {
Log.e(TAG, "触摸点与布局参数数量不一致");
}
if (moreControlBarView != null) { if (moreControlBarView != null) {
windowManager.addView(moreControlBarView, moreControlBarParams); windowManager.addView(moreControlBarView, moreControlBarParams);
} }
} }
isFloatingViewsShown = true;
logDebug("悬浮窗已添加,模式 = " + mode); logDebug("悬浮窗已添加,模式 = " + mode);
} }
@ -161,7 +153,7 @@ public class FloatingViewManager {
updateTouchPointPosition(paramX, paramY, dx, dy); updateTouchPointPosition(paramX, paramY, dx, dy);
AutoClickService service = AutoClickService.getInstance(); AutoClickService service = AutoClickService.getInstance();
if (service != null) { if (service != null) {
service.setClickPosition(touchPointX + 50, touchPointY + 50); service.setClickPosition(touchPointX, touchPointY);
logDebug("单点触摸点移动到: (" + touchPointX + ", " + touchPointY + ")"); logDebug("单点触摸点移动到: (" + touchPointX + ", " + touchPointY + ")");
} }
break; break;
@ -174,7 +166,6 @@ public class FloatingViewManager {
private void initMoreTouchPointView() { private void initMoreTouchPointView() {
moreTouchPointViews.clear(); moreTouchPointViews.clear();
moreTouchPointParams.clear(); moreTouchPointParams.clear();
addNewTouchPoint(100, 500);
} }
@SuppressLint("ClickableViewAccessibility") @SuppressLint("ClickableViewAccessibility")
@ -272,15 +263,17 @@ public class FloatingViewManager {
} }
}); });
ImageView playButton = moreControlBarView.findViewById(R.id.play_button);
ImageView addButton = moreControlBarView.findViewById(R.id.add_button); ImageView addButton = moreControlBarView.findViewById(R.id.add_button);
ImageView removeButton = moreControlBarView.findViewById(R.id.remove_button); ImageView removeButton = moreControlBarView.findViewById(R.id.remove_button);
ImageView playButton = moreControlBarView.findViewById(R.id.play_button); ImageView slideButton = moreControlBarView.findViewById(R.id.slide_button);
ImageView closeButton = moreControlBarView.findViewById(R.id.close_button); ImageView closeButton = moreControlBarView.findViewById(R.id.close_button);
ImageView settingButton = moreControlBarView.findViewById(R.id.settings_button); ImageView settingButton = moreControlBarView.findViewById(R.id.settings_button);
addButton.setOnClickListener(v -> addNewTouchPoint(100 + moreTouchPointViews.size() * 120, 500)); playButton.setOnClickListener(v -> toggleMoreClicking());
removeButton.setOnClickListener(v -> removeLastTouchPoint()); addButton.setOnClickListener(v -> addMoreTouchPoint());
playButton.setOnClickListener(v -> toggleMoreClicking(playButton)); removeButton.setOnClickListener(v -> removeMoreTouchPoint());
closeButton.setOnClickListener(v -> closeFloatingViews()); closeButton.setOnClickListener(v -> closeFloatingViews());
settingButton.setOnClickListener(v -> showInputDialog()); settingButton.setOnClickListener(v -> showInputDialog());
} }
@ -304,7 +297,7 @@ public class FloatingViewManager {
singleTouchPointView.setBackgroundResource(R.drawable.un_touch_point); singleTouchPointView.setBackgroundResource(R.drawable.un_touch_point);
Toast.makeText(context, "停止自动点击", Toast.LENGTH_SHORT).show(); Toast.makeText(context, "停止自动点击", Toast.LENGTH_SHORT).show();
} else { } else {
service.setClickPosition(touchPointX + 50, touchPointY + 50); service.setClickPosition(touchPointX, touchPointY);
service.startClicking(); service.startClicking();
play.setBackgroundResource(R.drawable.pause); play.setBackgroundResource(R.drawable.pause);
singleTouchPointView.setBackgroundResource(R.drawable.touch_point); singleTouchPointView.setBackgroundResource(R.drawable.touch_point);
@ -315,44 +308,6 @@ public class FloatingViewManager {
logDebug("单点服务是否点击中: " + service.isClicking()); logDebug("单点服务是否点击中: " + service.isClicking());
} }
private void toggleMoreClicking(ImageView play) {
if (isDebounced()) return;
AutoClickService service = AutoClickService.getInstance();
if (service == null) {
Log.e(TAG, "AutoClickService 未初始化");
Toast.makeText(context, "请在设置中启用无障碍服务", Toast.LENGTH_LONG).show();
Intent intent = new Intent(Settings.ACTION_ACCESSIBILITY_SETTINGS);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
return;
}
if (isClicking) {
service.stopClicking();
play.setBackgroundResource(R.drawable.play);
for (View point : moreTouchPointViews) {
point.setBackgroundResource(R.drawable.un_touch_point);
}
Toast.makeText(context, "停止多点自动点击", Toast.LENGTH_SHORT).show();
} else {
List<Point> positions = new ArrayList<>();
for (WindowManager.LayoutParams params : moreTouchPointParams) {
positions.add(new Point(params.x + 50, params.y + 50));
}
service.setMultiClickPositions(positions);
service.startClicking();
play.setBackgroundResource(R.drawable.pause);
for (View point : moreTouchPointViews) {
point.setBackgroundResource(R.drawable.touch_point);
}
Toast.makeText(context, "开始多点自动点击", Toast.LENGTH_SHORT).show();
}
isClicking = !isClicking;
logDebug("多点服务是否点击中: " + service.isClicking());
}
private void closeFloatingViews() { private void closeFloatingViews() {
AutoClickService service = AutoClickService.getInstance(); AutoClickService service = AutoClickService.getInstance();
if (service != null) { if (service != null) {
@ -379,6 +334,125 @@ public class FloatingViewManager {
LocalBroadcastManager.getInstance(context).sendBroadcast(intent); LocalBroadcastManager.getInstance(context).sendBroadcast(intent);
} }
private void toggleMoreClicking() {
if (isDebounced()) return;
AutoClickService service = AutoClickService.getInstance();
if (service == null) {
Log.e(TAG, "AutoClickService 未初始化");
Toast.makeText(context, "请在设置中启用无障碍服务", Toast.LENGTH_LONG).show();
Intent intent = new Intent(Settings.ACTION_ACCESSIBILITY_SETTINGS);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
return;
}
if (moreTouchPointViews.isEmpty()) {
Toast.makeText(context, "请先添加触摸点", Toast.LENGTH_SHORT).show();
return;
}
if (isMoreClicking) {
service.stopClicking();
Toast.makeText(context, "停止多点点击", Toast.LENGTH_SHORT).show();
} else {
service.setMoreClickPositions(getMoreTouchPositions());
service.startClicking();
Toast.makeText(context, "开始多点点击", Toast.LENGTH_SHORT).show();
}
isMoreClicking = !isMoreClicking;
logDebug("多点服务是否点击中: " + service.isClicking());
}
private void addMoreTouchPoint() {
View point = new View(context);
point.setBackgroundResource(R.drawable.un_touch_point);
WindowManager.LayoutParams params = new WindowManager.LayoutParams(
100, 100,
Build.VERSION.SDK_INT >= Build.VERSION_CODES.O ?
WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY :
WindowManager.LayoutParams.TYPE_PHONE,
WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE |
WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
PixelFormat.TRANSLUCENT
);
params.gravity = Gravity.TOP | Gravity.START;
params.x = screenWidth / 2 - 50;
params.y = screenHeight / 2 - 50;
point.setOnTouchListener(new View.OnTouchListener() {
private float lastX, lastY;
private float paramX, paramY;
@Override
public boolean onTouch(View v, MotionEvent event) {
int index = moreTouchPointViews.indexOf(v); // 获取当前触摸点索引
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
lastX = event.getRawX();
lastY = event.getRawY();
paramX = params.x;
paramY = params.y;
return true;
case MotionEvent.ACTION_MOVE:
float dx = event.getRawX() - lastX;
float dy = event.getRawY() - lastY;
Point constrainedPoint = ViewUtils.constrainToScreen(
paramX + dx, paramY + dy,
screenWidth - point.getWidth(), screenHeight - point.getHeight());
params.x = constrainedPoint.x;
params.y = constrainedPoint.y;
windowManager.updateViewLayout(point, params);
// 更新 moreTouchPointParams
if (index >= 0 && index < moreTouchPointParams.size()) {
moreTouchPointParams.set(index, params);
}
// 收集所有触摸点位置
List<Point> points = new ArrayList<>();
for (WindowManager.LayoutParams p : moreTouchPointParams) {
points.add(new Point(p.x, p.y));
}
// 更新 AutoClickService moreClickPositions
AutoClickService service = AutoClickService.getInstance();
if (service != null) {
service.setMoreClickPositions(points);
}
return true;
case MotionEvent.ACTION_UP:
v.performClick();
return true;
}
return false;
}
});
windowManager.addView(point, params);
moreTouchPointViews.add(point);
moreTouchPointParams.add(params);
}
private void removeMoreTouchPoint() {
if (!moreTouchPointViews.isEmpty()) {
View lastPoint = moreTouchPointViews.get(moreTouchPointViews.size() - 1);
try {
windowManager.removeView(lastPoint);
} catch (Exception e) {
Log.w(TAG, "移除 touchPoint 失败", e);
}
moreTouchPointViews.remove(moreTouchPointViews.size() - 1);
moreTouchPointParams.remove(moreTouchPointParams.size() - 1);
} else {
Toast.makeText(context, "没有更多触摸点可以删除", Toast.LENGTH_SHORT).show();
}
}
public void removeFloatingViews() { public void removeFloatingViews() {
try { try {
// 移除单点触摸视图 // 移除单点触摸视图
@ -423,77 +497,14 @@ public class FloatingViewManager {
moreControlBarView = null; moreControlBarView = null;
} }
isFloatingViewsShown = false;
isClicking = false; isClicking = false;
logDebug("悬浮窗已移除"); logDebug("悬浮窗已移除");
} catch (Exception e) { } catch (Exception e) {
Log.e(TAG, "移除悬浮窗失败", e); Log.e(TAG, "移除悬浮窗失败", e);
isFloatingViewsShown = false;
isClicking = false; isClicking = false;
} }
} }
private void addNewTouchPoint(int x, int y) {
View point = new View(context);
point.setBackgroundResource(R.drawable.un_touch_point);
WindowManager.LayoutParams params = createTouchPointLayoutParams(x, y);
windowManager.addView(point, params);
moreTouchPointViews.add(point);
moreTouchPointParams.add(params);
point.setOnTouchListener(new View.OnTouchListener() {
private float lastX, lastY, startX, startY;
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
lastX = event.getRawX();
lastY = event.getRawY();
startX = params.x;
startY = params.y;
break;
case MotionEvent.ACTION_MOVE:
float dx = event.getRawX() - lastX;
float dy = event.getRawY() - lastY;
params.x = (int) (startX + dx);
params.y = (int) (startY + dy);
windowManager.updateViewLayout(v, params);
logDebug("多点触摸点移动到: (" + params.x + ", " + params.y + ")");
break;
}
return true;
}
});
}
private void removeLastTouchPoint() {
if (moreTouchPointViews.size() <= 1) {
Toast.makeText(context, "至少保留一个触摸点", Toast.LENGTH_SHORT).show();
return;
}
int lastIndex = moreTouchPointViews.size() - 1;
View last = moreTouchPointViews.remove(lastIndex);
moreTouchPointParams.remove(lastIndex);
windowManager.removeView(last);
}
private WindowManager.LayoutParams createTouchPointLayoutParams(int x, int y) {
WindowManager.LayoutParams params = new WindowManager.LayoutParams(
100, 100,
Build.VERSION.SDK_INT >= Build.VERSION_CODES.O ?
WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY :
WindowManager.LayoutParams.TYPE_PHONE,
WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE |
WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
PixelFormat.TRANSLUCENT
);
params.gravity = Gravity.TOP | Gravity.START;
params.x = x;
params.y = y;
return params;
}
private void updateTouchPointPosition(float paramX, float paramY, float dx, float dy) { private void updateTouchPointPosition(float paramX, float paramY, float dx, float dy) {
Point constrainedPoint = ViewUtils.constrainToScreen( Point constrainedPoint = ViewUtils.constrainToScreen(
paramX + dx, paramY + dy, screenWidth - singleTouchPointView.getWidth(), screenHeight - singleTouchPointView.getHeight()); paramX + dx, paramY + dy, screenWidth - singleTouchPointView.getWidth(), screenHeight - singleTouchPointView.getHeight());
@ -520,6 +531,14 @@ public class FloatingViewManager {
windowManager.updateViewLayout(moreControlBarView, moreControlBarParams); windowManager.updateViewLayout(moreControlBarView, moreControlBarParams);
} }
private List<Point> getMoreTouchPositions() {
List<Point> points = new ArrayList<>();
for (WindowManager.LayoutParams params : moreTouchPointParams) {
points.add(new Point(params.x, params.y));
}
return points;
}
public void showInputDialog() { public void showInputDialog() {
EditText input = new EditText(context); EditText input = new EditText(context);
input.setInputType(InputType.TYPE_CLASS_NUMBER); input.setInputType(InputType.TYPE_CLASS_NUMBER);
@ -569,30 +588,37 @@ public class FloatingViewManager {
}); });
} }
public void flashTouchPoint() { // 改成只闪烁当前索引的触摸点
if (singleTouchPointView != null) { public void flashTouchPoint(int index) {
singleTouchPointView.animate() if (index == -1) {
.alpha(0.3f) // 单点模式
.setDuration(100) if (singleTouchPointView != null) {
.withEndAction(() -> singleTouchPointView.animate()
singleTouchPointView.animate() .alpha(0.3f)
.alpha(1.0f) .setDuration(100)
.setDuration(100) .withEndAction(() ->
.start() singleTouchPointView.animate()
) .alpha(1.0f)
.start(); .setDuration(100)
} .start()
for (View point : moreTouchPointViews) { )
point.animate() .start();
.alpha(0.3f) }
.setDuration(100) } else {
.withEndAction(() -> // 多点模式
point.animate() if (index >= 0 && index < moreTouchPointViews.size()) {
.alpha(1.0f) View point = moreTouchPointViews.get(index);
.setDuration(100) point.animate()
.start() .alpha(0.3f)
) .setDuration(100)
.start(); .withEndAction(() ->
point.animate()
.alpha(1.0f)
.setDuration(100)
.start()
)
.start();
}
} }
} }

View File

@ -0,0 +1,12 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="32dp"
android:height="32dp"
android:viewportWidth="1024"
android:viewportHeight="1024">
<path
android:fillColor="#FF000000"
android:pathData="M645.4,488.5H535.3V378.5c0,-13.3 -10,-23.3 -20,-23.3 -10,0 -20,10 -20,23.3v110H382c-13.3,0 -20,10 -20,23.3s10,23.3 20,23.3h110v110c0,13.3 10,23.3 20,23.3 10,0 20,-10 20,-23.3V535.2h110c13.3,0 20,-10 20,-23.3 0,-13.3 -6.7,-23.3 -16.7,-23.3z"/>
<path
android:fillColor="#FF000000"
android:pathData="M512,195.1c-173.4,0 -316.8,143.4 -316.8,316.8 0,173.4 143.4,316.8 316.8,316.8 173.4,0 316.8,-143.4 316.8,-316.8 0,-173.4 -140.1,-316.8 -316.8,-316.8zM512,785.3c-150.1,0 -273.4,-123.4 -273.4,-273.4S361.9,238.4 512,238.4s273.4,123.4 273.4,273.4S665.4,785.3 512,785.3z"/>
</vector>

View File

@ -0,0 +1,9 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="32dp"
android:height="32dp"
android:viewportWidth="1024"
android:viewportHeight="1024">
<path
android:fillColor="#FF000000"
android:pathData="M512,1024C229.2,1024 0,794.8 0,512S229.2,0 512,0s512,229.2 512,512 -229.2,512 -512,512zM512,128C300,128 128,300 128,512s172,384 384,384 384,-172 384,-384S724,128 512,128zM704,576L320,576a64,64 0,1 1,0 -128h384a64,64 0,0 1,64 64c0,35.4 -28.6,64 -64,64z"/>
</vector>

View File

@ -0,0 +1,18 @@
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="38.2dp"
android:height="32dp"
android:viewportWidth="1223"
android:viewportHeight="1024">
<path
android:pathData="M725.5,956.5l-0.5,-0.8c-0.7,-1.2 -1.8,-2.7 -2.9,-4l-0.3,-0.6c-0.5,-0.7 -1.1,-1.5 -1.5,-2.3l-2.6,-3.7 -0.3,-0.3 -126,-194a104.2,104.2 0,0 1,-15 -76.9,101.8 101.8,0 0,1 41.9,-65.4 96.7,96.7 0,0 1,97.9 -7.1v-324.2C716,220.8 758.5,174.8 810.7,174.8c52.1,0 94.7,46 94.7,102.4v104.1a75.9,75.9 0,0 1,23.8 -3.9c24.7,0 48,11.9 64.4,32.4a80,80 0,0 1,43.2 -13.4,78.7 78.7,0 0,1 48.7,17.2c10.9,8.5 20,19.5 26.6,32.2 7.7,-2.4 15.7,-3.7 23.7,-3.7 48.6,0 88.1,46 88.1,102.4v272.4c0,60.3 -26.6,126.9 -67.9,169.8 -23,23.9 -47.7,37.1 -69.9,37.1L816.9,1024c-50.5,0 -73.1,-37.4 -91.4,-67.5zM1091.6,973.6c8.2,0 28.5,-13.6 48.4,-43.8 21.4,-32.6 33.6,-71.6 33.6,-106.9L1173.5,542.7c0,-22.9 -14.1,-42.8 -30.2,-42.8a21.5,21.5 0,0 0,-10.2 2.6v98h-0.1c-1.1,16.4 -14.3,29.2 -30.2,29.2 -16,0 -29.2,-13 -30.3,-29.2h-0L1072.4,515.5l-1.8,-23.9c-1.6,-21.3 -15.2,-38.6 -30.4,-38.6 -6.7,0 -13.7,3.7 -19.1,10v106c-0,17.3 -13.6,31.3 -30.4,31.4 -16.7,-0.1 -30.3,-14.1 -30.3,-31.4v-93.3l-2.3,-10.9c-3.7,-18.1 -16.3,-31.8 -29.1,-31.8 -8.7,0 -17.5,6.2 -23.4,16.3l-1,105.1v39.5c0,15.3 -12.2,27.9 -27,27.9h-6.6c-14.9,0 -27,-12.6 -27,-27.9L843.9,278.4l-0.2,-11.1c0,-23.6 -16.6,-42.7 -37.1,-42.7 -20.5,0 -37.1,19.2 -37.1,42.7l1.3,306.7c0.1,0.9 0.1,1.9 0.1,2.8v121.7c-0.2,15.7 -11.6,28.8 -26.6,30.8a30.5,30.5 0,0 1,-33.2 -22.8l-11.4,-34.4a41.3,41.3 0,0 0,-26.3 -18.2,40.2 40.2,0 0,0 -31.1,6.4c-19,13.2 -24,39.8 -11.3,59.4l129.9,199.6 0.4,0.5 1.6,2.4 2,3.1c1.2,2 2.5,3.9 3.7,5.4l0.8,1.1 0.6,1.4c20.2,33.4 28,40.6 43.4,40.6h278v-0.2,0z"
android:fillColor="#000000"/>
<path
android:pathData="M586.9,268.3v50h-449.6v-50zM124.6,386.4l-87.9,-87.9a7.5,7.5 0,0 1,0 -10.6l87.9,-87.9a7.5,7.5 0,0 1,12.8 5.3v175.8a7.5,7.5 0,0 1,-12.8 5.3z"
android:fillColor="#000000"/>
<path
android:pathData="M12.5,137.4v-50h449.6v50z"
android:fillColor="#000000"/>
<path
android:pathData="M474.8,19.2l87.9,87.9a7.5,7.5 0,0 1,0 10.6l-87.9,87.9a7.5,7.5 0,0 1,-12.8 -5.3V24.5a7.5,7.5 0,0 1,12.8 -5.3z"
android:fillColor="#000000"/>
</vector>

View File

@ -20,14 +20,21 @@
android:layout_width="48dp" android:layout_width="48dp"
android:layout_height="48dp" android:layout_height="48dp"
android:layout_marginBottom="8dp" android:layout_marginBottom="8dp"
android:src="@drawable/save" /> android:src="@drawable/add" />
<ImageView <ImageView
android:id="@+id/remove_button" android:id="@+id/remove_button"
android:layout_width="48dp" android:layout_width="48dp"
android:layout_height="48dp" android:layout_height="48dp"
android:layout_marginBottom="8dp" android:layout_marginBottom="8dp"
android:src="@drawable/eye" /> android:src="@drawable/remove" />
<ImageView
android:id="@+id/slide_button"
android:layout_width="48dp"
android:layout_height="48dp"
android:layout_marginBottom="8dp"
android:src="@drawable/slide" />
<ImageView <ImageView
android:id="@+id/settings_button" android:id="@+id/settings_button"