Próbowałem z następującym kodem, ale ten kod nie działa zgodnie z oczekiwaniami. Właściwie wahałem się, czy poprosić o pomoc w sprawie tego prostego rozwiązania, ale straciłem dużo czasu, w końcu tu przyjechałem.
deltaX = bounds.right - bounds.left;
deltaY = bounds.bottom - bounds.top;
double distance = Math.sqrt(Math.pow(deltaX, 2) + Math.pow(deltaY, 2));
float arrowLength= (float) (distance / 3);
float lineAngle = (float) Math.atan2(deltaY, deltaX);
float angle = (float) Math.toRadians(20);
float sinValue = (float) Math.sin(lineAngle - angle);
point_x_1 = bounds.left - 20 * sinValue;
point_y_1 = (float) (bounds.bottom - 0.5 * arrowLength* Math.cos(lineAngle - angle));
angle = (float) Math.toRadians(60);
sinValue = (float) Math.sin(lineAngle + angle);
point_x_3 = bounds.left + 20 * sinValue;
point_y_3 = (float) (bounds.bottom + arrowLength* Math.cos(lineAngle + angle));
path.moveTo(bounds.right, bounds.top);
path.lineTo(bounds.left, bounds.bottom);
path.moveTo(point_x_1, point_y_1);
path.lineTo(bounds.left, bounds.bottom);
path.lineTo(point_x_3, point_y_3);
Uwaga: mam cztery kierunki, każdy będzie dostępny w różnych scenariuszach.
enum PathDirection {
TopLeftToBottomRight,
TopRightToBottomLeft,
BottomLeftToTopRight,
BottomRightToTopLeft
}
Powyższy kod próbowałem dla TopRightToBottomLeft.
Przykładowe wyniki
Rys 1: Wartości RectF: [180.0,560.0] [820.0,740.0]
Rys. 2: Wartości RectF: [240.0,480.0] [640.0,980.0]
Aktualizuj
path.reset();
canvas.save();
canvas.translate(200, 200);
float direction = (float) Math.atan2(400 - 200, 400 - 200);
canvas.rotate(direction);
path.moveTo(0, 0);
float distance = (float) Math.sqrt(200 * 200 + 200 * 200);
path.lineTo(distance, 0);
float x1 = distance - (distance * 20 / 100);
float y1 = -(distance * 15 / 100);
path.moveTo(x1, y1);
path.lineTo(distance, 0);
x1 = distance - (distance * 20 / 100);
y1 = (distance * 15 / 100);
path.lineTo(x1, y1);
canvas.drawPath(path, mPaint);
canvas.restore();
Użyłem tego kodu, aby narysować linię od pozycji 200, 200
do 300, 300
. Ale to narysuje linię od 0, 0
do distance
.
Zrzut ekranu
2 odpowiedzi
Z pomocą pskink doszedłem do rozwiązania, przykładowego kodu, które rysuje linię ze strzałką z 200, 200
do 400, 400
path.reset();
RectF rectF = new RectF(200, 200, 400, 400);
canvas.save();
canvas.translate(rectF.left, rectF.top);
float direction = (float) Math.atan2(rectF.bottom - rectF.top, rectF.right - rectF.left);
float degree = (float) Math.toDegrees(direction);
canvas.rotate(degree);
canvas.drawColor(Color.parseColor("#E3F2FD"));
path.moveTo(0, 0);
float x = rectF.right - rectF.left;
float y = rectF.bottom - rectF.top;
float distance = (float) Math.sqrt(x * x + y * y);
path.lineTo(distance, 0);
float x1 = distance - (distance * 20 / 100);
float y1 = -(distance * 15 / 100);
path.moveTo(x1, y1);
path.lineTo(distance, 0);
float x2 = distance - (distance * 20 / 100);
float y2 = (distance * 15 / 100);
path.lineTo(x2, y2);
canvas.drawPath(path, mPaint);
canvas.restore();
SC:
Uwaga Jeśli nie chcesz obracać płótna, możesz użyć Helder Sepulveda, działa również zgodnie z oczekiwaniami.
Zobacz poniższy kod javascript, który powinien ładnie przekładać się na Javę
canvas = document.getElementById("canvas");
ctx = canvas.getContext("2d");
function drawLine(p1, p2, asize) {
ctx.beginPath()
ctx.moveTo(p1.x, p1.y);
ctx.lineTo(p2.x, p2.y);
if (asize > 0) {
lineAngle = Math.atan2(p1.y - p2.y, p1.x - p2.x);
delta = Math.PI/6
for (i=0; i<2; i++) {
ctx.moveTo(p2.x, p2.y);
x = p2.x + asize * Math.cos(lineAngle + delta)
y = p2.y + asize * Math.sin(lineAngle + delta)
ctx.lineTo(x, y);
delta *= -1
}
}
ctx.stroke();
}
drawLine({x:10, y:10}, {x:100, y:20}, 20)
drawLine({x:20, y:15}, {x:140, y:120}, 20)
drawLine({x:140, y:20}, {x:80, y:50} , 20)
drawLine({x:150, y:20}, {x:150, y:90}, 20)
drawLine({x:180, y:90}, {x:180, y:20}, 20)
drawLine({x:200, y:10}, {x:200, y:140}, 10)
drawLine({x:220, y:140}, {x:220, y:10}, 10)
<canvas id="canvas">
Jeśli go uruchomisz, powinieneś zobaczyć kilka próbek.
Rozbijmy to, że drawLine
ma 3 parametry (p1, p2, asize)
pierwsze dwa to punkt początkowy i końcowy linii, ostatni to rozmiar strzałki, aby dać końcowemu użytkownikowi pewną kontrolę nad tym, jak duże są te strzały na końcu.
Większość matematyki zawierałaś w swoim kodzie, ale była trochę pomieszana, obliczyłeś lineAngle
, ale zgubiłem się w kolejności twoich operacji, więc lepiej zacznij od zera.
Podobne pytania
Nowe pytania
android
Android to mobilny system operacyjny Google, używany do programowania lub tworzenia urządzeń cyfrowych (smartfony, tablety, samochody, telewizory, Wear, Glass, IoT). W przypadku tematów związanych z Androidem użyj tagów specyficznych dla Androida, takich jak android-intent, android-activity, android-adapter itp. W przypadku pytań innych niż programowanie lub programowanie, ale związanych ze strukturą Androida, użyj tego linku: https: // android.stackexchange.com.