It would be great if aside from the current way of building widgets you could add JSX like capabilities. I mean add tiny syntactic sugar to enable XML like constructs inside dart code. It just makes code so much easier to read/develop/debug/maintain and also easier for powerful GUI builders to integrate with editable code.
Looking for something like DSX:
https://spark-heroku-dsx.herokuapp.com/index.html
Carlos.
The current issue with DSX is about proper integration with Flutter tools as to provide a great developer experience with debugger, auto-complete, etc. working on .dsx files.
Telling users that they can use DSX but can't use debugger or enjoy auto-complete is a non starter for me. If anybody wants to help, what I need is to figure out a way to add full preprocessing support (with source map) to Dart Tools and VS Code Dart plug in. Once the tools support that DSX or any other transpiling language (any language that is a superset of Dart but compiles everything down to Dart) would just work.
If you can and would like to help, let me know.
cc @lukechurch
@cbazza Can you elaborate on why you want this? Maybe show an example of what it would look like compared to today?
Ok, so the "Basic widgets" example on 'https://flutter.io/widgets-intro/#basic-widgets' would look like the following:
import 'package:flutter/material.dart';
class MyAppBar extends StatelessWidget {
MyAppBar({this.title});
// Fields in a Widget subclass are always marked "final".
final Widget title;
@override
Widget build(BuildContext context) {
let style = {
height: 56.0, // in logical pixels
padding: const EdgeInsets.symmetric(horizontal: 8.0),
decoration: <BoxDecoration color={Colors.blue[500]}/>,
};
return <Container style={style}>
<Row>
<IconButton
icon={<Icon name={Icons.menu}/>}
tooltip='Navigation menu'
onPressed={null}
/>
<Expanded>
{title}
</Expanded>
<IconButton
icon={<Icon name={Icons.search}/>}
tooltip='Search'
onPressed={null}
/>
</Row>
</Container>;
}
}
class MyScaffold extends StatelessWidget {
@override
Widget build(BuildContext context) {
// Material is a conceptual piece of paper on which the UI appears.
return <Material>
<Column>
<MyAppBar
title={<Text
text='Example title'
style={Theme.of(context).primaryTextTheme.title},
/>}
/>
<Expanded>
<Center>
<Text text='Hello, world!'/>
</Center>
</Expanded>
</Column>
</Material>;
}
}
void main() {
runApp(<MaterialApp
title='My app'
home={<MyScaffold/>}
/>);
}
How about this syntax?:
import 'package:flutter/material.dart';
class MyAppBar extends StatelessWidget {
MyAppBar({this.title});
// Fields in a Widget subclass are always marked "final".
final Widget title;
@override
Widget build(BuildContext context) {
return Container(
height: 56.0, // in logical pixels
padding: EdgeInsets.symmetric(horizontal: 8.0),
decoration: BoxDecoration(color: Colors.blue[500]),
child: Row(
children: <Widget>[
IconButton(
icon: Icon(Icons.menu),
tooltip: 'Navigation menu',
onPressed: null,
),
Expanded(
child: title,
),
IconButton(
icon: Icon(Icons.search),
tooltip: 'Search',
onPressed: null,
),
],
),
);
}
}
class MyScaffold extends StatelessWidget {
@override
Widget build(BuildContext context) {
// Material is a conceptual piece of paper on which the UI appears.
return Material(
child: Column(
children: <Widget>[
MyAppBar(
title: Text(
'Example title',
style: Theme.of(context).primaryTextTheme.title,
),
),
Expanded(
child: Center(
child: Text('Hello, world!'),
),
),
],
),
);
}
}
void main() {
runApp(MaterialApp(
title: 'My app',
home: MyScaffold(),
));
}
Huumm, a little improvement but not so good...
Here are the things that gets accomplished by using XML:
(1) No more 'child' & 'children' stuff
(2) easy for 3rd party tools to manipulate (parse, analyse and regenerate)
(3) notice that the switching between markup and programming is easily detected. I mean inside XML you have '{}' to delimit code and in code you have '
I know this is basically fully endorsing React's way but you are half way there anyways ;)
cc @kasperl
(1) No more 'child' & 'children' stuff
I don't really understand why that's desireable. "child" and "children" aren't special. Consider ListTile for example. How would you do that one? Why are "icon" in IconButton, or "home" in MaterialApp, something you want to give a name for, but not "child" in Expanded? All three are just arbitrary arguments that happen to take Widget objects. There's nothing magical about "child" vs "home".
(2) easy for 3rd party tools to manipulate (parse, analyse and regenerate)
You can parse, analyze, and regenerate Dart code. But I agree we should make that easier. Hopefully in the coming years the Dart team will provide better APIs for this.
(3) notice that the switching between markup and programming is easily detected.
Why is that desireable? I mean, why would any of this count as "programming"? It's all just expressions.
I mean inside XML you have '{}' to delimit code and in code you have '
I don't really understand the distinction.
Also separate all the 'style' things from the main structure.
You can do this today in Flutter if you really want to, just put the style in a variable like you did in the XML case.
I don't really understand why that's desireable. "child" and "children" aren't special. Consider ListTile for example. How would you do that one? Why are "icon" in IconButton, or "home" in MaterialApp, something you want to give a name for, but not "child" in Expanded? All three are just arbitrary arguments that happen to take Widget objects. There's nothing magical about "child" vs "home".
Less boilerplate, you don't need to say it because it is inherited in the structure.
Why is that desireable? I mean, why would any of this count as "programming"? It's all just expressions.
It's related to (2) because it makes life of toolmakers, specially GUI builders, much easier since they don't need to fully parse Dart; but it also makes reading the code easier.
I don't really understand the distinction.
The format of XML is very simple so when you see '{}' you know it is calculating an expression in dart. Same for the opposite, when reading dart code and you see '
Also in the final XML processor I would avoid passing objects to attributes of parents and instead create child tags as below:
this...
<MyAppBar>
<Title style={Theme.of(context).primaryTextTheme.title}>
Example title
</Title>
</MyAppBar>
instead of this...
<MyAppBar
title={<Text
text='Example title'
style={Theme.of(context).primaryTextTheme.title},
/>}
/>
Less boilerplate, you don't need to say it because it is inherited in the structure.
But why only for some of the properties? And how do you handle cases where there's two child slots, like ListItem? XML-ish syntax just doesn't seem to handle this very well.
Also I'm not really sure it's less boilerplate.
Compare:
<Container style={style}>
<Row>
<IconButton
icon={<Icon name={Icons.menu}/>}
tooltip='Navigation menu'
onPressed={null}
/>
<Expanded> {title} </Expanded>
</Row>
</Container>
Container(style: style,
child: Row(
children: [
IconButton(
icon: Icon(Icons.menu),
tooltip: 'Navigation menu',
onPressed: null,
),
Expanded(child: title),
],
),
)
It's not at all clear to me that the XML-ish syntax is cleaner or less boilerplatey. There's lots more punctuation, and some duplication of content (e.g. in the close tags). And you had to add some names, so sure, you lose "child", but you gain "name" on Icon.
Also with XML how do you make it clear that Row can take zero, one, or more than one child, while Center has to have exactly one child? What would happen if someone did this?:
<Center> <Test/> <Test/> </Center>
It's related to (2) because it makes life of toolmakers, specially GUI builders, much easier since they don't need to fully parse Dart;
They wouldn't need to fully parse Dart if we had a Dart parsing API either, though, right? I mean, you'd parse what you want to parse and leave the rest. Also I'm not sure it's actually easier to parse, since it's not actually XML; see below.
but it also makes reading the code easier.
I'm not at all convinced that the XMLy version here is easier to read. Once you've read a few build functions, you quickly get used to the nested constructor syntax.
The format of XML is very simple so when you see '{}' you know it is calculating an expression in dart.
It's not actually XML, though, right? It's some variant of XML. Are there well-defined parsing rules for it? For example, is this valid?
<Test name={describe("}")}>
How does it know that the first "}" isn't the end of the attribute expression, without parsing Dart?
Same for the opposite, when reading dart code and you see '
) you know that an object hierarchy is being created from XML markup.
You know this today when you see the new
keyword too, right? Or indeed in the new-less markup proposal above when you see any capitalised word. Is this really a benefit of XML, or are you more familiar with XML than Dart?
Also in the final XML processor I would avoid passing objects to attributes of parents and instead create child tags as below:
I really don't understand what you're proposing here. It's not well-formed XML at all as far as I can tell. Can you elaborate on exactly what the syntax you are proposing is and how it works? For example, the "Text" constructor seems to have disappeared; how does the processor know that
Sorry if I sound defensive or aggressive. :-) This is a topic that's come up several times but I've never had someone willing to actually argue the case before so I'm finding this conversation very useful in teaching me what the reasoning behind the request is. Please don't take my argumentative tone as dismissive, I'm very interested in your input here.
Look, you are mixing everything I say and this conversation is going nowhere. In legal terms you are "Badgering the witness".
If you are really interested in learning why JSX is hot, just google for "react tutorial" and notice that for the past 2 years all articles on React use JSX. The original way of creating component hierarchies in React (which is equivalent to the current way in Flutter) is never mentioned again because JSX became the preferred method (best practice).
https://facebook.github.io/react/tutorial/tutorial.html
https://facebook.github.io/react-native/docs/flatlist.html
Another interesting thing is that Typescript has adopted JSX also:
https://www.typescriptlang.org/docs/handbook/jsx.html
You failed to grasp that XML parsing (with some extra code to skip '{}' properly) is orders of magnitude simpler than fully parsing a programming language like Dart. That is a fact. You are assuming that tool builders will use Dart on their development, not the case, Intellij most likely is using Kotlin and Java on their IDEs that supports Dart (they are a special case because they specialize in language parsing; everybody else will struggle to fully parse Dart from another language).
What I like about putting XML inside another language is that it provides a cognitive separation between the two because XML is very distinct from programming languages. Just scrolling through the source file you can easily see what is code and what is declarative markup. Can't accomplish that with dart code pretending to be markup.
Stop nit-picking things that are not fully specified. All your doubts have answered for it just learn more about how that was handled in JSX. I just don't have the time for this here.
My apologies if I sound defensive or aggressive. This is a topic that's come up several times but I'd never had someone willing to actually argue the case before so I was finding this conversation very useful in teaching me what the reasoning behind the request was. Please don't take my argumentative tone as dismissive, I'm very interested in your input here.
Please don't feel you have to reply. I'm commenting here so that there is transparency regarding the issues that we would have to resolve before we're able to make a decision or design one way or the other. This is basically just a Socratic dialogue. Your participation is welcome but certainly you should not feel that it is your responsibility to defend your proposal.
I've no doubt that JSX is "hot". In React, the non-JSX syntax is a lot worse than the alternative syntax proposed in this issue (the one that looks like our current code but without the "new" and "const" keywords). What I'm trying to understand is whether the same reasons that JSX is "hot" in React apply to Flutter.
Regarding TypeScript doing JSX, In 2012 I was involved in efforts to specify E4H, and even before that there was E4X. Both efforts died. So it's important to me that we understand what exactly it is people like about JSX vs other syntaxes.
Parsing XML isn't easy, parsing sort-of-XML-but-with-curly-braces-somehow is not easy either. Parsing sort-of-XML-but-with-curly-braces-somehow-that-is-embedded-in-another-language is even less easy. However, how easy that is to implement probably isn't a big deal because it's going to be implemented once or twice and then the library that does it will be reused. (I've been heavily involved in writing the specs for parsing HTML and been involved in similar work for XML, and I've implemented a parser for Dart, so I have a pretty good idea of how difficult parsing markup languages vs programming languages actually is.)
What I like about putting XML inside another language is that it provides a cognitive separation between the two because XML is very distinct from programming languages. Just scrolling through the source file you can easily see what is code and what is declarative markup. Can't accomplish that with dart code pretending to be markup.
But why is it beneficial to be able to do that?
It's pretty obvious when scrolling through Flutter apps where the build functions are (they're the giant nested expressions). What is it about "declarative markup" that is important to separate from "code"?
Stop nit-picking things that are not fully specified. All your doubts have answered for it just learn more about how that was handled in JSX. I just don't have the time for this here.
As far as I can tell, JSX doesn't handle the things I was asking about. For example, React doesn't have the concept of child slots. The closest thing I could find is something they do by switching back to JS then back to JSX inside that, so you'd need to be able to parse both the programming language and the markup language.
What I'm trying to understand is whether the same reasons that JSX is "hot" in React apply to Flutter.
Yes, the exact same thing applies here. The current way looks good to you because that's the only option you have. Give people a second option and the same will happen.
Whether E4X died or not is irrelevant because nothing lives forever. I have used ActionScript with E4X a lot and thought that Adobe did an excellent job there. In a way Flutter is just a newer version of Adobe Flash with Flex apps.
(I've been heavily involved in writing the specs for parsing HTML and been involved in similar work for XML, and I've implemented a parser for Dart, so I have a pretty good idea of how difficult parsing markup languages vs programming languages actually is.)
Great so you know that parsing a markup language is trivial compared to parsing an imperative programming language.
But why is it beneficial to be able to do that?
Code readability and simplicity which in turn drives a whole bunch of other benefits.
It's pretty obvious when scrolling through Flutter apps where the build functions are (they're the giant nested expressions). What is it about "declarative markup" that is important to separate from "code"?
On your giant nested expressions can you easily see structure? can this structure be easily manipulated by other tools like GUI builders interchangebly ? I mean like Adobe Flex Builder use to do, drag and drop widgets around, wire them on UI and then switch to code view and just edit anything you want and then switch back to gui mode and continue to manipulate the widgets. You can't do that easily when the programmer goes inside your "giant nested expressions" and writes any valid dart code that doesn't follow the structure that the GUI editor is expecting. With a fixed XML structure that is not a problem.
As far as I can tell, JSX doesn't handle the things I was asking about. For example, React doesn't have the concept of child slots
It handles it just fine, you just don't know how to do it. So going forward just put the example in question here and I will provide you with what I think the JSX version should be.
new ListTile(
title: new Text('CineArts at the Empire',
style: new TextStyle(fontWeight: FontWeight.w500, fontSize: 20.0)),
subtitle: new Text('85 W Portal Ave'),
leading: new Icon(
Icons.theaters,
color: Colors.blue[500],
),
),
<ListTile>
<title>
<Text style={{fontWeight: FontWeight.w500, fontSize: 20.0}}>
CineArts at the Empire
</Text>
</title>
<subtitle>
<Text>85 W Portal Ave</Text>
</subtitle>
<leading>
<Icon data={Icons.theaters} color={Colors.blue[500]}/>
</leading>
</ListTile>,
It looks longer than the dart version but I could had placed everything in the same number of lines. Thing is an IDE/Editor can provide '+' & '-' to expand and collapse these XML nodes anyways.
Make Flutter look familiar to React developers and you have a chance of attracting a bunch of new users to Flutter.
Whether E4X died or not is irrelevant because nothing lives forever.
Whether it died isn't the issue, it's why it died. Did it die because it didn't provide a solution that people wanted? Did it die because of implementation issues? Did it die because of patent issues? Was it too early? Too late? I think it's important to learn lessons from past experiences. Why did E4X and E4H fail where JSX has succeeded?
What I find interesting is that people who are new to Flutter often ask for two things: a markup language, and animated GIFs. Then three months in, they are still asking for animated GIFs, but not for a markup language. It could be that this is because the markup language isn't actually needed once you're used to writing build methods in Dart. It could be that they still want a markup language but have worked around the omission and so don't think to ask anymore. It's worth figuring out which because otherwise we risk spending effort on something that is the wrong choice (in either direction).
On your giant nested expressions can you easily see structure?
Yes, at least as easily as with XML. Personally, I find XML to be very verbose and it obfuscates the structure. But I think this is more about what you're used to.
(We're also experimenting with IDEs that put in virtual "closing tag" comments for you so you can see the structure without having to actually write it.)
Great so you know that parsing a markup language is trivial compared to parsing an imperative programming language.
My experience is that declarative vs imperative is not the distinction that matters when it comes to determining how easy a language is to parse. (For example, HTML is "declarative" but it may be among the most complicated languages to parse that I've ever dealt with.)
Code readability and simplicity which in turn drives a whole bunch of other benefits.
If this is the main benefit then this is something we can test. We could take a mixture of engineers who are used to writing HTML, React, iOS code, Android code, Flutter, command-line apps, and so on, and present them each with various syntaxes, and ask them to describe what they think the resulting UI would look like. We can then measure which syntax gets the best results. @InMatrix is this something we could look at after the animation work wraps up, maybe?
can this structure be easily manipulated by other tools like GUI builders interchangebly ?
Yes, in principle at least. It should be relatively straight-forward to mechanically convert Dart expressions to XML or JSON or whatever other structured language one might use. It's just a matter of converting the syntax, the actual information is the same. Personally I wouldn't convert it to a different syntax if I was making a GUI editor, I would just parse it into a data structure in memory straight from Dart.
You can't do that easily when the programmer goes inside your "giant nested expressions" and writes any valid dart code that doesn't follow the structure that the GUI editor is expecting. With a fixed XML structure that is not a problem.
The thing is, you can put exactly the same "any valid dart code" in the XML structure as in the Dart expression. They are literally mechanically interchangeable. So I don't really see how using XML helps with this particularly. For example how would you turn this into XML?:
new ListView.builder(
padding: new EdgeInsets.all(8.0),
itemExtent: 20.0,
itemBuilder: (BuildContext context, int index) {
return new Text('entry $index');
},
)
It handles it just fine, you just don't know how to do it.
I meant specifically JSX. I agree that your proposed syntax would be a perfectly valid way to approach the problem.
I worked on Adobe's Flex SDK, which combined XML markup and ActionScript, for the last couple years that the product existed at Adobe. I understand the appeal of markup for defining UIs however I can also remember some drawbacks:
It's been years and I can no longer recall all the details. However my overall impression is that defining UIs with a combination of markup and code is a mixed bag at best.
Whether it died isn't the issue, it's why it died. Did it die because it didn't provide a solution that people wanted? Did it die because of implementation issues? Did it die because of patent issues? Was it too early? Too late? I think it's important to learn lessons from past experiences. Why did E4X and E4H fail where JSX has succeeded?
It died because E4X was only implemented in ActionScript which was only used inside Adobe Flash/Flex and Adobe killed the project. Instead Adobe changed direction towards open standards where there is no single source provider with possibility of lock-in and ecosystem implosion.
What I find interesting is that people who are new to Flutter often ask for two things: a markup language, and animated GIFs. Then three months in, they are still asking for animated GIFs, but not for a markup language. It could be that this is because the markup language isn't actually needed once you're used to writing build methods in Dart. It could be that they still want a markup language but have worked around the omission and so don't think to ask anymore. It's worth figuring out which because otherwise we risk spending effort on something that is the wrong choice (in either direction).
Well, if I asked you for 2 things and you didn't do either in 3 months and there is an alternative to the first thing, I would also only ask you for what is totally impossible to do given your responsiveness and previous delivery performance.
(We're also experimenting with IDEs that put in virtual "closing tag" comments for you so you can see the structure without having to actually write it.)
Kind of funny but it's like putting the XML closing tag that you mentioned before was too verbose.
If this is the main benefit then this is something we can test. We could take a mixture of engineers who are used to writing HTML, React, iOS code, Android code, Flutter, command-line apps, and so on, and present them each with various syntaxes, and ask them to describe what they think the resulting UI would look like. We can then measure which syntax gets the best results. @InMatrix is this something we could look at after the animation work wraps up, maybe?
Sure you can do that go ahead, I am sure you will find out that "Once you do React(with JSX) you simply don't go back". Survey experienced React developers and ask them if they think JSX is bad and it should never had been done. Show your way and ask them if they want to replace JSX with what you have. Before you do that, close the doors and lock up the place because these developers are just going to grab their stuff and sprint for the closest exit.
The thing is, you can put exactly the same "any valid dart code" in the XML structure as in the Dart expression.
Sure, but for the GUI builders that's just a block of bytes that doesn't need to be touched and can be easily skipped. Making it design/code interchangeability practically possible instead of in principle.
new ListView.builder(
padding: new EdgeInsets.all(8.0),
itemExtent: 20.0,
itemBuilder: (BuildContext context, int index) {
return new Text('entry $index');
},
)
let style = {
padding: new EdgeInsets.all(8.0),
itemExtent: 20.0
};
<ListView.builder style={style}>
{(context, index) => <Text> entry {index} </Text>}
</ListView.builder>
I used Adobe Flex Builder extensibly...
Developers tended to view it as an ActionScript tool.
Yes, but I often switched from design view to code view and vice-versa.
Starting a screen I would go to design view and use drag/drop to layout widgets and generate first static screen. Then I would add in code and some static data to fill in screen so I could show people something running that looked like production ready stuff. Productivity was incredible. As development progressed, I connected the front end to the back end and the amount of ActionScript code grew and yes it dominated the code overall but even at close to release time, I often used the design view to tweak the UI without having to dig into code.
However my overall impression is that defining UIs with a combination of markup and code is a mixed bag at best.
Not in today's world. Imperative languages have evolved in the philosophy of Python and are great for development. Declarative techniques with embedded markup (XML) became mainstream with the advent of React; and JSON became the preferred text based data format.
E4X was only implemented in ActionScript
E4X was an ECMA standard. Mozilla shipped it for a while, but then removed it (a very unusual move for a browser vendor). Other browser vendors never wanted to implement it. (They've implemented other new ECMA features, though.) With E4H, the browser vendors were never interested in implementing it (though again, they've implemented plenty of other things I've helped invent).
Well, if I asked you for 2 things and you didn't do either in 3 months and there is an alternative to the first thing, I would also only ask you for what is totally impossible to do given your responsiveness and previous delivery performance.
That's one possible theory. People tend to ask for many other things besides, though, and many of the things they ask for get implemented, and there are workarounds for animated GIFs too, so I'm not sure this fully explains the situation.
Kind of funny but it's like putting the XML closing tag that you mentioned before was too verbose.
Indeed. This is an optional IDE feature, and one that you don't have to write into the code, which makes a big difference to whether the verbosity is an issue, though.
...
ListView
...
How would a GUI editor handle this markup? I don't really understand how to visualise the UI for this.
This may be a counter argument to this request, and/or maybe some insight's to keep in mind if you want markup. I have strong feelings that adding markup creating some challenges with GWT I'd hate to see another API go through.
I've seen a couple other frameworks go through this transition regarding with UI building. Markup like this works great for tooling, in so far it's heavenly for the IDE developers. It's easier to separate the responsibilities of who does what. Although I think it can be done better.
GWT started out this way, building UI's with Java. Then came along UiBinder, where you could build the UI in xml markup, with a specification. Then the tooling, Eclipse Plugin, was able to generate UI's in xml markup. Android is doing it too, no need to belabor the point. So what I saw happen, markup works great for UI IDE developers. But really, markup is a huge huge investment in time and added complexity tooling to transition it to real program. And the tooling is always last to come. So in the mean time, while all that manifests into reality, there are two worlds. Two interesting ways of doing everything. One in the default language and one in markup. So I support GWT today. When I write documentation, I have to write it twice, once for Java and once for UiBinder XML Markup. So the real question, if you want to go down the markup road, I think the question should be asked, is the added complexity worth the journey!
JSX I think aims to solve other issues where you want to blend together what your doing with HTML and javascript. It really doesn't feel like the added complexity of markup specification suits the needs of writing UI with markup. Especially when you don't really have a document markup language as the target. At least not for the everyday user.
On a positive note. I like to work on tooling. So I can see a markup language being quite useful. It's much easier to write and modify AST when your using markup.
But then again, if you have enough minds on the job, it doesn't really matter what you do. At the end of the day, if the developer can write his application faster with your api, your going to get traction. But at what cost to the engineering team.
I think the real question is, how can the UI be built faster. I think tooling could write the dart, skip any middle man markup. And my aim isn't really to say it's not worth it, but really count the cost's on all the fronts if the road is taken!
E4X was an ECMA standard. Mozilla shipped it for a while, but then removed it (a very unusual move for a browser vendor). Other browser vendors never wanted to implement it.
I would say only Adobe fully championed E4X and had a good following with developers. Browser vendors do add and remove stuff from their browsers all the time; didn't Google remove MathML support?
That's one possible theory. People tend to ask for many other things besides, though, and many of the things they ask for get implemented, and there are workarounds for animated GIFs too, so I'm not sure this fully explains the situation.
Here is the thing about React and JSX. Initially I completely dismissed it, I was in love with Angular and doing massive work with Ember. I tried desperately to convince the team to go with Angular but that didn't go anywhere as others had their eyes on Aurelia. Someone pointed me to React, I read the docs and evaluated and simply said that there was nothing in there that Angular or others couldn't do it. Then last year I worked on a new project and had the chance to try something new so I gave React a try and you really don't fully appreaciate what React brings to the table until you develop with it for awhile, then it becomes night and day against all other frameworks. It's a mixture of simplicity and expressiveness brought together by JSX.
How would a GUI editor handle this markup? I don't really understand how to visualise the UI for this.
let style = {
padding: new EdgeInsets.all(8.0),
itemExtent: 20.0
};
<ListView.builder style={style}>
{(context, index) => <Text> entry {index} </Text>}
</ListView.builder>
I would represent the \
Since the child in this case is a function, you can simply put a rectangle saying 'uneditable/code' to tell users that this widget is created from code or in this case easily deduce that the function is a shallow wrapper to the
But really, markup is a huge huge investment in time and added complexity tooling to transition it to real program.
All I am asking is to add these simple extensions on the Dart compiler so that if developers want to they can write using this XML structure. The old way would continue to work and the amount of work involved to do this is not huge at all. You can actually see how many lines of code it takes the babel.js compiler to do JSX and I am talking hundreds and not thousands of lines (I just checked it).
And the tooling is always last to come. So in the mean time, while all that manifests into reality, there's two worlds. Two interesting ways of doing everything. One in the default language and one in markup
Sure but React has been like this and that is not an issue at all.
When I write documentation, I have to write it twice, once for Java and once for UiBinder XML Markup.
Not in React because markup lives inside code.
is the added complexity worth the journey!
Absolutely, it's like the argument of whether you should train your developers with the latest techniques and risk them leaving your company. The bigger risk is keeping them around untrained. So you must adopt the latest techniques out there or risk being left behind.
React is leading the journey with the latest techniques to develop UI/UX. It has tremendous traction with developers. Your greatest risk is not meeting the React bar.
JSX I think aims to solve other issues where you want to blend together what your doing with HTML and javascript
JSX is not just for HTML, React Native generates Views (like Flutter Widgets) from the XML markup.
I think the real question is, how can the UI be built faster.
More like how UI/UX can be built better. Better meaning: faster, higher quality (code and UI/UX), smooth designer-developer interaction, etc.
By the way, really nice job done on the developer tools; 'flutter doctor' was awesome !!!
I am now cooking with gas and can be dangerously creative ;)
I just wanted to respond to the readability question raised here, though I understand readability is only one of the many factors we need to consider.
Code readability and simplicity which in turn drives a whole bunch of other benefits.
If this is the main benefit then this is something we can test. We could take a mixture of engineers who are used to writing HTML, React, iOS code, Android code, Flutter, command-line apps, and so on, and present them each with various syntaxes, and ask them to describe what they think the resulting UI would look like. We can then measure which syntax gets the best results. @InMatrix is this something we could look at after the animation work wraps up, maybe?
There are certainly ways to empirically study code readability, and we can have a more serious discussion when it's time for Q4 planning. To make such a study useful, we need to define what kinds of reading tasks are important to developers in the context of Flutter programming. In addition to reading a whole build method and picture what the resulting UI might be, readability also affects smaller tasks such as identifying the build method in a dart file, matching braces, reading inline comments, etc.
To support some of those more narrowly-scoped tasks, we can experiment with UI enhancements in the editor first, which is usually cheaper than introducing and maintaining a markup language. The closing label feature in VS code is one of such UI enhancements, and we should understand how well it solves the brace matching problem it sets out to address. There are plenty of other options in this space we haven't tried yet. For example, a different font or background color might be used to display the build method to help the developer mentally separate it from the rest of their code.
Another thing that strikes me as important is how we can encourage people to not write giant build method and take advantage of the composition nature of the framework. If the build method is taller than the height of your screen, it's going to be hard to read regardless it's Dart or XML.
Another thing that strikes me as important is how we can encourage people to not write giant build method and take advantage of the composition nature of the framework. If the build method is taller than the height of your screen, it's going to be hard to read regardless it's Dart or XML.
It's not just the build method. It's all other methods that the build method calls to build the widget tree. Very common in React to use smaller methods to build sub-tree pieces and then call those into the larger tree.
Also in WebStorm with JSX, each XML node has +/- that can be used to expand/collapse node and children to make reading structures larger than the height of the screen easier.
One thing we've found in Flutter is that big build methods are not great for performance, and we try to encourage people to break down their build methods into smaller reusable widgets. In particular, in Flutter having a build method that's built out of the results of other methods is somewhat of an antipattern that we'd rather discourage rather than make easier. (This is somewhat of a recent realisation so a lot of our examples and widgets don't do this well yet.)
we try to encourage people to break down their build methods into smaller reusable widgets.
Does it really become a reusable widget or simply a wrapper/composite widget? I mean to be reusable you should have at least 2 usage instances.
The AppBar on https://flutter.io/catalog/samples/basic-app-bar/ is so unique that you can't really call it an reusable component; it's a wrapper/composite component and in these cases why not just use a local method to build that part of the UI? I guess if it did more things it would make sense to place it in a wrapper/composite component.
One thing we've found in Flutter is that big build methods are not great for performance
Since you mentioned performance, having the animation loop drive the build method will cause performance problems for smooth animation. You don't want your build method called 60 times a second or more, specially considering that the build method is user code (for example, it could have a super long loop that takes forever and it would cause animations to skip). Being a Flutter beginner perhaps I got that wrong.
The AppBar on https://flutter.io/catalog/samples/basic-app-bar/ is so unique that you can't really call it an reusable component
It's also relatively small, so that's ok.
Regarding performance, this is somewhat off-topic for this issue so please file a new issue if you want to discuss it (or e-mail flutter-dev or post on stack overflow, whatever you prefer).
It's crazy to see this issue getting buried. In my opinion it's going to be a make or break for Flutter to implement JSX-like syntax for composing widgets.
I simply don't understand the target audience, many ios and android devs are moving to react native, it would seem to be the perfect opportunity to harvest market share.
I encourage people involved to give react native a spin and see what we are talking about.
I don't miss JSX a bit in Flutter. This would only bloat the framework and tools for a few small gains here and there.
@birkir I am 100% with you on this issue. Lack of JSX, which is a perfect fit for Flutter, makes Flutter look old and rusty, feels like 1990s technology. Actually it seems like everyone, in one way or another, is adopting JSX; the latest one being the popular Vue.js framework.
+1
@zoechi What is your previous experience with JSX, have you really used it or just looked at it? I think you guys are underestimating JSX by saying it will give small gains here and there. If you don't have any users, you don't have a product.
@birkir I see lots of excitement about JSX here but nobody seems to bother to explain what exactly Flutter would gain from having such a DSL, except perhaps some better readability which is mostly subjective.
More features usually only hog down a framework instead of improving it.
Implementing them also consumes lots of resources that are missing from other areas where missing features actually prevent people from implementing certain applications.
So if you are excited about Flutter getting something like JSX, you should invest you time and energy in writing up convincing arguments.
Just adding something because others have it too, is probably the weakest argument there is.
There are also plans to improve Dart to make writing Flutter UI code less verbose which weakens the case for JSX even more.
So what are your convincing arguments?
Really !!! "nobody seems to bother to explain what exactly Flutter would gain... blah blah blah".
Haven't you read this thread fully? Is your attention span greater than your JSX knowledge?
You guys are suffering from NIH syndrome (Not-invented-here). "Good artists copy; great artists steal", mediocre artists, well, behave like you.
Just the fact that supporting JSX is relatively simple, and it will tremendously help attract new customers (React Native mobile developers) to the platform, makes it a no-brainer which you guys fail to see. It doesn't bold well for the platform.
Can we please keep a constructive tone when debating.
Adding features because others have it is weak argument. Okay.
Why does flutter have hot reloading? Where did that come from? Jesus dude.
How did we fail to provide solid argument for you guys? Project traction and attracting developers is our number one reason.
Reason number two, readability:
https://github.com/flutter/flutter/blob/master/examples/flutter_gallery/lib/demo/cupertino/cupertino_buttons_demo.dart vs https://gist.github.com/birkir/e921158239c324ab95bb0b174383a562
Reason number three, GUI Builders. I'll quote the first line in the README.
A new mobile app SDK to help developers and designers build modern mobile apps for iOS and Android.
I would hate to see Flutter going down the same rabbithole as Polymer before it even reaches beta.
Project traction and attracting developers
The relation is still unclear.
Reason number two, readability:
Making Dart code more readable seems a better goal to me
Reason number three, GUI Builders. I'll quote the first line in the README.
As far as I remember it was mentioned above already that there is no reason why using Dart code would prevent that.
Your counter arguments can't really dismiss the idea, can they?
There are also plans to improve Dart to make writing Flutter UI code less verbose
Nice to see acknowledgement that the current way could use some improvements.
Please do provide details on such proposal. Your best bet is to interact with the React Native community for feedback.
Several Dart language feature requests could make code more short/readable:
new
and const
for Dart 2child
argument to skip named argument.children
argument (like Row and Column) to skip this named argument and its list declaration.With those changes code could looks like:
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('Cupertino Buttons')),
body: Column(
Padding(padding: EdgeInsets.all(16.0),
Text(
'iOS themed buttons are flat. They can have borders or backgrounds but '
'only when necessary.'
),
),
Expanded(
Column(mainAxisAlignment: MainAxisAlignment.center,
Text(_pressedCount > 0
? 'Button pressed $_pressedCount time${_pressedCount == 1 ? "" : "s"}'
: ' '),
Padding(padding: EdgeInsets.all(12.0)),
Align(alignment: Alignment(0.0, -0.2),
Row(mainAxisSize: MainAxisSize.min,
CupertinoButton(onPressed: () { setState(() { _pressedCount += 1; }); },
Text('Cupertino Button'),
),
CupertinoButton(onPressed: null,
Text('Disabled'),
),
),
),
Padding(padding: EdgeInsets.all(12.0)),
CupertinoButton(
color: CupertinoColors.activeBlue,
onPressed: () { setState(() { _pressedCount += 1; }); },
Text('With Background'),
),
Padding(padding: EdgeInsets.all(12.0)),
CupertinoButton(
color: CupertinoColors.activeBlue,
onPressed: null,
Text('Disabled'),
)
),
),
)
);
}
Moreover depending on your IDE you can optionnaly have synthetic comments at the end of parenthesis and you could see something like this in your IDE:
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text('Cupertino Buttons')),
body: Column(
Padding(padding: EdgeInsets.all(16.0),
Text(
'iOS themed buttons are flat. They can have borders or backgrounds but '
'only when necessary.'
),
),
Expanded(
Column(mainAxisAlignment: MainAxisAlignment.center,
Text(_pressedCount > 0
? 'Button pressed $_pressedCount time${_pressedCount == 1 ? "" : "s"}'
: ' '), // Text
Padding(padding: EdgeInsets.all(12.0)),
Align(alignment: Alignment(0.0, -0.2),
Row(mainAxisSize: MainAxisSize.min,
CupertinoButton(onPressed: () { setState(() { _pressedCount += 1; }); },
Text('Cupertino Button'),
), // CupertinoButton
CupertinoButton(onPressed: null,
Text('Disabled'),
), // CupertinoButton
), // Row
), // Align
Padding(padding: EdgeInsets.all(12.0)),
CupertinoButton(
color: CupertinoColors.activeBlue,
onPressed: () { setState(() { _pressedCount += 1; }); },
Text('With Background'),
), // CupertinoButton
Padding(padding: EdgeInsets.all(12.0)),
CupertinoButton(
color: CupertinoColors.activeBlue,
onPressed: null,
Text('Disabled'),
), // CupertinoButton
), // Column
), // Expanded
), // Column
); // Scafold
}
This conversation is getting heated. I would like to encourage everyone to read our code of conduct:
https://flutter.io/design-principles/#conflict-resolution
I'm going to close this conversation for a few days while everyone considers how they can respectfully and productively contribute.
We all know that the syntax for building UI is a very important part of mobile development experience. For now the syntax is a little verbose, I have to new
something just for the purpose of adding a margin: margin: new EdgeInsets.symmetric(horizontal: 4.0)
, I think there may be an easier way.
Would it be possible to build a DSL like what the Kotlin team did for Android developers? It's called Anko, a DSL for building Android UI:
verticalLayout {
padding = dip(30)
editText {
hint = "Name"
textSize = 24f
}
button("Login") {
textSize = 26f
}
}
A concise syntax helps to keep the code readable & maintainable, can also make the building work enjoyable, it does matter. Please Flutter team estimate it seriously before you make the decision. We all love to see Flutter make a bigger success in the coming years.
Please dont introduce XML-like syntax to Flutter.
I programmed in Android Java for more than a year, then I started looking for a cross-platform toolset to try.
I started with React Native and then tried React. I didnt really like the JSX syntax because it is not quite javascript and not quite html, so just another thing to learn.
When I tried Flutter I found it much easier to get started (probably mainly due to my Java background).
I think some of the reasons why I wouldnt like to see an XML-syntax added to flutter :
I would go one step further and remove pubspec.yaml and replace it with pubspec.dart and have configuration in dart code.
If Devs are complaining about the difficulty of laying out the pages visually - an idea would be to create a layout designer which lets you set your themes and design pages visually by drag-and-drop. Then it would generate Flutter code which is not intended to ever be editted - but rather creates classes which can be used to compose your app.
It wouldnt need to be 2-way editing (XML/layout) like Android XML, but you just save your layout for later. If you need to change it you can regenerate the code and (hopefully) just change some arguments.
I know this conversation is old and yes it was getting quite hot, But i will like to drop a few lines to what i consider is happening here.
Flutter is NEW. Its a completely NEW way to do things. Yes, it did borrow from the react paradigm. But doesn't mean it needs to follow its same steps. I don't think its the flutter's team objective to attract developers from react native to come to flutter, its only to build something new that developers might find interest in. Google uses it internally before sharing it with the world and they have been productive with it. I share the comments with @Hixie that its not any different from JSX to build the UI. Yes its a little more verbose to right pure dart. But it actually makes debugging your code a lot easier.
The reason why im against a markup language or JSX or anything that sits on top of a technology is that it require tons more work from the platform. You can be happy composing Markup language for a UI, but you will have so many developers working on the platform crying and pulling hairs out to make it work for you. Another point of view is that JSX Worked for a Javascript community, Where as always its main objective is to make things easier for the developer and not worry about the tradeoffs. Don't get me wrong React(JSX) for web was a match made in heaven because HTML Is markup anyway. But for React Native look at all the code in the repository they had to do to make it work. Adding JSX to flutter would require tons of work and 2 things to think of when adding new features. And again just to be able to remove the child parameter and the const and new Keywords?. I prefer knowing what is really happening in the code and have control over what is happening than have magical Syntax that all its doing is add overhead.
Well that is my opinion. Don't want to start a new gigantic discussion. Just to mention the fact that JSX Is awesome for a react/javascript community because it worked for them, but for Dart/flutter i find it a bit overkill to add JSX Just to attract developers from React Native.
Wow, could have written a blog post xD
@Rockvole ,
Another thing to learn - could be spent learn Futures instead ;P
The thing to learn makes the current recursive object construction monstrosity simpler and familiar to everyday React Native devs, so my guess is people will prefer to learn that.
Context-switching - you are context switching between XML and code which is just unnecessary cognitive load.
Not an issue, there is no context-switch, it is just part of the environment that makes programming UI/UX cleaner.
Then it would generate Flutter code which is not intended to ever be editted
Why not? Not very useful then.
@franzsilva
I don't think its the flutter's team objective to attract developers from react native to come to flutter
Really !!! React Native is dominating and given that the total number of mobile devs using cross platform tools is limited, do you really think Flutter can become a home run hit without attracting React Native people?
Yes its a little more verbose to right pure dart. But it actually makes debugging your code a lot easier.
That's not a correct statement. Debugging JSX code, which is just javascript code is not any easier or harder, it is the same.
The reason why im against a markup language or JSX or anything that sits on top of a technology is that it require tons more work from the platform.
Who cares how much work was placed in the platform? Devs just want the latest techniques that improve code readability and productivity. No dev wants to use old and obsolete techniques when newer stuff provides better alternative.
I prefer knowing what is really happening in the code and have control over what is happening than have magical Syntax that all its doing is add overhead.
This is non-sense, I know exactly what goes on with JSX, it is a tiny little layer that transforms almost one to one but provides lots of benefits. Negligible compile time overhead if you ask me.
Just to mention the fact that JSX Is awesome for a react/javascript community because it worked for them, but for Dart/flutter i find it a bit overkill to add JSX Just to attract developers from React Native.
JSX should also work great for Dart/Flutter. It is not an overkill by any means. Is there any good reason why JSX would not work for Dart/Flutter? If I were to code it up and released it, why would it not be a good fit for Dart/Flutter development?
Let's take the concrete example from @xinthink:
For now the syntax is a little verbose, I have to
new
something just for the purpose of adding a margin:margin: new EdgeInsets.symmetric(horizontal: 4.0)
, I think there may be an easier way.
If you want to add a margin on the left and right, how would you like to express that? Specifically, let us take a simple example, and see what it would look like in various syntaxes.
// Flutter as written today
return new Container(
margin: new EdgeInsets.symmetric(horizontal: 4.0),
decoration: new ShapeDecoration(shape: new CircleBorder(), color: Colors.blue[100]),
child: new AnimatedCrossFade(
duration: const Duration(seconds: 3),
firstChild: const FlutterLogo(style: FlutterLogoStyle.horizontal, size: 100.0),
secondChild: const FlutterLogo(style: FlutterLogoStyle.stacked, size: 100.0),
crossFadeState: _showHorizontal ? CrossFadeState.showFirst : CrossFadeState.showSecond,
),
);
// Flutter as written later this year once we remove "new" and "const" keywords
return Container(
margin: EdgeInsets.symmetric(horizontal: 4.0),
decoration: ShapeDecoration(shape: CircleBorder(), color: Colors.blue[100]),
child: AnimatedCrossFade(
duration: Duration(seconds: 3),
firstChild: FlutterLogo(style: FlutterLogoStyle.horizontal, size: 100.0),
secondChild: FlutterLogo(style: FlutterLogoStyle.stacked, size: 100.0),
crossFadeState: _showHorizontal ? CrossFadeState.showFirst : CrossFadeState.showSecond,
),
);
How would you recommend we express these _exact_ semantics?
// Remove "new" and "const", infer the class for enum values, allow int literals for doubles
return Container(
margin: EdgeInsets.symmetric(horizontal: 4),
decoration: ShapeDecoration(shape: CircleBorder(), color: Colors.blue[100]),
child: AnimatedCrossFade(
duration: Duration(seconds: 3),
firstChild: FlutterLogo(style: horizontal, size: 100),
secondChild: FlutterLogo(style: stacked, size: 100),
crossFadeState: _showHorizontal ? showFirst : showSecond,
),
);
Babel.js has this neat little website, where you can type JSX and it converts it to plain Javascript:
https://babeljs.io/repl/#?babili=false&evaluate=true&lineWrap=false&presets=es2015%2Creact%2Cstage-0&code=function%20hello()%20%7B%0A%20%20return%20%3Cdiv%3EHello%20world!%3C%2Fdiv%3E%3B%0A%7D
I will do an equivalent one for DSX to Dart. Just a proof of concept, let's see how long it takes me...
Here’s @Hixie’s latest example in ”DSX“, using Airbnb’s style guide and assuming all child elements can automagically map to child
properties.
return (
<Container
margin={EdgeInsets.symmetric(horizontal: 4)}
decoration={ShapeDecoration(shape: CircleBorder(), color: Colors.blue[100])}
>
<AnimatedCrossFade
duration={Duration(seconds: 3)}
crossFadeState={_showHorizontal ? showFirst : showSecond}
>
<FlutterLogo style={horizontal} size={100} />
<FlutterLogo style={stacked} size={100} />
</AnimatedCrossFade>
</Container>
);
If the intention is to improve readability, I think future Dart wins in spades.
You have to check documentation to know what can turn into tags (presumably Widget
s only), or how many child elements are required/allowed.
If your goal is to output HTML from JavaScript, JSX makes a ton of sense as a middle ground. Because when you want tags at the end of the day, React.createElement('div', null, 'foo')
is far worse than <div>foo</div>
.
If your goal is to output a tree of Dart objects from... Dart, and a nicely formatted tree of Dart constructors is perfectly (arguably more) readable, I don’t see a point in detouring through XML. And I’m not missing those XMLs coming from Android.
It's what using XML enables... Look it's been 5 months with just talk, now I am doing something about it so give me some time (I do have a full time job and can only spare about 4 hours on weekends).
Just found this thread, interesting on both sides. As a React developer interested in Flutter there are a couple other arguments that I haven't seen mentioned (though I did only briefly skim all the comments.)
Closing tag declaration increases understanding of children vs properties. UI can unfortunately be deeply nested, and having a clear tag vs an unknown ) helps to clarify and parse children. It also allows me to move code around between components and very declaratively see when something it out of place (a closing tag before a for example.) This is trickier with multiple nested )'s.
My initial gut reaction to seeing multiple nested components inside constructors gives me flashbacks to "callback hell". It was a very painful era of JS that is starting to get better, going back to it feels a bit like a step backwards.
Related to #2, the unfortunate fact is we have to convince people to switch (or at least try it out). Many people are using React/React Native and even more using HTML/JS. Creating a simple and mostly syntactically familiar tutorial/guide that specifically targets some of React's pain points might be extremely compelling to those who are a tad bit fatigued.
One of the main reasons why React became popular in the Web Developers community was the support of JSX.
It's truly disappointing to see "down votes" on such a nice feature request. It improves readability and expedites adoption.
I think this is a major difference between Open JavaScript and Dart. JavaScript is truly open source whereas a request on Dart gets into conversation like this and ultimately you're demotivated with down-votes.
Make more room for new ideas!
@jayjun That looks amazing! Can I try it somewhere?
@sanketsahusoft Don't worry pretty soon you will be able to try my version and it is even better than @jayjun.
Quick update: 2 weekends ago I got the UI working great, Last weekend I got the parser fully working and half of the transpiler working. This coming weekend I hope to finish it off if I avoid the Superbowl ;)
I have thick skin and mule like stubbornness so I don't even notice these down-votes, thanks for pointing them out though.
Carlos.
Would this help with the issue of losing track of closing tags ?
Idea: Auto generated closing tags
Here's some proposed markup syntax for @Hixie 's example:
<Container margin=<EdgeInsets.symmetric horizontal=4 />
decoration=<ShapeDecoration shape=<CircleBorder> color={{ Colors.blue[100] }} />>
<AnimatedCrossFade duration=<Duration seconds=3 />
crossFadeState={{ _showHorizontal ? showFirst : showSecond }}>
<FlutterLogo style=horizontal size=100 />
<FlutterLogo style=stacked size=100 />
</AnimatedCrossFade>
</Container>
@abarth, the interesting thing you did was add a 3rd attrib possibility that simplifies the look of expressions when they are another tag.
JSX has:
1 - <tag attrib=""/>
or <tag attrib=''/>
2 - <tag attrib={}/>
You suggested another one:
3 - <tag attrib=<anotherTag.../>/>
with JSX you have to write it as:
<tag attrib={<anotherTag.../>}/>
@cbazza Yeah, the third case is quite common in Flutter, so it makes sense to skip the extra {
nesting.
@abarth Ah but I am making most of those things unnecessary by using css-like styles !!! The transpiler expands these css-like styles into appropriate Flutter calls. Now the tagging structure is much cleaner and styles can be easily imported from designer tools like InVision, Figma, Atomic, etc
@cbazza Cool, I use many widgets with closures like FutureBuilder
. I hope your transpiler can generate something like,
return new FutureBuilder(
future: Firestore.instance
.collection('stuff')
.document(id)
.get(),
builder: (context, snapshot) {
if (!snapshot.hasData) {
switch (snapshot.connectionState) {
case ConnectionState.waiting:
return const Text('Loading...');
default:
return new Text('${id} not found');
}
}
return new Text(snapshot.data['name']);
},
);
@jayjun, Yes, that's not a problem. The transpiler is a simple XML processor and when it comes to parsing expressions (everything inside {}), it just becomes a text blob so it writes it out verbatim.
@xinthink
Would it be possible to build a DSL like what the Kotlin team did for Android developers?
Seems like a lot of people would like to use Kotlin with Flutter. Honestly, I don't understand, why did the developers decide to reinvent the wheels in Dart?
In my humble opinion, Flutter doesn't need JSX. Flutter should have chosen Kotlin instead of Dart. Kotlin allows us to write complex ui logic with beautiful syntax out of the box, has huge community, production-ready tools, battle-tested in Android development...
Just saying.
Kotlin is nice, I am a fan but it doesn't run on iOS..... actually it does but it hasn't been released yet (pre-release stage right now).
For UI/UX development I still prefer JSX instead of Anko DSL. I like the fact that I can visually separate declarative markup from imperative code and be able to mix and match components together quite easily.
Dart, Kotlin and Swift all have similarities :
https://sethladd.github.io/swift-is-like-kotlin-and-kinda-like-dart/
I like that :
These are basically the reasons I chose Dart over Kotlin / Swift / React.
_Although the decision to support Dart and Swift in googles new Fuchsia OS is confusing to me._
I am not sure Dart is more familiar if you come from Java. I came from Java and have no problems with Kotlin or Swift; basically the type declaration is reversed, nothing really new as it was used in Pascal and ActionScript.
Yes, you can build web pages with Dart but I don't see major take up with that. The only other language that is doing well on the web is TypeScript, since it integrates well with the top 3 most popular web frameworks.
Take a look at the different syntax available for React on the Web:
https://github.com/Workiva/over_react#fluent-style-component-consumption
Both Dart versions have no chance against JSX !!!
TypeScript was designed to compile to Javascript and it is better than Dart for that. It also supports JSX.
Dart is getting squeezed from all sides. Swift has momentum so it is wise to support it on Fuchsia OS along with your baby.
How long until the prototype? I'd love to use it!
I used React for a while, and JSX increased my productivity ten-fold. This isn't a controversial issue: other teams decided, correctly, that this would be better, so why not Flutter? (Rhetorical: I read the thread... (facepalm))
I am working on it this weekend but I keep increasing the scope with new ideas so hopefully I can have something out this weekend.
Some of the interesting things I am experimenting with:
1) using xml namespace on child tags so they get inserted with correct Dart named argument in the parent.
2) spread operator to better organize style like properties so they can be defined/grouped outside xml in a map and then brought in and spread on a tag like typical React stuff.
3) styleCSS property that generates flutter styles from CSS.
(1) & (2) are generic so works for all Dart Flutter code.
(3) is specialized per Flutter Widget (Container, Text, etc) and I am only doing those 2 for now.
@yuriy-manifold just because something worked for JS doesn't mean it's a good idea for Dart.
If you had read above discussions, you'd see that in fact it is controversial.
I don't see why 2 languages would be better than one.
just because something worked for JS doesn't mean it's a good idea for Dart.
JSX is an incredible idea for UI/UX development in a reactive framework regardless of language. If I had more free time I would put out LSX which is JSX for Logo ;)
I don't see why 2 languages would be better than one.
You can program iOS with Objective-C and Swift (2 languages)
You can program Android with Java and Kotlin (2 languages)
...
I have yet to see an argument in favor of JSX.
Above discussions only contains arguments like "it's better", "it increases productivity", or similar but no argument why or how it would actually be better than pure Dart code, especially considering planned language changes that would reduce the difference between JSX-like and
pure Dart code even more.
@cbazza
You can program iOS with Objective-C and Swift (2 languages)
You can program Android with Java and Kotlin (2 languages)
How is that related to the JSX discussion? How can that be considered an advantage?
You can use Swift on iOS because it's the successor of Objectiv-C.
You can use Kotlin on Android because it's considered a slick improvement to Java.
That sounds like you argue that JSX should replace Dart. That doesn't make much sense to me.
@zoechi
How is that related to the JSX discussion? How can that be considered an advantage?
You can use Swift on iOS because it's the successor of Objectiv-C.
You can use Kotlin on Android because it's considered a slick improvement to Java.
That sounds like you argue that JSX should replace Dart. That doesn't make much sense to me.
You actually said it (JSX is a slick improvement over the current way) but came up to the wrong conclusion (JSX to replace Dart).
@cbazza that's just more of the same
what is the actual advantage over plain Dart?
"JSX is a slick improvement" is just not convincing in any way and isn't an argument.
It's just a personal opinion without (again) any argument to back it up,
similar with other pro-JSX arguments above.
You can't expect anyone to consider your suggestions if you're not willing to provide good arguments.
Adding something like JSX to Dart causes an awful lot of work and complexity in the Flutter tools and the IDE. You need to provide proper arguments for others to even consider looking at it.
@zoechi sounds like a broken record asking for 'good' arguments, plenty were given before but you just didn't get it; which is OK, 'to each their own'.
Adding something like JSX to Dart causes an awful lot of work and complexity in the Flutter tools and the IDE. You need to provide proper arguments for others to even consider looking at it.
Not really, my work is almost ready and it took me very little time considering I only worked on it on weekends.
Again, DSX is just a slick improvement that people can choose to use or not, because it doesn't change the current way, it just provides an alternative that others (React developers) will be instantly familiar with.
@cbazza
plenty were given
not really. Just general claims which can be true or not.
No additional details were provided that would allow others to verify.
Not really, my work is almost ready
Great. Then there is no need for the Flutter team to do anything and the issue can be closed ;p
Does this include support autocompletion and syntax checks in all IDEs supported by Flutter?
Great. Then there is no need for the Flutter team to do anything and the issue can be closed ;p
;)
Does this include support autocompletion and syntax checks in all IDEs supported by Flutter?
Most IDEs already support XML and JSX so it wouldn't be hard for them to add my minor additions.
I wonder if the JSX syntax might be more appreciated in angular Dart ? It seems like its more of a what-you-are-used-to situation rather than "better". The JSX syntax probably feels more natural for web developers.
I know that programming feels awkward for me even just using different code highlighting colors for a day.
Yes, Angular people will be very comfortable with JSX but so will React Native devs and this is for mobile development. JSX will certainly not be taken by current Flutter devs but this second alternative will attract new devs to Flutter and that's for sure.
The article above got it so wrong, React without JSX is basically non-existent and all reactive web frameworks do allow mixing of markup and programming on their DSL.
Time has come...
It's with great pleasure that I announce the online DSX transpiler
https://spark-heroku-dsx.herokuapp.com/index.html
Nice job with the transpiler cbazza
One thing I would say is easier to follow with JSX is the closing tags. The idea which I mentioned before :
Idea: Auto generated closing tags
In your first example, would give flutter code of (removed the optional new in future Dart) :
Material(
child: Column(
children: <Widget>[
MyAppBar(
title: Text(
'Example title',
style: Theme.of(context).primaryTextTheme.title,
)-Text,
)-MyAppBar,
Expanded(
child: Center(
child: Text(
'Hello, world!',
)-Text,
)-Center,
)-Expanded,
],
)-Column,
)-Material;
@cbazza I appreciate your work for the community and the people who want to build UIs that way, but I really hope I'm never forced to use anything like that in Flutter :-(((
As a newcomer to Flutter but pretty familiar with React, a few things stood out to me:
Regarding JSX:
<Item
right={() => new Text("Right")} {/* a named slot */}
left={() => new Text("Left")}> {/* another named slot */}
<ChildOne /> {/* generic children prop with 2 children */}
<ChildTwo>
<NestedChild />
</ChildTwo>
</Item>
I still think, as a newcomer to Flutter with some experience with Angular, React, etc., that the regular Dart way, and more in the Dart 2.0, is better than this DSX. It just makes more sense than some XML and CSS-ish parameters. 🤷♂️
@cbazza your second demo example has 466 chars compared to dart's 391 (both without spaces). To me it looks visually bloated. I would have to learn it's semantics, which I don't have to with normal Dart code. And I have no idea how to use general purpose programming paradigms with it (if, forEach, etc.).
If I had the choice, I would stick with the present model.
Everyone is just giving its own subjective opinion on comparing both syntaxes, but we have to agree on one fact: it's a very controversial feature. There is love and hate, but most opinion diverge on the usefulness of JSX over plain Dart.
In any case I think it's totally unreasonable to ask the Flutter team to commit to support this feature before the 1.0 release. While the current way of building UI may not seem great for everyone - it works (and it works great in some opinions).
If people really want a JSX-like syntax now, a community driven effort seems like the way to go. And it would help make the case (or not) when the Flutter team considers it in post 1.0 release.
Personally I strongly agree with the following argument: it's not because JSX works for React (where you are already building the UI using a markup language) that it automatically works for Flutter.
@tehfailsafe
The great news is that even is this was adopted by the Flutter team (which isn't likely based on this thread) no one would be FORCED to use it. It's an OPTION. I don't understand why it's so emotionally charged that some people might like writing code with a syntax you don't like...
I don't care what other people like or don't like. But I care about features that help me progress with my application. Resources are limited, and I would rather have a proper video/stream player, native child views, and some vector graphics format.
For example, right now in React and React Native you can write your whole application without JSX, it's just an option. Here's what React looks like without JSX:
[...]
It's a lot messier than the JSX version, and almost no one uses it. That's probably why some of us who are coming from React would appreciate the possibility to avoid having to do it this style again.
That's because the web was not designed for a system like that. If you have a static markup language like HTML and want to "dynamise" it, you have to invent a system that needs to work ontop of that. What you will end up with is some construct that is constrained by the underlying platform.
(see: https://gbracha.blogspot.de/2014/09/a-domain-of-shadows.html)
Flutter on the other hand has no markup language. I have yet to see a reason to invest resources into something that is less dynamic and less expressive.
I would like to know if people who disagree with it have used React with and without JSX. I encourage everyone to try it, so this discussion would be less theoretical. After the initial shallow learning curve, it becomes very natural (and it's not all about the number of characters, because the closing tags allow you to read it easier). It's not different from learning anything else that's new, like Flutter, which in the long run boosts productivity. And I agree that it's not for everyone, which is why it would be optional.
I think it's important to keep in mind that we have one another's best interests in mind - making it easier to build stuff. I think this transpiler would help, and it would be easier to adopt if it had official support.
Also, Thank you @cbazza :)
@yuriy-manifold
I don't think anybody here doubts that JSX React is an improvement over classic React. But like I said, that solution was created because of problems related to properties of the underlying platform. Flutter doesn't have these properties.
The question is not 'is JSX helpful for React?' the question is 'is something like JSX helpful for Flutter?'.
I think the answer is no.
There are a few other things to consider:
build
methods if they were transformed according to an upgradeable pragma into Dart code from an agnostic format like JSX.Nice job with the transpiler cbazza
@Rockvole, thank you.
I appreciate your work for the community and the people who want to build UIs that way, but I really hope I'm never forced to use anything like that in Flutter :-(((
@zoechi, thank you. Yes, it's just another option for people who love JSX to use. If that's not your thing cool continue doing as you are doing, nothing changes there.
I don't think it's necessary to invent new JSX syntax to support Flutter patterns.
@alexkrolick, yes you can use render props for the named parameters but there is nothing you can do about the positional parameters. The key was that I didn't want to hard code anything in the transpiler so that it would work for everything.
I still think, as a newcomer to Flutter with some experience with Angular, React, etc., that the regular Dart way, and more in the Dart 2.0, is better than this DSX. It just makes more sense than some XML and CSS-ish parameters.
@tenhobi, great use that then, obviously DSX is not for everyone.
If I had the choice, I would stick with the present model.
@b-strauss, this is not a replacement, it's an option for people that like JSX.
There is love and hate, but most opinion diverge on the usefulness of JSX over plain Dart.
@lukaspili, DSX is for React Native people that love JSX, if you don't see its benefits, don't use it. It's not DSX versus plain Dart. It's DSX vs. JSX, the closer the 2 are the better.
The great news is that even is this was adopted by the Flutter team (which isn't likely based on this thread) no one would be FORCED to use it. It's an OPTION. I don't understand why it's so emotionally charged that some people might like writing code with a syntax you don't like...
@tehfailsafe, thank you for listening !!! You hit the nail on the head why such huge resistance to something that will make React Native people really happy.
I don't care what other people like or don't like. But I care about features that help me progress with my application. Resources are limited, and I would rather have a proper video/stream player, native child views, and some vector graphics format.
@b-strauss, Once React Native fans move to Flutter there will be tonnes of people to help out on these other needed things. Priority 1 is to steal mind share from React Native and make it as simple as possible for React Native people to move over.
Flutter on the other hand has no markup language. I have yet to see a reason to invest resources into something that is less dynamic and less expressive.
@b-strauss, How is DSX 'less dynamic' and 'less expressive' than plain Dart? DSX is Dart didn't you try the transpiler.
@yuriy-manifold, thank you.
The question is not 'is JSX helpful for React?' the question is 'is something like JSX helpful for Flutter?'.
@b-strauss, off course it is. it is not helpful for current Flutter devs but it is very helpful for designers that can output CSS from their tools, it is very helpful for people vested in the React Native platform.
@alexkrolick, very good observations.
@cbazza
this is not a replacement, it's an option for people that like JSX.
I get that... It wouldn't affect me in that way, but as I said before, there are missing features right now that I need to create a flutter app.
Once React Native fans move to Flutter there will be tonnes of people to help out on these other needed things. Priority 1 is to steal mind share from React Native and make it as simple as possible for React Native people to move over.
So you propose the flutter team should put features on hold for something that is questionable and may or may not attract a fraction of a specific subset of web developers?
How is DSX 'less dynamic' and 'less expressive' than plain Dart? DSX is Dart didn't you try the transpiler.
Every DSL is by definition less expressive than a GPL. With DSX how do I conditionally hide a widget? How do I iterate over a collection and map every element to a widget? How do I use a switch? You now have to make up syntax and semantics for constructs that you already have in your GPL. So why invent the DSL in the first place?
off course it is. it is not helpful for current Flutter devs but it is very helpful for designers that can output CSS from their tools, it is very helpful for people vested in the React Native platform.
That wasn't the question... What problems would a DSL solve that you can't solve right now? You keep saying it's better, why is it better? I have no doubt DSX would attract some JSX people. I know people don't like things that are different. And familiarity seems to be the only argument. So why not use CSS?
Why not use JavaScript? More people know how to use these than Dart.
If you design your system based on some other thing for the sole purpose of being familiar, you're not really innovating.
@b-strauss to be clear, JSX compiles to function calls (in React calls to createElement(ComponentClass)
, in Dart it should be constructors).
<A property="a" />
new A(property: a)
<A property="a">
<B />
<C />
</A>
new A(property: a, children: <Widget>[new B(), new C()])
The only constructs are the transforms between the element names+attributes and the function calls+arguments, and escaped expressions ({...}
).
(JS)
{ condition && <A /> }
{ condition ? <A /> : <B /> }
(JS)
{ ['a', 'b'].map(i => <A property={i} />) }
So you propose the flutter team should put features on hold for something that is questionable and may or may not attract a fraction of a specific subset of web developers?
@b-strauss, React Native is not web development, it's cross platform mobile development that is the main competitor to Flutter; and yes JSX is like a light source, it will attract lots of React Native devs. I asked for this feature in Aug 2017, too much talking too little action.
Every DSL is by definition less expressive than a GPL. With DSX how do I conditionally hide a widget? How do I iterate over a collection and map every element to a widget? How do I use a switch? You now have to make up syntax and semantics for constructs that you already have in your GPL. So why invent the DSL in the first place?
You are completely wrong. The good news is that I was once wrong too. Most (but not all) DSLs try to recreate programming constructs in markup (and that is not very powerful), JSX brings markup into programming (taking full advantage of the host language). The difference is transformational. The answer to all your questions is basically use the way you do it in Dart because it is Dart. Everything in between '{}' is Dart code with the exception of the spread operator. It's all dart expressions but you can also use anonymous functions that returns an expression. As you see in the transpiler a tag (\
What problems would a DSL solve that you can't solve right now?
Why use Dart when you can use zeros and ones, isn't that all that is necessary to solve any computing problem?
You keep saying it's better, why is it better?
I gave my reasons before and won't repeat them here. JSX people will agree with me but 'to each their own'.
I have no doubt DSX would attract some JSX people. I know people don't like things that are different. And familiarity seems to be the only argument. So why not use CSS?
Why not use JavaScript? More people know how to use these than Dart.
Yes, using CSS makes sense to ease the designer-developer workflow. DSX supports that. The advantage of Dart over Javascript is execution speed (performance).
If you design your system based on some other thing for the sole purpose of being familiar, you're not really innovating.
You are so full of wrong biases that are most likely preventing you from reaching your full potential. Open your mind, try different things.
@alexkrolick , thank you for the details.
@cbazza
You are so full of wrong biases that are most likely preventing you from reaching your full potential. Open your mind, try different things.
I will unsubscribe from this issue now. Please never mention me here or anywhere again, thx.
@b-strauss
Sorry guy, I didn't mean to hurt your feelings... I was just trying to gently guide you while trying to manage my own frustrations. We are all humans after all.
@cbazza Can you send me an email please? ian@hixie.ch
Already made this proposal in the old thread but I still think that's an important point
IMHO removing the need to use new/const
already helped a lot. I have real difficulties in the way dart format formats the trees. it does not emphasis enough the tree structure IMHO compared to:
return Scaffold(
appBar: AppBar(title: Text("WeatherDemo")),
resizeToAvoidBottomPadding: false,
body:
Column(children: <Widget>
[
Padding(
padding: const EdgeInsets.all(16.0),
child:
TextField(
key: AppKeys.textField,
autocorrect: false,
controller: _controller,
decoration: InputDecoration(hintText: "Filter cities",),
style: TextStyle(fontSize: 20.0,),
onChanged: ModelProvider.of(context).textChangedCommand,
),
),
I agree for the purpose to make flutter simple that don’t want to use JSX-like syntax, and I also support the concept of split into multiple widgets, but now it let me feels like the MVC era is back in jquery. Such a scenario that there was a simple widget, with padding,border and center layout for it later, many "} " symbol seriously affect the readability.However, it is a integral widget, I don't want to split it, any useful solution? Though my english is poor,I try hard to express my thoughts.
Lord help us all.
Ok, this is going nowhere. It doesn't look like anyone's about to switch sides anytime soon. We definitely need to reach some sort of compromise here. Of course "pro-DSX" vs "anti-DSX" doesn't really have a remotely satisfying compromise, which is a frustrating realization. Could we possibly reframe our positions so that they could be more compatible?
@naiveaiguy "they" can have their DSX.
If the Flutter team doesn't implement it, it can be an open source initiative.
That doesn't mean the pure-Dart approach like it is now won't work anymore.
Both worlds can co-exist.
I agree so much with @zoechi that they can co-exist...thats it and I thought this had been settled on the old thread
@lrhn
Please everybody, be civil and constructive. We are discussing style here, something very subjective, so no matter how much everyone likes their own preference, it is unlikely to be inherently superior to everybody else's. Do list the advantages and disadvantages that you see with existing and proposed syntaxes, but remember that not everybody sees it the same way, and that's perfectly fine.
Bravo, that's absolutely it.
In React you can do it 4 ways (and I just found out about the other 2 ways today !!!)
(1) You can use JSX (which is what I like)
https://reactjs.org/docs/introducing-jsx.html
(2) You can use the original way (which is similar to Flutter)
https://reactjs.org/docs/react-without-jsx.html
At the end of the link above they even mention 2 promising community projects
(3) Hyperscript syntax for React.js markup
https://github.com/mlmorg/react-hyperscript
(4) Terse syntax for hyperscript.
https://github.com/ohanhi/hyperscript-helpers
Having alternatives is a good thing, gone are the days where you could get a Ford in any color you liked as long as it's black :)
@naiveaiguy why is it an issue for you if there is the current approach and DSX?
(that's what I derive from your downvotes)
@naiveaiguy "they" can have their DSX.
If the Flutter team doesn't implement it, it can be an open source initiative.
That doesn't mean the pure-Dart approach like it is now won't work anymore.
Both worlds can co-exist.
I fully agree with this. Though i think it should be a pluggable rather than an out-of-the-box solution. Having one standard that works but being able to customize the experience with extra things is a great paradigm. That way the Flutter team can keep its focus on (what i believe are) more relevant issues, the community can experiment with different tools/solutions and then we can have a discussion with more data and experience with DSX or any other alternatives to the current meta.
Having alternatives is a good thing, gone are the days where you could get a Ford in any color you
liked as long as it's black :)
True that. However, i think we can all agree we don't want Dart/Flutter to become another JS/Web Frontend ecosystem. Flutter isn't even out of beta yet and we're already want it to have 2 standards for something kinda subjective.
In React you can do it 4 ways (and I just found out about the other 2 ways today !!!)
Most are community driven though React refers to them. Good midway. Now, only 2 of them are officially supported: the React.createElement
and the JSX way, which is a wrapper over the other one. The value of JSX is notorious in that context but it is not that clear over here. With this in mind, can we meet midway by having only one official standard and the docs referencing DSX whenever relevant?
I believe the Flutter team should be focusing on the lacking features that truly prevent developers from building apps. I can't recommend Flutter to my managers if we can't even add Maps support and developing a Camera features takes 2 weeks.
Bear in mind, I'm not closing the door on DSX forever. Maybe it will become the solution for UI building but we need the community experimenting with it to make that decision.
@zoechi Personally I don't believe the two ideas can coexist in the current state of Flutter - we really shouldn't be encouraging a split of this nature this early - but at this point it looks like the only compromise.
@naiveaiguy
Personally I don't believe the two ideas can coexist in the current state of Flutter - we really shouldn't be encouraging a split of this nature this early
Could you be more specific as to why they can't coexist ? (given the fact that DSX is just syntatic sugar; or as @emalamela says "just a wrapper of the current way").
Also why is it too early to provide a different syntax to exactly the same thing? I am basically asking why is there a need to delay this, what would be different in the future that is not there yet right now?
@emalamela
However, i think we can all agree we don't want Dart/Flutter to become another JS/Web Frontend ecosystem.
Personally I rather not put any limits on what people can do with Dart/Flutter. Let the market/community decide. Basically if what is created doesn't add value, people won't use it and it will die. If it becomes popular, it is because the community found it useful and valued it. No need to pick winners and losers right now.
The only thing that is stopping me from giving Flutter a try is the fact that they chose not to use JSX.
IMHO JSX is the best choice to express component hierarchy
Heard about Flutter, wanted to give it a try, immediately stopped even considering that the minute I saw the syntax, which is a shame because chances are that this a great piece of tech. to build products.
I've been doing React/React Native development for the past 2.5 years, sacrificing the productivity leverage the JSX syntax offers when it comes to describing UI is a lot to ask. I would seriously consider spending the time to learn all about Flutter and study whether it's worth switching to when such a feature is supported out of the box.
I can't even imagine the numbers of potential adopters/users/devs Flutter is losing because of this, will revisit in the next months.
I can't even imagine the numbers of potential adopters/users/devs Flutter is losing because of this, will revisit in the next months.
Yeah, 44 Mio found it even important enough to upvote :D
Yeah, 44 found it even important enough to upvote :D
When sorted by 'upvote', this feature request is listed 7th on the list of 3131 opened tickets though.
https://github.com/flutter/flutter/issues?q=is%3Aissue+is%3Aopen+sort%3Areactions-%2B1-desc
@cbazza I don't want to argue against the feature but comments like "if you don't do x then horribly y will happen" are just ridiculous.
I've been doing React/React Native development for the past 2.5 years, sacrificing the productivity leverage the JSX syntax offers when it comes to describing UI is a lot to ask. I would seriously consider spending the time to learn all about Flutter and study whether it's worth switching to when such a feature is supported out of the box.
@sonaye
Since you mentioned productivity, can you provide an example that clearly showcases the productivity loss of using Flutter's Pattern instead of JSX? The example should be built with the basis of knowing enough JS and Dart to be able to code said example. I believe that if we don't take that into account then we are also comparing programming languages, which is not the same discussion.
When sorted by 'upvote', this feature request is listed 7th on the list of 3131 opened tickets though.
@cbazza
It is also the most downvoted one. It's quite controversial.
@emalamela,
It is also the most downvoted one. It's quite controversial.
Since this feature request is an alternative to the current way and it doesn't change the current way, there shouldn't be any controversy at all; if you don't like JSX/DSX continue programming as you do today.
The so called controversy only exists because the Flutter team needs to do work to enable the community to do DSX properly. If the Flutter tools (compiler, analyzer, ide support, etc) supported pre-processing with source maps, DSX would had been done long ago, and most likely other language innovations/ideas, from 3rd party developers, would had happened too.
new Card(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
AspectRatio(
aspectRatio: 18 / 11,
child: Image.asset('assets/diamond.png'),
),
new Padding(
padding: EdgeInsets.fromLTRB(16, 12, 16, 8),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Text('Title'),
SizedBox(height: 8),
Text('Secondary Text'),
],
),
),
],
),
)
Becomes:
<Card>
<Column crossAxisAlignment={CrossAxisAlignment.start}>
<AspectRatio aspectRatio={18 / 11}>
<Image src={asset('assets/diamond.png')} />
</AspectRatio>
<Padding padding={EdgeInsets.fromLTRB(16, 12, 16, 8)}>
<Column crossAxisAlignment={CrossAxisAlignment.start}>
<Text>Title</Text>
<SizedBox height={8} />
<Text>Secondary Text</Text>
</Column>
</Padding>
</Column>
</Card>
@emalamela The argument for and against JSX has been exhausted by discussion, there is plenty of material that you can look up. I'm only sharing my personal opinion.
First, code readability. I can immediately get a crisp clear idea about the structure of the UI in JSX (takes seconds), the mental modal is very visual. Second, usability. I would argue that JSX can be used even without knowing JS/Dart or anything about underlying API. This is very suitable for someone who is just learning programming, or for some one who is a part of my team, designers now can code the UI.
The description of the application is completely declarative (not just expressive), when you work on a large project with hundreds of components, this way of describing UI makes a huge difference (you have to try it to really appreciate it). I didn't like JSX when I first saw it too, once I used it just felt right, this how I want to describe UI from now on, it was a clear breakthrough in the way I approach building interfaces.
It's not about writing less lines of code, it's not about having a "syntax sugar", it's about building tools for humans. I'm also against the argument that everyone should use JSX, this is ridiculous. You use the tool that let's you get your work done faster with less confusion, in the case of many (including myself), it would be JSX (or DSX in the case of Flutter), that's all.
I'm coming from React, and first time trying out Flutter. It's really odd that flutter team doesn't have JSX syntax, I mean seriously! In JS world, JSX is extremely prevalent in every React-alternatives now a days! JSX is super friendly for developers. Please implement this ASAP, so you can help grow the community.
You can tell JSX (or DSX in this case) is a big deal just by looking for the amount of comments in this issue.
JSX is something that you don't know you love until you try it. It's weird at first to have markup in your code but then it becomes awesome.
It seems unnecessary for guys that already know flutter/dart, I get it. But for someone that never touched dart (like myself), JSX is way easier to start with and that's the point. If you guys want more people to come by and start building a lot more awesome stuff, the tooling needs to be easier.
And, as @eseidelGoogle (https://youtu.be/h7HOt3Jb1Ts?t=2m41s) told the other guy "Flutter is a way to write to iOS and Android in a single codebase. We try to make that fast and easy [...] Flutter talks all the way down to the hardware [...] We have a very layered approach, so you can take as little or as much as you want. [...] We have a bunch of investment in tooling."
Implement JSX, pretty please.
I'm a fan of Dart and also a heavy user of react. I always find Dart terser and more maintainable than JSX. So, I think JSX/DSX could and maybe should implemented in a community way.
@rajaraodv Just because Flutter is promoted as reactive style framework doesn't mean it's just a Flavor of ReactJS.
From most comments I get the impression people just have troubles accepting that something new isn't the same as what they already know.
You could try to work with Flutter for a while how it currently is and then provide proper arguments why you think JSX/DSX would be better then plain Dart in a factual way instead of just "because of personal preference" or "because it's better".
@zoechi, you are missing something: flutter was inspired from React, according to the Flutter doc.
Maybe it is only my issue. I really feel that I have a hard time to read the UI code, even it is in Dart 2 syntax.
flutter was inspired from React Native
I don't see how that says "everything is the same except the language is called Flutter instead of JS".
I really feel that I have a hard time to read the UI code
and you claim the only imaginable solution to that is DSX?
Have you considered that Flutter is not even 1.0 and that IDE support can improve over time?
There were only the first tiny steps taken recently to get better Flutter IDE support in the code editor like quick fixes ("wrap xxx") and closing labels.
There are unlimited possibilities to improve developer experience and most in this discussion is like
"Flutter is not yet perfect and therefore we need DSX"
usually without concrete arguments about how or why DSX would solve or improve that.
@zoechi ,
You could try to work with Flutter for a while how it currently is and then provide proper arguments why you think JSX/DSX would be better then plain Dart in a factual way instead of just "because of personal preference" or "because it's better".
Once again Plain Dart or DSX is simply a matter of style, no point arguing which is better. It is just a personal preference and people have their reasons for picking one or the other.
What has happened in the React World is that once you go with JSX, you simply don't go back. As others have stated above you get hooked on JSX after using for awhile. JSX has been adopted by others outside React's World (Typescript, Vue) and it is a great fit for Flutter.
and you claim the only imaginable solution to that is DSX?
What the community needs is generic pre-processing capabilities with source map support built in the Dart tools (compiler, analyser, IDE, etc) so that DSX or anything better can be developed by the community and fully integrated into Flutter (debugger, auto-complete, etc).
There are unlimited possibilities to improve developer experience and most in this discussion is like
"Flutter is not yet perfect and therefore we need DSX"
usually without concrete arguments about how or why DSX would solve or improve that.
Sure, thing is this ticket is not about a generic 'improving the developer experience' thing. It is very specific and it is about getting JSX support in Flutter. The community wants DSX as an alternative to the plain Dart way.
I cannot see myself using this (but I'm willing to give it a try). I dont think this is a silver bullet, but there is so much enthusiasm that its worthwhile doing.
I think google should remove the language obstacles to allow the community to build what they want.
I'm not aware of any obstacles preventing someone outside Google's Flutter/Dart teams from writing a JSX-like thing for Dart/Flutter. I would love to see bugs on those if someone is trying. (It's also possible that I've missed them in the comments above, since I admit not to having read every word of this very long bug.) :)
Thanks! Glad to see such enthusiasm!
@eseidelGoogle,
How would Intellij and/or VS Code (with Dart-Code) be able to set breakpoints and step through code from a .dsx file ? (I mean this is not a .dart file). How about auto-complete functionality from the .dsx file (as with a .dart file) ?
You have invested a lot on the tooling but the tooling does not support pre-processing (with source maps) of a new language (like DSX) that transpiles into Dart/Flutter seamlessly.
A transpiler is available but there is no easy way to fully integrate it:
https://spark-heroku-dsx.herokuapp.com/index.html
P.S. This ticket is only half of the comments !!!
https://github.com/flutter/flutter/issues/15922
@cbazza is there a repo with that compiler somewhere? It would be great to share the code and get the community involved on hacking on it, even if it isn't perfect.
@jonahwilliams, no the DSX transpiler code has not been released because it is way too early for that.
You can simply use 2 hand written equivalent files (.dsx and .dart) to test out pre-processing capabilities like breakpoints, stepping, auto-complete, etc.
Once the tools support pre-processing with some sort of source maps, I can add that to the transpiler and be unblocked. This would also enable others to experiment to their hearts desires.
I don't work on Flutter, but it seems sort of unreasonable to demand certain tooling to benefit others, but then also refuse to release any early source code or examples of what you want the tooling to integrate with.
For what it's worth, I don't know of any language or toolkit that provides pre-processing hooks of any kind - probably because it's just plain not easy, there are a lot of corner cases and assumptions around the language and syntax.
If you generated source maps (https://pub.dartlang.org/packages/source_maps), I imagine getting at least some basic support in an IDE is pretty trivial, independent of Dart/Flutter. But again, this is all conjecture without knowing what your tooling does and how you'd expect it to work.
@matanlurey, supporting pre-processing via source maps is a generic mechanism that does not depend on any specific transpiler. It is functionality that is meant to support any future imaginable language. The Chrome browser/debugger supports it quite nicely and I can debug any language that transpiles to JS.
For testing you can come up with any simple kind of transpiler to show how to use source maps. For example write a trivial transpiler that generates Dart/Flutter code with a blank line between every line on the original file. (.d2 => .dart, .d2 is Dart/Flutter file, out .dart file will contain a blank line between every line in the original file).
Yes, I can work on generating source map for a testfile.
Flutter is currently reluctant to try to please NativeScript, ReactNative, Android, Web, and other developers who accustomed to similar XML layouts. They have more important things to do, so let's disband and go to sleep.
I wished Amy proponent of JSX Syntax just to spend some days really working with Flutter before continuing lamenting. I came from an Xaml based systembut quickly got used to it. Just give it a real try.
@escamoteur
Hey, escamoteur. Do you think that I have not spent a lot of time learning flutter?
In the flutter.io/tutorials/layout/, at the end of "Packing widgets" section, the code that the tutorial gave does not work.
I mentioned the issue under the flutter issue block, but no one wants to care about this.
@JonathanSum is there any connection from your comment to the topic of this issue?
@zoechi
escamoteur said he hopes proponent of JSX Syntax just to spend some days really working with Flutter before continuing lamenting.
This comment shows we really have spent a lot of days working with Flutter, and the request of JSX is really our feeling from our heart.
Group Dart: "Dart syntax is way better and JSX/DSX is just not good"
Group JSX/DSX: "JSX/DSX syntax is way better and Dart is just not good"
I can't be the only person to see this? Both sides make valid points in favor and against their position. I think what is lost here is that @cbazza not only had criticism BUT ALSO DID SOMETHING ABOUT IT. Trying to bridge the gap of web devs/react/react-native and flutter in order to benefit Flutter.
And my 2 cents... As a full stack dev I have exp with a wide array of languages and approaches... JSX is one of my favorite ways to write code and I do hope there will be an alternative syntax to Darts... And i'm not saying the current syntax is bad, it's just that I prefer JSX style.
I have to disagree with this quote from the Group JSX/DSX
Dart is just not good
Dart is very good and robust language, nobody is dissing the language. The discussion is not about Dart, but a synthetic layer on top of it that most UI developers already use today, and we are proposing that Flutter incorporates something like that.
Most of these frameworks and languages have UI markup languages that separate the View from the Controller logic. Then React comes along with different approach (that we are proposing here) and I think we have to agree that RN is flying right now in terms of user growth and popularity, and I may be wrong, but mainly because of JSX.
...
Is it really so crazy proposal that we have to get this kind of feedback from Flutter team/users?
@birkir and all of them bring a host of troubles Flutter does not have \o/
There is no need for another language.
You can separate the view in Flutter as well, even with the same language.
@birkir this thread is 100% about Dart and syntax.
The discussion is not about Dart, but a synthetic layer on top of it that most UI developers already use today, and we are proposing that Flutter incorporates something like that.
So it's not about Dart... but Flutter needs to use something besides Dart for layouts? Seems like your saying Dart isn't good enough while also claiming this has nothing to do with Dart?
I don't think it matters at this point, the Flutter team has seen this feedback (on requesting a JSX/DSX approach) and they want to continue down their original path. I do think it could be handled better but it doesn't seem like they're opposed to the community creating solutions.
I'm happy there is another cross platform option... will Apple be the next to offer something up? And maybe they will see what so many of us like about react/react-native? IDK if they have anything cooking.
the Flutter team has seen this feedback (on requesting a JSX/DSX approach) and they
This bug is still open because we haven't figured out what we want to do here. We're eagerly looking at the experiments (e.g. cbazza's) to see how people use them. We're planning, at some point, to provide a hook in the build system for codegen tools such as this, though this isn't something we're likely to do in the near future. On the long term we hope to use what we learn here to influence Dart's development as a language. This could mean adding something like E4X/H4X/JSX/DSX to Dart itself. Or maybe we'll learn that nobody really ends up using it so we will do nothing. Or maybe everyone needs something different so codegen hooks and custom packages like cbazza's are the answer. We don't yet know.
@jstansbe - Apple thinks that cross platform means IPhone, IPad & Mac OS. They are more likely to add turrets on top of the walled garden than build something cross platform :)
I think than if would be possible indent and format the widget in other way would be more similar to jsx and friendly for users who have experience with xml and html (almost all the android devs)...check this code in codelab
return new Container(
margin: const EdgeInsets.symmetric(horizontal: 8.0),
child: new Row(
children: <Widget>[
new Flexible(
child: new TextField(
controller: _textController,
onSubmitted: _handleSubmitted,
decoration: new InputDecoration.collapsed(
hintText: "Send a message"),
),
),
new Container( //new
margin: new EdgeInsets.symmetric(horizontal: 4.0), //new
child: new IconButton( //new
icon: new Icon(Icons.send), //new
onPressed: () => _handleSubmitted(_textController.text)), //new
), //new
],
),
);
check this dart to jsx code
<Container margin="">
<Row>
<Flexible>
<TextField controller=""
onSubmitted=""
decoration="">
<OtherWidget></OtherWidget>
</TextField>
</Flexible>
</Row>
</Container>
and compare with this other format more htmlish
return Container(margin: const EdgeInsets.symmetric(horizontal: 8.0), child:
Row(children: <Widget>[
Flexible(child:
TextField(controller: _textController,
onSubmitted: _handleSubmit,
decoration: new InputDecoration.collapsed(hintText: "manda un mensaje"),),
),
Container(margin: const EdgeInsets.symmetric(horizontal: 4.0),child:
IconButton(icon: Icon(Icons.send),
onPressed: ()=>_handleSubmit(_textController.text),),)
],
)
);
this is a bit more similar and now you only need view from left to right to notice the different widgets similar to html/xml/jsx
the element (widget) attributes has more indentation than the new widgets, so this makes more clear could understand and check the code
would be great if I could have automatic indentation for this format on the different ides, right now I do this by hand....
After reading all of the comments here and privately discussing with my friends(native mobile apps developers,java/kotlin/objective-c/swift guys),My observation:
People are asking for two things,
new
, child
, children
) is annoying in current way of coding.There are also mainly two groups with different opinions,
new
,const
in Dart 2.0 and proposed virtual "closing tag" comments
feature.You can not easily conclude which one is better at present. So just let the community do their experiments first and make the final decision(accept or reject) later.
@hooluupog virtual closing tag comments already work in IntelliJ, AS, VSCode since a while
@Hixie
This bug is still open because we haven't figured out what we want to do here. We're eagerly looking at the experiments (e.g. cbazza's) to see how people use them.
People can't use my experiments because it can't be seamlessly embedded right now into Flutter; so it remains an outside/online experiment where people can only see the potential.
We're planning, at some point, to provide a hook in the build system for codegen tools such as this, though this isn't something we're likely to do in the near future. On the long term we hope to use what we learn here to influence Dart's development as a language.
Can you be more specific timewise for when can we expect some movement on the build system changes to support preprocessing? Are we talking a month, a quarter, six month, a year, 2 years, a decade, a jubilee, etc
This could mean adding something like E4X/H4X/JSX/DSX to Dart itself.
Please read the top paragraphs of the JSX spec to see that there is no need to change the Dart language since JSX/DSX has no semantics, and it is not meant to be implemented by engines or incorporated into languages. It is intended to be used in a preprocessor (transpiler). DSX could be used with Flutter & on Web to make React-Dart exactly like React.js but with the Dart language.
https://facebook.github.io/jsx/
Or maybe we'll learn that nobody really ends up using it so we will do nothing.
How can people use something that is not available for them to use in the first place and then conclude that nothing needs to be done because people are not using it ? This reminds me so much of Melissa McCarthy's Sean Spicer impersonation on SNL about the 'travel ban'... 'circular using of the word' :)
https://www.youtube.com/watch?v=1Dvo6EHEJQE&t=48s
Or maybe everyone needs something different so codegen hooks and custom packages like cbazza's are the answer. We don't yet know.
Preprocessing capabilities are badly needed to enable experimentation. Without it nothing moves forward and you won't learn anything new.
People can't use my experiments
I think you underestimate how willing people are to try things, even when they're not fully polished. For example, someone could easily write a shell script that wraps flutter run
to do the preprocessing first, then call flutter run
. I have a script myself that wraps hot reload to do something similar (I run the analyzer first, then only if it passes do I send the hot reload signal to the flutter
script).
Can you be more specific timewise for when can we expect some movement on the build system changes
Not really (see e.g. https://en.wikipedia.org/wiki/Forward-looking_statement for why it might be difficult to make such statements), but probably not in the coming weeks.
there is no need to change the Dart language
That's quite possible, indeed. I'm just saying that based on these experiments, we may reach any number of conclusions, all the way from "do nothing" to "add radical new features to the language syntax" and anything in between. The point being, we haven't made any decisions yet, and are very open to learning what needs to be done based on all these discussions and experiments.
Add JSX to backlog and let it compete, gladiator-style, with the million-plus-one other urgent requirements?
React is written for the web and thus needs a simple solution for writing HTML. JSX didn’t become popular because it’s the best solution for writing UIs, but because it’s the best solution for writing HTML.
Flutter doesn’t have that constraint, so we shouldn’t settle with a mediocre, verbose solution for the wrong reasons.
If we want to reduce verbosity I’d rather take inspiration e.g. from Anko (https://github.com/Kotlin/anko/wiki/Anko-Layouts). There you can define new local variables anywhere and use normal for-loops to dynamically construct the list of children, which can make the code easier to follow. Also, the LayoutBuilder would become easier on the eye since each nesting level is already a lambda function anyway (no need for passing an extra builder lambda). Anyway, this is just for inspiration and I don’t think Flutter should copy that 1:1.
React is written for the web and thus needs a simple solution for writing HTML. JSX didn’t become popular because it’s the best solution for writing UIs, but because it’s the best solution for writing HTML.
React Native is not web development nor it uses HTML. Ask experienced React developers (or fully read this and the other JSX thread) and you will see that JSX is considered by many React developers as the best way for writing UIs.
There you can define new local variables anywhere and use normal for-loops to dynamically construct the list of children, which can make the code easier to follow.
This statement clearly demonstrates that you don't know JSX. JSX (as in DSX) uses all programming constructs (for-loops, etc) from the hosting language (Javascript/Dart).
This ticket is only interested in JSX-like functionality, for other approaches (like Anko) please create your own ticket for discussion there.
React Native is not web development nor it uses HTML. Ask experienced React developers (or fully read this and the other JSX thread) and you will see that JSX is considered by many React developers as the best way for writing UIs.
React came out long before React Native. The original design of JSX is based on Rendering HTML, not native UIs. Nobody has been able to show a single convincing argument for what JSX does better. By comparing
new Scaffold(
appBar: new AppBar(
title: new Text(widget.title),
),
body: new Column(
child: ...,
),
)
to
<Scaffold
appBar={<AppBar title={<Text>{widget.title}</Text>} />}
>
<Column>
...
</Column>
</Scaffold>
you haven't done an up-to-date comparison and you're simply putting more stuff one a single line. You must compare it to:
Scaffold(
appBar: AppBar(title: Text(widget.title)),
body: Column(
child: ...,
),
)
Notice how all the ugly {<{<>} />}
and closing </...>
tags are gone.
This statement clearly demonstrates that you don't know JSX. JSX (as in DSX) uses all programming constructs (for-loops, etc) from the hosting language (Javascript/Dart).
No, you can’t use if statements or for-loops (or switch or any other statement) within JSX:
function render(data) {
return (
<div>
// This is impossible
let total = 0;
for (let item of data.list) {
total += item.value;
<div>{ total }</div>
<div>{ item.name }</div>
}
</div>
)
}
Only expressions are allowed. So you must use conditional operators (c ? x : y
, which makes else if
very ugly) and Array.map
etc. (which can also be very ugly) or move parts of your code to the top of the render function or into a separate helper function. It’s the same with Flutter, of course. Anko doesn’t have this limitation and makes writing (some) UI code more natural.
I think in a discussion about introducing JSX it’s quite valid and necessary to ask if that’s actually the best solution or if we can find something better. Otherwise we’ll waste resources on the wrong tasks.
React came out long before React Native. The original design of JSX is based on Rendering HTML, not native UIs.
The original design of JSX is about familiar way of creating/manipulating tree structures which specially show up when doing UI work; think component hierarchies (https://facebook.github.io/jsx/) which show up in web development, native development, any UI development, etc.
Nobody has been able to show a single convincing argument for what JSX does better.
That's the point, we are not looking to replace the current way, we are looking to add an alternative way that is familiar to React developers.
Your Anko proposal would be familiar to Android Kotlin developers so go ahead and propose a spec that works with current Flutter hierarchy in a separate ticket. Once I see (or try an online version of your spec) I would be able to see if it can generate/interoperate with current Flutter widget hierarchy.
No, you can't use if statements or for-loops (or switch or any other statement) within JSX:
Not that I recommend you doing this but it is possible: create an anonymous function and call it.
function render(data) {
return (
<div>
{ ()=>{
// This is *not* impossible
let divs=[];
let total = 0;
for (let item of data.list) {
total += item.value;
divs.push(<div>{ total }</div>);
divs.push(<div>{ item.name }</div>);
}
return divs;
}() }
</div>
)
}
I think in a discussion about introducing JSX it's quite valid and necessary to ask if that's actually the best solution.
There is no such thing as the best solution, it's all about having choice, having the choice of using something familiar that maps directly to Flutter widgets and adds no overhead.
By the way, try the following on my online transpiler at:
https://spark-heroku-dsx.herokuapp.com/index.html
@<Scaffold>
<appBar:AppBar>
<title:Text [widget.title]/>
</appBar:AppBar>
<Column>
{kids}
</Column>
</Scaffold>@
and you get:
--------new Scaffold(
-------- appBar: new AppBar(
-------- title: new Text(
-------- widget.title,
-------- ),
-------- ),
-------- child: new Column(
-------- child: kids,
-------- ),
--------);
DSX is similar to JSX but for Dart & Flutter so it has features of its own which are described on the link above.
when I see this, I get flashbacks from xml layouts from Android.. I don't think it's a good idea to implement this. Now that you dont even have to write new
and const
it even looks better.
@charafau Can you share an example/img/link of, "xml layouts from Android" you're referring to?
No, @wkornewald. If "JSX didn’t become popular because it’s the best solution for writing UIs, but because it’s the best solution for writing HTML", why does React still uses JSX for building a mobile app and desktop app? Even your Github desktop application, Walmart cross-platform mobile app, and Tesla app, and Skype are also built by RN.
React does not put a for loop in the JSX tag because the concept of React is about the component. The upper part is the logic and the below part is the JSX, and It is always like this. Everything is separated into many components and connected together into a large component.
In fact, most of the people here who against JSX can only guess JSX is some kind of HTML, XML, or a less verbose solution. People should understand why people love to build an app either with React and why JSX is so important on this.
@JonathanSum
most of the people here who against JSX can only guess JSX is some kind of HTML
I think it's rather because there were no other arguments in favor of JSX/DSX other than personal preference. That's fine of course as discussed already above, but please don't imply people are against JSX because they don't understand it, when there is no list of good factual arguments that show where JSX is better than plain Dart.
I think it's rather because there were no other arguments in favor of JSX/DSX other than personal preference.
Not really, many were given before, just read fully both threads. I did mention these 2 things before:
(1) No more 'child' & 'children' stuff
(2) easy for 3rd party tools to manipulate (parse, analyse and regenerate)
With (2) you can enhance the markup to do things not possible with just Dart; for example DSX's spread operator or generating many function parameters from a smaller set.
Others have provided lots of good points but I am not digging it up for you ;)
(1) as mentioned such things can also be changed/improved in Dart and there were already discussions. This just won't happen before Dart 2 release.
Just assuming that DSX allows all kind of new features and Dart doesn't isn't really a fair argument in my opinion.
(2) I'm pretty sure this can as well done with Dart and there is of course already a parser for Dart.
Others have provided lots of good points but I am not digging it up for you ;)
There is no need to dig them up for me, but this comes up frequently and you might be able to convince others that you actually have valid arguments.
I followed the discussion and can't remember good factual arguments and that might be the same for others. If you summarize them you can just post a link to the next that questions that.
As discussed before I can accept personal preference as a valid argument, but if you claim to have lots of factual arguments as well, then I think it's valid to ask to get them pointed out.
You keep asking for 'valid arguments' and when they are given you dismiss them as 'future Dart will have this' or 'this is not a valid argument'.
The fact is that right now Dart/Flutter has noisy child/children everywhere when building a widget and XML/DSX doesn't. Right now it is a very valid argument for using DSX to remove this child/children noise. Can you just accept that as a valid argument? (just because you say Dart will have that in the future, it doesn't make the argument invalid).
It is also a fact that parsing XML is much simpler than parsing the full Dart language and every language out there has an XML parser, whereas only Dart has a full and complete Dart language parser. Can you see that this is also a valid argument?
There are lots of valid arguments, they are just not valid for you and that's why I stopped arguing about it. If people are interested in what was said, just read the 2 threads on JSX fully. I have no interest in convincing you to use DSX, you are happy with plain Dart so be it; I am not.
Arguments for an optional DSX syntax:
1) Onboard and attract more developers coming from React (web and native)
2) Better experience of porting React Native components into Flutter widgets
3) Drives consistency of child/children properties in widgets
4) Code readability (opinionated argument)
5) View logic linting separate from the dart linting
6) Opens up a world for UI building tools
7) Opens up the ecosystem for pre processors
DSX +1
DSX +1
Would've loved to write a bunch of pro/cons, but by having read all these comments, I feel like I'm just gonna repeat everything over and over.
Stop being so naive and ignorant, nobody says you'll be FORCED to write UIs using DSX, it's simply an option (better alternative).
There's a reason you can write JS in 101203103 different ways.
Well, there's always the option writing an analyzer plugin that parses DSX and converts them into regular Dart function calls, so that the compiler doesn't have to do any extra work.
The real question is whether analyzer plugins apply within the context of the compiler.
If you ask me, DSX should only be opt-in, ideally through some sort of plug-in. I think it's extremely unnecessary to add it to the language itself, as then server-side and Web users of Dart have to adapt to the changes, not just Flutter users. The vast majority of code written in Dart doesn't even remotely need any XML syntax, so enforcing it on everybody is a bad decision.
TLDR; if you want DSX that bad, write an analyzer plugin and bring it to Dart yourself. The Internet will love you, you'll get thousands of Github stars, and you'll feel just like it's React. Win-win.
P.S. I'll even race you to do it
Well, there's always the option writing an analyzer plugin that parses DSX and converts them into regular Dart function calls, so that the compiler doesn't have to do any extra work.
There is currently no way in the dart language to implement this without any hacks (think race conditions, recursive imports and stuff). This needs to be integrated at level where everything will work as expected, hot reloading, static analysis, etc.
If you ask me, DSX should only be opt-in, ideally through some sort of plug-in. I think it's extremely unnecessary to add it to the language itself, as then server-side and Web users of Dart have to adapt to the changes, not just Flutter users. The vast majority of code written in Dart doesn't even remotely need any XML syntax, so enforcing it on everybody is a bad decision.
If you read the thread, that has been the idea from day one. We just want the support from flutter/dart to make an transpiler.
TLDR; if you want DSX that bad, write an analyzer plugin and bring it to Dart yourself. The Internet will love you, you'll get thousands of Github stars, and you'll feel just like it's React. Win-win.
Read the thread, this has already been done by @cbazza (analyzer plugin isn't gonna cut it)
https://github.com/flutter/flutter/issues/11609#issuecomment-388484681
P.S. I'll even race you to do it
Great! Just even a theory of how this would work would be interesting to see.
SGTM. Guess we’re all waiting on some sort of pre-processing support, then.
I prefer builder syntax than passing parameters through constructor
@override
Widget build(BuildContext context) {
return container()
.height(56.0)
.padding(8.0)
.decoration(BoxDecoration(color: Colors.blue[500]))
.child(text("Hello world!")
.style(...)
.build());
}
like in https://fblitho.com/
Text.create(context)
.text("Hello World")
.textSizeDip(50)
.build();
DSX +1
I get the arguments for JSX, but I think there are just as many folks (self included) who hate the thought of jamming XML into a programming language. It just feels wrong (but I totally get that others don't feel the same way).
Given that it is next to impossible to take features away once implemented, I'd suggest the pre-cautionary principle. Let's see how some of newer Dart 2 syntax features play out before committing to a substantial change to the way Flutter apps are built.
@wstrange
I can understand you. I used to be against JSX and mixing js with xml/html.... then I tried it. After a few months spent with react, I fell in love with JSX. Two killer advantages are:
@wstrange,
Given that it is next to impossible to take features away once implemented,
That's not a given, who would had thought that Google would remove MathML from Chrome?
Let's see how some of newer Dart 2 syntax features play out before committing to a substantial change to the way Flutter apps are built.
It is not a change to the way Flutter apps are build at all, it's just an alternative way that doesn't change the current way, and most important it is simply a different syntax to the class library. A simple transpiler does the mapping without needing any information from Flutter classes so it works just fine for anybody's code, as well as Flutter now and in the future.
@Bessonov,
Yes, you don't know React until you spend a few months working with it and then you realise how phenomenal a library it is for dealing with component hierarchies.
@cbazza I could say exactly the same thing about Flutter. Spend some weeks using it and you won't miss JSX.
The reaction tells us everything.
As now, +1
nearly double times -1
@escamoteur,
Yes, very fair statement to say but I have spent a lot of time with Flutter and I can certainly see the value DSX would add to it. As @leedstyh has noticed, DSX fans lead the race by almost 2-to-1 which is pretty amazing considering people in this forum are Flutter people.
I have a question:
When using DSX syntax, we implicitly assume that the nested child/children is of type Widget. What if we want to explicitly state that we want nested child/children be a specific sub-type of Widget?
for example, when I want children of my custom widget only accept a list of Container, I can annotate the children with List<Container>
and IDE will give an error as soon as I put anything different from Container. As I’m aware of there is no way to enforce type safe like this when using dsx. Maybe we can have some error when the app compiles though but I think the error raise when I’m typing is still a better experience.
I think we should give everyone some time to try out and get familiar with flutter way to declare UI, at least after v1 release. Then we could have a better look at this feature.
@sandangel ,
Very good catch !!! I bowl my virtual hat to you. My initial prototype has had some holes in it from the beginning that I was aware of and just waiting to people to find them and come forward. I was just hoping people were interested in discussing the technology instead of fighting over it.
The solution I have to this is to provide the array type as another parameter on the namespace. As the namespace is getting large, we can set the short form for 'children' be '*'.
In Example 2 at https://spark-heroku-dsx.herokuapp.com/index.html, if actions were an array of 'Container' instead of default 'Widget', it would look like the following alternatives:
<actions:children:Container>
<IconButton
icon={new Icon(Icons.search)}
tooltip='Search'
onPress={null}
/>
</actions:children:Container>
<actions:*:Container>
<IconButton
icon={new Icon(Icons.search)}
tooltip='Search'
onPress={null}
/>
</actions:*:Container>
hi @cbazza , thank you for your response.
I'm wondering about your solution. Are we misusing the xml namespace as described in w3shool-XML Namespaces?
As it states that namespace is primarily used to solve the naming conflict in XML document.
So when someone reads the above XML, they might think that you are declaring a Container tag under the namespace 'children' of the namespace 'actions', not you are enforcing every nested children must be a Container. It does confuse me when I first read your propose syntax without reading the above explanation.
Could we have something better?
DSX is not XML, it's XML-like so it doesn't need to follow XML semantics, kind of like Angular template language ;) Anyways, I am always open to better alternatives or suggestions and would love to have a discussion here.
Coming From React-native, I first supported JSX like implementation, and didn't like the nested objects, but I am beginning to enjoy OOP and see everything as an Object!
For the people coming from React-native, I highly recommend this plugin! https://marketplace.visualstudio.com/items?itemName=CoenraadS.bracket-pair-colorizer
@clarktank
Can you expand on your exp with react-native(JSX), Flutter(OOP), and your journey from one to the other?
@cbazza I think angular template syntax does follow xml semantics and as I'm aware of there is no conflict use case between angular syntax and xml document.
In typescript, we have support for generic component.
So I think we could have something like this:
<children<Container>>
<Container/>
</children>
But again, the generic component is used for type checking the property input. I don't know if the above syntax has a right semantic meaning in this use case.
I really feel that Flutter team have created the current API specifically for the new way to declare UI they supposed that's better than JSX and any effort we are trying to bind JSX syntax to the current API just make it look unnatural/uncomfortable to use.
The reaction tells us everything.
As now, +1 nearly double times -1
This doesn't mean anything.
Except those who are watching all Flutter issues double the one that land on this issue because they are already used to JSX (and are explicitaly looking for it). So this rather means _the people that want a JSX-like experience double the people watching all issues that have voted -1_. (imho a part of the people voting +1 haven't even really tried flutter)
@sandangel ,
I think angular template syntax does follow xml semantics and as I'm aware of there is no conflict use case between angular syntax and xml document.
Sure but JSX doesn't use namespace so it is not a XML feature of interest.
<children<Container>>
<Container/>
</children>
Since you split the 'children' out of action into it's own tag, kind of reminds me of the new Fragment tag of React. It's a balance between verbosity and conciseness that's for sure.
I really feel that Flutter team have created the current API specifically for the new way to declare UI they supposed that's better than JSX and any effort we are trying to bind JSX syntax to the current API just make it look unnatural/uncomfortable to use.
There is nothing new in the way Flutter declares UI in code, Perhaps using DSX is unnatural/uncomfortable to you but to JSX developers it is not. JSX/DSX is perfect for Flutter, it fits like a glove and if you don't like gloves go bare handed ;)
@a14n ,
This doesn't mean anything.
it sure does !!! you can argue with 'feeling', 'thinking', 'suspect', 'imho', 'opinion' but this is data, a concrete data point. If the data is useless it shouldn't be collected. I guess the data is useless because it doesn't paint your picture.
@cbazza I mean when we're trying to answer the question I have above about enforcing sub-type of widget for child/children, I feel that Dart code is doing a better job than JSX.
DSX is not XML, it's XML-like so it doesn't need to follow XML semantics
Sure but JSX doesn't use namespace so it is not a XML feature of interest.
I'm not sure but I have read some of your comments above and I think you have mentioned JSX/XML node interchangeably. Anyway, personally I think using namespace as a solution is not ideal.
Just compare
<actions:children:Container>
</actions:children:Container>
and
actions: <Container>[]
syntax.
@sandangel,
Yes, the tagging syntax is more verbose for this case and that's why I mentioned the short form for children being '*'. Anyways, this case is the exception and not the rule. Most of the time you don't need to even specify 'children', let alone 'Container'; but the functionality needs to be there to cover all possible use cases.
@a14n vote is vote, it sure means.
I respect your feeling, maybe it's true. But even with a reverse ratio (1 to 2), that still means 33% user base. Can you say 33% is a small share?
people that want a JSX-like experience
Yeah, some people are watching. This also means _lack of JSX-like is one of the reasons prevent people from choosing flutter_.
Flutter aims at more developers, not only ones read all issues.
@jstansbe
I am a self-taught programmer, and like most self-taught guys, I started with Javascript.
Then I started to learn React and React-Native. I think in recent years, specially after ES6, OOP style was added to Javascript.
So people like me aren't used to OOP style of programming. Even though React native Component
are classes just like Widgets
in Flutter.
JSX kind of hides the pure OOP picture. Basically, it hides what happens under the hood. Note: React was designed for web developers, and web developers are used to html syntax. That is why JSX is so popular, among web developers.
Personally, I think pure OOP makes more sense for big projects.
@clarktank,
When discussing computer languages you have to be aware of:
(1) Syntax - the characters and words that make up the language
(2) Semantics - the meaning of those characters and words
For example, function calls in many languages look like the following (i.e. have the following syntax):
a = someFunction(param1, param2)
Imagine now that another language decides to use square brackets instead of rounded brackets for function calls; it would look like the following:
a = someFunction[param1, param2]
The thing here is that the syntax is different but the semantics are the same. I mean both are basically doing function calls but with a different syntax.
JSX kind of hides the pure OOP picture. Basically, it hides what happens under the hood.
Not true at all. JSX/DSX is just a different syntax to exactly the same thing (the semantics are the same). In the case of JSX, XML tags just create React Components (just like you can do it in Pure Javascript). In the case of DSX, XML tags just create Flutter Widgets (just like you can do it in Pure Dart). The syntax is different but it generates exactly the same thing so it is identical under the hood.
Note: React was designed for web developers, and web developers are used to html syntax. That is why JSX is so popular, among web developers.
JSX is popular because it is a great way to manage component tree hierarchies, whether for web, mobile or any UI development. Notice in the code below you don't know if the dropdown component is for web or mobile for example.
https://facebook.github.io/jsx/
// Using JSX to express UI components.
var dropdown =
<Dropdown>
A dropdown list
<Menu>
<MenuItem>Do Something</MenuItem>
<MenuItem>Do Something Fun!</MenuItem>
<MenuItem>Do Something Else</MenuItem>
</Menu>
</Dropdown>;
render(dropdown);
Personally, I think pure OOP makes more sense for big projects.
How is that? (considering that using JSX/DSX or Pure Javascript/Dart generates exactly the same thing under the hood).
@cbazza
I used react-native for almost one year and had no idea JSX elements are Objects that are being instantiated, until I started with Flutter/Dart. From my perspective, it does hide the OOP picture, even though as you said it semantically does the same thing under the hood!
In large application, JSX could also get as ugly as heavily nested objects. So syntactically, I would rather stay consistent than introducing another style which could be as confusing.
@clarktank,
In large application, JSX could also get as ugly as heavily nested objects. So syntactically, I would rather stay consistent than introducing another style which could be as confusing.
For me having it look different than the rest of the code is actually a benefit.
(I apologize in advance for the wall of text.)
As someone who hasn't used either React-Native or Flutter long enough to consider myself a definitive source whether raw Dart or JSX/DSX is "better", this issue thread has been rather fascinating to read. There are a couple things that I would like to put my $0.02 down on though.
To begin, I find myself agreeing with various people on the nature of what JSX actually is and how it benefits developers. First and foremost, JSX was designed as a form of "dynamic HTML" that could be inlined into existing Javascript code. It's indispensable for JS-based web platforms like React in that it enables web developers to cleanly and efficiently interact with the DOM without having to wrestle with the god-awful native way (or the only-slightly-better jQuery way). Also, by its very nature, JSX encourages UI development that can be easily decoupled from the underlying data, promoting a well-organized project structure. In that environment, JSX is a tool to enable greater productivity, and I feel that it would be virtually impossible to argue with that.
How that paragraph relates to React-Native is that, even though it is a mobile-development platform, it is directly descended from React. As such, nearly all of the syntax and paradigms were still originally created with web-development in mind. That is by design - RN's whole shtick is that you can "create cross-platform mobile apps using React", so it's _supposed_ to feel like web development when using it. RN apps are also predominantly written in Javascript, so the inclusion of JSX is a natural one. JSX helps RN development for nearly all the same reasons that it helps in web development. (I really think that this is one big reason that, in RN at least, the JSX approach is used so much more frequently than the native approach. RN itself just _feels_ like a web platform, so the more web-natural approach is inevitably going to become predominant.)
Flutter, on the other hand, has no such design philosophy. It is intended to be a purely native cross-platform solution, and though it states that it was inspired by React-Native, it writes a lot more like a native desktop or mobile app than a web app. It also runs using Dart and not Javascript, which from the standpoint of integrating something like JSX is a major consideration. For one, while the JS DOM functions can horribly verbose (both because of the function's design and the JS language itself), Dart as a language is much more facilitating of clean UI-declarative code while Flutter for the most part does a good job of keeping UI constructors concise. For another (as @sandangel pointed out) Dart is a statically-typed language, so the nature of JSX being designed for a dynamically-typed language like JS is going to run into snags in cases where, for example, a UI constructor requires a Widget of a specific type, the only solution to which just adds to the verbosity. Personally, it feels like a solution that, over time, will inevitably result in a DSL that has gotten bloated and difficult to maintain as it has to account for a growing number of use cases inherent in a system that it wasn't intended to be used for.
As such, I really don't see how JSX/DSX would benefit Flutter development productivity beyond just being a matter of personal preference. Both syntaxes overall are roughly equivalent in verbosity, and where one loses verbosity in specific instances it makes up for it in clarity (the closing XML tags, for example). It largely boils down to if someone is coming to Flutter from a web-oriented background (React/RN, Angular, etc.) or from a native background (Java/Kotlin/Swift, WPF/UWP, etc.) that will determine which approach they would prefer. Even on this thread alone, there are a lot of user stories that say they were extremely skeptical of JSX at first but after using it for a few months changed their opinion to "can't do without". (Though the cynical part of me wants to point out that the same thing could very well happen to them for the native Dart approach if they gave it a chance.)
All that being said, I can't really see myself agreeing that DSX should become officially supported by the Flutter team as an alternative to native UI constructors. While it's perfectly fine as a third-party solution (and all the props to @cbazza for actually implementing it), it doesn't really fit with the core nature of Flutter as a non-web-technology-based platform. As such, more power to anyone who wants to use DSX in their own projects, but I would side with the mindset that there are plenty of other more important things the Flutter team could and should be spending their time on.
Now with THAT being said, while I don't really agree with DSX being officially supported, I do think that there should be an official UI format of _some_ kind. As @birkir pointed out, nearly every major native UI platform, be it desktop or mobile, has a UI format in addition to the direct code-based approach (and most of them are pre-processed into the code-based approached anyway). Having separate UI files from logic files has always been the recommended way to embrace the MVVM pattern (which, incidentally, is one thing that has always rubbed me the wrong way about JSX). What I would argue, therefore, is that Flutter have something similar - instead of an inline UI DSL format, it should have a separate UI format that is intended to go into its own file away from the Dart code.
As part of this line of thinking, I've actually done some work this past weekend along that end. If I could be allowed to shill for a moment, I developed a project that I've coined "FLUI" that is my attempt to show what such a format might look like. Rather than going with an existing DSL (or a modified version), I developed an entirely new one that takes inspiration from YAML and I've tried my best to keep close to the "feel" of the Flutter-constructor-approach layout. Granted, it's a _very_ early implementation, so I don't really expect it to not have a massive slew of issues, but I've included the source for the processor script (written in C#/.NET Standard) so that people can play with it if they want to. :)
As both a React/RN and a Flutter user, I heavily disagree with the idea of "DSX".
DSX would bring nothing. JSX is used in react because the JS syntax is horrible. But in the case of Flutter, widgets creations is super easy.
The classical :
Widget build(BuildContext context) {
return Center(
child: Text("foo"),
);
}
it is already out of the box readable, easy to write, type/generic compatible, and without any unneeded duplication.
The only complain you could possibly have with the current syntax is "It is hard to know where is the closing parenthesis of a widget"
But then again, dart plugin of the officially supported IDEs solves this problem. So that when we open the code from before in say vscode, we'll see
Widget build(BuildContext context) {
return Center(
child: Text("foo"),
); // Center
}
As for the "It's hard to differenciate casual code from UI code", react rules apply to flutter too :
Widgets should be either dumb or smart. Smart widget don't have UI logic. Dumb widgets have nothing but UI logic.
If you follow this pattern, you should never fall into a situation where you fail to differentiate UI from the rest.
This is even more true when following something like BLoC pattern; which heavily enforce separation of business and UI.
JSX is used in react because the JS syntax is horrible
Very opinionated statement and simply not true.
render() {
return React.createElement(Container, { padding: EdgeInsets.all(20.0) },
React.createElement(Text, { style: { color: Colors.black } },
'foo'
)
);
}
Widget build(BuildContext context) {
return Container(
padding: EdgeInsets.all(20.0),
child: Text(
'foo',
style: TextStyle(color: Colors.black)
),
);
}
render() {
return (
<Container padding={EdgeInsets.all(20.0)}>
<Text style={{ color: Colors.black }}>foo</Text>
</Container>
);
}
Widget build(BuildContext context) {
return (
<Container padding={EdgeInsets.all(20.0)}>
<Text style={TextStyle(color: Colors.black)}>{'foo'}</Text>
</Container>
);
}
Very opinionated statement and simply not true.
There's a lot of unneeded characters in the default react syntax.
Let's compare words repetition and characters count for each syntax (excluding function definition, indentation and 'return')
React without JSX:
:
, 4 ,
and 11 spacesReact.createElement
written twiceJSX:
:
, 4 <>
and 5 spacesContainer
and Text
written twiceDart:
:
, 3 ,
and 4 spacesIn term of characters, the obvious winner here is dart syntax.
Now we also have to take other dart specifics into account.
Dart types single child vs multi-child, has const
constructors and allows generics and even positioned parameters. JSX supports none of these.
A few examples that would badly convert to JSX :
Not always children
:
Scaffold(
appBar: AppBar(),
body: Container(),
)
OR
SingleChildScrollView(
child: Container(
height: 100.0,
),
)
const
constructor on widget themselves
const Padding(
padding: const EdgeInsets.all(4.0),
)
generics
NotificationListener<ScrollNotification>(
onNotification: (foo) {
},
child: child,
)
positioned props :
Text("foo")
Named constructor
Positioned.fill(
child: Container(),
);
builders (dart doesn't support union type so children
can't be both a Widget and function)
Builder(
builder: (context) => Container(),
)
@rrousselGit
As mentioned several times before DSX is simply a different
syntax and it is a superset of Dart, so everything you can do with
Dart you can do it inside DSX. You can also mix and match both
syntaxes as you see fit. Obviously you didn't even bother to check
out what are some of the DSX features that were done to support
Dart:
https://spark-heroku-dsx.herokuapp.com/index.html
-1---------------------------------------
In Dart:
Scaffold(
appBar: AppBar(),
body: Container(),
)
OR
SingleChildScrollView(
child: Container(
height: 100.0,
),
)
In DSX:
<Scaffold
appBar={<AppBar/>}
body={<Container/>}
/>
OR
<SingleChildScrollView>
<Container
height={100.0}
/>
</SingleChildScrollView>
-2---------------------------------------
In Dart:
const Padding(
padding: const EdgeInsets.all(4.0),
)
In DSX:
const Padding(
padding: const EdgeInsets.all(4.0),
)
-3---------------------------------------
In Dart:
NotificationListener<ScrollNotification>(
onNotification: (foo) {
},
child: child,
)
In DSX:
<NotificationListener<ScrollNotification>
onNotification={(foo) {
}}
child={child}
/>
-4---------------------------------------
In Dart:
Text("foo")
In DSX:
<Text ["foo"]/>
-5---------------------------------------
In Dart:
Positioned.fill(
child: Container(),
);
In DSX:
<Positioned.fill>
<Container/>
</Positioned.fill>
-6---------------------------------------
In Dart:
Builder(
builder: (context) => Container(),
)
In DSX:
<Builder
builder={(context) => <Container/>}
/>
<MyAppBar>
<title:Text [] style={Theme.of(context).primaryTextTheme.title}>
Example title
</title:Text>
</MyAppBar>
And none of your examples here or from your link actually simplify the code or improves readability
As much as I can relate to your feeling of missing JSX (got the same when starting flutter), after some experience, the native syntax feels pretty good actually
As a side note, there's a much better solution to your separation of concern. That is a template file
You could have an xml/yaml file next to your widget. And then use the awesome code generation tooling dart provides.
I'd rather prefer a :
// main.dart
import 'package:flutter/material.dart';
part 'main.g.dart';
class MyState extends StatefulWidget {
@override
_MyStateState createState() => _MyStateState();
}
class _MyStateState extends State<MyState> {
@override
Widget build(BuildContext context) {
return $myStateStateTemplate(theme: Theme.of(context));
}
}
combined with a
// main.xml
@theme ThemeData
<Container color={@theme.cardColor} />
which then using a custom code-gen generates the following dart file :
part of 'main.dart';
Widget $myStateStateTemplate({ThemeData theme}) {
return Container(
color: theme.cardColor,
);
}
The end result is even better than a "DSX" for separation of UI/logic. It's better for potential UI generators too. And it's much easier to implement using built
.
As JSX is radically different from your prototype :
Really !!! The only thing radical in these discussions has been the reaction of the naysayers.
As it's stated in the title of this ticket, DSX is JSX-like, it is not JSX-identical or else it would had been called JSX; and the additions to it are minor and provides options to developers.
You could write it like:
<MyAppBar>
<title:Text [] style={Theme.of(context).primaryTextTheme.title}>
Example title
</title:Text>
</MyAppBar>
or
<MyAppBar>
<title:Text ['Example title'] style={Theme.of(context).primaryTextTheme.title}/>
</MyAppBar>
or
<MyAppBar
title={<Text [] style={Theme.of(context).primaryTextTheme.title}>
Example title
<Text>}
/>
or
<MyAppBar
title={<Text ['Example title'] style={Theme.of(context).primaryTextTheme.title}/>}
/>
Hummmm, you seem to be confusing 'separation of concern' with 'separation of technology'. These things are very different; you separating dart code and markup code in different files, is simply 'separation of technology' and provides none of the benefits of 'separation of concerns'. A concern here would a component/widget that encapsulates reusable code cleanly, it doesn't matter that inside that component/widget it is using different technologies.
Also separating technologies as you recommend is highly inferior to JSX/DSX which uses the host language for all of its imperative constructs (for loops, function calls, if statements, etc).
After much of code and examples posted here (especially), I come to conclusion, that JSX adds much more value to JS in contrast to DSX and Dart. But one feature is very important from my point of view: Closing tags. Like:
<SingleChildScrollView>
<Container
height={100.0}
/>
</SingleChildScrollView>
reduces a LOT of cognitive complexy in deep structures like here in contrast to:
SingleChildScrollView(
child: Container(
height: 100.0,
),
)
But well, if you use it like this:
<Scaffold
appBar={<AppBar/>}
body={<Container/>}
/>
there is a small profit.
As it's stated in the title of this ticket, DSX is JSX-like, it is not JSX-identical
You missed my "But then the argument of having an easier conversion from react to flutter is invalid."
Half of the arguments for DSX is "JSX is popular in react, we need this here too". But you're proposing something different (and more complex) from JSX.
The other half is about separating UI from code; which a template file can do too.
Also separating technologies as you recommend is highly inferior to JSX/DSX which uses the host language for all of its imperative constructs (for loops, function calls, if statements, etc).
Not true. You could do if
and stuff inside your template file. Look at cshtml
or angular templates.
The thing is a template file, as long as you already have a parser for it, could be implemented for flutter in less than a week fully working.
Be it yaml, xml, cshtml, or html with directives.
While a DSX would require a lot of work.
@Bessonov They recently added virtual comments on supported IDEs to mock closing tag.
So in your vscode you'll see the following :
SingleChildScrollView(
child: Container(
height: 100.0,
), // Container
) // SingleChildScrollView
The benefits of closing tags. Without having to type them
@rrousselGit
They recently added virtual comments on supported IDEs to mock closing tag.
Yeah, I've seen that in cited comment. But it's not the same. This introduce an align shift and disturb reading flow. And this doesn't help me in other IDEs and text processors.
The thing is a template file
IMHO templates suffers from NIH syndrom. I don't say that approach to mix PHP and HTML is the right way to do that. But react shows with JSX how it can be done better.
@rrousselGit
You missed my "But then the argument of having an easier conversion from react to flutter is invalid."
No, I didn't miss the comment at all, it just makes no sense you telling me that people coming from JSX will find DSX too complex.
Half of the arguments for DSX...
There are many reasons to choose DSX but with alternatives people will pick what they prefer for whatever reason they have.
Not true. You could do if and stuff inside your template file. Look at cshtml or angular templates.
The thing is a template file, as long as you already have a parser for it, could be implemented for flutter in less than a week fully working.
Be it yaml, xml, cshtml, or html with directives.
While a DSX would require a lot of work.
Totally opposite, DSX only implements 2 xml transforms and gains everything else for free from the hosting language. Imagine the effort trying to re-implement the power of Dart inside your new templating language. No thanks, I'll take Dart.
No, I didn't miss the comment at all, it just makes no sense you telling me that people coming from JSX will find DSX too complex.
The same thing applies to the current dart implementation.
Anyway, I don't think we can convince each other here. So I'll just list a few more reasons as to why I dislike JSX in flutter and then "wait and see".
1. Widget creation is different from React
In react, it's the library that handles components creation. JSX is fine because it says "Don't bother about how things work. We do things for you".
In flutter that is not the case. We manually instantiate a new widget every on build call. This is really important to understand, and JSX would make it less clear.
And, in the continuation of that logic :
2. Peoples may think <Foo />
does something special that new Foo()
don't
<Foo />
in a method feels special. It seems like it does something extraneous built-in in the framework. Which is true in react, where components are wrapped into a React.Element
.
This translates in react into <Foo />
!= new Foo()
and don't have direct access to Foo
.
This doesn't apply in flutter and may cause confusion.
Also :
<Foo>
<Bar />
</Foo>
In react, if Foo
never uses its child then Bar
is never instantiated. And Foo
is instantiated after the render
method returns.
While in flutter this is the opposite. Both Bar
and Foo
are created immediately
This would potentially lead in React developers making un-optimized flutter code.
3. In general Dart/flutter is not JS/react
If we add JSX in dart, I can already see the issues about type union or be able to do
return foo && <Component />
or the upcoming async rendering in react.
Justified with a "we already have JSX so we can have that too !"
I'd prefer a proprietary syntax or no syntax at all, for the sake of not having to implement the latest JSX/react feature in dart
4. JSX makes some dart specifics unclear
A small example, Scaffold
requires for appbar
a PrefferedSizeWidget
.
If we created Scaffold
using JSX, peoples would expect that you can replace any given JSX with another. Which is not true
I mean, it makes it very unclear why we can do
<Scaffold
appbar={<AppBar />}
/>
but not
<Scaffold
appbar={<Container />}
/>
@rrousselGit
Anyway, I don't think we can convince each other here. So I'll just list a few more reasons as to why I dislike JSX in flutter and then "wait and see".
I disagree with a lot of what you said but I appreciate your effort since you are taking the time to think deeply into the issue.
- Widget creation is different from React
To me it doesn't matter because this is just an implementation detail, conceptually once you see some XML, in React it is a Component, in Flutter it is a Widget.
- Peoples may think
does something special that new Foo() don't
I think people will learn pretty quickly that Dart/DSX is not Javascript/JSX.
- In general Dart/flutter is not JS/react
Yes, we finally agree on something but even though they are different the common thread is that they are declarative UI frameworks and I think declarative tree structures are handled nicely with JSX/DSX. It keeps you on the declarative programming way of thinking.
If we add JSX in dart, I can already see the issues about type union or be able to do
return foo && <Component />
or the upcoming async rendering in react.
Justified with a "we already have JSX so we can have that too !"
We are not adding JSX in Dart, we are adding DSX, it is different but has similarities to JSX and familiarity is a huge thing.
I'd prefer a proprietary syntax or no syntax at all, for the sake of not having to implement the latest JSX/react feature in dart.
So with that reasoning why are you using Dart? it looks pretty similar to Java and yet it is different than Java; the heck with it, let's scrap all of these Java keywords and concepts and come up with something vaguely similar to Erland that you can only program with one hand while doing a pretzel yoga move on top of Mount Everest ;)
- JSX makes some dart specifics unclear
Not really, if you connect incomparable Widgets the Dart compiler will spit error messages just like if you did it in plain Dart. I can not emphasize enough that DSX is simply thin syntactic sugar, there is no magic, just a difference syntax to the same thing.
@cbazza I spent hours reading your posts and I really appreciate your effort on this issue. But I think it is (kind of) easy to end the argument. Remember that flux was the official state management solution for react but now everyone is using redux? And how many navigation libs are there for react-native? Just make a DSX repo and let react devs jump in.
@rrousselGit
I've never seen the part
/part of
syntax in Dart before, and I'm having trouble finding any documentation for it. Is it something that Dart/Flutter officially supports? I'd love to use something like that in FLUI.
@cbazza
You keep going around in circles with the DSX justification. DSX is not JSX. DSX is JSX-like. DSX is meant to be a familiar syntax for React developers. DSX is merely think syntactic sugar for Dart. People will learn that DSX is not JSX. (And so on.)
While I get the point you are trying to make with all those explanations, I think the fact that you have to keep making them reveals a major issue regarding the nature of DSX in general, and it's a point that rrouselGit brought up as well. Even as you keep saying that DSX is _not_ JSX, people who find it are going to think that it is, and that's a problem. JSX, and the people who use it, come from an ecosystem that is so conceptually different on fundamental levels from Dart/Flutter. As such, developing a feature for "familiarity" is not necessarily a good thing. One of the more apparent reasons for such is, as was pointed out, people are going to try something like this:
Widget build(BuildContext context) {
return isDialogVisible && <Widget>...</Widget>;
}
Because they come from Javascript/JSX, they expect that syntax to work in DSX. When it doesn't, it becomes a point of cognitive dissonance which may actually _hurt_ their interest in not just DSX but in Flutter as a whole. Familiarity is beneficial when it's used as a means to ease people into something new, but that can be a double-edged sword - when 90% of the features are the same, the remaining 10% can serve to just frustrate and annoy.
Another issue with DSX is that it is not likely to be a seamlessly integrated feature any time soon, regardless of if it's a third-party plugin or if it gets officially adopted by Flutter. As you've said yourself, in order for it to truly work with the Flutter debugging and deployment process, it needs official support from not only the Flutter team but also the Dart team. Failing that, without pre-processing and tooling support, the only way DSX would work is with external manual conversion tools, which is just another (potentially lengthy) step that developers will have to go through.
While typing this up, there's another thing that occurred to me. There have been several pro-JSX people in this thread that have praised JSX, saying that the "separation of concerns" approach to UI design is really the only way they will ever consider developing UIs again. If that's the case, why is React the only framework with market presence that is using it? Both native and cross-platform mobile app frameworks have stuck with their storyboards, their XML files, their XAML files, and other such UI definition DSTs. Even other popular JS frameworks like Angular and the up-and-coming Vue still do the "separation of technologies" approach. React developers talk like JSX is the way of the future, but I've yet to see it pop up anywhere other than in React in a framework that has gotten any real traction.
@andrewackerman
part
/part of
is an existing dart feature. It somehow joins two files into one. Usually used for code generation.
There are a few real cases scenarios that use such technique. Like json_serializable
which generates a toJSON
method and a fromJSON
factory for classes based on their properties.
part
/part of
don't really do anything on its own. The interesting part is when you combine it to something like source_gen.
@sunnylqm
I don't think putting code on a repo would solve my problem because the current issue is about properly integrating DSX with Flutter tools as to provide a great developer experience with debugger, auto-complete, etc. working on .dsx file.
Telling users that they can use DSX but can't use debugger or enjoy auto-complete is a non starter for me. If anybody wants to help, what I need is to figure out a way to add full preprocessing support (with source map) to Dart Tools and VS Code Dart plug in. Once the tools support that DSX or any other transpiling language (any language that is a superset of Dart but compiles everything down to Dart) would just work.
@andrewackerman
I don't need to justify anything, I am very confident that DSX will be a hit and there are almost 100 people interested in it on this ticket alone.
Failing that, without pre-processing and tooling support, the only way DSX would work is with external manual conversion tools, which is just another (potentially lengthy) step that developers will have to go through.
The DSX transpiler is blindingly fast and can transform .dsx files into .dart files faster than you can blink, so speed is not a problem; just trying to get feature parity as to make it a no-brainer for people to use DSX.
If that's the case, why is React the only framework with market presence that is using it? Both native and cross-platform mobile app frameworks have stuck with their storyboards, their XML files, their XAML files, and other such UI definition DSTs.
Just make a timeline and you will see the UI development evolution. Android and iOS development via their current ways started over 10 years ago so it uses 10 years old techniques (totally imperative techniques). The Reactive UI development (declarative) techniques started to appear for the web around 8 years ago. React appeared 5 years ago and it was the first Reactive framework to combine technologies seamlessly with JSX. Vue is now the latest Reactive framework that supports the older 'separation of technologies' techniques but it also supports JSX. On mobile Flutter is the latest and it uses Reactive framework techniques as React and it could take advantage of DSX just as Vue takes advantage of JSX. Vue is killing Angular because it is providing choice to developers and not being overly opinionated.
The problem with separate template files is that the imperative programming constructs there (if, for loop, etc) are so weak compared to what's available on the programming language used for the business logic. Combining the 2 in the way JSX does, to me, is clearly the future.
React developers talk like JSX is the way of the future,
It is !!!
but I've yet to see it pop up anywhere other than in React in a framework that has gotten any real traction.
Vue uses JSX
@cbazza
I don't need to justify anything, I am very confident that DSX will be a hit and there are almost 100 people interested in it on this ticket alone.
I'm not saying you _do_ need to justify anything. Back when you were insisting that the Flutter team pick up this proposal and implement it themselves, yeah, I would've said you had a fair amount of justifying to do. Now that you are trying to do it yourself, you can do whatever you want for what ever justification you think is sufficient, and more power to you. I'm merely stating the reasons I see that it might not be as easy or as popular as you seem to think it will be, and I am putting the ball in your court to defy them.
The DSX transpiler is blindingly fast and can transform .dsx files into .dart files faster than you can blink, so speed is not a problem; just trying to get feature parity as to make it a no-brainer for people to use DSX.
I assume that, at this point, you've tested it so far on UIs and Apps that are trivial in size. What about non-trivial ones? What about ones that fall within edge cases? Also, the actual time that the process takes is not the only relevant part - just the fact that the developer has to go through another checklist of manual actions before they can build is enough of a turn off for many people.
You also have yet to actually release the source code of the project, so no one's been able to go through your process, double-check your findings, and suggest improvements. At this point, all anyone can really do is take you at your word that it is both convenient and performant.
Vue uses JSX
I've been using Vue for coming close to a year now, and in that time I have gone through a good number of open source project repos to see how different things are done. While I don't consider myself a Vue master by any means, what I will say is that in not a single one of them have I ever seen JSX actually utilized - people seem to massively prefer the .vue
approach (template-script-styling) over the render+JSX approach. I didn't even know myself that Vue even supported JSX (via a babel plugin at least) until after your reply I did some digging through the Vue documentation and discovered a tiny snippet of information on it in the render function section.
But this is irrelevant to my overall point. Vue is still a Javascript framework. Flutter is most assuredly not. As such, there are a lot of reasons that make JSX the newest greatest thing in a Javascript-centric environment that won't translate to Dart+Flutter, many of which have already been covered in this thread.
It is !!!
Until I see it catch on in a non-Javascript development environment, I shall respectfully disagree.
Vue uses JSX
Vue specify has a broad variety of usages. JSX is just "there". But it's not the dominant syntax
You could plug JSX to Angular if you wanted to. Although nobody does
React developers talk like JSX is the way of the future,
It is !!!
A big candidate for the future is web-components. And they are used directly in html similar to what you'd find in Angular or the most common form of Vue
@andrewackerman
just the fact that the developer has to go through another checklist of manual actions before they can build is enough of a turn off for many people.
Who said anything about manual actions? Didn't I make myself clear that I am trying to get complete seamless IDE integration (best possible user experience for developers).
You also have yet to actually release the source code of the project, so no one's been able to go through your process, double-check your findings, and suggest improvements.
How does that have anything to do with people using DSX? I've used JSX for over 2 years and couldn't care less for its source code. Do you need to look at the source code of the Dart compiler to be able to program in Dart?
what I will say is that in not a single one of them have I ever seen JSX actually utilized - people seem to massively prefer the .vue approach (template-script-styling) over the render+JSX approach.
JSX is a new addition so it will take time to spread but the important point to get is that Vue accepts other approaches without forcing developers to use 'the correct way and only way' that things should be done in Vue.
Vue is still a Javascript framework. Flutter is most assuredly not.
Riiiiight, so instead of JSX you use DSX with Flutter.
@rrousselGit
A big candidate for the future is web-components.
Web components are zoobies, dead but still walking; they are as widespread as kangaroos in Canada. I could go on for days but to avoid digressing...
https://dmitriid.com/blog/2017/03/the-broken-promise-of-web-components/
@cbazza
Who said anything about manual actions? Didn't I make myself clear that I am trying to get complete seamless IDE integration (best possible user experience for developers).
You also said that you needed preprocessing support from the Flutter/Dart team in order to do so. Am I incorrect in that?
How does that have anything to do with people using DSX? I've used JSX for over 2 years and couldn't care less for its source code.
JSX was developed by Facebook for React, put through a rigorous proposal/design/implementation/iteration process, and then released into the world years before you got your hands on it. It's been rigorously tested and proven time and time again in real world environments. It's a mature technology. There's no reason to demand to see a spec sheet for something like that.
DSX, on the other hand, is being developed today by you and a handful of people. You've waxed eloquently about what it can and will be able to do, but all we've actually _seen_ is a small handful of purpose-built code snippets and your word that they were generated by the transpiler. People who have even want to try it out and suggest possible changes or improvements aren't able to do so, so they have no reason to support your efforts beyond "Yay JSX!".
I'm not accusing you of lying or anything, I'm just saying that JSX has earned a level of faith that DSX has not, so how are you going to turn some heads if you don't let people tinker with it?
JSX is a new addition so it will take time to spread but the important point to get is that Vue accepts other approaches without forcing developers to use 'the correct way and only way' that things should be done in Vue.
JSX has been in Vue for almost 2 years now. And unlike Vue itself, JSX is a pre-existing technology that needs no introduction, especially for people familiar to React. If JSX was going to take the Vue.js world by storm, I can't help but feel it would've done so by now. (Particularly if it's any indication that as many people are clamoring for JSX in Flutter as you claim.)
Riiiiight, so instead of JSX you use DSX with Flutter.
JSX and DSX are the same syntactic concept. The problem is that, where JSX was built on a weakly-typed dynamic language like JavaScript, DSX is being built on a strongly-typed static language like Dart. That means there are lots of problems DSX will have to account for that JSX didn't have to if it's going to be anything other than a niche "JSX for Flutter" implementation, and it's going to take some _ingenious_ modifications to make DSX really work without making it too bloated to justify claiming that it's more visually concise.
And to address the "DSX is just Dart, if DSX can't do something, just use Dart" rebuttal, then my counter-rebuttal would be if I have to keep falling back to Dart whenever I run into a scenario that DSX doesn't handle, then why shouldn't I just use Dart all the time?
And to address the rebuttal for that reading "you can if you want to, DSX is just an option", then you are really selling yourself short. Even if it really is just going to be "an option", it still needs to bring something to the table that is going to convince people to use it. You yourself said that DSX is not JSX, so people who want just JSX aren't going to get what they want. That means there needs to be some tangible reasons beyond the "JSX-like appeal" for people to want to use it.
If you're just building a tool that you yourself want to use, then all this is moot and you can go nuts. But if you are actually building something you intend for other people to use, then you need to put it in a solid form why you think they should.
Web components are zoobies, dead but still walking; they are as widespread as kangaroos in Canada. I could go on for days but to avoid digressing...
Somewhat off-topic, but I would like to point out that web components really are a promising look at the future, even if support for them is getting added slower than tar. Think about it this way: React does what it does because it essentially implements the idea of web components in Javascript-only. Imagine how much better it would be if those features were supported by the browser and benefitted from non-sandboxed performance and not having to operate through DOM manipulation? (Granted it might be another 20 years before we find out, but still...)
@andrewackerman
Sorry dude I don't have the time to argue endlessly and repeat what I said before over and over; we won't end up in agreement anyways so best of luck with your FLUI.
You've waxed eloquently about what it can and will be able to do, but all we've actually seen is a small handful of purpose-built code snippets and your word that they were generated by the transpiler.
The online DSX transpiler has been live since Feb 2018 and anybody can use it so there is no need to take my word for anything. Press 'Compile' and it compiles what its written on the left panel and places results on right panel. Open debugger and you will see the AST written out.
https://spark-heroku-dsx.herokuapp.com/index.html
The problem is that, where JSX was built on a weakly-typed dynamic language like JavaScript, DSX is being built on a strongly-typed static language like Dart.
It makes no major difference at all, like the OOP (Object Oriented Programming) concept and syntax for 'classes'. It's almost identical in typeless Javascript or typed Dart; same can be said for 'if' statement, 'for' statement, etc
it still needs to bring something to the table that is going to convince people to use it.
Apparently it already does for 100 people in this ticket; and that's 100 times larger than just me using it; good enough for me.
@cbazza
Sorry dude I don't have the time to argue endlessly and repeat what I said before over and over; we won't end up in agreement anyways so best of luck with your FLUI.
I'm not arguing with you just for the sake of argument or because of some deep-seated anti-JSX bias. I'm trying to get you to answer questions that need to be answered. You are developing a tool that you presumably intend for other people to use, yet you still haven't offered a compelling reason _why_ they should use it beyond the vague and subjective benefits of "familiarity" and "because it's better". The former, as I said before, is not necessarily a good thing, and the latter is as of yet a claim made without any tangible support.
If you want your tool to be a success, it needs to be set in stone what you are doing and why you are doing it, and you need to do so in a way that it can be easily conveyed to others. That's not to say that you can't make a product until it is liked by _everyone_, but clear and concise objectives are crucial to shaping design and implementation. Otherwise you are just going to end up with a direction-less utility that will be a niche product at best and will be extremely lucky if it ends up in production code of any scale.
The online DSX transpiler has been live since Feb 2018 and anybody can use it so there is no need to take my word for anything. Press 'Compile' and it compiles what its written on the left panel and places results on right panel. Open debugger and you will see the AST written out.
I didn't even see that that link was a working example. I've never used herokuapp before and it just looked like a gist or something, so that's on me. :P
(Though I will point out that tinkering with an online sandbox is not the same as testing the transpiler in a more practical environment.)
It makes no major difference at all, like the OOP (Object Oriented Programming) concept and syntax for 'classes'. It's almost identical in typeless Javascript or typed Dart; same can be said for 'if' statement, 'for' statement, etc
You already had to deal with one such difference in child strong-typing. What about attribute strong-typing? What about widgets in different libraries with the same name? What happens if someone makes a widget with more than one nameless positional argument? What happens if we import two libraries that have widgets with the same name? What happens in some scenario that I haven't thought of pops up to further showcase the inherent difference between systems like Javascript and Dart? I have to say, you being so flippant on this discussion point makes me worry about DSX's longevity in a real-world setting.
Apparently it already does for 100 people in this ticket; and that's 100 times larger than just me using it; good enough for me.
Again, that's 100 people who upvoted the issue on the basis of "Consider JSX-like syntax inside dart code". They upvoted because they want _JSX_, and as you've been so keen to point out, DSX is not JSX. So why else would they want to use DSX? Because inline XML-like UI declaration is "the future"? Again, I just don't see it.
We've already covered JSX in Vue not getting any traction, but there's also the two React alternatives mentioned in the Web Components article you linked: Inferno and Preact. As far as I can tell, they have both failed to make any kind of waves at all in the JS-based web-app development world, despite also natively supporting JSX-like syntax. I really think that people need to have a long and hard look about _exactly why_ people like JSX in React, because by all accounts it just doesn't seem to be because of JSX itself. If _that_ question can be answered, then we can move forward toward "future" innovations rather than just frankensteining that one feature from that one library we liked into everywhere else we personally think it should be.
Thinking on the amount of energy that was invested just in this discussion and what could have been done good to improve the current framework instead makes me sad.
@andrewackerman
The problem is that, where JSX was built on a weakly-typed dynamic language like JavaScript, DSX is being built on a strongly-typed static language like Dart.
Sorry, but this isn't a problem. Furthermore, this doesn't make any sense at all. Beside of that, we use JSX with TypeScript.
@escamoteur absolutely!
@escamoteur I'm with you on this one. _The 100._
@Bessonov
Sorry, but this isn't a problem. Furthermore, this doesn't make any sense at all. Beside of that, we use JSX with TypeScript.
React wasn't designed for TypeScript. It was designed for Javascript. All the widget definitions, attributes, properties, and everything else was designed to be used in the dynamic environment of JavaScript, so the type safety of TypeScript doesn't introduce any new factors with how JSX interacts with React. This is yet another example of how JSX was designed for a completely different setting than what Flutter is.
@andrewackerman
Why do you think it does matter? JSX is a way to describe interface. It's language agnostic on it's own. Look here. It's not JavaScript. But well, why it can't be done with JSX? (Beside there is no implementation of this (yet))
And.. you know... flow come from fb too:
Flow is a static typechecker for JavaScript.
Please, stop selling arguments for and against extensions you've never use. I use JSX every day and I'm happy with it ATM, although I was very skeptical about it. I can imagine, that JSX evolves in other patterns, like it was with AngularJS.
And maybe this topic helps to find better pattern for Dart? DSX is just one proposal. Look at builder pattern example above or other language tweaks presented here. And, well, maybe your flui is a better way? I don't know. But let's find it out and help to each other to improve their suggestions instead of discussing about bad things in someones else proposal.
I would like to propose close this topic and open new umbrella topic with limited conversation. All proposals to improve the way, how flutter may be used, discuss in own topics objectively with love and without hate.
Yeap, the amount of hate here is epic, just consider this:
There are 3587 open tickets, if you sort them by "thumbs down" you get
1 (this one) with 57 "thumbs down"
3586 (other tickets) with 1 or less "thumbs down"
@Bessonov
Why do you think it does matter? JSX is a way to describe interface. It's language agnostic on it's own. Look here. It's not JavaScript. But well, why it can't be done with JSX? (Beside there is no implementation of this (yet))
It's a way to describe UI _in Javascript_ (hence the "JS" part of the name). And no, since it's an inlined DSL, it is _not_ language-agnostic. And even if it was, that still doesn't make it the "better choice", since there are plenty of truly language-agnostic DSLs out there that would be woefully inadequate for UI declarations.
And.. you know... flow come from fb too:
Flow is just like TypeScript: a static type checking system for Javascript. It is not a React tool, nor was React designed to be used with it. React is first and foremost a Javascript library, and JSX was designed to be used with React. Whatever secondary tools and utilities get introduced into React development are ultimately irrelevant to React+JSX interoperability.
Please, stop selling arguments for and against extensions you've never use. I use JSX every day and I'm happy with it ATM, although I was very skeptical about it. I can imagine, that JSX evolves in other patterns, like it was with AngularJS.
I have used JSX, and though I do have personal opinions of it, I have deliberately left those opinions out of this discussion. In fact, had you read my previous comments, you would know that I had praised JSX for revolutionizing UI development in React. Other than some mildly tangential comments I've made about the market penetration of JSX as a whole, my arguments have been specifically about JSX _in Flutter_. And on that topic, there is no practical basis to determine the efficacy of DSX, so all we can do is examine how JSX has been implemented in other places, and that examination does not bode overly well.
Unless, of course, you've been using DSX every day as well and can enlighten us on the practical advantages of using DSX in Flutter?
And maybe this topic helps to find better pattern for Dart? DSX is just one proposal. Look at builder pattern example above or other language tweaks presented here. And, well, maybe your flui is a better way? I don't know. But let's find it out and help to each other to improve their suggestions instead of discussing about bad things in someones else proposal.
_That is what I'm doing._ DSX is being proposed as a UI solution for people familiar with JSX. There are key design elements in JSX that were intended to be used for an environment completely different from Dart and Flutter. _Those differences need to be addressed for DSX to be successful._ I am not being a _hater_. I'm trying to promote constructive discussion and ask the important questions. Yet all the responses I've been getting has amounted to subjective tautology ("JSX is good because it's the future, and it's the future because it's good"), dismissive hand-waving of crucial design points ("DSX does not need to account for differences between JS and Dart because there aren't any"), or just plain hostile ("You obviously don't like JSX so stop talking about DSX").
You do not make a successful product solely with unadulterated praise. It needs to stand up to and account for criticism as well. People showing up and saying "OMG yes please, make DSX", while uplifting, is not helpful. There have been several people throughout this thread that have brought up perfectly valid criticisms of DSX, both with its initial design and with the concept as a whole. And for the most part, many of these criticisms have yet to be directly addressed, with the general attitude being dismissive.
My only fear is that all this unconditional love for JSX is preventing people from viewing DSX objectively. I get why you guys want something like JSX in Flutter, and I can relate - my opinion that Flutter needs a dedicated UI DSL is what lead me to create flui. But if the only people allowed to talk about DSX are the people who have nothing but good things to say about it, then it _will_ fail.
Can we recenter the discussion on this topic?
In fact, I don't see any reason to keep this issue open.
Dart team stated that they have other priorities. And the pro JSX side volunteered to make their own DSX implementation
Maybe we should just have a few open source repository proposing different solutions (even barely working). Such as DSX, or templates.
And then consider redirecting from Flutter's readme or awesome_flutter to these repos. And if there's anything blocking a DSX implementation, create another issue with the specifics.
Then let the community do its job.
Leave it opened as is because people will continue to open new tickets asking for JSX (as it has already happened twice before).
Leave it open as is because people will continue to open new tickets asking for JSX (as it has already happened twice before).
The difference here is that we would now be able to answer with the following :
"We don't plan on implementing this in dart/flutter for now. But you can take a look at community alternatives [here] and [there] or read [this issue]"
and close the issue as duplicate.
One place for comments and votes and it is here. The request for JSX-like functionality is not going away and the ticket is opened because it needs Flutter tools support (compiler & VS Code IDE) and I have updated the ticket request with this info (first comment). If an enormous number of people starts asking for this, it will give the Flutter team incentive to put resources into it.
Looks like most of the controversy here is not around JSX at this point, but DSX. I'd suggest splitting DSX discussion into it's own thread and leave this one generic to JSX.
In the end DSX is just one way of getting something closer to JSX so we shouldn't be mixing these two discussions in one thread regardless.
Big no for this, i really think that 1 language only is a big gain, jsx syntax will come with more things like separation of xml from js, etc... Not good.
thats my opinion.
That's the longest and pointless Github issue I ever seen.
@cbazza Good job 👍
DSX + 1
@BarryYan, Thank you
Please avoid this kind of comment, be it "+1" or "Thanks".
This sends an email to all subscribers for nothing interesting.
Please avoid this kind of comment, be it "+1" or "Thanks".
This sends an email to all subscribers for nothing interesting.
Nothing interesting to you !!!
Please avoid telling people what they can say or do and focus only on what you can say or do.
@cbazza
Dude, it's basic etiquette. Any new message on this thread emails everyone subscribed to it, so it's rude to post comment that doesn't contribute to the discussion because it annoys people for no reason. Basic reactions like "+1" and "Thanks" can be conveyed with a simple thumbs up reaction, so just do that.
That being said, if this thread has really devolved into arguing over whether someone should or shouldn't post a "+1" message, that's a big red flag that all constructive discussion has officially died, and it really should be closed (perhaps permanently this time).
@andrewackerman,
Got it but while you are at it perhaps you should also consider basic etiquette while blasting this thread with your novels (long & fictional writing).
Please stop spreading FUD (fear uncertainty & doubt) with your spray-and-pray barrage of senseless questions (you know, throw as much crap on the wall and see if anything sticks) and demands.
After all your writings you haven't added any value to DSX so I have no interest having a discussion with you on this subject. Your motive is obvious though, promote FLUI while blasting DSX.
Tell me something, do you have answers to your own questions when they are applied to FLUI? Let's discuss FLUI for a bit shall we?
@cbazza
Got it but while you are at it perhaps you should also consider basic etiquette while blasting this thread with your novels (long & fictional writing).
The fact that you refer to my responses that I put a lot of time and effort into being as well-thought-out and unbiased as I can make them as "long & fictional writing" illustrates a lot about your character and how you are approaching this discussion. I'm trying to promote discussion regarding very real issues surrounding any implementation of JSX in Flutter, while you lambast anyone with any form of contrary opinion. Which of us is the bigger offender of basic etiquette?
Please stop spreading FUD (fear uncertainty & doubt) with your spray-and-pray barrage of senseless questions (you know, throw as much crap on the wall and see if anything sticks) and demands.
The only thing I am "demanding" is that you address the numerous issues brought up by many people regarding DSX with more than either a hand-wave or open hostility. For someone who is proposing a significant change/addition to Flutter's feature set, I feel like that's not an unreasonable expectation.
After all your writings you haven't added any value to DSX so I have no interest having a discussion with you on this subject. Your motive is obvious though, promote FLUI while blasting DSX.
I'm asking _you_ to defend your position. You've repeatedly said that JSX/DSX is the best/future, but have yet to explain how or why. Several people have expressed valid concerns about DSX, but instead of addressing them, you wave it off by hiding behind the counterargument "if you don't like it, don't use it". My "motive" is to get you to answer questions that need to be asked regarding _any_ technical project, first and foremost being why people should ever use it over the alternatives. (And as I have explained before, familiarity is not a good enough reason.)
As far as FLUI is concerned, all I am doing is proposing an alternative solution to the overall problem (UI declarative syntax for Flutter) while requesting that people do the same to it that I am doing to DSX - offer sincere and constructive criticism. I am not saying that FLUI is objectively better than DSX - I'm proposing an alternative formed from a different approach to UI development and asking people to form their own opinions.
(I'd also like to point out that, other than my initial mention where I was proposing a possible alternative approach to GUI representation, the only times I've ever even talked about FLUI is when you brought it up. So how does it makes sense that my ulterior motive is to promote it when you are talking about it more than I am?)
Tell me something, do you have answers to your own questions when they are applied to FLUI? Let's discuss FLUI for a bit shall we?
FLUI is not DSX - it doesn't have to answer _every_ question that I posed to you regarding DSX because many of them are specific to DSX's design. That's not to say that it doesn't have its own set of questions that need to be answered, though, and no, I don't have all those answers. That's _why_ I value critical discussion - FLUI/DSX aren't going to stand up to the court of public opinion unless they can survive getting raked across the coals a couple times. This is not the appropriate place to discuss FLUI though. If you want to discuss FLUI at length, the project has its own issue board, so feel free to post there.
Instead of responding to criticism, you've instead been defensive and evasive, so much so that you are directly responsible for the two separate occasions (approaching three) where this thread had to be temporarily closed due to things getting too heated. So I'm going to break from "etiquette" and say this once: shelf your ego, stop interpreting criticisms as personal attacks, and answer the important questions. Either that, or make peace with DSX never getting off the ground.
andrewackerman Good job 👍
+ 1
@andrewackerman
Good job
Dude, you get a compliment from @jstansbe which conveys a lot more information than a thumb up and you thumb down on the compliment?
Obviously you didn't take my hint on length to heart but don't come to conclusions about my character because you don't know me at all.
The fact that you refer to my responses that I put a lot of time and effort into being as well-thought-out and unbiased as I can make them
That I appreciate and I read all your 'long writings', answering everything: no way, but when I answer properly you don't understand my answer and concludes that I am being dismissive.
It is obvious to me that you are not very experienced with JSX, you really don't understand how it works. So instead of doubling down just own it and I'll explain it in more detail. For example JSX & DSX only does the following 2 transforms (mentioned several times before):
(1)
<A property="a" />
becomes
new A(property: a)
(2)
<A property="a">
<B />
<C />
</A>
becomes
new A(property: a, children: <Widget>[new B(), new C()])
Everything else is handled by the host language, so for example: how does it handle import of components named the same; answer: host language. I am not being dismissive, it is the way it is designed and the source of it's strength. You see if you separate markup and programming into separate files, you start to duplicate the programming inside the markup with simple constructs for 'if', etc. You end up building a declarative programming language inside the markup that can never be as powerful as the main programming language. So by bringing the markup into the programming language you have the best of both worlds and that's the power of JSX/DSX.
Notice above on (2) that the transform hardcoded <Widget>
and that's not always the case, so now you can specify that if needed as discussed before. Look at the transforms and now all symbols come from source or can be specified so there won't be some major magic gotchas in the future.
while you lambast anyone with any form of contrary opinion.
That's not true, you can have contrary opinion but you can't claim something true when I can proof otherwise.
For someone who is proposing a significant change/addition to Flutter's feature set, I feel like that's not an unreasonable expectation.
But that's the thing, I wanted the Flutter team to implement DSX but then I did it so what they need to implement is generic stuff that doesn't depend on DSX and DSX is not the only beneficiary. The browser js engine supports source maps which enabled an ecosystem of new languages in the browser that transpiled to js; it enabled the creation of Dart !!! and several others (Coffeescript, Typescript, Reason, etc). Dart could do the same now and benefit from the ecosystem that it helps bring up, all boats rise.
I'm asking you to defend your position.
I've already done it many times and the conclusion is that Plain Dart or DSX comes down to user preference; and the important thing is to provide option instead of forcing people one way.
first and foremost being why people should ever use it over the alternatives.
I would use DSX because I prefer it, like spaces or tabs, type definition before or after the variable name. There is no point fighting for it, just accept that people have different preferences; there is more than 1 programming editor out there right?
familiarity is not a good enough reason
Just your opinion, why do we use "if" statements in almost every language, 'for' statement, 'class', and now 'asyn/await'.
This is not the appropriate place to discuss FLUI though. If you want to discuss FLUI at length, the project has its own issue board, so feel free to post there.
Very good, now you gained my respect.
you are directly responsible for the two separate occasions (approaching three) where this thread had to be temporarily closed due to things getting too heated.
Thing is even if it gets closed again it won't stop people from asking for JSX-like capabilities.
shelf your ego, stop interpreting criticisms as personal attacks, and answer the important questions.
I have no ego but I do have short temper so there is no mistaking when someone pisses me off (it comes out right away). Not to offend you but your questions were not important.
Either that, or make peace with DSX never getting off the ground.
You are not the meter used to measure success and you don't know what I am up to.
Dude, you get a compliment from @jstansbe which conveys a lot more information than a thumb up and you thumb down on the compliment?
You apparently didn't pick up on the sarcasm inherent in his comment. (He literally did everything I said not to do.) While a fun bit of trolling that I can appreciate, it's not appropriate here. And if, by chance, he was being sincere, then I apologize for my snideness, but my point still stands - that kind of comment is _still_ not appropriate here.
It is obvious to me that you are not very experienced with JSX...
Did my disclaimer in my very first comment on this thread perhaps tip you off?
...you really don't understand how it works.
You equate me not having much experience with JSX and me not knowing how it works at all? While I've never worked on any serious React project, I've done my fair share of tinkering. I understand perfectly well how it _works_.
Everything else is handled by the host language, so for example: how does it handle import of components named the same; answer: host language.
And that makes sense in the case where the markup language and the host language are distinct. With JSX, the markup language is designed as an _extension_ of the host language. As such, JSX was designed as an extension of JS, and that's why it works as well as it does. DSX is an implementation of JSX for Dart.
You don't see the problem there? A markup language designed as an extension of one language being jerry-rigged into a foundationally different language. It is _inevitable_ for there to be a load of issues, edge cases, and considerations.
You see if you separate markup and programming into separate files, you start to duplicate the programming inside the markup with simple constructs for 'if', etc. You end up building a declarative programming language inside the markup that can never be as powerful as the main programming language.
First, the whole idea behind separating markup and programming is that, if you are doing it correctly, there is a clear separation between the two which results in _no_ duplication.
Secondly, if you are doing anything much more complex than if
s and for
s in your UI code (which are constructs that can easily be handled in many markup solutions), then I would argue that it's a sign there is something wrong in your design anyway. As per MVC/MVVM design principles, if you are incorporating complex logic in your UI constructs, that's a potential sign of smelly code and you should seriously consider a redesign anyway.
(That's not to say that you _can't_ write declarative UI in the MVVM fashion using JSX, but it's just something that invites trouble for little objective gain. Why use something in which you _can_ write code that is standards-compliant when you can use something that makes it difficult to write code that _isn't_?)
That's not true, you can have contrary opinion but you can't claim something true when I can proof otherwise.
You haven't "proved" anything. You've given a bunch of subjective claims that have yet to be backed up with any substantiating logic. (Though to your credit, this latest post is a big improvement.)
But that's the thing, I wanted the Flutter team to implement DSX but then I did it so what they need to implement is generic stuff that doesn't depend on DSX and DSX is not the only beneficiary.
You are still asking for them to do non-trivial stuff, so the onus is on you to convince them and the rest of us why they should and why it's so important that they should push down other things on their to-do list.
The browser js engine supports source maps which enabled an ecosystem of new languages in the browser that transpiled to js; it enabled the creation of Dart !!!
It is in the nature of JS itself that such a thing is easily doable (relatively speaking), so much so that Dart is far from the only language that has a transpiler to JS. As I have pointed out many times, Dart is not JS. It is static and strongly typed, meaning a lot of things that would be easy to do in JS are hugely complex in Dart.
I would use DSX because I prefer it, like spaces or tabs, type definition before or after the variable name. There is no point fighting for it, just accept that people have different preferences; there is more than 1 programming editor out there right?
By that logic, I should make a UI solution in which you define constructs using hex-encoded braille. I mean, if all that really matters is personal preference, all I need to say to defend its existence is that "some people prefer it", right?
You are developing a tool that you intend for other people to use, so you need reasoning beyond "some people might like it" to make yourself convincing. If you can't put it into words _why_ they should use it over something else, then what makes you believe that they will? And what's there to incentivize you to _ensure_ that they will when designing DSX's feature set?
Just your opinion, why do we use "if" statements in almost every language, 'for' statement, 'class', and now 'async/await'.
First, those keywords (aside from async/await
) became common programming lexicon because of the immense popularity of languages like C and BASIC over the course of several decades. As I've mentioned before, JSX is far from proven in its longevity - it's been around for 5 years and is yet to see any significant use outside of React despite the option being available.
Second, there's a big difference between familiarity and convention. if
, while
, for
, struct
, class
, enum
, try/catch/finally
, async/await
... those are all great ways to verbally represent a concept. There are reasons to defend using those keywords beyond them just being what people are familiar with - they make conceptual sense. (Of course, that doesn't mean that they are constants. Some languages do if ... then
. Some do if ... elif
while others do if ... else if
and still others do if...endif
. Some do foreach
, others do from
. And so on, and so forth.)
Meanwhile, the argument to use JSX because it is "familiar" doesn't fit the same category. JSX is one way to represent declarative UI, but it is neither the only one nor the most popular one. Furthermore, it was designed to be used in one type of environment, so using it in another environment can turn familiarity into a bad thing - familiarity leads them to expect it to work more or less exactly the same way it works elsewhere, so if it doesn't then that leads to a mental disconnect which is something that you want to _avoid_.
Thing is even if it gets closed again it won't stop people from asking for JSX-like capabilities.
They ask for it anyway, and the issue gets redirected here all the same. I don't see how the thread being closed would change that.
You are not the meter used to measure success and you don't know what I am up to.
Read any book about product design. Chapter one is always about creating a statement, a manifesto, a slogan, anything tangible and expressible in plain English that describes what the product is and why people should care about it. There's a reason that the most common form of advice given to amateur entrepreneurs is to make an "elevator pitch", something that clearly and concisely communicates the product and the draw in 30 seconds or less. If you can't put it succinctly why people should use your product, it's a sign that it's suffering from an identity crisis. If the person designing the product can't adequately respond to criticism, then that gives the impression of a lack of faith in their own product. Both of those things are big red flags to investors.
In this situation, the product is DSX, and the investors are developers considering using it. The only people you have backing you are people who apparently would unconditionally cheer on anything with "JSX" in the description. Every other person in this thread I have seen question what you are doing has walked away seemingly unconvinced following your answer.
You are currently sitting at or near a 0% conversion rate, and _that's_ where I'm coming from when I say that you have yet to adequately respond to criticism. Maybe you don't care, but if you seriously intend for DSX to be a UI declaration markup plugin usable and used in real-world projects, you might want to start.
But then again, maybe you are an exception.
Ok this conversation has gone well beyond the kinds of discussions that we consider acceptable in the Flutter community, and so I'm going to lock this thread and close the bug. Please consider reading https://flutter.io/design-principles/#conflict-resolution for more details on how we behave here.
The next step if anyone wants to contribute code to address this issue would be to come up with a design for how to do build system integration such that we can have code generation work with Gradle, Xcode, hot reload, and integration with existing apps. If anyone is interested in working on this, please don't hesitate to reach out to me. Otherwise I expect this is something we'll work on early next year. Once we have a mechanism to do that, solutions like DSX will be easy to integrate into the Flutter ecosystem. We may even find solutions that should be integrated by default. In the meantime we're also working on improvements to Dart's syntax to see if we can make UI expressions even easier to write.
I would like to ask that people do not open new bugs on this topic unless there is something very constructive and new that is worth bringing up.
Most helpful comment
Ok, so the "Basic widgets" example on 'https://flutter.io/widgets-intro/#basic-widgets' would look like the following: