Let's choose a view framework for docs, generated packages, etc. #5756

Open
thedaniel opened this Issue Feb 26, 2015 · 127 comments

Projects

None yet
@thedaniel
Contributor

(This is an attempt to restate #3752, explain the current position and present options)

A blessed view system for Atom

We're in an interesting place with respect to generating views in packages and core. We wrote space-pen and used it heavily, but ultimately decided to discontinue using it for new views (though some base views still use space-pen we are no longer recommending it). So now we find ourselves in an unfortunate position of using the DOM APIs directly, and suggesting package authors do the same, choose a framework themselves, or ╮(. ❛ ᴗ ❛.)╭ - Not a great place to be, and makes it hard to write docs with nice examples.

We used React in the editor component for six months or so, and it was a good experience, but it has a bit of a learning curve.

We experimented with a few things inspired by React and Polymer, and have done some research on 3rd-party view frameworks, but haven't come to a decision. As we work on better docs for the run up to 1.0, we have to start taking this seriously.

Requirements

  • Embrace modern browser features (custom elements, Object.observe, etc) as much as possible
  • It absolutely does not pollute the global namespace
  • Data-binding preferred to imperative updates if templates are used
  • View model / MVVM-style separation of rendering and logic
  • No dependencies on jQuery-like helper libs
  • Small learning curve
    • somewhat self-explanatory when used in docs examples
    • in other words, most web developers will be able to recognize the concepts that are applied without reading a book on it

Contenders / experiments

  • React
  • Etch - a library for writing HTML-based view components that provides the convenience of a virtual DOM while at the same time striving to be minimal, interoperable, and explicit - written by @nathansobo and @maxbrunsfeld
  • rivets for templating+data binding plus some basic JS object glue for Atom
  • television - "Television aims to cleanly integrate the virtual DOM approach of React.js into HTML 5 custom elements." - an experiment from @nathansobo
  • virtual-dom this library is used by television, but could be a component in a similar solution that accomplishes the above goals.
  • elmer - An experiment from @benogle based on Polymer's template binding
  • vue.js - simple, component-based, simple & small
  • Something custom, delightful & new from your friends the Atom team (but we don't reallllly want to maintain another view frameowrk)

Want to help?

One way to help speed this along is to do some experimentation with using your favorite framework in a package. See https://github.com/benogle/template-explore as an example package using https://github.com/atom/elmer.

A couple questions I would try to answer with the package:

  • How does it handle model/DOM updates? Data-binding? Imperative + virtual-dom like react?
  • How does it handle events? i.e. How do I bind a click handler to an element?
  • Can it work with Object.observe and not it's own model system?
  • Does it inject any globals?
  • How does it interact with web components, both in terms of creating new ones and using existing components written using different frameworks?

Discuss

We're interested in hearing the pros and cons of the various ways we can satisfy the items listed under requirements, recommendations for solutions we don't have listed, and questions about the reqs and how and why we arrived at them.

Also, I encourage @atom/core and maintainers to edit the Contenders section in the issue body as more come in, and let me know if I missed / misstated anything in Requirements

@mark-hahn
Contributor

That is good news. There was a vacuum for new package developers.

On Wed, Feb 25, 2015 at 6:38 PM, Daniel Hengeveld notifications@github.com
wrote:

(This is an attempt to restate #3752
#3752, explain the current position
and present options)
A blessed view system for Atom

We're in an interesting place with respect to generating views in packages
and core. We wrote space-pen https://github.com/atom/space-pen and used
it heavily, but ultimately decided to discontinue using it for new views (though
some base views still use space-pen
https://github.com/atom/atom-space-pen-views we are no longer
recommending it). So now we find ourselves in an unfortunate position of
using the DOM APIs directly, and suggesting package authors do the same,
choose a framework themselves, or ╮(. ❛ ᴗ ❛.)╭ - Not a great place to be,
and makes it hard to write docs with nice examples.

We used React in the editor component for six months or so, and it was a
good experience, but it has a bit of a learning curve.

We experimented with a few things inspired by React and Polymer, and have
done some research on 3rd-party view frameworks, but haven't come to a
decision. As we work on better docs for the run up to 1.0, we have to start
taking this seriously.
Requirements

  • Embrace modern browser features (custom elements, etc) as much as
    possible
  • recognizable markup (allow users to write 'normal HTML')
    • data binding preferred to imperative updates if templates are used
      • View model / MVVM-style separation of rendering and logic
  • Easy for developers to replace with another preferred library
    • this implies not polluting the global namespace
      • No dependencies on jQuery-like helper libs
  • Small learning curve
    • somewhat self-explanatory when used in docs examples
    • in other words, most web developers will be able to recognize the
      concepts that are applied without reading a book on it

Contenders / experiments

Discuss

We're interested in hearing the pros and cons of the various ways we can
satisfy the items listed under requirements, recommendations for solutions
we don't have listed, and questions about the reqs and how and why we
arrived at them.

Also, I encourage @atom/core https://github.com/orgs/atom/teams/core
and maintainers to edit the Contenders section in the issue body as more
come in, and let me know if I missed / misstated anything in Requirements


Reply to this email directly or view it on GitHub
#5756.

@steelbrain
Contributor

I am using vanilla-jsx, it supports JSX but it spits out native HTML Elements so it's performant and lightweight

@mindeavor

Mithril.js saved JavaScript for me. Like many others frameworks/libraries it uses a virtual DOM, but most importantly it's just JavaScript. No JSX, no OOP, no arbitrary html-ish templating languages. Once you learn its five or so core methods, you're free to think and do anything JavaScript without Mithril getting in the way.

@mark-hahn
Contributor

no arbitrary html-ish templating languages

I think there should be a blessed template syntax as per the "recognizable
markup" requirement. I want to be able to easily read other package's
code.

IMHO it should be a simple noise-free template syntax like that of
space-pen.

On Wed, Feb 25, 2015 at 8:02 PM, Gilbert notifications@github.com wrote:

Mithril.js http://lhorie.github.io/mithril/index.html saved JavaScript
for me. Like many others frameworks/libraries it uses a virtual DOM, but
most importantly it's just JavaScript. No JSX, no OOP, no arbitrary
html-ish templating languages. Once you learn its five or so core methods,
you're free to think and do anything JavaScript without Mithril getting in
the way.


Reply to this email directly or view it on GitHub
#5756 (comment).

@thedaniel
Contributor

IMHO it should be a simple noise-free template syntax like that of space-pen.

This conflicts with the second requirement listed - I personally am strongly against anything like space-pen's syntax, or HAML, and I believe the rest of the team either doesn't feel strongly, or prefers that if we use templates at all we do data binding + templates similar to Polymer: https://www.polymer-project.org/docs/polymer/databinding.html

I'll let them chime in, but I wouldn't get your hopes up for something space-pen-like.

@mark-hahn
Contributor

I personally am strongly against anything like space-pen's syntax, or HAML

I don't see how Atom could bless coffeescript and not Space-Pen syntax. They are one and the same.

I know we have to use an existing solution so there probably won't be such a syntax available but I would certainly argue for matching coffeescript if we could.

@benogle
Contributor
benogle commented Feb 26, 2015

recognizable markup (allow users to write 'normal HTML')

This is definitely not a requirement. Television, for example is more space-pen-like (and even more react like, minus the jsx). I personally like the markup better than the code-like definition, but it's not a requirement.

Easy for developers to replace with another preferred library; this implies not polluting the global namespace

The global namespace issue is a super hard requirement. Not really for ease of switching, but for playing nice with other versions of the framework, and with other frameworks.

We basically want the option of more than one framework to be used as a dep. That way we're relatively future proof. When the next react or whatever comes along, we can use it by including it as a dependency.

@mark-hahn
Contributor

The television link is a 404.

@benogle
Contributor
benogle commented Feb 26, 2015

@mark-hahn it should work now. Sorry about that

@thedaniel
Contributor

Perhaps I let my opinions leak into the requirements - we're evaluating some options that don't use normal markup in their templates. I still think it's very prudent from a docs perspective but I'll move it out of the issue body and into "thedaniel's suggestions in the comments" since it's not actually a hard requirement.

@mark-hahn
Contributor

Television looks awesome. It looks cleaner and less-noisy than space-pen. And the custom element handling seems simple, even to a luddite like me. I think it would be accessible to beginners.

@lhorie
lhorie commented Feb 26, 2015

Mithril's out of the box syntax is very similar to virtual-dom/television, but you can also get HTMLy syntax via MSX (basically the same thing as React's JSX) if curly braces are important.

There's also SugarTags for a different flavor of code-like definitions.

@lee-dohm
Member

I like the template+data-binding approach. I think it would be awesome if the template language was pluggable so if people wanted something more HTML-like, they could have it, closing tags and all. And if they wanted something simplified a la HAML/Jade/Slim, they could have that too.

@benogle
Contributor
benogle commented Feb 26, 2015

If anyone out there is interested, one way to help speed this along is to do some experimentation with using your favorite framework in a package. See https://github.com/benogle/template-explore as an example package using https://github.com/atom/elmer.

A couple questions I would try to answer with the package:

  • How does it handle model/DOM updates? Data-binding? Imperative + virtual-dom like react?
  • How does it handle events? i.e. How do I bind a click handler to an element?
  • Can it work with Object.observe and not it's own model system?
  • Does it inject any globals?
@nathansobo
Contributor
  • How does it interact with web components, both in terms of creating new ones and using existing components written using different frameworks?
@benogle
Contributor
benogle commented Feb 26, 2015

I added a section in the body about helping out and answering these questions.

@nathansobo nathansobo self-assigned this Feb 26, 2015
@benogle
Contributor
benogle commented Feb 26, 2015

I'm taking a look at Vue.

❤️ Thanks. I briefly looked at it to see if it supported Object.observe, but iirc it didnt right now, and was not clear how to hack it in.

@lee-dohm
Member

🙇 You're welcome. This is my opportunity to dig deeper into the DOM and rendering, so I figured I'd give it the good ol' college try. I'm currently running into unsafe eval issues, but I'll take another crack at it later tonight.

@wmertens

Things that make me prefer React:

  • largest community of the proposed options
  • battle-tested with constant focus on performance
  • good dev tools: chrome devtools extension, webpack hotloader support etc.
  • JSX is optional and you can use television-like syntax as well
  • Plays well with immutability; statelessness gives you almost-free undo management and can really speed up your page draws while maintaining a simple concept for the code. For an example, see Goya (written in clojurescript on top of React) and the code it needed for undo management.
    • Note that if you embrace statelessness you don't need Object.Observe, or am I mistaken?
@Zireael07

Focus on performance? Me likey.

@mark-hahn
Contributor

This framework is for packages and almost no package has any performance
issues.

On Fri, Feb 27, 2015 at 11:03 PM, Zireael07 notifications@github.com
wrote:

Focus on performance? Me likey.


Reply to this email directly or view it on GitHub
#5756 (comment).

@wmertens

@mark-hahn Hmmm, I have like 40 packages installed. A lot of small slowdowns also results in a large slowdown... So I think that potential performance should be weighed as well.
For example, if I go to the dev tools timeline and record, I get a ton of timers fired and redraws every second, even though nothing changed and nothing is active. The timers are mostly from minimap which seems to poll the dom every 0.1s but doesn't turn off the polling when a pane is not active (I'll open a bug).
I'm just armchair programming here, but if immutability were used, the minimap would be only dependent on the editor text and the window position. Whenever either changes, it can re-render (and it would have both old and new versions available for diffing). No polling would be needed then.

@nathansobo
Contributor

@abe33 Would you consider switching mini-map to use atom.views.pollDocument to coordinate polling with the editor? It's currently an experimental API and it would be nice to get some external feedback on it. There's also atom.views.readDocument and updateDocument for coordinating reads and writes which may be of interest.

@mark-hahn
Contributor

. A lot of small slowdowns also results in a large slowdown...

I'm arguing that slowdowns aren't caused by the framework when the package is only working on a small part of the DOM, like a half-dozen divs.

I get a ton of timers fired and redraws every second, even though nothing changed and nothing is active.

If this is true then there should be a core API to consolidate these. I have asked before for the presenter to be able to be used by packages.

@kolya-ay
kolya-ay commented Mar 5, 2015

Regarding React alternatives there is a good thread on Reddit with comments from frameworks authors. The most mature Virtual DOM's implementations could be catched form Virtual DOM Benchmark project. Actually lot of full featured "frameworks" are based on the great virtual-dom library (mercury, aforementioned television, elm language to name a few).
Personally, I'm a huge fan of Mithril because of its internal elegance and simplicity. However its scope is a bit bigger than just a "view system". Besides view layer it embraces routing and Ajax wrapper which might be considered as a bloat for Atom

@johanlunds

FYI: I've been trying out Rivets.js for my first package: https://github.com/johanlunds/atom-ruby-debugger

Here are my impressions so far.

What I like:

  • simple and small, quick to learn
  • only view-layer
  • CoffeeScript, easy to read and understand. Simple implementation.
  • Good documentation
  • Integrates pretty nicely with Atom

