برنامه نویسی

ایجاد Kotlin DSL برای اجزای آهنگسازی Jetpack

آشنایی با Kotlin DSL

Kotlin DSL (زبان خاص دامنه) یک ویژگی قدرتمند Kotlin است که به شما امکان می دهد API های اعلانی و بصری را ایجاد کنید. این ماده به طور گسترده ای در اکوسیستم کوتلین استفاده می شود که Gradle Kotlin DSL یک نمونه کلاسیک است. با استفاده از Kotlin DSL ، می توانید تنظیمات پیچیده را به بلوک های ساده و سازمان یافته تبدیل کنید.

اما اگر بتوانیم همان مفهوم را برای آهنگسازی Jetpack بیاوریم ، چه می شود؟ تصور کنید که اجزای UI خود را با استفاده از یک رویکرد اعلانی و انعطاف پذیر تعریف کنید. در این مقاله به بررسی نحوه ساخت DSL سفارشی برای یک مؤلفه آهنگسازی ، مانند CustomButton می پردازیم.
CustomButton

این مقاله در ابتدا در Medium منتشر شده است: ایجاد Kotlin DSL برای اجزای آهنگسازی Jetpack

چرا DSL برای اجزای آهنگسازی ایجاد می کنید؟

رویکرد اعلانی آهنگسازی JetPack در حال حاضر تعاریف UI را بصری تر می کند. با این حال ، هنگام برخورد با مؤلفه های قابل استفاده مجدد و بسیار قابل تنظیم ، DSL مزایای اضافی را ارائه می دهد:

  • خوانایی روشن: تنظیمات به بلوک های منطقی سازماندهی می شوند و درک آنها را آسان تر می کنند.
  • قابلیت استفاده مجدد: شما می توانید منطق تکراری را محاصره کرده و API های ساده را برای استفاده مجدد ایجاد کنید.
  • قابلیت گسترش: افزودن تنظیمات جدید ساده و بصری است.

بیایید یک مثال عملی بسازیم تا بهتر این کار را درک کنیم.

ساختن DSL از ابتدا

تعریف کلاس پیکربندی

ابتدا یک کلاس ایجاد می کنیم تا پیکربندی های مؤلفه خود را نگه دارید:

class CustomButtonConfig {
    var text: String = ""
    var icon: ImageVector? = null
    var onClick: (() -> Unit)? = null
    var backgroundColor: Color = MaterialTheme.colors.primary
    var textColor: Color = Color.White
    val shapes = mutableListOf<ComposedShape>()
}
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

این کلاس خواصی را که کاربران می توانند در این مؤلفه پیکربندی کنند ، از جمله اشکال تشکیل شده تعریف می کند.

ایجاد @DslMarker حاشیه نویسی

برای جداسازی دامنه DSL و جلوگیری از درگیری بین بلوک های مختلف ، یک حاشیه نویسی سفارشی ایجاد می کنیم:

@DslMarker
annotation class CustomButtonDSL
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

ما کلاسهای مربوطه را به روز می کنیم تا این حاشیه نویسی را اعمال کنیم:

@CustomButtonDSL
class ComposedShape {
    val shapes = mutableListOf<ShapeConfig>()
}

@CustomButtonDSL
sealed class ShapeConfig {
    data class TriangleConfig(var base: Float, var height: Float, var color: Color) : ShapeConfig()
    data class RhombusConfig(var sideLength: Float, var angle: Float, var color: Color) : ShapeConfig()
}
حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

ایجاد توابع DSL برای شکل در متن دکمه

ما توابع را برای پیکربندی اشکال در دکمه DSL اضافه می کنیم:

fun CustomButtonConfig.composedShape(block: ComposedShape.() -> Unit) {
    shapes.add(ComposedShape().apply(block))
}

fun ComposedShape.triangle(base: Float, height: Float, color: Color) {
    shapes.add(ShapeConfig.TriangleConfig(base, height, color))
}

