ב-Compose, אובייקט Painter
משמש לייצוג של משהו שאפשר לצייר (תחליף לממשקי ה-API של Drawable
שמוגדרים ב-Android) ומשפיע על המדידה ועל הפריסה של הרכיב המתאים שאפשר להרכיב שמשתמש בו . A
BitmapPainter
לוקח ImageBitmap
שיכול לצייר Bitmap
על המסך.
ברוב תרחישי השימוש, הפונקציה painterResource()
שלמעלה מחזירה את האובייקט הנכון של המחלקה Painter עבור הנכס (כלומר BitmapPainter
או VectorPainter
). למידע נוסף על ההבדלים בין שני האובייקטים, אפשר לקרוא את הקטע ImageBitmap לעומת ImageVector.
Painter
שונה מDrawModifier
, שמוגבלת לגבולות שמוגדרים לה ולא משפיעה על המדידה או על הפריסה של הרכיב.
כדי ליצור צייר בהתאמה אישית, מרחיבים את המחלקה Painter
ומטמיעים את השיטה onDraw
, שמאפשרת גישה ל-DrawScope
כדי לצייר גרפיקה בהתאמה אישית. אפשר גם לשנות את intrinsicSize
, שישפיע על רכיב ה-Composable שהוא מוכל בו:
class OverlayImagePainter constructor( private val image: ImageBitmap, private val imageOverlay: ImageBitmap, private val srcOffset: IntOffset = IntOffset.Zero, private val srcSize: IntSize = IntSize(image.width, image.height), private val overlaySize: IntSize = IntSize(imageOverlay.width, imageOverlay.height) ) : Painter() { private val size: IntSize = validateSize(srcOffset, srcSize) override fun DrawScope.onDraw() { // draw the first image without any blend mode drawImage( image, srcOffset, srcSize, dstSize = IntSize( this@onDraw.size.width.roundToInt(), this@onDraw.size.height.roundToInt() ) ) // draw the second image with an Overlay blend mode to blend the two together drawImage( imageOverlay, srcOffset, overlaySize, dstSize = IntSize( this@onDraw.size.width.roundToInt(), this@onDraw.size.height.roundToInt() ), blendMode = BlendMode.Overlay ) } /** * Return the dimension of the underlying [ImageBitmap] as it's intrinsic width and height */ override val intrinsicSize: Size get() = size.toSize() private fun validateSize(srcOffset: IntOffset, srcSize: IntSize): IntSize { require( srcOffset.x >= 0 && srcOffset.y >= 0 && srcSize.width >= 0 && srcSize.height >= 0 && srcSize.width <= image.width && srcSize.height <= image.height ) return srcSize } }
עכשיו, אחרי שיצרנו את Painter
המותאם אישית, אנחנו יכולים להוסיף תמונה על גבי תמונת המקור באופן הבא:
val rainbowImage = ImageBitmap.imageResource(id = R.drawable.rainbow) val dogImage = ImageBitmap.imageResource(id = R.drawable.dog) val customPainter = remember { OverlayImagePainter(dogImage, rainbowImage) } Image( painter = customPainter, contentDescription = stringResource(id = R.string.dog_content_description), contentScale = ContentScale.Crop, modifier = Modifier.wrapContentSize() )
אפשר לראות את הפלט של שילוב שתי התמונות באמצעות כלי ציור מותאם אישית למטה:

אפשר להשתמש גם ב-Modifier.paint(customPainter)
כדי לצייר את התוכן לרכיב שאפשר להרכיב באופן הבא:
val rainbowImage = ImageBitmap.imageResource(id = R.drawable.rainbow) val dogImage = ImageBitmap.imageResource(id = R.drawable.dog) val customPainter = remember { OverlayImagePainter(dogImage, rainbowImage) } Box( modifier = Modifier.background(color = Color.Gray) .padding(30.dp) .background(color = Color.Yellow) .paint(customPainter) ) { /** intentionally empty **/ }
מומלץ עבורך
- הערה: טקסט הקישור מוצג כש-JavaScript מושבת
- ImageBitmap לעומת ImageVector {:#bitmap-vs-vector}
- גרפיקה ב-Compose
- טעינת תמונות {:#loading-images}