What is difficult/what I don't like:

  • very limited
  • computed bindings (ie. function calls) is a bit difficult, and you have to declare the properties/attributes that the function depends on in your HTML-code
  • bindings have to be keypaths, they can't be JS-expressions
  • no {{ }} bindings in textContent or attributes, ie. <span>Hello {{ name }}<span>
  • no transclude à la Angular.js (although it's probably possible with custom "binders" or components that manipulate el)

It's possible to write an adapter to make it use Object.observe, but I haven't tried writing one yet and I couldn't find an existing one. Not 100% sure how to implement it.

Checklist: Requirements

  • Embrace modern browser features (custom elements, Object.observe, etc) as much as possible.

Answer: yes. Custom elements. Object.observe is possible with an adapter

  • It absolutely does not pollute the global namespace.

Answer: yes, it seems ok

  • Data-binding preferred to imperative updates if templates are used

Answer: yes, bindings to keypaths. No full JS-expressions in the templates

  • View model / MVVM-style separation of rendering and logic

Answer: yes, I guess so. You can declare your own components = custom elements that can have their own class = view model

  • No dependencies on jQuery-like helper libs

Answer: yes

  • Small learning curve.
    • somewhat self-explanatory when used in docs examples
    • in other words, most web developers will be able to recognize the concepts that are applied without reading a book on it

Answer: yes

Checklist: questions

  • How does it handle model/DOM updates? Data-binding? Imperative + virtual-dom like react?

Answer: It's very basic and a bit constrained. Not as full-featured as for example Angular or Vue.js I think. But the upside is that the implementation is simple. Data-binding: yes. Virtual-dom: no. I don't think DOM-updates are batched.

  • How does it handle events? i.e. How do I bind a click handler to an element?

Answer: use rv-on-click="model.function" in the HTML-template. It does not use event delegation I think

  • Can it work with Object.observe and not it's own model system?

Answer: yes

  • Does it inject any globals?

Answer: no

  • How does it interact with web components, both in terms of creating new ones and using existing components written using different frameworks?

Answer: Pretty sure that won't be a problem, but I haven't really tried

@mnquintana
Member

A few ideas:

  • Whatever we end up going with, I'd really like it to be something that encourages separation of the template from the controller / view model / glue logic (in separate files, really). Space Pen encourages the exact opposite of that - templates are smashed right into the logic for that template - and I've always found it really messy and unnecessarily confusing.
  • I'd really prefer a Component-based separation of concerns over an MVVM / MVC / MVW approach (if they are mutually exclusive at all, that is).
@wmertens

@mnquintana Actually, that was my original concern about React too - I have seen way too many crappy PHP apps. They always worked nicely but the code was a mess.

Turns out that if you write React code in a sane way, having your template together with your code is great. Most of the time you are not actually outputting HTML tags but custom elements that combine into what you need, and can have unit tests etc.

@lee-dohm
Member

I'd really like it to be something that encourages separation of the template from the controller / view model / glue logic (in separate files, really)

I'd agree with this as long as it is "encourages" and not "requires". One of the things that is awesome about Atom is that one doesn't have to write a package to create a simple command. One can just put some code into the init.config to experiment. But, when the code is ready, it can be wrapped up into a package. It is a gradual learning curve that has easy steps between each level.

As @mark-hahn has pointed out, I'd like there to be a simple way to create small packages with UI that doesn't require more than two files (template and code). And then an obvious transition (perhaps simply documented as best practices or advanced use) that allows people to build whatever abstraction is designed to be "the right way".

@Aedaeum
Aedaeum commented May 17, 2015

I know it's a bit bleeding-edge, but Aurelia seems to meet the described requirements. It does leverage Object.observe when it can. It's development seems just as active as Atoms and its devs are actively listening to the community on how to move forward.

  • two-way, one-way, only-once bindings
  • Leverages the shadowDOM (optional)
  • Custom Elements (with template's) and Attributes.
  • Tries to avoid dirty-checking in favor of Object.observe
  • Uses systemjs and jspm for a truly modular experience
  • Pure ES6 syntax support with Babel

I'm currently using it in a project of mine and I feel like this could be the big one to replace all the major frameworks out there. This of course is coming from someone who doesn't have a lot of experience with Angular/React frameworks. The closest I've gotten to MVC is Knockout. That being said, the creator of Aurelia was part of the Angular team, whom felt that their (new) philosophy wasn't in line with his own, thus the birth of Aurelia.

Currently the only pitfall it has right now is its lack of documentation, but that's indicative of its current age. It's still very much a WIP. However, I see Atom in the same light as I see Aurelia. Both share a quick development life-cycle and testing is essentially community driven. Bugs are found because of the community. I understand that sharing a philosophy alone isn't enough to decide adoption, but it's good incentive right?

Here are some links
Aurelia.io
Docs
Example app
on Github
Discussion platform

Let me know what you think 😄

@devmondo

another vote for Aurelia 👍

@mark-hahn
Contributor

Does Aurelia work well with coffeescript?

I'm in the middle of a project using Vue. I am impressed with it's
simplicity and bindings. I started the same project with rivets and
ampersand before. They were hard for me to understand. I spent two days
on each before trying Vue. It works great with coffeescript.

On Sun, May 17, 2015 at 11:33 AM, Feras Khoursheed <notifications@github.com

wrote:

another vote for Aurelia [image: 👍]


Reply to this email directly or view it on GitHub
#5756 (comment).

@thomasjo
Member

Aurelia seems much too heavy for the specific use case at hand. It's basically an entire application framework. We only want views (and perhaps some form of model binding). We definitely do not need routing, dependency injection, and what not. At least from my initial investigation I'm 👎 on Aurelia.

@mnquintana
Member

So, I definitely understand why React didn't work out for the editor component, but is there any reason why React wouldn't work for these other use cases?

@thomasjo
Member

Well, this issue is about finding a view framework, not an application framework. I have done zero work with React, but if it's possible to only use the view bits, then it's at least worth investigating. But I'm really against pulling in some huge framework in order to only use it's view (and model binding) aspect.

@thomasjo
Member

And this isn't really meant for core itself (from my understanding), this issue is targeting code examples, documentation etc, and is meant as the officially sanctioned recommendation for a view framework. That's why I think it's important whatever we choose should only be a view framework, to ensure we don't give people false ideas about routing and what not.

Just my thoughts anyway.

@mark-hahn
Contributor

We only want views (and perhaps some form of model binding).

This is pretty much an exact description of Vue. And it's binding is
top-notch transparent 2-way binding that uses the latest JS features. The
views and components are also quite nice.

It can do a lot with a small amount of code. Check out the home page ...
http://vuejs.org/guide/

On Sun, May 17, 2015 at 12:23 PM, Thomas Johansen notifications@github.com
wrote:

And this isn't really meant for core itself (from my understanding), this
issue is targeting code examples, documentation etc, and is meant as the
officially sanctioned recommendation for a view framework. That's why I
think it's important whatever we choose should only be a view framework, to
ensure we don't give people false ideas about routing and what not.

Just my thoughts anyway.


Reply to this email directly or view it on GitHub
#5756 (comment).

@mnquintana
Member

Well, this issue is about finding a view framework, not an application framework. I have done zero work with React, but if it's possible to only use the view bits, then it's at least worth investigating. But I'm really against pulling in some huge framework in order to only use it's view (and model binding) aspect.

I'm totally with you on that, but my understanding (also as someone who has yet to do anything with React – I'd love to have an excuse to play with it though 😄) is that React is just view bits, not a full application framework (although the community has built libraries around it that effectively transform it into one).

And this isn't really meant for core itself (from my understanding), this issue is targeting code examples, documentation etc, and is meant as the officially sanctioned recommendation for a view framework.

Right, that makes sense, although honestly many, many core packages would benefit from one of these view frameworks too (since most of those UIs are written imperatively with jQuery, with some Space Pen magic).

@thomasjo
Member

Right, that makes sense, although honestly many, many core packages would benefit from one of these view frameworks too (since most of those UIs are written imperatively with jQuery, with some Space Pen magic).

My understanding is that everything in core will eventually move to custom DOM elements, but I might be mistaken.

but my understanding [..] is that React is just view bits, not a full application framework

Well if that's the case, then it would seem like a decent candidate. I need to check out both Vue and React it seems!

@Aedaeum
Aedaeum commented May 17, 2015

One of the benefits of Aurelia is also that it doesn't leverage jQuery or any such other libraries other than the ones I mentioned. I understand that if all you want is the MV aspect, Aurelia might be a bit too all-encompassing.

@wmertens

I'm a big React fan, it's easy to learn and pretty lightweight. It can be
used as a view framework only without issues.

The only problem is that it's not a great idea to load two versions of
React in the same app, at least not currently, see
facebook/react#2402

So that means that everything should use the same React version, or the
different versions should not touch each other's elements.

On Sun, May 17, 2015, 9:35 PM Aedaeum notifications@github.com wrote:

One of the benefits of Aurelia is also that it doesn't leverage jQuery or
any such other libraries other than the ones I mentioned. I understand that
if all you want is the MV aspect, Aurelia might be a bit too cumbersome.


Reply to this email directly or view it on GitHub
#5756 (comment).

@wmertens

Very interesting, a 10kb alternative to React:
https://segment.com/blog/deku-our-functional-alternative-to-react/

On Sun, May 17, 2015, 11:29 PM Wout Mertens wout.mertens@gmail.com wrote:

I'm a big React fan, it's easy to learn and pretty lightweight. It can be
used as a view framework only without issues.

The only problem is that it's not a great idea to load two versions of
React in the same app, at least not currently, see
facebook/react#2402

So that means that everything should use the same React version, or the
different versions should not touch each other's elements.

On Sun, May 17, 2015, 9:35 PM Aedaeum notifications@github.com wrote:

One of the benefits of Aurelia is also that it doesn't leverage jQuery or
any such other libraries other than the ones I mentioned. I understand that
if all you want is the MV aspect, Aurelia might be a bit too cumbersome.


Reply to this email directly or view it on GitHub
#5756 (comment).

@paulpflug

I'm currently looking into some view frameworks for another project.
Main feature should be good readability and thus maintainability.
I think a strong declarative syntax is a must, which includes two-way-binding (as the project relies heavily on user input - similar to atom ;)
Custom elements / modularity is also very important I think.
So I looked at aurelia, vue and polymer (coming from angular).

The huge downside of aurelia is jspm. I think it could be possible to use only the view framework for your cause, but how to extract that could be troublesome. The conceptual logic/view separation is troublesome for me.

Polymer has nice performance in chrome, comparable to react (sadly I don't find the benchmark anymore), but pollutes the global namespace and relies on bower. The components already out there are nice, but probably useless for atom.

Vue has a nice approach on two-way-binding .. no dirty checking, but no object.observe either (at least what I can see). The components syntax is very similar to polymer. A downside is the low general adoption, although it looks well maintained. What I really like, is that I could use coffee/jade/stylus without problems..

so from my side a +1 for vue

@basarat
Contributor
basarat commented Jun 3, 2015

FWIW I really want something that is reliably statically analyzable (and verifiable). JSX seems to be the defacto html -> function calls (similar to space pen dsl) thing out there. And react is its biggest consumer. So 👍 on react.

@paulpflug

I'm not sure how, the mostly very tiny?, packages will benefit from that?

Am 3. Juni 2015 09:51:28 schrieb Basarat Ali Syed notifications@github.com:

FWIW I really want something that is reliably statically analyzable (and
verifiable). JSX seems to be the defacto html -> function calls (similar
to space pen dsl) thing out there. And react is its biggest consumer.


Reply to this email directly or view it on GitHub:
#5756 (comment)

@basarat
Contributor
basarat commented Jun 3, 2015

@paulpflug even small packages have big UI sometimes. That said I'm not entirely sold on react either

@paulpflug

I'm in the middle of a project using Vue. I am impressed with it's
simplicity and bindings. I started the same project with rivets and
ampersand before. They were hard for me to understand. I spent two days
on each before trying Vue. It works great with coffeescript.

@mark-hahn did you publish your tests somewhere? Could you point me to it? I would love to read them.

@mark-hahn
Contributor

@mark-hahn https://github.com/mark-hahn did you publish your tests
somewhere?

They weren't tests. I just started using them with a project I was
starting. I guess I could dig out my git repos but you will just see my
aborted code. The problem was with my inability to get up to speed with
how they work.

For example. Ampersand had a sample project that was gigantic and assumed
I knew a bunch of other technologies. Their forum was just a IRC kind of
discussion. I don't remember my rivets problem at the moment.

I consider the learning curve to be very important for Atom developers.
Web developers should be able to hit the ground running when they do their
first package.

Vue has a very simple method of connecting the DOM and the model. The code
is easy to understand and is minimal.

On Thu, Jun 4, 2015 at 2:50 AM, Paul Pflugradt notifications@github.com
wrote:

I'm in the middle of a project using Vue. I am impressed with it's
simplicity and bindings. I started the same project with rivets and
ampersand before. They were hard for me to understand. I spent two days
on each before trying Vue. It works great with coffeescript.

@mark-hahn https://github.com/mark-hahn did you publish your tests
somewhere? Could you point me to it? I would love to read them.


Reply to this email directly or view it on GitHub
#5756 (comment).

@paulpflug

Ok. I misunderstood . I thought, that you wrote a atom package with vue..

I tried now to use vue, but it doesn't work. Vue's object.observe alternative relies on unsafe eval, so atom refuses to use it - sadly.

On a side node: jade also uses unsafe eval for compilation, which excludes it from using it at runtime - equally sadly.

maybe we should add "no eval" to the requirements list? if it is a strict requirement?

@paulpflug

I was wrong, Vue has a csp version without eval.

I played a little with it and created a boilerplate for a package using vue here

So far I like it. To use components, there has to be a compilation step, which should not occur at runtime cause it is slow. But besides that, there is no downside visible for me.

Especially two-way binding is good to have 😄

Questions

How does it handle model/DOM updates? Data-binding? Imperative + virtual-dom like react?

One and two-way data-binding.

How does it handle events? i.e. How do I bind a click handler to an element?

<button v-on="click: func"></button>
#in model:
methods:
  func: -> alert "clicked"

Can it work with Object.observe and not it's own model system?

no

Does it inject any globals?

no

How does it interact with web components, both in terms of creating new ones and using existing components written using different frameworks?

most definitely needs converters.
this is what a raw vue-component looks like:

var __vue_template__ = "<h1>Hello World!</h1>";
module.exports = {
  data: function() {
    return {
      someData: ""
    };
  },
  methods: {
    someFunction: function(){}
  }
};
;(typeof module.exports === "function"? module.exports.options: module.exports).template = __vue_template__;
@steelbrain
Contributor

After using react for months, and inventing my own virtual DOM library and struggling with AngularJS, RiotJS, Polymer and others.
I've ended up on the vanilla API. It's fast as hell, the custom elements just make it so appealing, You feel free of limitations when writing code in vanilla. The only downside is that the codebase increases, but I say it's totally worth it!

So my vote goes for Custom Elements.

@ibnesayeed ibnesayeed referenced this issue in codingtwinky/atom-ungit Jun 7, 2015
Open

Should Atom-Ungit use Space Pen #37

@mark-hahn
Contributor

So my vote goes for Custom Elements.

They are hard for newbies. It is important that users are encouraged to
write packages.

On Sun, Jun 7, 2015 at 6:25 AM, Steel Brain notifications@github.com
wrote:

After using react for months, and inventing my own virtual DOM library and
struggling with AngularJS, RiotJS, Polymer and others.
I've ended up on the vanilla API. It's fast as hell, the custom elements
just make it so appealing, You feel free of limitations when writing code
in vanilla. The only downside is that the codebase increases, but I say
it's totally worth it!

So my vote goes for Custom Elements.


Reply to this email directly or view it on GitHub
#5756 (comment).

@mark-hahn
Contributor

To use components, there has to be a compilation step, which should not
occur at run-time cause it is slow.

Can you quantify the slowness? I'm compiling at run-time and I have
noticed no delays. There isn't any code to trigger it. It happens
automatically.

Even if it is slow, we are only talking about using it in packages, not
core. If someone has a hot spot, like responding on each keystroke, they
can use custom elements.

On Sun, Jun 7, 2015 at 10:10 AM, Mark Hahn mark@hahnca.com wrote:

So my vote goes for Custom Elements.

They are hard for newbies. It is important that users are encouraged to
write packages.

On Sun, Jun 7, 2015 at 6:25 AM, Steel Brain notifications@github.com
wrote:

After using react for months, and inventing my own virtual DOM library
and struggling with AngularJS, RiotJS, Polymer and others.
I've ended up on the vanilla API. It's fast as hell, the custom elements
just make it so appealing, You feel free of limitations when writing code
in vanilla. The only downside is that the codebase increases, but I say
it's totally worth it!

So my vote goes for Custom Elements.


Reply to this email directly or view it on GitHub
#5756 (comment).

@paulpflug

I'm sorry, I wasn't specific enough: only the format described here needs a (slow) compilation step.
I love the capsulation it allows, though.

@mark-hahn
Contributor

The only complaint I have about components is that if you use the component
registry they are all stored globally in one namespace. Of course I can
fake namespaces by putting the module name at the beginning of every
component name.

On Sun, Jun 7, 2015 at 11:36 AM, Paul Pflugradt notifications@github.com
wrote:

I'm sorry, I wasn't specific enough: only the format described here
https://github.com/vuejs/vue-component-compiler needs a (slow)
compilation step.
I love the capsulation it allows, though.


Reply to this email directly or view it on GitHub
#5756 (comment).

@paulpflug

I'm currently still learning vue, but it seams pretty well crafted.
You don't have to register a component globally

# just the creation
aComponent = Vue.extend({
  template: "<div></div>"
  data: #stuff
})

# global registration
Vue.component "a-component", aComponent

# local registration
vueObj = new Vue({
  #stuff
  components:
    'a-component': aComponent
})

# inline creation:
vueObj = new Vue({
  #stuff
  components:
    'a-component': 
      template: "<div></div>"
      data: #stuff
})
@yyx990803

Vue author here and happy to answer any questions.

Re interop with Web Components - it is possible to package Vue compoents as real custom elements with vue-element.

@benogle benogle referenced this issue Jun 12, 2015
Closed

Atom 1.0 #3684

18 of 25 tasks complete
@isiahmeadows

Mithril does have some baggage, but it's still relatively small (the entire framework fits reasonably into a single file). Although, it may become more interesting if lhorie/mithril.js#665 is accepted.

@mike-engel

I'd like to throw in Ampersand.js into the mix. I've found it easy to learn, easy to write markup (it uses the data-hook attribute), and it handles data very well. It's got no dependencies, and you only import the modules you need unlike backbone which you have to use everything.

@gavynriebau

I think knockoutjs could be a decent choice.

  • Very simple syntax
  • Small learning curve
  • Good readability
  • Well established (been around since 2010)

Example code (from package that, when finished, will delete matched lines):

Package link

https://atom.io/packages/delete-lines

ViewModel

utils = require './utils'
ko = require '../bower_components/knockoutjs/dist/knockout.debug.js'

module.exports =
class DeleteLinesView
  constructor: (serializedState) ->
    # Create root element
    @element = document.createElement('div')
    @element.classList.add('delete-lines')

    # Create observable values
    @editorText = ko.observable()

    # Load the HTML file then call ko.applyBindings to trigger data-binding.
    utils.loadHtmlIntoElement @element, '/html/delete-lines.html', () =>
      ko.applyBindings @

  # Returns an object that can be retrieved when package is activated
  serialize: ->

  # Tear down any state and detach
  destroy: ->
    @element.remove()

  getElement: ->
    @element

  onRemoveClick: =>
    text = @editorText() # Grabs the text from the editor using the "editorText" observable variable.
    console.log "onRemoveClick: #{text}"

View markup
click events are hooked up to "onRemove" function
text changes are hooked up to an observable variable "editorText"

<div>
  <section class="header">
    <span>Delete matching lines</span> <span class="subtle-info-message">Close this panel with the <span class="highlight">esc</span> key</span>
  </section>
  <div class="editor-wrap">
    <input id="delete-editor" type="text" data-bind="textInput: editorText" />
    <button id="delete-btn" data-bind="click: onRemoveClick" class='btn'>Delete</button>
  </div>
</div>
@nathansobo nathansobo removed their assignment Jul 23, 2015
@Galadirith Galadirith referenced this issue in Galadirith/magnetite Jul 29, 2015
Open

[INFO] using BrowserWindow from electron #1

@mangecoeur

This is an issue - I've just been using space-pen and i really like the coffeescript DSL.

my 2cents on frameworks

  • whatever is used has to be just as happy in Coffeescript as in plain JS
  • Atom plugins are not web pages - you want to extend existing or add chunks of UI (possibly including other chunks of pre-built UI widgets). Full stack frameworks (angular/knockout etc) are not really a good fit.
  • You aren't really concerned with updating all sorts of crazy things happening around the page (you're not implemeting FlipBoard!) - most of the high-perf stuff is in the core, plugins use it but don't implement it, so probably data binding, virtual dom, and all these optimizations are a bit overkill.
  • atom has the luxury of guaranteeing support for cutting edge HTML features - lets take advantage of them. E.g. we don't need Model class systems because we have coffeescript/es6 classes. We have inheritance and interfaces, web components, etc.
  • I think React has the right idea that separating JS and HTML is separating languages rather than separating concerns. The space-pen DSL shows you can generate DOM pretty nicely without template files.
  • The main problem with direct DOM manipulation is that it's really clunky. From a functionality side a lot of things that were once provided by frameworks are baked into HTML5. The goal is really to make taking advantage of this a bit less verbose and a bit more natural.

Frankly no web-oriented framework really fits the bill, because they are designed for doing full web pages in many browsers (so come with polyfills and model systems and lots of irrelevant bits). I think space-pen was already very much headed in the right direction, providing a tool adapted to the specific requirements of writing atom plugins - I'm sad it's not maintained, I think Atom probably need's it's own library (which hopefully will also have a longer half-life than your average JS framework)

@carlosingles

I've been working on an updated version of space-pen called space-brush, you can check out the repo here:

https://github.com/carlosingles/space-brush

There's an example in the lib/example folder that shows how it can be used.

@tomekmarchi

I don't see any of those being the right choice besides the last. I would rather see an option like the last "Something custom, delightful & new". Not using virtual DOM and focused on utilizing the change records from Object.observe would be a huge plus. A more vanilla approach would provide longevity as compared to frameworks that come and go.

@nathansobo
Contributor

I wrote a library in collaboration with @maxbrunsfeld that represents what I want in a view framework:

https://github.com/nathansobo/etch

It's only been used in a single package so far, so it needs more usage and feedback, but check it out.

@tomekmarchi

@peduxe I disagree with it's implementation utterly.
IMO A view system that uses batched requestAnimationFrame, Object.observe and a global capture event system is best for this context. That does use O.o from what I recall, so it is much closer to the best possible end game. Using any of the other listed frameworks is just asking for more trouble down the road and now. It's not realistic or practical to go with them IMHO.

@nathansobo
Contributor

Unfortunately, as I learned talking to a maintainer on the v8 team, Object.observe isn't standardized and isn't even guaranteed to remain in Chrome. That's why I steered away from it in Etch despite an initial desire to use it.

@basarat
Contributor
basarat commented Sep 11, 2015

Object.observe isn't standardized and isn't even guaranteed to remain in Chrome

That is the word on the street ... even before your confirmation 🌹

@tomekmarchi

I hope not, I call hear-say for now; won't hold up in court. I hope they don't plan on etching RIP into O.o's tombstone. Sad day this would be for many projects like angular and reacts future. As noted O.o would be a sublime benefit. Without confirmation I say there is enough evidence pointing to the contrary. IMHHO

@basarat
Contributor
basarat commented Sep 11, 2015

Sad day this would be for many projects like angular and reacts future

neither use Object.observe ... I think

@isiahmeadows

AFAICT from this Angular 1.x bug, the reason it didn't get traction there initially is that it was not especially fast at first (it was slower than the old dirty checking for quite a while). I know there is still some interest, but performance is still their main concern. It appears that at the moment, on the JS end, AngularJS uses code generation to do the change detection. And it also appears that much of the change detection itself is pluggable, probably in response to the fact people can't seem to agree on what data format is best to back a model with, mostly immutable vs observable. In the case of immutable data, Object.observe is virtually pointless. In the other case, there are a lot of observation utilities out there, and Object.observe is just one option.

Polymer used Object.observe for some time, until they realized they could monitor the changes far more efficiently by simply installing setters on the custom element prototype's observed properties (monitoring single properties instead of all properties).

React itself has very little use for Object.observe, since it uses a virtual DOM to create patches for DOM. There's some dirty checking of the virtual DOM in the process, but it's minimal. The main use case for Object.observe in those circles would be more efficient models, for the ones that use stateful models. (Those who use the Flux pattern have no need for them, as there's nothing to observe. It's mostly immutable, and the state could almost be modelled as a circular stream.)

@yyx990803

On the point of Object.observe: one additional problem with O.o is that it's pure observation, i.e. it only tells you when something has changed, but doesn't tell you when something has been accessed. It doesn't help when you want to build up a reactive dependency graph (which would in turn enable powerful computed properties).

Vue.js delivers reactivity on POJOs and computed properties with ES5 getter/setters (think Knockout but without having to explicitly create observables). In addition, this type of fine-grained reactivity offers great performance (only update what's changed) and much, much simpler optimization requirements than dirty checking or even virtual dom diffing.

The only use for Object.observe is these scenarios is probably detecting added/deleted properties, which I think is marginally useful because it's a bad idea not to have a pre-defined schema for your state model.

Basically, once you actually try to implement a reactive view system with it, you will find Object.observe to be quite inadequate.

@tomekmarchi

@basarat they do not as to my point why it would be sad, they could have taken advantage of it in a future context. Given time the performance will come.

@tomekmarchi

@yyx990803 it's very easy to combine the two this is exactly what I experimented with in the past although have stopped development. One would use O.o for the changes and when new props are added. S/G to add observers to properties that may be objects/arrays for deep observations or as you said when simply getting properties. O.o with G/S is best of both worlds.
Here is an example of it working
http://acidjs.com/site/demos/
This is all old including the library some will not work but click on the observable demos those have O.o with S/G.

@tomekmarchi

It does seem as if O.o is the John Snow of JS APIs. Looks good and fights well but to an early grave it may go.

@yyx990803

Honestly I'd rather see Proxies that can work directly on objects. That would really be the best of both worlds.

@tomekmarchi

@yyx990803 Yes, Proxies would also be a great addition although they are more of just a robust replacement for G/S. Thus O.o with Proxies would also be feasible.

@mangecoeur

Talking about the implementation and relative merits of underlying tech seems a bit besides the point - you want to offer a stable API, with optimisations happening under the hood.

For package developers performance is frankly not even such a big deal - most packages introduce a relatively small number of UI elements and are more likely to run into performance issues in the business logic rather than the UI. Many just re-use existing UI elements like the modal pane, the search panel, the status bar, or the context menus.

What package developers need is stability and maintenance - whatever is used needs to have a stable, versioned API and be maintained over time, no one wants to re-write packages just because the view library gets depreciated. Arguing over implementation details at this point is putting the cart before the horse, so to speak.

@yyx990803

@mangecoeur quite a few previous comments mentioned "leveraging Object.observe" as an evaluation criteria, and the discussion is in fact trying to point out that using O.o as a criteria doesn't make sense, because O.o doesn't necessarily lead to a good API.

In terms of stability - I also think quite a few commenters were eschewing some lesser-known solutions without even looking at them carefully. Take my project, Vue.js, for example - it's been around for over a year and a half, with a still growing user base, actively maintained (commits every day), used by people in production, with issues closed under an average of 17 hours, and currently has zero reproducible open bugs. The ongoing 0.12 -> 1.0 upgrade is introducing some breaking changes, but there is a migration build which is completely compatible with 0.12 with deprecation warnings so the upgrade path is clear.

Vue is also very embeddable (i.e. not trying to own the whole stack), and I believe it has the most approachable learning curve among all existing solutions out there. A sweeping comment like "there's nothing that fits the bill" doesn't sound like an educated conclusion to me.

@tomekmarchi

Frankly no web-oriented framework really fits the bill, because they are designed for doing full web pages in many browsers (so come with polyfills and model systems and lots of irrelevant bits). I think space-pen was already very much headed in the right direction, providing a tool adapted to the specific requirements of writing atom plugins - I'm sad it's not maintained, I think Atom probably need's it's own library (which hopefully will also have a longer half-life than your average JS framework)

@paulpflug

I have to second that, coming from angular, trying spacepen and looking in
at least 4 other frameworks, vue is clearly the best.
I'm working with it for 6 months now and I'm still impressed of its quality.
I would clearly encourage everyone to take a closer look.

Am 11. September 2015 9:05:46 nachm. schrieb Evan You
notifications@github.com:

@mangecoeur quite a few previous comments mentioned "leveraging
Object.observe" as an evaluation criteria, and the discussion is in fact
trying to point out that using O.o as a criteria doesn't make sense,
because O.o doesn't necessarily lead to a good API.

In terms of stability - I also think quite a few commenters were eschewing
some lesser-known solutions without even looking at them carefully. Take my
project, Vue.js, for example - it's been around for over a year and a half,
still with a growing user base, actively maintained (commits every day),
used by people in production, with issues closed under an average of 17
hours, and currently has zero reproducible open bugs. The ongoing 0.12
-> 1.0 upgrade is introducing some breaking changes, but there is a
migration build which is completely compatible with 0.12 with deprecation
warnings so the upgrade path is clear.

Vue is also very embeddable (i.e. not trying to own the whole stack), and I
believe it has the most approachable learning curve among all existing
solutions out there. A sweeping comment like "there's nothing that fits the
bill" doesn't sound like an educated conclusion to me.


Reply to this email directly or view it on GitHub:
#5756 (comment)

@tomekmarchi

Talking about the implementation and relative merits of underlying tech seems a bit besides the point - you want to offer a stable API, with optimisations happening under the hood.
A sweeping comment like "there's nothing that fits the bill" doesn't sound like an educated conclusion to me.
I also think quite a few commenters were eschewing some lesser-known solutions without even looking at them carefully.

Given this React is best in that context. If we are talking longevity, docs, support, performance, community, "well known", ease of use and solid backing then that's React.

@nathansobo
Contributor

React has serious interoperability issues, both between different instances/versions of React in the same DOM and between DOM APIs and React components. I like the core ideas, but they target a slightly different problem space in ways I found problematic.

Ultimately people are free to use whatever they want. I personally find the virtual DOM concept React introduced really intuitive and powerful, which is why I wrapped the excellent virtual-dom Node module with a bit of convenience for a lightweight solution in the form of Etch. For me this represents the biggest bang for the buck in terms of abstraction overhead. I'd like to think the right library can be simple enough and have small enough conceptual surface area to not need a ton of iteration.

Vue is definitely the nicest data binding library I've seen and what I would try if I wanted to use data binding. It seems to interoperate cleanly with the DOM and be lightweight and non-monolithic which is really important for Atom packages. However, for the time being I'm most excited about a virtual-dom approach as the basis of a recommended library for Atom. I need more real world feedback to validate my intuition before pulling the trigger on anything "official".

Bottom line: experiment, follow your own instincts and try stuff. That's what I'm doing too. The only view framework we will ever mandate in Atom is the DOM itself.

@basarat
Contributor
basarat commented Sep 14, 2015

between different instances/versions of React in the same DOM

They seem to be working on it : https://github.com/facebook/react/pull/4747/files but haven't tested myself 🌹

@ghost
ghost commented Oct 26, 2015

https://github.com/google/incremental-dom

higher perf than react, due to specific design for low heap allocation.
very similar to React, and works with react
simple
transpilerable.
Its basically ASM DOM.

@nathansobo
Contributor

Incremental-dom looks cool and I appreciate the a la carte offering and performance focus. One thing I wonder is whether they allow arbitrary components to be embedded like the virtual-dom Widget interface. That's useful for interoperating with components that aren't written using the incremental-dom approach.

@ghost
ghost commented Oct 26, 2015

@nathansobo

true. very useful. not sure. i am also curious.
but maybe there are better ways to approach the issue - it does interoperate with react and a few other new kids on the block. see docs.

also see the benchmarks !!! very clear that react sucks

check this out.
https://github.com/justinfagnani/stampino

btw this will likely be going into polymer. its used for the polymer designer now.

@steelbrain
Contributor

I was working on the linter UI improvements and considered using etch, The reason I decided to choose etch was because it had JSX, I could write html in my javascript files and it would work, I however did not want to include the virtual-dom library because I don't need it at all, the views I was creating were not meant to be modified heavily or in need of virtual-dom.

So I would like to show you guys a little experiment of my own, vanilla-jsx. You can write JSX with it, and what you get is pure native HTML Elements. It's very small and usable almost everywhere.

@kanekotic kanekotic referenced this issue in reergymerej/todo Dec 10, 2015
Closed

use a templating engine or atom view #6

@pamtbaau

Allmost 10 months after the quest started for a new view system in Atom and still no white smoke... Gives me an unsettling feeling about the future of Atom...

Or have I overlooked something in the docs/discussions?

@isiahmeadows

@pamtbaau It's called Atom doesn't really have an opinion, since they had to resort to very explicit, low-level DOM management because of major memory and speed problems (they also switched to integer constants to denote types for similar reasons). It is probably up to the plugin developers for what opinion to use at this point.

@nathansobo
Contributor

My recommendation is etch. We're using it to prototype some packages internally. Getting good reviews from teammates. Give it a try or use whatever you want. The goal of Atom is to be agnostic beyond standard DOM APIs.

@mangecoeur

I think by now almost every js view library in existence has been
suggested... If we really want progress we need a clear outline of
requirements first- and from that determine what kind of library is needed,
if any...
On 12 Dec 2015 20:57, "Nathan Sobo" notifications@github.com wrote:

My recommendation is etch https://github.com/nathansobo/etch. We're
using it to prototype some packages internally. Getting good reviews from
teammates. Give it a try or use whatever you want. The goal of Atom is to
be agnostic beyond standard DOM APIs.


Reply to this email directly or view it on GitHub
#5756 (comment).

@mark-hahn
Contributor

Apparently there isn't much real need since packages are being developed at a fast pace. I was one of the biggest bitchers when the space-pen standard was killed but since then I've found several different solutions based on the nature of my package.

they also switched to integer constants to denote types for similar reasons

Can you elaborate? I've never heard of any performance improvement from using integers. Integers are virtually the same performance as string compares after V8 optimizations.

@isiahmeadows

@mark-hahn One example was using integers and a global look-up table to make Atom able to read large files. Or, in this particular case, it reduced the memory requirement for tokenized lines (i.e. visited by the syntax highlighter) by 70%:

  • An array of integers are used to represent both token scopes (e.g. storage.type.function.js for the JS keyword function) and their associated string text. Negative numbers are used for scopes, and positive numbers for text.
  • A lookup table is used to translate the scopes and strings to their respective values.
  • The array uses a JSON-like tree format to denote scopes, similar to how incremental-dom does it for DOM nodes.

Or, borrowing their example, it converted this:

[
  {value: 'function', scopes: ['source.js', 'meta.function.js', 'storage.type.function.js']},
  {value: ' ', scopes: ['source.js', 'meta.function.js']},
  {value: '(', scopes: ['source.js', 'meta.function.js', 'punctuation.definition.parameters.begin.js']},
  {value: ')', scopes: ['source.js', 'meta.function.js', 'punctuation.definition.parameters.end.js']},
  {value: ' ', scopes: ['source.js', 'meta.function.js']},
  {value: '{', scopes: ['source.js', 'punctuation.section.scope.begin.js']},
  {value: '}', scopes: ['source.js', 'punctuation.section.scope.end.js']}
]

to this format:

[
  {start: 'source.js'},
    {start: 'meta.function.js'},
      {start: 'storage.type.function.js'},
        "function",
      {end: 'storage.type.function.js'},
      " ",
      {start: 'punctuation.definition.parameters.begin.js'},
        "(",
      {end: 'punctuation.definition.parameters.begin.js'},
      {start: 'punctuation.definition.parameters.end.js'},
        ")",
      {end: 'punctuation.definition.parameters.end.js'},
    {end: 'meta.function.js'},
    " ",
    {start: 'punctuation.section.scope.begin.js'},
      "{",
    {end: 'punctuation.section.scope.begin.js'},
    {start: 'punctuation.section.scope.end.js'},
      "}",
    {end: 'punctuation.section.scope.end.js'},
  // note 'source.js' isn't closed yet
]

but it really looks like this:

{
  text: "function() {}",
  tags: [-1, -3, -5, 8, -6, 1, -7, 1, -8, -9, 1, -10, -4, 1, -11, 1, -12, -13, 1, -14]
}

and the lookup table is used on demand so that lines that aren't visible don't have scopes held in memory (looking up strings for a single 10-line tile is cheap, but holding tens of thousands of them in memory isn't).

@lee-dohm
Member

Let's try and keep things here focused on the view framework. Discuss is always available for more generalized discussion.

@pamtbaau

@mark-hahn

Apparently there isn't much real need since packages are being developed at a fast pace.

I have looked at the newest packages and the vast majority does not use any view. The handful that does use a view use jQuery, raw DOM, or space-pen. It might indeed be that a view framework isn't needed, however...

Space-pen was developed for a reason (there probably was a need for it) and deprecated for a reason. And also the quest for a replacement has been started for a reason (there probably still is a need for it).

As a newbe I don't know any of the reasons the team used to come to their decisions, and I don't need to know. When I experiment with some new technology, I would like to see a clear direction and good samples. I also like to read/extend other add-ons to learn and master the technology.

I don't mind which view framework the team picks as long as I know what the best option is to start with. Pick one and endorse it...

Don't get me wrong, I love Atom and that's mostly because of its hackability...

@mark-hahn
Contributor

Space-pen was developed for a reason (there probably was a need for it)
and deprecated for a reason.

My big argument at the time was that they removed space-pen for no reason.
They turned the sample package from a friendly newbie experience into
something useless as a template. I did manage to convince the team to keep
supporting space-pen but they wouldn't put it in the sample code.

On Tue, Dec 15, 2015 at 8:11 AM, pamtbaau notifications@github.com wrote:

@mark-hahn https://github.com/mark-hahn

Apparently there isn't much real need since packages are being developed
at a fast pace.

I have looked at the newest packages and the fast majority does not use
any view. The handful that does use a view use jQuery, raw DOM, or
space-pen. It might indeed be that a view framework isn't needed, however...

Space-pen was developed for a reason (there probably was a need for it)
and deprecated for a reason. And also the quest for a replacement has been
started for a reason (there probably still is a need for it).

As a newbe I don't know any of the reasons the team used to come to their
decisions, and I don't need to know. When I experiment with some new
technology, I would like to see a clear direction and good samples. I also
like to read/extend other add-ons to learn and master the technology.

I don't mind which view framework the team picks as long as I know what
the best option is to start with. Pick one and endorse it...

Don't get me wrong, I love Atom and that's mostly because of its
hackability...


Reply to this email directly or view it on GitHub
#5756 (comment).

@benogle
Contributor
benogle commented Dec 15, 2015

You guys should try etch. It is really easy to work with and has the potential to be the new recommended framework. As @nathansobo said, we are prototyping some things internally with it, and it has been going really well. It's very simple, well contained, and really really easy to pick up, especially if you have used react.

@pamtbaau

Ok, I'll give etch a try and compare it by updating my vue.js based package. At first glance, vue.js looks easier then etch though... But let's learn something new first and then compare...

@kanekotic

So i have been working this last few weeks with vue-js to try to develop my own package. I have found something that i have not been able to overcome. There must be something in the underlying frameworks that I dont understand (i am a newby in vue and in atom).

The concern i have is how to do a bindings for user inputs, the options i see are:

  • HTML Inputs: are not really used, they dont behave well inside atom.

  • {{ text }} : displays everything correctly and gets the events as expected, but is not doing a two-way binding.

  • Vue component with template and sync parameter: this was the most promising solution but the sync seems to be ignored (is this due eval not been allowed?).

    so an example of my code right now:

The coffeescript:

@vue = allowUnsafeNewFunction =>
          new Vue
            el: @view
            data: @model
            components:
                'my-text':
                    props: ['text'],
                    template: '<atom-text-editor mini /> {{ text }} </atom-text-editor>'
            methods:
                search: () ->
                    console.log 'search'

The HTML:

<atom-panel class='modal'>
    <div v-on:keyup.esc="close" class='select-list'>
        <my-text v-on:keyup.enter="search" :text.sync="query"></my-text>
        <div class='select-list'>
             ...
        </div>
    </div>
</atom-panel>

project repository

user input is one of the most common things to work with, so there is a need for an easy solution for this kind of scenario.

@pamtbaau

@kanekotic I think it's best to open your own specific issue instead of hijacking this thread.

@kanekotic

@pamtbaau i am not trying to hijack this thread, I actually have an open thread in the vue forum for it (so chill bro ;), because i am not asking questions just showing a snippet and saying it doesnt work as expected).

I just want to point out that at least with vue i dont see an easy way to have a two way binding for user input inside atom. This is because user input in atom is done by atom-text-editor and vue supports two way bindings using v-model only on elements input, select and textarea. so binding atom-text-editor in a two-way is not straight forward (i might be wrong but i would think this could be related to the need to also use loophole but i am not an expert in neither of the frameworks).

Most of the examples i have seen are oversimplified just showing that is possible to use the framework but ignores basic cases exposed on the Styleguide. I would expect that the solution selected should at least be able to natively support some basic cases.

I agree with your concern of this becoming an unsustainable discussion of frameworks and everyone providing his own findings, so i would think that it would be a good idea to have an open thread per each of the tested frameworks to track pros and cons.

PS. if anyone else feels annoyed or think that is not useful at all my previous post let me know and i will remove it or refactor it. But my concerns still the same 'how to treat user input'

@pamtbaau

@kanekotic See Two-way element binding in Atom using Vue #1 in your project repository. I've posted a sample that works for me.

@lee-dohm
Member

user input in atom is done by atom-text-editor

It can be, but doesn't have to be. If you look at my bug-report package, I use standard input tags for text input. I do it this way because it's easier and I didn't need all the fancy features provided by atom-text-editor.

@littlebee

Around the same time I started hacking on Atom, a teammate introduced me to React. React and space-pen both changed a fundamental belief I had about web development, which was that view logic and markup should be separate and distinct concerns. I loath templates like I've seen in Php and Ruby where there is a lot of flow control and looping embedded in the template - which was one of the things that turned me off about Angular when it started to gain popularity on other teams.

I came back to work from my hack-cation in Aug. with the View base class we'd been missing. It was almost space-pen because it gel'd so well with our psuedo Backbone view, heavily jQuery + underscore template views. Making the view objects themselves jQuery instances meant less wiring code.

The winner though, was React. space-pen was deprecated around that time and the components built with React were more reusable and compositing components was easier + a LOT less wiring.

Convincing my team was easy - I just showed them the 334 lines of coffeescript + _ templates specific to one view in our system replaced by 64 lines of React + JSX - assuming they would let me go off and develop some components we would need to connect to our existing Backbone models and collections 😄.

The beauty of Atom and Node though is that you don't have to choose for us. Anyone can use any or all of the above, no?

@mnquintana
Member

Just to clarify, there will be no "official" view framework per se – this is all just to choose the library that will be used in examples in the docs and in the package generator, and that's about it. Package authors will remain free to use whatever they want.

@kanekotic

so why then not leave it as is? (just using the DOM). It will be the clean solution, as per there are no extra packages/dependencies added.

Maybe what it will be cool is to have a repository in atom where people can collaborate with basic example for the different frameworks that have been experimented with.

@mark-hahn
Contributor

so why then not leave it as is? (just using the DOM).

No one develops the DOM by using only javascript calls. It is painful, verbose, and hard to remember. I can't think of anything that would scare away newbies more than this. The fact that the sample package uses this is a big problem. No one seems to care about newcomers.

@lee-dohm
Member
lee-dohm commented Jan 6, 2016

The general idea is that we want to make writing an Atom package, even one with a custom UI, as streamlined as possible. To that end, we feel that we should have a view framework that the Atom team is familiar with so we can assist when people get stuck.

Maybe what it will be cool is to have a repository in atom where people can collaborate with basic example for the different frameworks that have been experimented with.

I think this is a great idea and I would be willing to add a section in the Flight Manual for "reference implementations" of a simple package with a UI that is implemented in various frameworks by community authors. To that end, I've started a topic on Discuss to come up with what that "reference package" could be.

@steelbrain
Contributor

@mark-hahn I've DOM by only javascript calls in linter panel. It was worth it for the flexibility, I could do all sorts of optimizations specific to linter there

@Hurtak
Hurtak commented Jan 6, 2016

How about starting some official 'todoMVC' repo for atom packages. One specific simple package would be developed in several frameworks/libraries, atom devs would then be able to evaluate what suits best to beginners, and potential package developers would see how to develop packages in their favorite framework

@kanekotic

@mark-hahn I agree that using only DOM calls is painful. But i also agree with @lee-dohm and @mnquintana and the flexibility of using different frameworks, but i think the knowledge to help in the different ones should reside in the community it will probably become a burden.
I think the atom package generator should offline continue as is just a simple thing that explains how to start, and maybe extended with an extra option that will clone base projects based on a selected framework, that will allow the flexibility of selecting a framework.

@mark-hahn
Contributor

todoMVC would be perfect since it has become the standard go-to demo app. It would need to be tweaked to somehow fit into atom instead of the standard web page.

@mark-hahn
Contributor

an extra option that will clone base projects based on a selected framework,

I don't see why the sample projects @leedohm wants couldn't be loaded as projects.

@mark-hahn
Contributor

It was worth it for the flexibility, I could do all sorts of optimizations specific to linter there

I can't imagine any optimization that couldn't be done with a framework, particularly vue, which is what I use.

@steelbrain
Contributor

@mark-hahn We have to handle cases with ~5k error messages in one panel, we have to keep a pool of DOM elements and re-use them in both panel and bubble and for that we have to design the message elements to be disposable + reusable.

@mark-hahn
Contributor

we have to design the message elements to be disposable + reusable.

Actually, vue components would be perfect for that. I'm not saying you
should use vue, just that you underestimate what good frameworks are
capable of.

On Wed, Jan 6, 2016 at 1:10 PM, Steel Brain notifications@github.com
wrote:

@mark-hanh We have to handle cases with ~5k error messages in one panel,
we have to keep a pool of DOM elements and re-use them in both panel and
bubble and for that we have to design the message elements to be disposable

  • reusable.


Reply to this email directly or view it on GitHub
#5756 (comment).

@paulpflug

@mark-hahn We have to handle cases with ~5k error messages in one panel, we have to keep a pool of DOM elements and re-use them in both panel and bubble and for that we have to design the message elements to be disposable + reusable.

I did exactly that with vue already, of course you can't use the built in for loop, though.
(I used a list of entries which change their text and position on scrolling, each entry is a vue component and so the logic of the list and the entry is seperated)

But back on topic: I would prefer something other than todoMVC or a modified todoMVC which uses something of the atom api at least

@steelbrain
Contributor

@mark-hahn I evaluated several options including view frameworks but linter messages caching is complicated than you think, consider this

class MessageView {
  constructor() {
    this.rootElement = getRootElement()
    this.nameElement = getNameElement()
    this.typeElement = getTypeElement()
    this.messageElement = getMessageElement()
    this.rootElement.appendChild(this.nameElement)
    this.rootElement.appendChild(this.typeElement)
    this.rootElement.appendChild(this.messageElement)
  }
  attach(message) {
    if (message.name) {
      this.messageElement.textContent = message.name
    } else this.messaegElement.setAttribute('hidden', 'true')
    ... same for type ...
    if (message.hasLink) {
      // create link outside of pool, costy
      this.messageElement.appendChild(getMessageLink())
    }
  }
}

Now the difficult thing here is that the structure of each component is different, some are divs, some are spans, some are hyperlinks. Any generic caching technique would never be able to give us results that I can get this way. I can create generic message element view objects and attach and detach messages from them

@mnquintana
Member

I think a TodoMVC-esque example package for Atom is a great idea, but I agree with @paulpflug that it shouldn't literally be TodoMVC, but rather something that makes significant use of the Atom API.

@mark-hahn
Contributor

@steelbrain, I'm too lazy to argue by writing vue samples. I remain convinced though that it can be done with vue in an elegant way. You haven't presented anything to sway me, not that you should care.

Anything turing complete could do it but we'd have to compare final results to really get a good comparison.

@kanekotic

@mnquintana maybe something that will use the API and could be an adapt is a 'find TODO comments' on the editor.

@paulpflug

@steelbrain I believe, what you would need is something similar to clusterize.js and I'm sure you could implement and adapt it to your use case in nearly any view framework - only a matter of time ;)

@kierans
kierans commented Jan 7, 2016

I agree with @mnquintana that an examples need to showcase the Atom API, as well as have several different UI widgets to show what's possible.

@willnwhite
willnwhite commented Jun 2, 2016 edited

Whilst this has been going on, I started to just write functions in my code to create and append elements. It reminded me of HyperScript:

var h = require('hyperscript')
h('div#page',
  h('div#header',
    h('h1.classy', 'h', { style: {'background-color': '#22f'} })),
  h('div#menu', { style: {'background-color': '#2f2'} },
    h('ul',
      h('li', 'one'),
      h('li', 'two'),
      h('li', 'three'))),
    h('h2', 'content title',  { style: {'background-color': '#f22'} }),
    h('p',
      "so it's just like a templating engine,\n",
      "but easy to use inline with javascript\n"),
    h('p',
      "the intension is for this to be used to create\n",
      "reusable, interactive html widgets. "))

I'm a big fan of the HTML-like nesting. I will try it out on my package.

@k33g
k33g commented Jun 10, 2016 edited

Hello 🌍 , cc @thedaniel
I'm starting some quick experiments with Atom and UI:

With RactiveJS

http://www.ractivejs.org/

Learning curve is small, abs Ractive is pleasant to use

export default class MyPlugInView {

  constructor(serializedState) {
    this.element = document.createElement('div');

    let myForm = new Ractive({
      el: this.element,
      template: `
      <div>
        <p>{{greeting}}, {{recipient}}!</p>
        <div on-click="activate">{{message}}</div>
      </div>
      `,
      oninit: function () {
        this.on( 'activate', () => { // fooo
        });
      },
      data: {
        greeting: 'Hello world',
        message: 'Click me!'
      }
    });
  }
  serialize() {}
  destroy() {
    this.element.remove();
  }
  getElement() {
    return this.element;
  }
}

With HTMLElement (Custom Element and VanillaJS)

For small codes, to my mind it's enough: Custom Elements with Classes

Nothing but does the work for small tests

'use babel';

class Small extends HTMLElement {
  constructor() { super(); }
  createdCallback() {}
  attachedCallback(){}
  template(data) { return `<div></div>`; }
  html(data) {
    this.innerHTML = this.template(data);
    this.events(data);
  }
  init(data) {}
  static of(tagName, data) {
    let Element = document.registerElement(tagName, this);
    let instance = new Element()
    instance.init(data)
    instance.html(data)
    return instance
  }
}
export default Small;

And then I use it like that:

'use babel';

import Small from './small';

class MyForm extends Small {
  constructor() { super(); }
  template(data) {
    return `<div>
      <h3>${data.message}</h3>
      <form>
        <input type="text" placeholder="${data.placeholder}"/>
        <button>Click Me!</button>
      </form>
    </div>`;
  }
  events(data) {
    this.querySelector('button').addEventListener('click', (e) => {
      let value = this.querySelector("input").value;
      this.querySelector("h3").innerHTML = value;
    });
  }
  init(data) {
    console.log('Inititialize ...', data)
  }
}

export default class MyPlugInView {
  constructor(serializedState) {
    this.element = document
      .createElement('div')
      .appendChild(
        MyForm.of('my-form', {message:'Hello world!', placeholder:'???'})
      )
  }

  serialize() {}
  destroy() {
    this.element.remove();
  }
  getElement() {
    return this.element;
  }
}
@VernonGrant VernonGrant referenced this issue in VernonGrant/break Jun 14, 2016
Merged

Updated #21

@amitab amitab referenced this issue in amitab/atom-cscope Feb 11, 2017
Open

Object.add is deprecated. #26

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment