Пытаюсь реализовать оценку выстрела по мишени. Мишень вот такого типа:
Она прописана в ImageView с прописанным свойством fitCenter в scaleType. Т.е. будет растягиваться под ширину экрана, находясь строго в центре, границами мишени буквально упираясь в границы экрана.
Пользователь касанием устанавливает и перемещает пробоину на мишени, после чего нажатием кнопки "Сохранить" вносит данные и оценку в что-то-типа-БД (SharedPreferences)
Сейчас у меня на оценке висит вот такой код:
public void getTheMarkForShot(float absoluteX, float absoluteY){
ImageView aimTarget = findViewById(R.id.aimTarget);
TextView textView = findViewById(R.id.textView2);
ImageView red_dot = findViewById(R.id.red_dot);
//Координаты центра - считаются правильно
float centerX=aimTarget.getX() + aimTarget.getWidth() / 2;
float centerY=aimTarget.getY() + aimTarget.getHeight() / 2;
//Определим расстояние от центра пробоины до центра мишени
double absoluteDistance = Math.sqrt(Math.pow(absoluteX - centerX, 2) + Math.pow(absoluteY - centerY, 2));
//Определяем координаты точки на пробоине, ближайшей к центру мишени
double betterX = absoluteX * ((absoluteDistance - (red_dot.getWidth() / 2)) / absoluteDistance);
double betterY = absoluteY * ((absoluteDistance - (red_dot.getHeight() / 2)) / absoluteDistance);
//Определение оценки и вывод результата
byte finalMark;
//Если координаты ближайшей точки находятся вне круга (смотрим по его радиусу)
if ((Math.pow(betterX - centerX, 2) + Math.pow(betterY - centerY, 2)) >
Math.pow(aimTarget.getWidth() / 2 , 2)){
//Оценка равна 0. Выводим результаты на экран.
finalMark = 0;
String coordinatesMessage =
String.format("Координаты выстрела: (%.2f, %.2f). Оценка: %s",
absoluteX - centerX, centerY - absoluteY, finalMark);
textView.setText(coordinatesMessage);
}
//Иначе - определяем в каком из сегментов круга находится пробоина
else {
//Разделим ширину круга на части
for (int i = 10; i > -1; i--) {
if ((Math.pow(betterX - centerX, 2) + Math.pow(betterY - centerY, 2)) <=
Math.pow(aimTarget.getWidth() / 2 - (i * (aimTarget.getWidth() / 2/10)), 2)){
finalMark = (byte)i;
String coordinatesMessage =
String.format("Координаты выстрела: (%.2f, %.2f). Оценка: %s",
absoluteX - centerX, centerY - absoluteY, finalMark);
break;
}
}
}
}
На касание на данный момент прописано следующее:
@SuppressLint("ClickableViewAccessibility")
public void getTouchCoordinates(){
final ImageView aimTarget = findViewById(R.id.aimTarget);
final ImageView red_dot = findViewById(R.id.red_dot);
aimTarget.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
float x;
float y;
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN: {
break;
}
case MotionEvent.ACTION_MOVE: {
x = event.getX();
y = event.getY();
red_dot(x, y);
getTheMarkForShot(x,y);
return true;
}
case MotionEvent.ACTION_UP: {
x = event.getX();
y = event.getY();
red_dot(x, y);
getTheMarkForShot(x,y);
return false;
}
}
return true;
}
});
}
Результат вышеописанного - определяется только оценка 0. В остальных случаях определяются только координаты, без оценки (реализовал в функции red_dot).
Итак, сам вопрос: как в данном случае можно наиболее корректно определить оценку выстрела?
Три страницы гугла трижды в день на протяжении трёх дней выдали единственное схожее задание: Задачка по C++ про мишени. Пытался реализовать, в итоге оценка 0 определяется вообще по всему экрану.
Очень прошу помочь, время не то что поджимает - его вообще нет =(
Ответ
Ты все емного усложнил. Все чо тебе надо было, это найти центр круга, он у тебя есть, найти радиус круга, у тебя половина от ширины экрана, расстояние от центра до точки нажатия, тоже считаешь. И надо только проверить как близко точка находится от центра относительно радиуса. Если больше радиуса - 0, в остальном расстояние/радиус и будет от 0 до 1. Инвертироваь еще, отнять это число от 1, чтобы в центре было большее значени. Умнож на 10 и округли и будет число в которое попал
Комментариев нет:
Отправить комментарий