Flutter XML Part 1: Static Flutter Layout From XML
By: Ali Ghanbari
Tags: Flutter Ui, Parser, Xml, Flutter, Dart

If you ever worked with any front-end framework before, you would know that the standard way of declaring your app’s UI is using some sort of markup language, like Html or XAML, and it’s been that way for a long time for the good reason of separating logic code from UI code.

Here in flutter land, we use code for everything, but what if we used XML with flutter? is it even possible to do that? well… that’s what I want to find out.

So here I wrote a very simple flutter page layout using XML:

<scaffold>

<appbar>

<title>

<text>Counter App</text>

</title>

</appbar>

<body>

<center>

<text>hello world</text>

</center>

</body>

</scaffold>

This piece of XML is just something I wrote and can use to conduct my experiment. for parsing the XML I will be using the XML package for dart from pub.dev.

The first step is to find a way to parse the body. because we don’t know what widget is inside the body element, we need to check the name of the XML element. Here is a recursive function that can convert the body element of the XML above to an equivalent flutter widget:

Widget parseWidget(BuildContext context, XmlElement element) {

if(element == null){

return Container();

} else if (element.name.local == 'center') {

return Center(

child: parseWidget(context, element.firstElementChild),

);

} else if(element.name.local == 'text'){

return Text(element.text);

} else {

throw '${element.name.local} is not implemented.';

}

}

I also made a custom widget that can help us construct our layout from XML:

class XmlWidgetBuilder extends StatelessWidget {

final String name;

final String namespace;

final XmlElement element;

final String xml;

final Widget Function(BuildContext context, XmlElement element) builder; const XmlWidgetBuilder({

Key key,

@required this.name,

this.namespace,

@required this.builder,

this.element,

this.xml,

}) : assert(element != null || xml != null,

'xml string or an XmlElement must be provided.'),

assert(!(element != null && xml != null),

'you can either provide xml string or an XmlElement.'),

assert(name != null, 'you should have the name of the element'),

super(key: key); @override

Widget build(BuildContext context) {

var el = xml != null

? parse(xml).getElement(name)

: null ?? element.getElement(name);

return builder(context, el);

}

}

This widget will take an XML string or an XML element and using them to call the builder function.

Using the parser function and the XmlWidgetBuilder, we can finally construct our page:

@override

Widget build(BuildContext context) {

return XmlWidgetBuilder(

name: 'scaffold',

xml: xml, // this is the xml string

builder: (context, scaffold) {

var appbar = scaffold.getElement('appbar');

var title = appbar.getElement('title');

return Scaffold(

appBar: AppBar(

title: parseWidget(context, title.firstElementChild),

),

body: XmlWidgetBuilder(

name: 'body',

element: scaffold,

builder: (context, body) {

return parseWidget(context, body.firstElementChild);

},

),

);

},

);

}

And here is the output:

So as we found out(if it wasn’t obvious from the beginning), it is possible to create a flutter layout from XML. this can also be used in a variety of ways, for example: creating an Html rendering widget.

This was a very basic experiment, in the next parts, I want to experiment with displaying variables and calling functions from an XML layout.