Litho uses a unidirectional data flow with immutable inputs. Following the name established by React, the inputs that a
Component takes are known as props.
The props for a given
Component are the union of all arguments annotated with
@Prop in your spec methods. You can access the value of the props in all the methods that declare it as an
The same prop can be defined and accessed in multiple lifecycle methods. The annotation processor will ensure you're using consistent prop types and consistent annotation parameters across all the spec methods.
Take the following
Component spec, for example:
MyComponentSpec defines two props: a String prop called
prop1 and an int prop named
prop1 is optional and it needs to be marked as such in all the methods that define it, otherwise the annotation processor will throw an exception.
When the lifecycle methods get called, the
@Prop parameters will hold the value passed down from the Component's parent when the Component was created (or their default values).
Props are defined and used the same way in
For each unique prop defined on the spec, the annotation processor creates a builder pattern method on the Component Builder that has the same name as the prop and that takes as only parameter the value to set for that prop.
You pass down values for these props by calling the appropriate methods on the generated Component Builder:
PropDefault can be used for setting
the default value of an optional
Prop in a
MountSpec. The annotated field must
be a constant (i.e.
static final) with the same name and type as the
Prop. We'll often want to
define explicit default values for our optional props instead of simply using Java's defaults.
Let's see an how we can declare and use
PropDefault also support values from Resources via setting a
resId. Let's define
PropDefault with a resource value:
When creating layouts, it's very common to use values from Android's resource system such as dimensions, colors, strings, etc. Litho provides convenient ways to set prop values from Android resources using annotations.
Let's consider a simple example:
In the example above,
MyComponent has props that are expected to take a color integer (
someColor), a pixel dimension (
someSize), and a string (
someString) as value. Very often, you'll want to set the value of these props using resource values:
The framework allows you to annotate props with resource types so that your component builder has convenience methods to use resource values directly.
With the changes above,
MyComponent's builder will contain Res, Attr, Dip, and Px methods for the annotated props according to their resource types. So you'll be able to do the following:
Other supported resource types are
Sometimes, you want to support having a list of items. This can unfortunately
be a bit painful since it requires the developer to make a list, add all the
items to it, and pass list to the component builder's method. The
parameter aims to makes this a little easier.
This can then be used as follows:
This also works for props with a
resType. For instance, given a Component like this:
You can add multiple sizes through calls to the builder:
The props of a Component are read-only. The Component's parent passes down values for the props when it creates the Component and they cannot change throughout the lifecycle of the Component. If the props values must be updated, the parent has to create a new Component and pass down new values for the props. The props objects should be made immutable. Due to background layout, props may be accessed on multiple threads. Props immutability ensures that no thread safety issues can happen during the component's lifecycle.
Common props are props that are available on all Components, e.g.
flex etc. A full list of CommonProps can be found in the code here.
You may want to access a Common Prop inside your Component (e.g. to see if a click handler was set on it), in which case you should use set
isCommonProp, and name your prop using the same name as the Common Prop. If you wish to override the behavior of the Common Prop, then you should also set the