assemble / assemble-less

Grunt task for compiling LESS to CSS. This task does for less what Assemble does for HTML, making it much easier to modularize and reduce repetition in stylesheets.
http://github.com/assemble/assemble/
MIT License
66 stars 20 forks source link

less "modules" #13

Open jonschlinkert opened 11 years ago

jonschlinkert commented 11 years ago

@doowb, pull this down and take a look at it when you get a chance. :-)

https://github.com/assemble/assemble-less/tree/less-modules

It's just a first step, but it's an interesting feature for sure.

doowb commented 11 years ago

:+1:

jonschlinkert commented 11 years ago

@hariadi, I'm not sure if you use LESS or not, but if you are interested (and you have a moment) would you mind pulling this down and see if it builds for you? (the "less-modules" branch that is)

I haven't done documentation for this yet, since it's in a branch, but the idea here is that LESS files can be installed as "modules", either via npm or bower. So maybe try both if you want (the less dependencies are already defined in the package.json and bower.json). The value of this feature (to me) is that it will allow me to abstract out libraries of commonly used styles, mixins and variables and then just "require" them into a project. A good example of when this would be useful is with documentation for a component. Let's say you create a project for a specific UI component, like a button, and you want to have a demo of the button in the repo. This feature would allow you to "require" the styles for the demo, instead of including them in the project alongside the actual component's styles. (I'm also planning on adding this for assemble, for templates and common metadata.)

Anyway, it's not as flexible as I'd like it to be but I want feedback before I invest more time in it. Let me know what you think!

thanks

hariadi commented 11 years ago

Pulling down and build as expected. I like the idea (installed as module), but not very clear how to use (for example how to require font awesome/more less file?).

jonschlinkert commented 11 years ago

You would just add font-awesome to the dependencies in the bower.json of the project. If present, the task will use the directory defined in a .bowerrc file to find installed components (vendor is arbitrarily used in the following example). If it doesn't exist, then the task defaults to bower_components, same as bower.

Then, if font-awesome has properly defined the main property in their bower.json file, then the task will just find it and add @import (reference) "vendor/font-awesome/path/to/font-awesome.less"; to the less task options:

less: {
  options: {
    imports: {
      reference: [/* the task merges discovered packages with other manually defined paths in this property */]
    }
  }
}

@import (reference) is a new feature of less.js that allows you to "reference" imported less files. For example, in a custom local less file if you put

@import (reference) "bootstrap.less";

// Custom styles

.global-nav:extend(.navbar all) {
  // my styles
}
.toolbar {
  .clearfix();
}

then ONLY the targeted styles (extended and/or mixed in) from Bootstrap would be rendered in the generated CSS. Pretty awesome. I have some other things in the works to take full advantage of this. Let me know if this is interesting to you.

jonschlinkert commented 11 years ago

Oh, one more thing. This feature is (initially) intended for our internal use, so we would typically be "requiring" packages that we defined ourselves. So main property should always be configured properly. I don't know how broadly applicable this will be yet, we need to get some experience using it first.

hariadi commented 11 years ago

Interesting.

Implement in assemble-docs or buttons repo maybe? ;p

jonschlinkert commented 11 years ago

probably... but I think this could be really useful for a UI component library ;-)

jonschlinkert commented 11 years ago

btw, the grunt-inline-less repo is related (as a proof-of-concept). I really love the idea of being able to add @require statements to a less file, and just resolve using npm or bower. Other preprocessors have libraries that can be "required" in a project, like nib and compass. I started upstage to do this for less (to date, all of the projects for upstage have been for testing out features like this one, so they are nowhere near the quality and "cool factor" that they will be when I feel like it's time to start creating "real" components)

jonschlinkert commented 11 years ago

has been updated to allow @require statements in less files. again, this is experimental so feedback would be great. If any of these angles work out well and show promise then I will also draft a feature request for less.js.

hariadi commented 11 years ago

:+1:

jonschlinkert commented 11 years ago

https://github.com/jonschlinkert/grunt-inline-less/issues/2

jonschlinkert commented 11 years ago

@wnr, you commented:

add an option "output" that will default to "css" but can be changed to "less". Then include the lib/tree.js file and basically do the same.

Actually, let's make the output JSON :-) like the format you used in the tests for grunt-inline-less, but with a couple of tweaks. For example:

graph.json

[
  {
    "path": "import/one.less",
    "filename": "one.less",
    "ext": "less",
    "statement": "@import \"import/one.less\";",
    "content": "body { color: #900; }"
  },
  {
    "path": "import/two.less",
    "filename": "two.less",
    "ext": "less",
    "statement": "@import \"import/two.less\";",
    "content": ".sidebar { with: 250px; }"
  }
]

Temporarily, to manage related options we can add a graph option, then add other "sub options" to that while we're trying to figure this out. For example:

less: {
  options: {
    graph: {
      output: 'graph.json',
      foo: '',
      bar: []
    }
  }
}

Maybe we just start with this, then go from there? what do you think?

jonschlinkert commented 11 years ago

really, it could just be something like:

  {
    "file": "import/two.less",
    "statement": "@import \"import/two.less\";",
    "content": ".sidebar { with: 250px; }"
  }

and maybe we should add a property for the new import statement directives, e.g. @import (reference) "foo.less";.

  {
    "file": "import/two.less",
    "statement": "@import (reference) \"import/two.less\";",
    "directive": "reference",
    "content": ".sidebar { with: 250px; }"
  }

I'm not sure, @wnr what are your thoughts on this?

jonschlinkert commented 11 years ago

I started over and created a new project here: https://github.com/jonschlinkert/resolve-dep I think this might become one of my favorite grunt tools, it's really useful so far. // cc @doowb, @hariadi if you have a chance to test it out, let me know if you have any issues, thanks!