У меня есть ImageView и 4 других изображения, которые я перетаскиваю, чтобы припарковать определенные точки в моем изображении. Тип масштаба изображения установлен на fitCenter . Теперь я воспользовался помощью одного из постов и рассчитал горизонтальный и вертикальный буфер. Проблема здесь в том, что иногда для вычисления буфера приходится делить на 2, а иногда на 4 в функции compileSaveData . Что делает его ненадежным. Может кто-нибудь, пожалуйста, помогите мне с решением. Я разместил внизу свои xml и java ниже.
MarkPointsActivity. java
public class MarkPointsActivity extends BaseActivity implements View.OnClickListener {
private ImageView imgMapper,imgTopLeft,imgTopRight,imgBottomLeft,imgBottomRight;
private Button btnSave;
private int lastAction;
private float dY;
private float dX;
private boolean zooming;
private float newX,newY;
private Image image;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Override
public int getLayoutById() {
return R.layout.activity_mark_points;
}
@Override
public void getViewById() {
image = (Image) getIntent().getSerializableExtra(ExtraUtils.IMAGE_PATH);
imgMapper = findViewById(R.id.imgMapper);
Glide.with(this).load(image.getPath()).into(imgMapper);
imgTopLeft = findViewById(R.id.imgTopLeft);
imgTopRight = findViewById(R.id.imgTopRight);
imgBottomLeft = findViewById(R.id.imgBottomLeft);
imgBottomRight = findViewById(R.id.imgBottomRight);
btnSave = findViewById(R.id.btnSave);
btnSave.setOnClickListener(this);
movePoints();
}
@SuppressLint("ClickableViewAccessibility")
private void movePoints() {
DisplayMetrics metrics = getResources().getDisplayMetrics();
final int windowWidth = metrics.widthPixels;
final int windowHeight = metrics.heightPixels;
imgTopLeft.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
dX = v.getX() - event.getRawX();
dY = v.getY() - event.getRawY();
lastAction = MotionEvent.ACTION_DOWN;
case MotionEvent.ACTION_MOVE:
newX = event.getRawX() + dX;
newY = event.getRawY() + dY;
// check if the view out of screen
if ((newX <= 0 || newX >= windowWidth-v.getWidth()) || (newY <= 0 || newY >= windowHeight-v.getHeight()))
{
lastAction = MotionEvent.ACTION_MOVE;
break;
}
v.setX(newX);
v.setY(newY);
lastAction = MotionEvent.ACTION_MOVE;
zooming = true;
break;
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_CANCEL:
zooming = false;
break;
}
return true;
}
});
imgTopRight.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
float newX, newY;
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
dX = v.getX() - event.getRawX();
dY = v.getY() - event.getRawY();
lastAction = MotionEvent.ACTION_DOWN;
break;
case MotionEvent.ACTION_MOVE:
newX = event.getRawX() + dX;
newY = event.getRawY() + dY;
// check if the view out of screen
if ((newX <= 0 || newX >= windowWidth-v.getWidth()) || (newY <= 0 || newY >= windowHeight-v.getHeight()))
{
lastAction = MotionEvent.ACTION_MOVE;
break;
}
v.setX(newX);
v.setY(newY);
lastAction = MotionEvent.ACTION_MOVE;
break;
}
return true;
}
});
imgBottomLeft.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
float newX, newY;
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
dX = v.getX() - event.getRawX();
dY = v.getY() - event.getRawY();
lastAction = MotionEvent.ACTION_DOWN;
break;
case MotionEvent.ACTION_MOVE:
newX = event.getRawX() + dX;
newY = event.getRawY() + dY;
// check if the view out of screen
if ((newX <= 0 || newX >= windowWidth-v.getWidth()) || (newY <= 0 || newY >= windowHeight-v.getHeight()))
{
lastAction = MotionEvent.ACTION_MOVE;
break;
}
v.setX(newX);
v.setY(newY);
lastAction = MotionEvent.ACTION_MOVE;
break;
}
return true;
}
});
imgBottomRight.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
float newX, newY;
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
dX = v.getX() - event.getRawX();
dY = v.getY() - event.getRawY();
lastAction = MotionEvent.ACTION_DOWN;
break;
case MotionEvent.ACTION_MOVE:
newX = event.getRawX() + dX;
newY = event.getRawY() + dY;
// check if the view out of screen
if ((newX <= 0 || newX >= windowWidth-v.getWidth()) || (newY <= 0 || newY >= windowHeight-v.getHeight()))
{
lastAction = MotionEvent.ACTION_MOVE;
break;
}
v.setX(newX);
v.setY(newY);
lastAction = MotionEvent.ACTION_MOVE;
break;
}
return true;
}
});
}
@Override
public void manageToolBar() {
}
@Override
public void onClick(View v) {
switch (v.getId()){
case R.id.btnSave:
compileAndSaveData();
break;
}
}
private void compileAndSaveData() {
BitmapFactory.Options options = new BitmapFactory.Options();
options.inScaled = false;
BitmapFactory.decodeFile(image.getPath(), options);
options.inJustDecodeBounds = false;
int width = options.outWidth;
int height = options.outHeight;
double scaleFactor=0.0;
if (width>height)
scaleFactor= width/(imgMapper.getWidth()*1.0);
else
scaleFactor = height/(imgMapper.getHeight()*1.0);
int xBuffer= (int) (imgMapper.getWidth() - (width/scaleFactor))/2;
int yBuffer = (int) (imgMapper.getHeight() - (height/scaleFactor))/2;
//top left corner
double topLeftX = imgTopLeft.getX();
double topLeftY = imgTopLeft.getY();
//top right corner
double topRightX = imgTopRight.getX();
double topRightY = imgTopRight.getY();
//bottom left corner
double bottomLeftX = imgBottomLeft.getX();
double bottomLeftY = imgBottomLeft.getY();
//bottom right corner
double bottomRightX = imgBottomRight.getX();
double bottomRightY = imgBottomRight.getY();
double[] arr = getRealXY(topLeftX,topLeftY,xBuffer,yBuffer,scaleFactor);
topLeftX = arr[0];
topLeftY = arr[1];
}
private double[] getRealXY(double topLeftX, double topLeftY, int xBuffer, int yBuffer, double scaleFactor) {
if (topLeftX < xBuffer || topLeftX > imgMapper.getWidth()-xBuffer)
{
//ignore the click, outside of your image.
}
else if (topLeftY < yBuffer || topLeftY > imgMapper.getHeight()-yBuffer)
{
//ignore the click, outside of your image.
}
else
{
topLeftY = (topLeftY-yBuffer) * scaleFactor;
topLeftX = (topLeftX - xBuffer) * scaleFactor;
}
double[] arr = new double[2];
arr[0]=topLeftX;
arr[1]=topLeftY;
return arr;
}
}
activity_mark_points. xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/layoutContainer"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:orientation="vertical"
android:layout_height="match_parent"
tools:context=".ui.activity.MarkPointsActivity">
<ImageView
android:id="@+id/imgMapper"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="fitCenter" />
<ImageView
android:layout_margin="48dp"
android:id="@+id/imgTopLeft"
android:layout_width="24dp"
android:layout_height="24dp"
android:src="@drawable/tag" />
<ImageView
android:layout_margin="48dp"
android:layout_alignParentRight="true"
android:id="@+id/imgTopRight"
android:layout_width="24dp"
android:layout_height="24dp"
android:layout_gravity="right"
android:src="@drawable/tag" />
<ImageView
android:layout_margin="48dp"
android:layout_alignParentBottom="true"
android:id="@+id/imgBottomLeft"
android:layout_width="24dp"
android:layout_height="24dp"
android:src="@drawable/tag"
/>
<ImageView
android:layout_margin="48dp"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:id="@+id/imgBottomRight"
android:layout_width="24dp"
android:layout_height="24dp"
android:src="@drawable/tag"
android:layout_gravity="right"/>
<Button
android:id="@+id/btnSave"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="save"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"/>
</RelativeLayout>