prateekbh / preact-material-components

preact wrapper for "Material Components for the web"
https://material.preactjs.com
MIT License
555 stars 81 forks source link

Dont be a thin opionionless wrapper over `mdc-web` #1003

Open prateekbh opened 6 years ago

prateekbh commented 6 years ago

This library started as a thin opinion-less wrapper over mdc-web. Which meant that we were just a declarative preact layer above whatever mdc-web ships.

Also this was my personal decision because mdc-web was/is a great lib to build modern web apps. They had extensive set of UI components, all served separately which was superb for perf. They had gestures and every thing and seemed the perfect fit.

Overtime however they have jumped over many breaking changes due to

a.) because they never said to be stable b.) because may be they are prepping for material 2.0

In past I have tried to stick as close to mdc-web as possible because frankly I never wanted to be an author of a gigantic UI lib alone, that too when our weekly downloads are ~600ish. But now we have a decent set of contributors to the lib

Now I see the frustrations of going through breaking changes every now and then(renamed components, renamed props etc etc) and also mdc-web has decided to remove gestures from the lib. I always wanted this lib to be a tool for modern web and without gestures its a no go.

Ideally I would want to keep this lib based on but not restricted to mdc-web.

We need to have gestures and a stable developer experience if not available by mdc-web, and also should polyfill any super obvious components if not available, say spinner.

But before I push the entire codebase on this journey I'd like to ask and see what the core team members think

a.) is it worth the time with the https://github.com/material-components/material-components-web-react getting more mature?

b.) does every one still feel enthusiastic and have enough free cycles to go over a major pmc2.0 release?

If it turns out that this all might not be worth it, I'd be happy to retire this repo in favor of material-components-web-react and make sure it works with preact so that the users of our lib are not left in limbo.

porfirioribeiro commented 6 years ago

I get your feeling, i am also wrapping some material components on my company frontend, as our design is mostly based on Material, it helps allot to use their css to base our components, and it's frustrating that many updates just break most of my code. I hated when they decided to remove the non boxed version of textfield, my designer hated it even more :disappointed: so i had to override some styles to get the old look back, keeping the new features.

Actually i am not working at the moment in any project with preact-material-components. I hope material-components-web-react get more mature, supporting more components and preact. Maybe we can help with that.

prateekbh commented 6 years ago

@porfirioribeiro should i safely assume you'd prefer to rather support stabilization of material-components-web-react and making sure it supports preact?

Also same feels dude :)

garrett-thompson commented 6 years ago

Hey all,

Im in a similar position where I’m not using preact-material-components anymore in any work projects. We’ve started to use MaterialUI on new projects 😕

cromefire commented 6 years ago

a) that sounds like a good idea first, but if you try to use typescript and preact with react libs you can simply give up b) I mean it won't be up to date after a day, but I can work on it. Maybe we could pin the versions and just update from time to time. Like every few months.

Also I'm in favor to just sometimes be not a direct wrapper of mdc-web, but to invent components based on them and the material guidelines

cromefire commented 6 years ago

Also we should consider breaking down the components into single packages like many packages do these days, because then we fix and release them individually.

Also we should consider writing some documentation on our structure and strategy before refactoring and document breaking changes and how to fix them in the future in some kind of documentation so we can just point people to that.

prateekbh commented 6 years ago

I'll wait to hear from @yeppha and @filoozom

filoozom commented 6 years ago

I just started a masters degree and run a company on the side, so honestly I don't think that I'll have time for this project, sorry. 🙁

I can still handle the infrastructure / Travis part of things, but that's pretty much it, maintaining or reviewing PR would probably be a bit too time consuming.

prateekbh commented 6 years ago

congrats @filoozom, you've been great help!!! 🤗

porfirioribeiro commented 6 years ago

Yes @prateekbh would be nice if we see material-components-web-react more stable and more feature-full compared with material-components-web.

Of course supporting preact would be great. That and TypeScript, as soon you get used to it it's hard to go back :joy:

YePpHa commented 6 years ago

I think we should go forward with this. Even though it might take a lot of work. I think it will be worth it in the end.

prateekbh commented 6 years ago

tumblr_oeblsgtp1p1v1qzojo1_500 Ok let's rip this thing open and make it better. Here's a few things I'd want to do.

