בפיתוח הקומפוזביליות, אובייקט Painter
משמש לייצוג משהו שניתן לצייר (תחליף לממשקי ה-API של Drawable
שמוגדרים ב-Android) ולהשפיע על המדידה והפריסה של התוכן הקומפוזבילי התואם שמשתמש בו . BitmapPainter
מקבל ImageBitmap
שיכול לצייר Bitmap
במסך.
ברוב תרחישי השימוש, השימוש ב-painterResource()
שלמעלה מחזיר את כלי הציור הנכון של הנכס (למשל 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}
- גרפיקה בכתיבה
- Loading images {:#loading-images}