Top Related Projects
A Kotlin compiler plugin to make dependency injection with Dagger 2 easier.
Epoxy is an Android library for building complex screens in a RecyclerView
Uber's cross-platform mobile architecture framework.
A small, yet full-featured framework that allows building View-based Android applications
Flexbox for Android
Quick Overview
Litho is a declarative UI framework for Android, developed and open-sourced by Facebook. It provides a component-based architecture that allows developers to build complex and efficient user interfaces for their Android applications.
Pros
- Declarative UI: Litho uses a declarative approach to UI development, which makes it easier to reason about and maintain the application's state.
- Performance: Litho is designed for high-performance, with features like automatic layout calculations and efficient rendering.
- Testability: Litho's component-based architecture makes it easier to write unit tests for individual UI components.
- Flexibility: Litho can be integrated with existing Android UI frameworks, allowing developers to use it alongside other libraries and tools.
Cons
- Learning Curve: Litho's declarative approach and component-based architecture may require a significant learning curve for developers who are more familiar with traditional Android UI development.
- Ecosystem: Litho is primarily developed and used by Facebook, and the ecosystem of third-party libraries and tools may be smaller compared to other popular Android UI frameworks.
- Adoption: As a relatively new framework, Litho may have a smaller user base and community compared to more established Android UI libraries.
- Complexity: The declarative nature and component-based architecture of Litho can add complexity to the development process, especially for larger and more complex applications.
Code Examples
Here are a few examples of how to use Litho in your Android application:
- Creating a Simple Text Component:
@LayoutSpec
object TextComponentSpec {
@OnCreateLayout
fun onCreateLayout(c: ComponentContext): Component {
return Text.create(c)
.text("Hello, Litho!")
.textSizeDip(24f)
.build()
}
}
- Handling User Interactions:
@LayoutSpec
object ButtonComponentSpec {
@OnCreateLayout
fun onCreateLayout(c: ComponentContext): Component {
return Button.create(c)
.text("Click me!")
.clickHandler(ButtonComponentSpec.onClick(c))
.build()
}
@OnEvent(ClickEvent::class)
fun onClick(c: ComponentContext) {
Toast.makeText(c.androidContext, "Button clicked!", Toast.LENGTH_SHORT).show()
}
}
- Composing Components:
@LayoutSpec
object ContainerComponentSpec {
@OnCreateLayout
fun onCreateLayout(c: ComponentContext): Component {
return Column.create(c)
.child(TextComponentSpec.create(c))
.child(ButtonComponentSpec.create(c))
.build()
}
}
Getting Started
To get started with Litho, you can follow these steps:
- Add the Litho dependencies to your Android project's
build.gradle
file:
dependencies {
implementation "com.facebook.litho:litho-core:${LITHO_VERSION}"
implementation "com.facebook.litho:litho-annotations:${LITHO_VERSION}"
annotationProcessor "com.facebook.litho:litho-processor:${LITHO_VERSION}"
implementation "com.facebook.litho:litho-widget:${LITHO_VERSION}"
implementation "com.facebook.yoga:yoga:${YOGA_VERSION}"
}
- Create a new Litho component by annotating a Kotlin class with
@LayoutSpec
:
@LayoutSpec
class MyComponentSpec {
@OnCreateLayout
fun onCreateLayout(c: ComponentContext): Component {
return Text.create(c)
.text("Hello, Litho!")
.textSizeDip(24f)
.build()
}
}
- Use the Litho component in your Android activity or fragment:
class MyActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(
LithoView.create(this) {
MyComponent.create(it)
}
Competitor Comparisons
A Kotlin compiler plugin to make dependency injection with Dagger 2 easier.
Pros of Anvil
- Anvil provides a more declarative and reactive approach to building Android UI, which can lead to more maintainable and testable code.
- Anvil's layout system is highly customizable, allowing developers to create complex and dynamic UIs with ease.
- Anvil's performance is optimized, with features like incremental layout updates and efficient rendering.
Cons of Anvil
- Anvil has a smaller community and ecosystem compared to Litho, which may make it harder to find resources and third-party libraries.
- Anvil's learning curve may be steeper for developers who are more familiar with traditional Android UI development.
- Anvil's documentation and tooling may not be as comprehensive as Litho's.
Code Comparison
Litho:
@LayoutSpec
public class MyComponentSpec {
@OnCreateLayout
static Component onCreateLayout(
ComponentContext c, @Prop String title, @Prop String subtitle) {
return Column.create(c)
.child(Text.create(c).text(title).textSizeSp(24).build())
.child(Text.create(c).text(subtitle).textSizeSp(16).build())
.build();
}
}
Anvil:
@Composable
fun MyComponent(title: String, subtitle: String) {
Column {
Text(title, fontSize = 24.sp)
Text(subtitle, fontSize = 16.sp)
}
}
Epoxy is an Android library for building complex screens in a RecyclerView
Pros of Epoxy
- Epoxy provides a more modular and composable approach to building UI components, allowing for better reusability and maintainability.
- Epoxy's support for data binding and automatic view updates can simplify the development process and reduce boilerplate code.
- Epoxy's flexible and extensible architecture allows for easy integration with other libraries and frameworks.
Cons of Epoxy
- Epoxy's learning curve may be steeper than Litho's, as it requires understanding the concept of models and controllers.
- Epoxy's performance may not be as optimized as Litho's, especially for large and complex UI hierarchies.
- Epoxy's documentation and community support may not be as extensive as Litho's, which is backed by Facebook.
Code Comparison
Litho:
@LayoutSpec
public class MyComponentSpec {
@OnCreateLayout
static Component onCreateLayout(ComponentContext c) {
return Column.create(c)
.child(Text.create(c).text("Hello, World!"))
.build();
}
}
Epoxy:
class MyModel : EpoxyModel<MyView>() {
override fun getDefaultLayout(): Int {
return R.layout.view_my_model
}
override fun bind(view: MyView) {
view.setText("Hello, World!")
}
}
Uber's cross-platform mobile architecture framework.
Pros of RIBs
- Modular Architecture: RIBs promotes a modular and scalable architecture, making it easier to manage complex applications.
- Testability: The RIBs architecture encourages the separation of concerns, which enhances the testability of individual components.
- Dependency Management: RIBs provides a clear and structured way to manage dependencies between different parts of the application.
Cons of RIBs
- Complexity: The RIBs architecture can be more complex to set up and understand, especially for smaller projects or teams.
- Learning Curve: Developers may need to invest more time in learning the RIBs framework and its concepts, compared to more straightforward approaches.
Code Comparison
Litho
@LayoutSpec
public class MyComponentSpec {
@OnCreateLayout
static ComponentLayout onCreateLayout(
ComponentContext c, @Prop String text, @Prop boolean isEnabled) {
return Column.create(c)
.child(
Text.create(c)
.text(text)
.textSizeSp(16)
.textColor(isEnabled ? Color.BLACK : Color.GRAY))
.build();
}
}
RIBs
class HomeRib(
private val dependencies: HomeRibDependencies
) : Router<HomeRibBuilder.ParentComponent, HomeRibListener>() {
override fun willAttachToParentViewGroup() {
super.willAttachToParentViewGroup()
attachHomeView()
}
private fun attachHomeView() {
val homeView = HomeView(dependencies.context)
attachView(homeView)
}
}
A small, yet full-featured framework that allows building View-based Android applications
Pros of Conductor
- Conductor provides a more flexible and modular approach to building Android applications, allowing for easier management of complex UI hierarchies.
- Conductor's lifecycle management and view state handling can simplify the development process compared to traditional Android Fragment-based approaches.
- Conductor's support for nested controllers and view transitions can enable more dynamic and visually appealing user interfaces.
Cons of Conductor
- Conductor has a steeper learning curve compared to Litho, as it introduces a new set of concepts and abstractions that developers need to understand.
- Conductor's reliance on a custom view hierarchy management system may make it more difficult to integrate with existing Android libraries and frameworks.
- Conductor's performance characteristics may not be as optimized as Litho's, which is designed specifically for high-performance UI rendering.
Code Comparison
Litho:
@LayoutSpec
public class MyComponentSpec {
@OnCreateLayout
static Component onCreateLayout(
ComponentContext c, @Prop String text, @Prop boolean isEnabled) {
return Text.create(c)
.text(text)
.isEnabled(isEnabled)
.build();
}
}
Conductor:
public class MyController extends Controller {
@NonNull
@Override
protected View onCreateView(@NonNull LayoutInflater inflater, @NonNull ViewGroup container) {
View view = inflater.inflate(R.layout.my_view, container, false);
TextView textView = view.findViewById(R.id.text_view);
textView.setText(text);
textView.setEnabled(isEnabled);
return view;
}
}
Flexbox for Android
Pros of Flexbox Layout
- Flexbox Layout provides a more robust and flexible layout system compared to Litho, allowing for easier management of complex UI elements.
- The library is actively maintained by Google and has a larger community, potentially offering more support and resources.
- Flexbox Layout is a well-established and widely-adopted layout solution, making it a more familiar choice for many developers.
Cons of Flexbox Layout
- Litho is specifically designed for Android development, while Flexbox Layout is a more general-purpose layout solution, which may make it less optimized for certain Android-specific use cases.
- The learning curve for Flexbox Layout may be steeper compared to Litho, which is designed to be more intuitive for Android developers.
- Litho may offer better performance and integration with the Android platform, as it is developed and maintained by Facebook specifically for Android development.
Code Comparison
Litho:
@LayoutSpec
public class MyComponentSpec {
@OnCreateLayout
static Component onCreateLayout(ComponentContext c) {
return Column.create(c)
.child(Text.create(c).text("Hello, World!"))
.build();
}
}
Flexbox Layout:
FlexboxLayout flexboxLayout = new FlexboxLayout(context);
FlexboxLayout.LayoutParams layoutParams = new FlexboxLayout.LayoutParams(
ViewGroup.LayoutParams.WRAP_CONTENT,
ViewGroup.LayoutParams.WRAP_CONTENT);
TextView textView = new TextView(context);
textView.setText("Hello, World!");
flexboxLayout.addView(textView, layoutParams);
Convert designs to code with AI
Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.
Try Visual CopilotREADME
Litho
Litho is a declarative framework for building efficient UIs on Android.
- Declarative: Litho uses a declarative API to define UI components. You simply describe the layout for your UI based on a set of immutable inputs and the framework takes care of the rest.
- Asynchronous layout: Litho can measure and layout your UI ahead of time without blocking the UI thread.
- View flattening: Litho uses Yoga for layout and automatically reduces the number of ViewGroups that your UI contains.
- Fine-grained recycling: Any component such as a text or image can be recycled and reused anywhere in the UI.
To get started, check out these links:
- Learn how to use Litho in your project.
- Get started with our tutorial.
- Read more about Litho in our docs.
Installation
Litho can be integrated either in Gradle or Buck projects. Read our Getting Started guide for installation instructions.
Quick start
1. Initialize SoLoader
in your Application
class.
public class SampleApplication extends Application {
@Override
public void onCreate() {
super.onCreate();
SoLoader.init(this, false);
}
}
2. Create and display a component in your Activity
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
final ComponentContext c = new ComponentContext(this);
final Component component = Text.create(c)
.text("Hello World")
.textSizeDip(50)
.build();
setContentView(LithoView.create(c, component));
}
Run sample
You can find more examples in our sample app.
To build and run (on an attached device/emulator) the sample app, execute
$ buck fetch sample
$ buck install -r sample
or, if you prefer Gradle,
$ ./gradlew :sample:installDebug
Contributing
Before contributing to Litho, please first read the Code of Conduct that we expect project participants to adhere to.
For pull requests, please see our CONTRIBUTING guide.
See our issues page for ideas on how to contribute or to let us know of any problems.
Please also read our Coding Style and Code of Conduct before you contribute.
Getting Help
- Post on StackOverflow
using the
#litho
tag. - Chat with us on Gitter.
- Join our Facebook Group to stay up-to-date with announcements.
- Please open GitHub issues only if you suspect a bug in the framework or have a feature request and not for general questions.
License
Litho is licensed under the Apache 2.0 License.
Top Related Projects
A Kotlin compiler plugin to make dependency injection with Dagger 2 easier.
Epoxy is an Android library for building complex screens in a RecyclerView
Uber's cross-platform mobile architecture framework.
A small, yet full-featured framework that allows building View-based Android applications
Flexbox for Android
Convert designs to code with AI
Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.
Try Visual Copilot