developit commented 6 years ago

It would be good to have a rough guideline like "PMC implements material design, using material-components-web where possible".

I'm extremely supportive of this direction. This library is important for Preact's ecosystem and community, and we haven't done enough to highlight that. PMC should have it's own Guide section on the Preact site, and we should promote it in our boilerplates. We should feature it on the getting started page alongside Preact CLI.

cromefire commented 6 years ago

I think out guide line should be to implement components that respect the material guidelines: https://material.io/design/

Download commented 5 years ago

Hi @prateekbh @developit @YePpHa @porfirioribeiro @cromefire @filoozom

Sorry for reviving this old issue... But reading @prateekbh post was like a total deja vu from seeing the author of react-mdc slowly get completely weared out of trying to keep up with the changes in material components from Google... Also, I find that MDC is not doing a great job of supporting modern frameworks like preact/react still, even though they promised to do so. They sorta still target the jQuery model of a mostly static DOM.

At the same time I am looking at things like Surface and it is quitte brilliant. Pure CSS is not the complete solution but it can do a lot without introducing the painful JS that MDC gives us. I rewrote the MDC drawer at least 3 times now, of which 2 versions were pure CSS and all of them work better than the standard component... Which has these issues with focus trap etc.

I even started with some Pure CSS framework for material design at one point named solids... but it is a broken attempt.

But....

What if we created a repo and pooled our resources to make TRUE Preact components that work well without many issues and that function with CSS only where possible?

My interest in pure CSS is 3-fold:

  1. Simplicity. Nothing beats loading a (bunch of) styles and then just rendering some markup with some classes. I find that the script part of MDC introduces lots of complexity for things like a simple ripple effect that imho is not worth it.

  2. Time To Interactive (TTI). Because Pure CSS is native, basically components are interactive as soon as they are rendered. If things in the app shell like the drawer are pure CSS, your app will feel like it's responsive instantly.

  3. AMP. Strangely enough, Google's 2 biggest movements in the area of mobile web/pwa are AMP and Material Design, but these are mutually exclusive ?? MDC has explicitly stated it does not / will not support AMP. A Pure CSS implementation of Material Design would be AMP compliant by default.

Finally, I think mdc went a little overboard with the class-names. Just look a the raw markup of a simple piece of UI and omg do we really need that many, that long, class names??

I have for a long time now reserved the package name preact-material on NPM. I would love for an original, mostly CSS-only, implementation of Material Design to live there but, like most of you, I can't do such a thing alone.

Thoughts?

cromefire commented 5 years ago

What if we created a repo and pooled our resources to make TRUE Preact components that work well without many issues and that function with CSS only where possible?

Sometimes I'm thinking that someone has to really build a framework that really works with preact (or react).

At the same time I am looking at things like Surface and it is quitte brilliant. Pure CSS is not the complete solution but it can do a lot without introducing the painful JS that MDC gives us. I rewrote the MDC drawer at least 3 times now, of which 2 versions were pure CSS and all of them work better than the standard component... Which has these issues with focus trap etc.

That sounds pretty great, what if you have the css coming from the outside and adding the actual function (closing / opening / onclick...) in preact? I actually started implementing bootstrap in preact, but had to find out that I have to implement any javascript again, because they are using jQuery.

cromefire commented 5 years ago

I have for a long time now reserved the package name preact-material on NPM. I would love for an original, mostly CSS-only, implementation of Material Design to live there but, like most of you, I can't do such a thing alone.

We could start by "upgrading" one component after the other (we have split them into multiple packages for 2.0), for example, I think the ripple of mwc is quite nice, so we could keep that, but many things are just "to havy" (or buggy, like the drawer) and could be replaced with things like surface.

Download commented 5 years ago

Hi @cromefire , thanks for your interest.

I actually have experimented a lot with this, because every time I want to do stuff with Material Design I am faced with the hard choices :)

Let me start by showing you this codepen I just created: https://codepen.io/StijnDeWitt/full/LMJNQd

Please observe that the JS tab is empty ;)