fun ComposedShape.rhombus(sideLength: Float, angle: Float, color: Color) {
    shapes.add(ShapeConfig.RhombusConfig(sideLength, angle, color))
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

به روزرسانی CustomButton جزء

ما اصلاح می کنیم customButton عملکرد برای ارائه اشکال ترکیب شده:

@Composable
fun customButton(configure: CustomButtonConfig.() -> Unit) {
    val config = CustomButtonConfig().apply(configure)

    Button(
        onClick = config.onClick ?: {},
        colors = ButtonDefaults.buttonColors(backgroundColor = config.backgroundColor),
        modifier = Modifier.padding(8.dp)
    ) {
        Column(
            modifier = Modifier.fillMaxWidth(),
            horizontalAlignment = Alignment.CenterHorizontally
        ) {
            // Render Shapes
            config.shapes.forEach { composedShape ->
                composedShape.shapes.forEach { shape ->
                    when (shape) {
                        is ShapeConfig.TriangleConfig -> {
                            Text(
                                text = "\u25B2", // Triangle representation
                                color = shape.color,
                                modifier = Modifier.size(shape.base.dp, shape.height.dp)
                            )
                        }

                        is ShapeConfig.RhombusConfig -> {
                            Text(
                                text = "\u25C6", // Rhombus representation
                                color = shape.color,
                                modifier = Modifier.size(shape.sideLength.dp)
                            )
                        }
                    }
                }
            }
            // Render Text and Icon
            Row(
                horizontalArrangement = Arrangement.Center,
                verticalAlignment = Alignment.CenterVertically
            ) {
                config.icon?.let {
                    Icon(imageVector = it, contentDescription = null, tint = config.textColor)
                }
                if (config.icon != null) Spacer(modifier = Modifier.width(8.dp))
                Text(text = config.text, color = config.textColor)
            }
        }
    }
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

نمونه های عملی

مثال 1: دکمه با مثلث و رومبوس

customButton {
    text = "With Shapes"
    textColor = Color.Black
    backgroundColor = Color.LightGray
    onClick = { println("Button with shapes clicked!") }

    composedShape {
        triangle(base = 50f, height = 30f, color = Color.Red)
        rhombus(sideLength = 40f, angle = 45f, color = Color.Blue)
    }
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

مثال 2: دکمه ساده

customButton {
    text = "Click Here"
    textColor = Color.Black
    onClick = { println("Button clicked!") }
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

مثال 3: دکمه با نماد

customButton {
    text = "Favorite"
    icon = Icons.Default.Favorite
    textColor = Color.Black
    onClick = { println("Favorite clicked!") }
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

مثال 4: دکمه با سبک سفارشی

customButton {
    text = "Send"
    icon = Icons.Default.Send
    onClick = { println("Send clicked!") }
    backgroundColor = Color.Green
    textColor = Color.White
}

حالت تمام صفحه را وارد کنید

از حالت تمام صفحه خارج شوید

مزایای Kotlin DSL

  1. خوانایی بهبود یافته: تنظیمات به بلوک های واضح و منطقی سازماندهی می شوند.
  2. دیگ بخار کاهش یافته: کد کمتر تکراری ، بیشتر روی آنچه مهم است تمرکز کنید.
  3. قابلیت گسترش: ویژگی های جدید را می توان بدون تغییر کد موجود به DSL اضافه کرد.
  4. بهره وری: API اعلانی باعث پیشرفت می شود و تجربه توسعه دهنده را افزایش می دهد.

نمونه

نمونه تصویر مؤلفه

پایان

ایجاد Kotlin DSL برای اجزای سازنده به شما امکان می دهد تا از قدرت کوتلین برای ساده سازی و سازماندهی UI خود به روشی اعلامیه استفاده کنید. علاوه بر این که کد قابل خواندن تر است ، این روش قابلیت استفاده مجدد و مقیاس پذیری قطعات را ترویج می کند.

چرا آن را امتحان نکنید و DSL خود را ایجاد کنید؟ با کوتلین ، امکانات بی پایان است. بیایید کار کنیم!

نوشته های مشابه

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

دکمه بازگشت به بالا