createCoreWidgets function
A widget library for Remote Flutter Widgets that defines widgets that are
implemented on the client in terms of Flutter widgets from the widgets
Dart library.
The following widgets are implemented:
- Align
- AspectRatio
- Center
- ClipRRect
- ColoredBox
- Column
- Container (actually uses AnimatedContainer)
- DefaultTextStyle
- Directionality
- Expanded
- FittedBox
- FractionallySizedBox
- GestureDetector
- GridView (actually uses GridView.builder)
- Icon
- IconTheme
- IntrinsicHeight
- IntrinsicWidth
- Image (see below)
- ListBody
- ListView (actually uses ListView.builder)
- Opacity (actually uses AnimatedOpacity)
- Padding (actually uses AnimatedPadding)
- Placeholder
- Positioned (actually uses AnimatedPositionedDirectional)
Rotation
(actually uses AnimatedRotation)- Row
- SafeArea
Scale
(actually uses AnimatedScale)- SingleChildScrollView
- SizedBox
SizedBoxExpand
(actually SizedBox.expand)SizedBoxShrink
(actually SizedBox.shrink)- Spacer
- Stack
- Text
- Wrap
For each, every parameter is implemented using the same name. Parameters that take structured types are represented using maps, with each named parameter of that type's default constructor represented by a key, with the following notable caveats and exceptions:
-
Enums are represented as strings with the unqualified name of the value. For example, MainAxisAlignment.start is represented as the string
"start"
. -
Types that have multiple subclasses (or multiple very unrelated constructors, like ColorFilter) are represented as maps where the
type
key specifies the type. Typically these have an extension mechanism. -
Matrices are represented as column-major flattened arrays. Matrix4 values must have exactly 16 doubles in the array.
-
AlignmentGeometry values can be represented either as
{x: ..., y: ...}
for a non-directional variant or{start: ..., y: ...}
for a directional variant. -
BoxBorder instances are defined as arrays of BorderSide maps. If the array has length 1, then that value is used for all four sides. Two values become the horizontal and vertical sides respectively. Three values become the start, top-and-bottom, and end respectively. Four values become the start, top, end, and bottom respectively.
-
BorderRadiusGeometry values work similarly to BoxBorder, as an array of Radius values. If the array has one value, it's used for all corners. With two values, the first becomes the
topStart
andbottomStart
corners and the second thetopEnd
andbottomEnd
. With three, the values are used fortopStart
,topEnd
-and-bottomEnd
, andbottomStart
respectively. Four values map to thetopStart
,topEnd
,bottomStart
, andbottomEnd
respectively. -
Color values are represented as integers. The hex literal values are most convenient for this, the alpha, red, green, and blue channels map to the 32 bit hex integer as 0xAARRGGBB.
-
ColorFilter is represented as a map with a
type
key that matches the constructor name (e.g.linearToSrgbGamma
). Thematrix
version uses thematrix
key for the matrix, expecting a 20-value array. Themode
version expects acolor
key for the color (defaults to black) and ablendMode
key for the blend mode (defaults to BlendMode.srcOver). Other types are looked up in ArgumentDecoders.colorFilterDecoders. -
Curve values are represented as a string giving the kind of curve from the predefined Curves, e.g.
easeInOutCubicEmphasized
. More types may be added using ArgumentDecoders.curveDecoders. -
The types supported for Decoration are
box
for BoxDecoration,flutterLogo
for FlutterLogoDecoration, andshape
for ShapeDecoration. More types can be added withdecorationDecoders
. -
DecorationImage expects a
source
key that gives either an absolute URL (to use a NetworkImage) or the name of an asset in the client binary (to use AssetImage). In the case of a URL, thescale
key gives the scale to pass to the NetworkImage constructor. DecorationImage.onError is supported as an event handler with arguments giving the stringified exception and stack trace. Values can be added to ArgumentDecoders.imageProviderDecoders to override the behavior described here. -
Duration is represented by an integer giving milliseconds.
-
EdgeInsetsGeometry values work like BoxBorder, with each value in the array being a double rather than a map.
-
FontFeature values are a map with a
feature
key and avalue
key. Thevalue
defaults to 1. (Technically thefeature
defaults toNONE
, too, but that's hardly useful.) -
The dart:ui.Gradient and painting.Gradient types are both represented as a map with a type that is either
linear
(for LinearGradient),radial
(for RadialGradient), orsweep
(for SweepGradient), using the conventions from the painting.Gradient version. Thetransform
property on these objects is not currently supported. New gradient types can be implemented using ArgumentDecoders.gradientDecoders. -
The
GridDelegate
type is represented as a map with atype
key that is eitherfixedCrossAxisCount
for SliverGridDelegateWithFixedCrossAxisCount ormaxCrossAxisExtent
for SliverGridDelegateWithMaxCrossAxisExtent. New delegate types can be supported using ArgumentDecoders.gridDelegateDecoders. -
IconData is represented as a map with an
icon
key giving the IconData.codePoint (and corresponding keys for the other parameters of the IconData constructor). To determine the values to use for icons in the MaterialIcons font, see how the icons are defined in Icons. For example, Icons.flutter_dash isIconData(0xe2a0, fontFamily: 'MaterialIcons')
so it would be represented here as{ icon: 0xE2A0, fontFamily: "MaterialIcons" }
. (The client must have the font as a defined asset.) -
Locale values are defined as a string in the form
languageCode
,languageCode-countryCode
, orlanguageCode-scriptCode-countryCode-ignoredSubtags
. The string is split on hyphens. -
MaskFilter is represented as a map with a
type
key that must beblur
; only MaskFilter.blur is supported. (The other keys must bestyle
, the BlurStyle, andsigma
.) -
Offsets are a map with an
x
key and ay
key. -
Paint objects are represented as maps; each property of Paint is a key as if there was a constructor that could set all of Paint's properties with named parameters. In principle all properties are supported, though since Paint is only used as part of painting.TextStyle.background and painting.TextStyle.foreground, in practice some of the properties are ignored since they would be no-ops (e.g.
invertColors
). -
Radius is represented as a map with an
x
value and optionally ay
value; if they
value is absent, thex
value is used for both. -
Rect values are represented as an array with four doubles, giving the x, y, width, and height respectively.
-
ShapeBorder values are represented as either maps with a
type
or as an array of ShapeBorder values. In the array case, the values are reduced together using ShapeBorder.+. When represented as maps, the type must be one ofbox
(BoxBorder),beveled
(BeveledRectangleBorder),circle
(CircleBorder),continuous
(ContinuousRectangleBorder),rounded
(RoundedRectangleBorder), orstadium
(StadiumBorder). In the case ofbox
, there must be asides
key whose value is an array that is interpreted as per BoxBorder above. Support for new types can be added using the ArgumentDecoders.shapeBorderDecoders map. -
Shader values are a map with a
type
that is eitherlinear
,radial
, orsweep
; in each case, the data is interpreted as per the Gradient case above, except that the gradient is specifically applied to a Rect given by therect
key and a TextDirection given by thetextDirection
key. New shader types can be added using ArgumentDecoders.shaderDecoders. -
TextDecoration is represented either as an array of TextDecoration values (combined via TextDecoration.combine) or a string which matches the name of one of the TextDecoration constants (e.g.
underline
). -
VisualDensity is either represented as a string which matches one of the predefined values (
adaptivePlatformDensity
,comfortable
, etc), or as a map with keyshorizontal
andvertical
to define a custom density.
Some of the widgets have special considerations:
-
Image does not support the builder callbacks or the Image.opacity parameter (because builders are code and code can't be represented in RFW arguments). The map should have a
source
key that is interpreted as described above for DecorationImage. If thesource
is omitted, an AssetImage with the nameerror.png
is used instead (which will likely fail unless such an asset is declared in the client). -
Parameters of type ScrollController and ScrollPhysics are not supported, because they can't really be exposed to declarative code (they expect to be configured using code that implements delegates or that interacts with controllers).
-
The Text widget's first argument, the string, is represented using the key
text
, which must be either a string or an array of strings to be concatenated.
One additional widget is defined, AnimationDefaults. It has a duration
argument and curve
argument. It sets the default animation duration and
curve for widgets in the library that use the animated variants. If absent,
a default of 200ms and Curves.fastOutSlowIn is used.
Implementation
LocalWidgetLibrary createCoreWidgets() => LocalWidgetLibrary(_coreWidgetsDefinitions);