This codepen has some nice feautures:

  1. Observe that when you scroll down, the toolbar shrinks and finally becomes fixed, at which point it becomes 'raised' (gets a drop-shadow) and content starts to flow behind it.

  2. Observe that when you resize the screen, the drawers start to exhibit different behavior depending on screen size:

    • On small screens, the drawer becomes modal and overlaps the main content
    • On large screens, the drawer becomes a collapsible sidebar
  3. Observe that the buttons in the toolbar have a CSS-only ripple effect. This effect is not quitte as good as I want it, mostly because it copies some bad elements from MDC (specifically, the button keeps hover state on touch devices). I already have a fix for this but it is not in this codepen.

  4. Observe that when you open the modal drawer (on small screen), the mouse scroll wheel actually does not scroll the page. Also note how there is no flickering/jumping of page content when the modal drawer opens, unlike in MDC (because they hide the scrollbar). Also note that the drawer actually slides open more smoothly than the one in MDV :)

In addition, I think I can develop a pretty solid overflow menu for the action buttons in the toolbar (primitive experiment here). I know there are near perfect CSS only versions of the input-with-floating-label from Material Design etc etc.

There are a few things we cannot do CSS-only. But we can put that stuff in the Preact components.

Specifically about the open/close drawer commands... The nice thing about CSS-only drawers is that there are no open-close commands, there is no closed boolean in state or in a redux store. Nothing. Because the state is in the checkbox in the HTML and completely managed by the browser.

I am currently starting a new project for which I want to do Preact + SSR, so I cannot use preact-cli (sadly) and the reason I got interested (yet again) in this is that MDC in all it's wisdom is publishing modules to NPM with import statements in them, so which need to be transpiled, which means messing with webpack to make it transpile into node_modules, which means a royal PITA :(

Anyway, for this project I want to finish up the components you see in the codepen so I have a simple app shell with normal Preact components and none of this MDC nonsense in it. So I am reviving my attempts at this solids thing. I will be committing regularly to these 2 repos:

https://github.com/download/solids https://github.com/download/solids-www

The solids-www project was supposed to become the project homepage + demo/playground... But for now the actual components are in it because it made development easier.

I actually spent a lot of time thinking what was the best way to use pure CSS components in a preact setting and here is what I came up with:

There is a project solids that contains components, each of which has:

There is a project preact-solids, which contains Preact components. These components are very thin. Most are pure functional components that basically accept a whole bunch of (mostly boolean) attributes and trigger style classes based on that. They render the markup + class names needed to add the components. Now here is the clever part: the Preact components use the class names imported from the JS files from the solids project. This enables some CSS Modules cleverness. More on that next.

There is an app project (I am using solids-www for that for now), which installs preact-solids. This app project then imports components from preact-solids and imports the related CSS in it's own style sheet. Assuming this style sheet is loaded with CSS Modules, it then gets a module definition from the loader, which it can set as a theme and all the solids components will use those class names and the style sheet will contain them as well. E.g. after being loaded by CSS Modules, the class names appbar and drawer would be transformed to appbar_2fy and drawer_4ft or something similar.

Anyway, it is maybe a lot to talk about. But I am convinced we could build a Material Design library for Preact which is:

Basically I have most of the principles worked out (I think) but it just is soo much work :)

cromefire commented 5 years ago

Observe that the buttons in the toolbar have a CSS-only ripple effect. This effect is not quitte as good as I want it, mostly because it copies some bad elements from MDC (specifically, the button keeps hover state on touch devices). I already have a fix for this but it is not in this codepen.

You also simply use the md ripple, that is something that's working nicely

There are a few things we cannot do CSS-only. But we can put that stuff in the Preact components.

Why not build css and let the rest be the concern of the framework (or at least only provide helper functions)

I am currently starting a new project for which I want to do Preact + SSR, so I cannot use preact-cli (sadly) and the reason I got interested (yet again) in this is that MDC in all it's wisdom is publishing modules to NPM with import statements in them, so which need to be transpiled, which means messing with webpack to make it transpile into node_modules, which means a royal PITA :(

I just wrote a webpack config one time and and copy it from project to project and at sometime I have to create a template...

Tip: For SSR write multiple configs and a base config, let webpack put the file in some dir (with target: "node", a different entry point and preact-render-to-string) and lastly just perform a relative import

I think there would be a bit more work needed (for example I would propose TypeScript, as it help you and all others to catch errors quickly and worse thing for all using typescript (which are a lot) is when types are not provided), but conceptually it's the right way