nfroidure / gulp-svgicons2svgfont

Bundle several SVG icons to a single SVG font
MIT License
45 stars 20 forks source link

Save mapping of codepoints to file #4

Closed backflip closed 10 years ago

backflip commented 10 years ago

In order to be able to create CSS templates, e.g., it would be necessary to know the mapping of codepoints. While it would be possible to use options.appendCodepoints and then read the file names to get the mapping, I'd prefer to create a JSON file instead: https://github.com/backflip/gulp-svgiconstosvgfont/commit/f0b3d07449ed4a237aab60eabc6bccc3db963155

This way, the icons keep their original name and could be updated later on without having to delete the renamed files first.

What do you think?

nfroidure commented 10 years ago

We discussed about that with @MoOx. There is at least 2 solutions. They are all based on the same principles. The whole font pipeline let pass unconcerned files through so, you can add a plugin before the svgicon2svgfont one to create new files (like CSS ones), like that:

gulp.src('icons/*.svg')
// generate CSS files and pass it through with the svg icons
.pipe(yourCSSPlugin({
  conf: 'file.json'
}))
// this plugin (and all the others i made) will simply ignore CSS files
.pipe(svgicons2svgfont())
// use rename to route your files in their respective folders
.pipe(rename(...))
.pipe(gulp.dest('www'));

You can:

backflip commented 10 years ago

Sounds reasonable, thanks.

backflip commented 10 years ago

So something along the lines of this (based on https://github.com/sindresorhus/gulp-jscs/blob/master/index.js):

'use strict';
var path = require('path');
var gutil = require('gulp-util');
var through = require('through2');
var fs = require('fs');
var _ = require('lodash');

module.exports = function (config) {
    var map = {},
        currentGlyph = 0xE000;

    return through.obj(function (file, enc, cb) {
        if (file.isNull()) {
            this.push(file);
            return cb();
        }

        if (file.isStream()) {
            this.emit('error', new gutil.PluginError('gulp-iconfont-glyphmap', 'Streaming not supported'));
            return cb();
        }

        currentGlyph++;

        map[path.basename(file.path, '.svg')] = 'u' + currentGlyph.toString(16).toUpperCase();

        this.push(file);
        cb();
    }, function (cb) {
        if (_.size(map) > 0) {
            fs.writeFile('test.json', JSON.stringify(map), function(err) {
                if(err) {
                    gutil.log(err);
                } else {
                    gutil.log("The codepoint mapping was saved to " + 'test.json');
                }
            });
        }

        cb();
    });
};

Or should the JSON file be added to the stream? If so, how would you do that?

nfroidure commented 10 years ago

I think you can just create the CSS file instead of using a JSON file if you base your work on filename code points.

If you want some help, just create a repo and i'll PR you good basis to base your code on.

I can point you some issues on the above snippet:

var map = [];
// (...)
map.push({
  filename: Path.basename(file.path,'.svg'),
  codepoint: currentGlyph
});
// (...)
if(map.length) {
}

s/map/glyphs/

backflip commented 10 years ago

Thank you so much for helping out! Here you go: https://github.com/backflip/gulp-iconfont-scss

nfroidure commented 10 years ago

If you rename files, it will not change the original files since svgicons2svgfont reduce them to a single file so gulp.dest will only save this new one.

Let's continue the conversation here for the other things https://github.com/backflip/gulp-iconfont-scss/pull/1