J'ai trouvé une fonction pour les rectangles dont les 4 coins sont arrondis, mais je veux que seuls les 2 coins supérieurs soient arrondis. Que puis-je faire ?
canvas.drawRoundRect(new RectF(0, 100, 100, 300), 6, 6, paint);
J'ai trouvé une fonction pour les rectangles dont les 4 coins sont arrondis, mais je veux que seuls les 2 coins supérieurs soient arrondis. Que puis-je faire ?
canvas.drawRoundRect(new RectF(0, 100, 100, 300), 6, 6, paint);
Une façon simple et efficace de dessiner un côté solide est d'utiliser l'écrêtage - l'écrêtage de rectangle est essentiellement gratuit, et beaucoup moins de code à écrire qu'un chemin personnalisé.
Si je veux un rectangle de 300x300, avec les parties supérieures gauche et droite arrondies de 50 pixels, c'est possible :
canvas.save();
canvas.clipRect(0, 0, 300, 300);
canvas.drawRoundRect(new RectF(0, 0, 300, 350), 50, 50, paint);
canvas.restore();
Cette approche ne fonctionnera que pour l'arrondi de 2 ou 3 coins adjacents, elle est donc un peu moins configurable qu'une approche basée sur le chemin, mais l'utilisation de rectangles ronds est plus efficace, puisque drawRoundRect() est entièrement accéléré par le matériel (c'est-à-dire, tessellé en triangles) alors que drawPath() revient toujours au rendu logiciel (le logiciel dessine un bitmap de chemin, et le télécharge pour être mis en cache sur le GPU).
Ce n'est pas un gros problème de performance pour les petits dessins peu fréquents, mais si vous animez des chemins, le coût du dessin logiciel peut allonger le temps de trame et augmenter le risque de perte de trames. Le masque de chemin coûte également de la mémoire.
Si vous souhaitez adopter une approche basée sur les chemins, je vous recommande d'utiliser GradientDrawable pour simplifier les lignes de code (en supposant que vous n'ayez pas besoin de définir un shader personnalisé, par exemple pour dessiner un bitmap).
mGradient.setBounds(0, 0, 300, 300);
mGradient.setCornerRadii(new int[] {50,50, 50,50, 0,0, 0,0});
Avec GradientDrawable#setCornerRadii() vous pouvez définir n'importe quel coin pour qu'il soit arrondi, et animer raisonnablement entre les états.
Voici ma réponse à la question ci-dessus. Ici, j'ai créé une fonction d'extension Kotlin qui utilise les éléments suivants Path
ainsi que le quadTo
qui peut également être utilisée dans les API de niveau inférieur.
fun Canvas.drawRoundRectPath(
rectF: RectF,
radius: Float,
roundTopLeft: Boolean,
roundTopRight: Boolean,
roundBottomLeft: Boolean,
roundBottomRight: Boolean,
paint: Paint) {
val path = Path()
//Move path cursor to start point
if (roundBottomLeft) {
path.moveTo(rectF.left, rectF.bottom - radius)
} else {
path.moveTo(rectF.left, rectF.bottom)
}
// drawing line and rounding top left curve
if (roundTopLeft) {
path.lineTo(rectF.left, rectF.top + radius)
path.quadTo(rectF.left, rectF.top, rectF.left + radius, rectF.top)
} else {
path.lineTo(rectF.left, rectF.top)
}
// drawing line an rounding top right curve
if (roundTopRight) {
path.lineTo(rectF.right - radius, rectF.top)
path.quadTo(rectF.right, rectF.top, rectF.right, rectF.top + radius)
} else {
path.lineTo(rectF.right, rectF.top)
}
// drawing line an rounding bottom right curve
if (roundBottomRight) {
path.lineTo(rectF.right, rectF.bottom - radius)
path.quadTo(rectF.right, rectF.bottom, rectF.right - radius, rectF.bottom)
} else {
path.lineTo(rectF.right, rectF.bottom)
}
// drawing line an rounding bottom left curve
if (roundBottomLeft) {
path.lineTo(rectF.left + radius, rectF.bottom)
path.quadTo(rectF.left, rectF.bottom, rectF.left, rectF.bottom - radius)
} else {
path.lineTo(rectF.left, rectF.bottom)
}
path.close()
drawPath(path, paint)
}
Nous pouvons appeler la fonction avec l'objet canvas et passer l'objet RectF
avec la dimension sur laquelle on veut appliquer la courbe.
Nous pouvons également passer le booléen pour les coins que nous voulons arrondir. Cette réponse peut encore être personnalisée pour accepter le rayon des coins individuels.
Utilisez PaintDrawable pourrait être meilleur :
val topLeftRadius = 10
val topRightRadius = 10
val bottomLeftRadius = 0
val bottomRightRadius = 0
val rect = Rect(0, 0, 100, 100)
val paintDrawable = PaintDrawable(Color.RED)
val outter = floatArrayOf(topLeftRadius, topLeftRadius, topRightRadius, topRightRadius,
bottomLeftRadius, bottomLeftRadius, bottomRightRadius, bottomRightRadius)
paintDrawable.setCornerRadii(outter)
paintDrawable.bounds = rect
paintDrawable.draw(canvas)
Dessine un rectangle avec des coins arrondis à gauche
private void drawRoundRect(float left, float top, float right, float bottom, Paint paint, Canvas canvas) {
Path path = new Path();
path.moveTo(left, top);
path.lineTo(right, top);
path.lineTo(right, bottom);
path.lineTo(left + radius, bottom);
path.quadTo(left, bottom, left, bottom - radius);
path.lineTo(left, top + radius);
path.quadTo(left, top, left + radius, top);
canvas.drawPath(path, onlinePaint);
}
Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.
1 votes
Ne pouvez-vous pas simplement dessiner un rectangle arrondi puis un rectangle ordinaire sur la moitié inférieure (en remplaçant les coins arrondis par des coins normaux) ?