Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

804 - ODS cards - Provide XML version of cards #805

Draft
wants to merge 3 commits into
base: develop
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ fun ComponentBanners() {
this.firstButtonText = firstButtonText
this.secondButtonText = secondButtonText
odsBanner.onFirstButtonClick = onFirstButtonClick
odsBanner.onSecondButtonClick = onFirstButtonClick
odsBanner.onSecondButtonClick = onSecondButtonClick
if (hasImage) {
odsBanner.image = AppCompatResources.getDrawable(context, placeholderResId)
val onDrawable: (Drawable?) -> Unit = { odsBanner.image = it }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@

package com.orange.ods.app.ui.components.cards

import android.graphics.drawable.Drawable
import androidx.appcompat.content.res.AppCompatResources
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.padding
Expand All @@ -25,9 +27,13 @@ import androidx.compose.ui.res.dimensionResource
import androidx.compose.ui.res.painterResource
import androidx.compose.ui.res.stringResource
import coil.compose.rememberAsyncImagePainter
import coil.imageLoader
import coil.request.ImageRequest
import com.orange.ods.app.R
import com.orange.ods.app.databinding.OdsHorizontalCardBinding
import com.orange.ods.app.domain.recipes.LocalRecipes
import com.orange.ods.app.ui.LocalThemeManager
import com.orange.ods.app.ui.UiFramework
import com.orange.ods.app.ui.components.utilities.clickOnElement
import com.orange.ods.app.ui.utilities.DrawableManager
import com.orange.ods.app.ui.utilities.code.CodeImplementationColumn
Expand All @@ -51,29 +57,64 @@ fun CardHorizontal(customizationState: CardCustomizationState) {
.verticalScroll(state = rememberScrollState())
.padding(dimensionResource(id = com.orange.ods.R.dimen.spacing_m))
) {
val title = recipe.title
val subtitle = if (hasSubtitle) recipe.subtitle else null
val text = if (hasText) recipe.description else null
val firstButtonText = stringResource(id = R.string.component_element_first_button)
val onFirstButtonClick = if (hasFirstButton) {
{ clickOnElement(context, firstButtonText) }
} else null
val secondButtonText = stringResource(id = R.string.component_element_second_button)
val onSecondButtonClick = if (hasSecondButton) {
{ clickOnElement(context, secondButtonText) }
} else null
val cardText = stringResource(id = R.string.component_card_element_card)

OdsHorizontalCard(
title = recipe.title,
image = OdsCard.Image(
rememberAsyncImagePainter(
model = buildImageRequest(context, recipe.imageUrl, darkModeEnabled),
placeholder = painterResource(id = DrawableManager.getPlaceholderResId()),
error = painterResource(id = DrawableManager.getPlaceholderResId(error = true))
),
""
),
subtitle = if (hasSubtitle) recipe.subtitle else null,
text = if (hasText) recipe.description else null,
onClick = if (isClickable) {
{ clickOnElement(context, cardText) }
} else null,
firstButton = if (hasFirstButton) OdsCard.Button(firstButtonText) { clickOnElement(context, firstButtonText) } else null,
secondButton = if (hasSecondButton) OdsCard.Button(secondButtonText) { clickOnElement(context, secondButtonText) } else null,
imagePosition = imagePosition.value,
divider = hasDivider
val placeholderResId = DrawableManager.getPlaceholderResId()
val errorPlaceholderResId = DrawableManager.getPlaceholderResId(error = true)

UiFramework<OdsHorizontalCardBinding>(
compose = {
OdsHorizontalCard(
title = title,
image = OdsCard.Image(
rememberAsyncImagePainter(
model = buildImageRequest(context, recipe.imageUrl, darkModeEnabled),
placeholder = painterResource(id = placeholderResId),
error = painterResource(id = errorPlaceholderResId)
),
""
),
subtitle = subtitle,
text = text,
onClick = if (isClickable) {
{ clickOnElement(context, cardText) }
} else null,
firstButton = onFirstButtonClick?.let { OdsCard.Button(firstButtonText, it) },
secondButton = onSecondButtonClick?.let { OdsCard.Button(secondButtonText, it) },
imagePosition = imagePosition.value,
divider = hasDivider
)
},
xml = {
this.title = title
this.subtitle = subtitle
this.text = text

this.firstButtonText = firstButtonText
this.secondButtonText = secondButtonText
odsHorizontalCard.onFirstButtonClick = onFirstButtonClick
odsHorizontalCard.onSecondButtonClick = onSecondButtonClick

odsHorizontalCard.image = AppCompatResources.getDrawable(context, placeholderResId)
val onDrawable: (Drawable?) -> Unit = { odsHorizontalCard.image = it }
val request = ImageRequest.Builder(buildImageRequest(context, recipe.imageUrl, darkModeEnabled))
.error(errorPlaceholderResId)
.target(onError = onDrawable, onSuccess = onDrawable)
.build()
context.imageLoader.enqueue(request)
this.imagePosition = [email protected]
}
)

CodeImplementationColumn(
Expand Down
76 changes: 76 additions & 0 deletions app/src/main/res/layout/ods_horizontal_card.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
<?xml version="1.0" encoding="utf-8"?>

<!--
~ Software Name: Orange Design System
~ SPDX-FileCopyrightText: Copyright (c) Orange SA
~ SPDX-License-Identifier: MIT
~
~ This software is distributed under the MIT licence,
~ the text of which is available at https://opensource.org/license/MIT/
~ or see the "LICENSE" file for more details.
~
~ Software description: Android library of reusable graphical components
-->

<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">

<data>

<variable
name="title"
type="String" />

<variable
name="subtitle"
type="String" />

<variable
name="text"
type="String" />

<variable
name="firstButtonText"
type="String" />

<variable
name="secondButtonText"
type="String" />

<variable
name="imagePosition"
type="com.orange.ods.compose.component.card.OdsCard.Image.Position" />
</data>

<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">

<com.orange.ods.xml.component.card.OdsHorizontalCard
android:id="@+id/ods_horizontal_card"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:title="@{title}"
app:subtitle="@{subtitle}"
app:text="@{text}"
app:firstButtonText="@{firstButtonText}"
app:secondButtonText="@{secondButtonText}"
app:odsHorizontalCardImagePosition="@{imagePosition}" />

<!-- Invisible OdsHorizontalCard used for tests -->
<com.orange.ods.xml.component.card.OdsHorizontalCard
android:id="@+id/ods_horizontal_card_test"
android:visibility="gone"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:title="Card title"
app:subtitle="Card subtitle"
app:text="Text displayed in the card."
app:firstButtonText="First button"
app:secondButtonText="Second button"
app:imageContentDescription="Content description of the image"
app:odsHorizontalCardImagePosition="end" />

</FrameLayout>

</layout>
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
/*
* Software Name: Orange Design System
* SPDX-FileCopyrightText: Copyright (c) Orange SA
* SPDX-License-Identifier: MIT
*
* This software is distributed under the MIT licence,
* the text of which is available at https://opensource.org/license/MIT/
* or see the "LICENSE" file for more details.
*
* Software description: Android library of reusable graphical components
*/

package com.orange.ods.xml.component.card

import android.content.Context
import android.graphics.drawable.Drawable
import android.util.AttributeSet
import androidx.appcompat.content.res.AppCompatResources
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.setValue
import androidx.core.content.withStyledAttributes
import androidx.databinding.BindingAdapter
import com.google.accompanist.drawablepainter.rememberDrawablePainter
import com.orange.ods.compose.component.card.OdsCard
import com.orange.ods.compose.component.card.OdsHorizontalCard
import com.orange.ods.extension.ifNotNull
import com.orange.ods.xml.R
import com.orange.ods.xml.component.OdsAbstractComposeView
import com.orange.ods.xml.utilities.extension.fromXmlAttrValue
import com.orange.ods.xml.utilities.extension.getResourceIdOrNull

class OdsHorizontalCard @JvmOverloads constructor(context: Context, attrs: AttributeSet? = null) : OdsAbstractComposeView(context, attrs) {

var image by mutableStateOf<Drawable?>(null)
var imageContentDescription by mutableStateOf("")
var title by mutableStateOf("")
var subtitle by mutableStateOf<String?>(null)
var text by mutableStateOf<String?>(null)
var firstButtonText by mutableStateOf<String?>(null)
var onFirstButtonClick by mutableStateOf<(() -> Unit)?>(null)
var secondButtonText by mutableStateOf<String?>(null)
var onSecondButtonClick by mutableStateOf<(() -> Unit)?>(null)
var imagePosition by mutableStateOf(OdsCard.Image.Position.Start)

init {
context.withStyledAttributes(attrs, R.styleable.OdsHorizontalCard) {
image = getResourceIdOrNull(R.styleable.OdsHorizontalCard_image)?.let { AppCompatResources.getDrawable(context, it) }
imageContentDescription = getString(R.styleable.OdsHorizontalCard_imageContentDescription).orEmpty()
title = getString(R.styleable.OdsHorizontalCard_title).orEmpty()
subtitle = getString(R.styleable.OdsHorizontalCard_subtitle)
text = getString(R.styleable.OdsHorizontalCard_text)
firstButtonText = getString(R.styleable.OdsHorizontalCard_firstButtonText)
secondButtonText = getString(R.styleable.OdsHorizontalCard_secondButtonText)
imagePosition = OdsCard.Image.Position.fromXmlAttrValue(getInteger(R.styleable.OdsHorizontalCard_odsHorizontalCardImagePosition, 0))
}
}

@Composable
override fun OdsContent() {
OdsHorizontalCard(
title = title,
image = OdsCard.Image(rememberDrawablePainter(drawable = image), imageContentDescription),
subtitle = subtitle,
text = text,
firstButton = ifNotNull(firstButtonText, onFirstButtonClick) { text, onClick ->
OdsCard.Button(text, onClick)
},
secondButton = ifNotNull(secondButtonText, onSecondButtonClick) { text, onClick ->
OdsCard.Button(text, onClick)
},
imagePosition = imagePosition
)

}

}

internal object OdsHorizontalCardBindingAdapter {

@JvmStatic
@BindingAdapter("odsHorizontalCardImagePosition")
fun com.orange.ods.xml.component.card.OdsHorizontalCard.setOdsHorizontalCardImagePosition(position: OdsCard.Image.Position) {
this.imagePosition = position
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
/*
* Software Name: Orange Design System
* SPDX-FileCopyrightText: Copyright (c) Orange SA
* SPDX-License-Identifier: MIT
*
* This software is distributed under the MIT licence,
* the text of which is available at https://opensource.org/license/MIT/
* or see the "LICENSE" file for more details.
*
* Software description: Android library of reusable graphical components
*/

package com.orange.ods.xml.utilities.extension

import com.orange.ods.compose.component.card.OdsCard

/**
* @return [OdsCard.Image.Position] associated to the provided [xmlId]
* BE CAREFUL: If the enum values change you have to update associated XML attributes in the lib-xml.
*/
fun OdsCard.Image.Position.Companion.fromXmlAttrValue(xmlId: Int): OdsCard.Image.Position = OdsCard.Image.Position.entries[xmlId]

/**
* XML enum value corresponding to this [OdsCard.Image.Position]
* BE CAREFUL: As there is no way to access XML enum names directly, if an enum name change, you have to update this method.
*/
val OdsCard.Image.Position.xmlEnumValue
get() = when (this) {
OdsCard.Image.Position.Start -> "start"
OdsCard.Image.Position.End -> "end"
}
14 changes: 14 additions & 0 deletions lib-xml/src/main/res/values/attrs.xml
Original file line number Diff line number Diff line change
Expand Up @@ -84,4 +84,18 @@
<attr name="displaySurface" />
</declare-styleable>

<declare-styleable name="OdsHorizontalCard">
<attr name="title" format="string" />
<attr name="subtitle" format="string" />
<attr name="text" />
<attr name="image" />
<attr name="imageContentDescription" />
<attr name="firstButtonText" />
<attr name="secondButtonText" />
<!-- BE CAREFUL: If this enum change, don't forget to update associated extension -->
<attr name="odsHorizontalCardImagePosition" format="enum">
<enum name="start" value="0" />
<enum name="end" value="1" />
</attr>
</declare-styleable>
</resources>
Original file line number Diff line number Diff line change
Expand Up @@ -153,7 +153,9 @@ object OdsCard {
}

enum class Position {
Start, End
Start, End;

companion object
}
}

Expand Down
Loading