fontcustomtoadstool 0.1.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,18 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
18
+ spec/fixtures/fontcustom/*
@@ -0,0 +1,12 @@
1
+ ## 0.1.0 (12/2/2012)
2
+
3
+ * Changed API to use Thor `class_option`s
4
+ * Added option to change the name of the font and generated files ([#6](https://github.com/endtwist/fontcustom/issues/6))
5
+ * Added option to disable the file name hash ([#13](https://github.com/endtwist/fontcustom/issues/13))
6
+ * `fontcustom watch` compiles automatically on the first run
7
+ * Better help messages
8
+
9
+ ## 0.0.2 (11/26/2012)
10
+
11
+ * Fixed gemspec dependency bug ([#2](https://github.com/endtwist/fontcustom/pull/2))
12
+ * Fixed Windows Chrome PUA bug ([#1](https://github.com/endtwist/fontcustom/issues/1))
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in fontcustom.gemspec
4
+ gemspec
@@ -0,0 +1,15 @@
1
+ # A sample Guardfile
2
+ # More info at https://github.com/guard/guard#readme
3
+
4
+ guard 'spork' do
5
+ watch('Gemfile.lock')
6
+ watch('spec/spec_helper.rb') { :rspec }
7
+ end
8
+
9
+ guard 'rspec', :cli => '--color --drb' do
10
+ watch(%r{^spec/.+_spec\.rb$})
11
+ watch(%r{^lib/fontcustom/(.+)\.rb$}) { |m| "spec/fontcustom/#{m[1]}_spec.rb" }
12
+ watch('lib/fontcustom.rb') { 'spec/fontcustom/fontcustom_spec.rb' }
13
+ watch('lib/fontcustom/core.rb') { 'spec/fontcustom/fontcustom_spec.rb' }
14
+ watch('spec/spec_helper.rb') { 'spec' }
15
+ end
@@ -0,0 +1,60 @@
1
+ fontcustom
2
+
3
+ Copyright (c) 2012 Yifei Zhang, Joshua Gross
4
+
5
+ MIT License
6
+
7
+ Permission is hereby granted, free of charge, to any person obtaining
8
+ a copy of this software and associated documentation files (the
9
+ "Software"), to deal in the Software without restriction, including
10
+ without limitation the rights to use, copy, modify, merge, publish,
11
+ distribute, sublicense, and/or sell copies of the Software, and to
12
+ permit persons to whom the Software is furnished to do so, subject to
13
+ the following conditions:
14
+
15
+ The above copyright notice and this permission notice shall be
16
+ included in all copies or substantial portions of the Software.
17
+
18
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
22
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25
+
26
+
27
+ sfnt2woff
28
+
29
+ Version: MPL 1.1/GPL 2.0/LGPL 2.1
30
+
31
+ The contents of this file are subject to the Mozilla Public License Version
32
+ 1.1 (the "License"); you may not use this file except in compliance with
33
+ the License. You may obtain a copy of the License at
34
+ http://www.mozilla.org/MPL/
35
+
36
+ Software distributed under the License is distributed on an "AS IS" basis,
37
+ WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
38
+ for the specific language governing rights and limitations under the
39
+ License.
40
+
41
+ The Original Code is WOFF font packaging code.
42
+
43
+ The Initial Developer of the Original Code is Mozilla Corporation.
44
+ Portions created by the Initial Developer are Copyright (C) 2009
45
+ the Initial Developer. All Rights Reserved.
46
+
47
+ Contributor(s):
48
+ Jonathan Kew <jfkthame@gmail.com>
49
+
50
+ Alternatively, the contents of this file may be used under the terms of
51
+ either the GNU General Public License Version 2 or later (the "GPL"), or
52
+ the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
53
+ in which case the provisions of the GPL or the LGPL are applicable instead
54
+ of those above. If you wish to allow use of your version of this file only
55
+ under the terms of either the GPL or the LGPL, and not to allow others to
56
+ use your version of this file under the terms of the MPL, indicate your
57
+ decision by deleting the provisions above and replace them with the notice
58
+ and other provisions required by the GPL or the LGPL. If you do not delete
59
+ the provisions above, a recipient may use your version of this file under
60
+ the terms of any one of the MPL, the GPL or the LGPL.
@@ -0,0 +1,28 @@
1
+ #FontCustom v0.1.2
2
+
3
+ **Generate custom icon webfonts from the comfort of the command line.**
4
+
5
+ [Full documentation](http://endtwist.github.com/fontcustom/)<br/>
6
+ [Feedback and issues](https://github.com/endtwist/fontcustom/issues) to the core app.
7
+
8
+
9
+ ##What is FontCustom.sass?
10
+ There are two difference between FontCustom and FontCustom.sass. The main difference is that I converted the [template files](http://goo.gl/GZ53q) from old vanilla CSS to Sass. Nothing really magical there.
11
+
12
+ The next difference is that I beat up on the [generator.rb](http://goo.gl/IGZi0) file so that this better suits the Toadstool framework. Specific placement of the generated font files and a generated Sass partial as well.
13
+
14
+ ##Installation
15
+ ```sh
16
+ # Requires FontForge
17
+ brew install fontforge eot-utils ttfautohint
18
+ gem install fontcustom
19
+ ```
20
+
21
+ ##Usage
22
+ ```sh
23
+ fontcustom compile path/to/vectors # Compile icons and css to path/to/fontcustom/*
24
+ fontcustom watch path/to/vectors # Watch for changes
25
+ ```
26
+
27
+ ##To-do
28
+ See [project issues](http://goo.gl/RfCKl) for an updated list.
@@ -0,0 +1,10 @@
1
+ require "bundler/gem_tasks"
2
+ require 'rake/testtask'
3
+
4
+ Rake::TestTask.new do |t|
5
+ t.libs = t.libs + ['lib/fontcustom', 'spec', 'spec/fixtures']
6
+ t.test_files = FileList['spec/fontcustom/*_spec.rb']
7
+ t.verbose = true
8
+ end
9
+
10
+ task :default => :test
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'fontcustom/cli'
4
+
5
+ Fontcustom::CLI.start
@@ -0,0 +1,32 @@
1
+ # -*- encoding: utf-8 -*-
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'fontcustom/version'
5
+
6
+ Gem::Specification.new do |gem|
7
+ gem.name = "fontcustomtoadstool"
8
+ gem.version = Fontcustomtoadstool::VERSION
9
+ gem.authors = ["Yifei Zhang", "Joshua Gross", "Dale Sande"]
10
+ gem.email = ["yz@yifei.co", "joshua@gross.is", "dale.sande@gmail.com"]
11
+ gem.summary = %q{Generate custom icon webfonts from the comfort of the command line.}
12
+ gem.description = %q{Transforms EPS and SVG vectors into icon webfonts. Generates compatible CSS for Toadstool framework}
13
+ gem.homepage = "https://github.com/blackfalcon/fontcustom.sass"
14
+
15
+ gem.files = `git ls-files`.split($/)
16
+ gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
17
+ gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
18
+ gem.require_paths = ["lib"]
19
+
20
+ gem.add_dependency 'json'
21
+ gem.add_dependency 'thor'
22
+ gem.add_dependency 'listen'
23
+
24
+ gem.add_development_dependency 'rake'
25
+ gem.add_development_dependency 'bundler'
26
+ gem.add_development_dependency 'rspec'
27
+ gem.add_development_dependency 'fakefs'
28
+ gem.add_development_dependency 'spork'
29
+ gem.add_development_dependency 'guard-spork'
30
+ gem.add_development_dependency 'guard-rspec'
31
+ gem.add_development_dependency 'rb-fsevent', '~> 0.9.1'
32
+ end
@@ -0,0 +1,21 @@
1
+ require 'fontcustom/version'
2
+ require 'fontcustom/generator'
3
+ require 'fontcustom/watcher'
4
+
5
+ module Fontcustom
6
+ # Usage:
7
+ # Fontcustom.compile 'path/to/vectors', '-o', 'path/to/output'
8
+ def compile(*args)
9
+ Fontcustom::Generator.start(args) # as array
10
+ end
11
+
12
+ def watch(*args)
13
+ Fontcustom::Watcher.watch(*args)
14
+ end
15
+
16
+ def stop
17
+ Fontcustom::Watcher.stop
18
+ end
19
+
20
+ module_function :compile, :watch, :stop
21
+ end
@@ -0,0 +1,24 @@
1
+ require 'thor'
2
+ require 'fontcustom'
3
+
4
+ module Fontcustom
5
+ class CLI < Thor
6
+ # duplicated from Fontcustom::Generator so as to also appear under `fontcustom help` command
7
+ class_option :output, :aliases => '-o', :desc => 'Specify an output directory. Default: $DIR/fontcustom'
8
+ class_option :name, :aliases => '-n', :desc => 'Specify a font name. This will be used in the generated fonts and CSS. Default: fontcustom'
9
+ class_option :nohash, :type => :boolean, :default => false, :desc => 'Disable filename hashes. Default: false'
10
+
11
+ desc 'compile DIR [options]', 'Generates webfonts and CSS from *.svg and *.eps files in DIR.'
12
+ def compile(*args)
13
+ # workaround to pass arguments from one Thor class to another
14
+ ARGV.shift
15
+ Fontcustom.compile(*ARGV)
16
+ end
17
+
18
+ desc 'watch DIR [options]', 'Watches DIR for changes and regenerates webfonts and CSS automatically.'
19
+ def watch(*args)
20
+ ARGV.shift
21
+ Fontcustom.watch(*ARGV)
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,87 @@
1
+ require 'json'
2
+ require 'thor/group'
3
+
4
+ module Fontcustom
5
+ class Generator < Thor::Group
6
+ include Thor::Actions
7
+
8
+ desc 'Generates webfonts from given directory of vectors.'
9
+
10
+ argument :input, :type => :string
11
+ class_option :output, :aliases => '-o'
12
+ class_option :name, :aliases => '-n'
13
+ class_option :nohash, :type => :boolean, :default => false
14
+
15
+ def self.source_root
16
+ File.dirname(__FILE__)
17
+ end
18
+
19
+ def verify_fontforge
20
+ if `which fontforge` == ''
21
+ raise Thor::Error, 'Please install fontforge first.'
22
+ end
23
+ end
24
+
25
+ def verify_input_dir
26
+ if ! File.directory?(input)
27
+ raise Thor::Error, "#{input} doesn't exist or isn't a directory."
28
+ elsif Dir[File.join(input, '*.{svg,eps}')].empty?
29
+ raise Thor::Error, "#{input} doesn't contain any vectors (*.svg or *.eps files)."
30
+ end
31
+ end
32
+
33
+ def verify_or_create_output_dir
34
+ @output = options.output.nil? ? File.join(File.dirname(input), 'public/fonts/') : options.output
35
+ empty_directory(@output) unless File.directory?(@output)
36
+ end
37
+
38
+ def normalize_name
39
+ @name = if options.name
40
+ options.name.gsub(/\W/, '-').downcase
41
+ else
42
+ 'fontcustom'
43
+ end
44
+ end
45
+
46
+ def cleanup_output_dir
47
+ css = File.join(@output, 'fontcustom.scss')
48
+ old_name = if File.exists? css
49
+ line = IO.readlines(css)[5] # font-family: "Example Font";
50
+ line.scan(/".+"/)[0][1..-2].gsub(/\W/, '-').downcase # => 'example-font'
51
+ else
52
+ 'fontcustom'
53
+ end
54
+
55
+ old_files = Dir[File.join(@output, old_name + '-*.{woff,ttf,eot,svg}')]
56
+ old_files << css if File.exists?(css)
57
+ old_files.each {|file| remove_file file }
58
+ end
59
+
60
+ def generate
61
+ gem_file_path = File.expand_path(File.join(File.dirname(__FILE__)))
62
+ name = options.name ? ' --name ' + @name : ''
63
+ nohash = options.nohash ? ' --nohash' : ''
64
+
65
+ # suppress fontforge message
66
+ # TODO get font name and classes from script (without showing fontforge message)
67
+ `fontforge -script #{gem_file_path}/scripts/generate.py #{input} #{@output + name + nohash} > /dev/null 2>&1`
68
+ end
69
+
70
+ def show_paths
71
+ file = Dir[File.join(@output, @name + '*.ttf')].first
72
+ @path = file.chomp('.ttf')
73
+
74
+ ['woff','ttf','eot','svg'].each do |type|
75
+ say_status(:create, @path + '.' + type)
76
+ end
77
+ end
78
+
79
+ def create_stylesheet
80
+ files = Dir[File.join(input, '*.{svg,eps}')]
81
+ @classes = files.map {|file| File.basename(file)[0..-5].gsub(/\W/, '-').downcase }
82
+ @path = File.basename(@path)
83
+
84
+ template('templates/fontcustom.scss', File.join(@output, '../../sass/typography/_fontcustom.scss'))
85
+ end
86
+ end
87
+ end
@@ -0,0 +1,78 @@
1
+ import fontforge
2
+ import os
3
+ import argparse
4
+ import md5
5
+ import json
6
+ import subprocess
7
+
8
+ parser = argparse.ArgumentParser(description='Convert a directory of svg and eps files into a unified font file.')
9
+ parser.add_argument('dir', metavar='directory', type=unicode, nargs=2, help='directory of vector files')
10
+ parser.add_argument('--name', metavar='fontname', type=unicode, nargs='?', default='fontcustom', help='reference name of the font (no spaces)')
11
+ parser.add_argument('--nohash', '-n', action='store_true', help='disable hash fingerprinting of font files')
12
+ args = parser.parse_args()
13
+
14
+ f = fontforge.font()
15
+ f.encoding = 'UnicodeFull'
16
+
17
+ m = md5.new()
18
+ cp = 0xf100
19
+ files = []
20
+
21
+ KERNING = 15
22
+
23
+ for dirname, dirnames, filenames in os.walk(args.dir[0]):
24
+ for filename in filenames:
25
+ name, ext = os.path.splitext(filename)
26
+ filePath = os.path.join(dirname, filename)
27
+ size = os.path.getsize(filePath)
28
+
29
+ if ext in ['.svg', '.eps']:
30
+ m.update(filename + str(size) + ';')
31
+ glyph = f.createChar(cp)
32
+ glyph.importOutlines(filePath)
33
+
34
+ glyph.left_side_bearing = KERNING
35
+ glyph.right_side_bearing = KERNING
36
+
37
+ # possible optimization?
38
+ # glyph.simplify()
39
+ # glyph.round()
40
+
41
+ files.append(name)
42
+ cp += 1
43
+
44
+ if args.nohash:
45
+ fontfile = args.dir[1] + '/' + args.name
46
+ else:
47
+ hashStr = m.hexdigest()
48
+ fontfile = args.dir[1] + '/' + args.name + '-' + hashStr
49
+
50
+ f.fontname = args.name
51
+ f.familyname = args.name
52
+ f.fullname = args.name
53
+ f.generate(fontfile + '.ttf')
54
+ f.generate(fontfile + '.svg')
55
+
56
+ # Fix SVG header for webkit
57
+ # from: https://github.com/fontello/font-builder/blob/master/bin/fontconvert.py
58
+ svgfile = open(fontfile + '.svg', 'r+')
59
+ svgtext = svgfile.read()
60
+ svgfile.seek(0)
61
+ svgfile.write(svgtext.replace('''<svg>''', '''<svg xmlns="http://www.w3.org/2000/svg">'''))
62
+ svgfile.close()
63
+
64
+ scriptPath = os.path.dirname(os.path.realpath(__file__))
65
+ p = subprocess.Popen([scriptPath + '/sfnt2woff', fontfile + '.ttf'], stdout=subprocess.PIPE)
66
+ out, err = p.communicate()
67
+ if err is not None:
68
+ out += err
69
+ # If the local version of sfnt2woff fails (i.e., on Linux), try to use the
70
+ # global version. This allows us to avoid forcing OS X users to compile
71
+ # sfnt2woff from source, simplifying install.
72
+ if 'OSError' in out:
73
+ subprocess.call(['sfnt2woff', fontfile + '.ttf'])
74
+
75
+ subprocess.call('mkeot ' + fontfile + '.ttf > ' + fontfile + '.eot', shell=True)
76
+
77
+ # Hint the TTF file
78
+ subprocess.call('ttfautohint -s -n ' + fontfile + '.ttf ' + fontfile + '-hinted.ttf && mv ' + fontfile + '-hinted.ttf ' + fontfile + '.ttf', shell=True)
@@ -0,0 +1,72 @@
1
+ /*
2
+ Font Custom - icon webfonts made simple
3
+ */
4
+
5
+ @font-face {
6
+ font-family: "<%= @name %>";
7
+ src: url("<%= @path %>.eot?#iefix") format("embedded-opentype"),
8
+ url("<%= @path %>.woff") format("woff"),
9
+ url("<%= @path %>.ttf") format("truetype"),
10
+ url("<%= @path %>.svg#<%= @name %>") format("svg");
11
+ font-weight: normal;
12
+ font-style: normal;
13
+ }
14
+
15
+ /*
16
+ Bootstrap Overrides
17
+ */
18
+
19
+ [class^="icon-"]:before, [class*=" icon-"]:before {
20
+ font-family: "<%= @name %>";
21
+ font-weight: normal;
22
+ font-style: normal;
23
+ display: inline-block;
24
+ text-decoration: inherit;
25
+ }
26
+
27
+ a [class^="icon-"], a [class*=" icon-"] {
28
+ display: inline-block;
29
+ text-decoration: inherit;
30
+ }
31
+
32
+ /* makes the font 33% larger relative to the icon container */
33
+ .icon-large:before {
34
+ vertical-align: top;
35
+ font-size: 1.333em;
36
+ }
37
+
38
+ /* keeps button heights with and without icons the same */
39
+ .btn [class^="icon-"], .btn [class*=" icon-"] {
40
+ line-height: 0.9em;
41
+ }
42
+
43
+ li [class^="icon-"], li [class*=" icon-"] {
44
+ display: inline-block;
45
+ width: 1.25em;
46
+ text-align: center;
47
+ }
48
+
49
+ /* 1.5 increased font size for icon-large * 1.25 width */
50
+ li .icon-large[class^="icon-"], li .icon-large[class*=" icon-"] {
51
+ width: 1.875em;
52
+ }
53
+
54
+ li[class^="icon-"], li[class*=" icon-"] {
55
+ margin-left: 0;
56
+ list-style-type: none;
57
+ }
58
+
59
+ li[class^="icon-"]:before, li[class*=" icon-"]:before {
60
+ text-indent: -2em;
61
+ text-align: center;
62
+ }
63
+
64
+ li[class^="icon-"].icon-large:before, li[class*=" icon-"].icon-large:before {
65
+ text-indent: -1.333em;
66
+ }
67
+
68
+ /*
69
+ Icon Classes
70
+ */
71
+ <% @classes.each_with_index do |name, index| %>
72
+ .icon-<%= name %>:before { content: "\<%= (61696+index).to_s(16) %>"; }<% end %>
@@ -0,0 +1,65 @@
1
+ // *Font Custom - icon webfonts made simple */
2
+
3
+ @font-face {
4
+ font-family: "<%= @name %>";
5
+ src: url("public/fonts/<%= @path %>.eot?#iefix") format("embedded-opentype"),
6
+ url("public/fonts/<%= @path %>.woff") format("woff"),
7
+ url("public/fonts/<%= @path %>.ttf") format("truetype"),
8
+ url("public/fonts/<%= @path %>.svg#<%= @name %>") format("svg");
9
+ font-weight: normal;
10
+ font-style: normal;
11
+ }
12
+
13
+
14
+ [class^="icon-"]:before, [class*=" icon-"]:before {
15
+ font-family: "<%= @name %>";
16
+ font-weight: normal;
17
+ font-style: normal;
18
+ display: inline-block;
19
+ text-decoration: inherit;
20
+ }
21
+
22
+ a [class^="icon-"], a [class*=" icon-"] {
23
+ display: inline-block;
24
+ text-decoration: inherit;
25
+ }
26
+
27
+ // * makes the font 33% larger relative to the icon container */
28
+ // .icon-large:before {
29
+ // vertical-align: top;
30
+ // font-size: 1.333em;
31
+ // }
32
+
33
+ // * keeps button heights with and without icons the same */
34
+ // .btn [class^="icon-"], .btn [class*=" icon-"] {
35
+ // line-height: 0.9em;
36
+ // }
37
+
38
+ // li [class^="icon-"], li [class*=" icon-"] {
39
+ // display: inline-block;
40
+ // width: 1.25em;
41
+ // text-align: center;
42
+ // }
43
+
44
+ // * 1.5 increased font size for icon-large * 1.25 width */
45
+ // li .icon-large[class^="icon-"], li .icon-large[class*=" icon-"] {
46
+ // width: 1.875em;
47
+ // }
48
+
49
+ // li[class^="icon-"], li[class*=" icon-"] {
50
+ // margin-left: 0;
51
+ // list-style-type: none;
52
+ // }
53
+
54
+ // li[class^="icon-"]:before, li[class*=" icon-"]:before {
55
+ // text-indent: -2em;
56
+ // text-align: center;
57
+ // }
58
+
59
+ // li[class^="icon-"].icon-large:before, li[class*=" icon-"].icon-large:before {
60
+ // text-indent: -1.333em;
61
+ // }
62
+
63
+ // *Icon Classes */
64
+ <% @classes.each_with_index do |name, index| %>
65
+ %icon-<%= name %>:before { content: "\<%= (61696+index).to_s(16) %>"; }<% end %>
@@ -0,0 +1,3 @@
1
+ module Fontcustomtoadstool
2
+ VERSION = "0.1.2"
3
+ end
@@ -0,0 +1,36 @@
1
+ require 'listen'
2
+
3
+ module Fontcustom
4
+ class Watcher
5
+ def self.watch(*args)
6
+ callback = Proc.new do |modified, added, removed|
7
+ puts ' >> Changed: ' + modified.join(' ') unless modified.empty?
8
+ puts ' >> Added: ' + added.join(' ') unless added.empty?
9
+ puts ' >> Removed: ' + removed.join(' ') unless removed.empty?
10
+
11
+ changed = modified + added + removed
12
+ Fontcustom.compile(*args) unless changed.empty?
13
+ end
14
+
15
+ dir = args.first
16
+ @listener = Listen.to(dir).filter(/\.(eps|svg)$/).change(&callback)
17
+
18
+ begin
19
+ puts "Fontcustom is watching your icons at " + dir
20
+ Fontcustom.compile(*args)
21
+ @listener.start()
22
+
23
+ # Catches Cmd/Ctrl + C
24
+ # Does listen gem have a better way of handling this?
25
+ rescue SignalException
26
+ stop
27
+ end
28
+ end
29
+
30
+ def self.stop
31
+ # Newline exists so message is not prepended with ^C on SIGTERM
32
+ puts "\nFontcustom is signing off. Goodnight and good luck."
33
+ @listener.stop
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,4 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" id="Layer_1" x="0px" y="0px" width="100px" height="100px" viewBox="0 0 100 100" enable-background="new 0 0 100 100" xml:space="preserve">
2
+ <path d="M50,0C22.389,0,0,22.383,0,49.994V100h100V49.994C100,22.383,77.617,0,50,0z M96.667,96.667H3.333V49.994 c0-25.729,20.938-46.66,46.667-46.66c25.729,0,46.667,20.931,46.667,46.66V96.667z"/>
3
+ <path d="M50,10c-22.083,0-40,17.91-40,39.994V90l30-30V50c0-5.521,4.479-10,10-10c5.521,0,10,4.479,10,10v10l30,30V49.994 C90,27.91,72.09,10,50,10z"/>
4
+ </svg>
@@ -0,0 +1,3 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" id="Layer_1" x="0px" y="0px" width="100px" height="100px" viewBox="0 0 100 100" style="enable-background:new 0 0 100 100;" xml:space="preserve">
2
+ <path style="fill:#010101;" d="M87.5,75c-3.039,0-5.725,1.221-7.886,3.016l-19.056-13.6c1.209-2.49,1.941-5.225,1.941-8.166 c0-4.041-1.318-7.775-3.491-10.828l22.29-22.302C83.154,24.207,85.193,25,87.5,25c6.909,0,12.5-5.591,12.5-12.5S94.409,0,87.5,0 S75,5.591,75,12.5c0,2.307,0.793,4.346,1.88,6.201L54.59,41.004c-3.076-2.197-6.787-3.504-10.84-3.504 c-7.153,0-13.306,4.064-16.467,9.973l-15.052-5.029C11.621,39.637,9.24,37.5,6.25,37.5C2.795,37.5,0,40.295,0,43.75 S2.795,50,6.25,50c1.574,0,2.979-0.635,4.077-1.6l14.966,4.993C25.146,54.334,25,55.273,25,56.25C25,66.602,33.398,75,43.75,75 c5.151,0,9.826-2.088,13.221-5.457l18.933,13.514C75.366,84.448,75,85.926,75,87.5c0,6.896,5.591,12.5,12.5,12.5 S100,94.396,100,87.5S94.409,75,87.5,75z"/>
3
+ </svg>
@@ -0,0 +1,3 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.2" baseProfile="tiny" id="Layer_1" x="0px" y="0px" width="100px" height="100px" viewBox="0 0 100 100" xml:space="preserve">
2
+ <path fill="#000000" d="M96.897,37.513c1.921,0,3.478-1.558,3.478-3.479c0-1.92-1.557-3.478-3.478-3.478s-3.478,1.558-3.478,3.478 c0,0.422,0.079,0.825,0.217,1.2l-10.153,8.649l-12.864-7.567c0.073-0.297,0.116-0.607,0.116-0.927c0-2.142-1.736-3.878-3.878-3.878 c-0.869,0-1.668,0.289-2.314,0.772L52.92,23.054c0.054-0.22,0.086-0.448,0.086-0.684c0-1.581-1.281-2.861-2.861-2.861 s-2.861,1.281-2.861,2.861c0,0.729,0.275,1.393,0.724,1.898l-5.835,12.488c-0.26-0.045-0.526-0.074-0.8-0.074 c-0.86,0-1.662,0.239-2.351,0.647l-15.438-6.915c0.036-0.225,0.06-0.454,0.06-0.689c0-2.38-1.929-4.309-4.309-4.309 c-2.379,0-4.309,1.929-4.309,4.309s1.929,4.309,4.309,4.309c1.352,0,2.556-0.623,3.346-1.596l14.682,6.576 c-0.384,0.674-0.607,1.452-0.607,2.284c0,0.852,0.293,1.605,0.694,2.29l-8.233,8.237c-1.136-0.811-2.506-1.294-4.003-1.294 c-2.642,0-4.915,1.501-6.082,3.684l-0.096-0.032c-0.001,0.012-0.004,0.023-0.005,0.035L7.553,49.002 c0.016-0.134,0.025-0.271,0.025-0.409c0-1.989-1.612-3.601-3.601-3.601s-3.601,1.612-3.601,3.601s1.612,3.601,3.601,3.601 c1.054,0,1.999-0.455,2.657-1.177l11.723,5.329c-0.005,0.013-0.009,0.025-0.015,0.037l0.056,0.019 c-0.054,0.348-0.108,0.694-0.108,1.055c0,1.954,0.813,3.716,2.115,4.975l-0.017,0.013c0.004,0.005,0.008,0.01,0.012,0.014 l-5.973,8.802c-0.155-0.027-0.314-0.044-0.478-0.044c-1.479,0-2.678,1.198-2.678,2.678c0,1.479,1.199,2.678,2.678,2.678 c1.479,0,2.678-1.199,2.678-2.678c0-0.501-0.14-0.969-0.38-1.37l5.364-7.904l0.71-0.877c0.881,0.407,1.859,0.641,2.894,0.641 c1.902,0,3.629-0.771,4.883-2.016l6.993,4.991c-0.199,0.514-0.334,1.06-0.334,1.641c0,2.548,2.065,4.617,4.617,4.617 c2.159,0,3.965-1.483,4.471-3.482l15.916-4.923c0.977,1.815,2.893,3.05,5.099,3.05c1.273,0,2.447-0.417,3.403-1.114l7.12,6.611 c-0.038,0.193-0.059,0.393-0.059,0.597c0,1.734,1.406,3.14,3.14,3.14s3.139-1.405,3.139-3.14c0-1.733-1.405-3.139-3.139-3.139 c-0.707,0-1.358,0.236-1.883,0.631l-6.811-6.323c0.552-0.887,0.893-1.93,0.893-3.05c0-2.815-1.661-5.16-4.661-5.677V39.104 c1-0.172,1.082-0.478,1.513-0.878l13.332,7.848l11.179,15.655c-0.092,0.23-0.146,0.481-0.146,0.745c0,1.125,0.91,2.037,2.035,2.037 s2.037-0.912,2.037-2.037s-0.913-2.037-2.038-2.037c-0.03,0-0.06,0.003-0.09,0.005L85.094,45.422l9.931-8.459 C95.565,37.31,96.207,37.513,96.897,37.513z M61.07,62.474c0,0.21,0.013,0.416,0.035,0.62l-15.275,4.724 c-0.522-1.975-2.316-3.435-4.458-3.435c-1.123,0-2.114,0.451-2.913,1.113l-7.038-5.022c0.447-0.92,0.717-1.93,0.717-3.017 c0-1.492-0.487-2.871-1.29-3.999l8.233-8.237c0.686,0.401,1.438,0.694,2.291,0.694c1.642,0,3.079-0.857,3.897-2.147l17.222,14.914 C61.609,59.699,61.07,61.022,61.07,62.474z M66,56.797c-1,0.1-1.135,0.273-1.596,0.502l-18.36-15.846 c0.002-0.052-0.023-0.102-0.023-0.154c0-1.485-0.718-2.802-1.806-3.646l5.799-12.428c0.046,0.002,0.088,0.007,0.134,0.007 c0.53,0,1.023-0.147,1.449-0.399l11.621,9.229c-0.151,0.415-0.113,0.861-0.113,1.328c0,1.757,0.895,3.238,2.895,3.715V56.797z"/>
3
+ </svg>
@@ -0,0 +1,42 @@
1
+ require 'spec_helper'
2
+
3
+ describe Fontcustom do
4
+ let(:input_dir) { 'spec/fixtures/vectors' }
5
+ let(:output_dir) { 'tmp' }
6
+ let(:fake_file) { output_dir + '/non-vector.txt' }
7
+
8
+ context 'when ouput_dir already contains files' do
9
+ # Compile, add non-fontcustom file, change input vectors, recompile
10
+ before(:all) do
11
+ # originals
12
+ Fontcustom.compile(input_dir, '-o', output_dir, '-n', 'Original Font')
13
+ FileUtils.touch(fake_file, :verbose => true)
14
+ @original_fonts = Dir[output_dir + '/fontcustom-*.{woff,eot,ttf,svg}']
15
+ @original_css = File.read(output_dir + '/fontcustom.css')
16
+
17
+ FileUtils.mv(input_dir + '/C.svg', input_dir + '/E.svg', :verbose => true)
18
+ Fontcustom.compile(input_dir, '-o', output_dir)
19
+ end
20
+
21
+ after(:all) do
22
+ cleanup(output_dir)
23
+ FileUtils.mv(input_dir + '/E.svg', input_dir + '/C.svg', :verbose => true)
24
+ end
25
+
26
+ it 'should delete previous fontcustom generated files' do
27
+ new_files = Dir[output_dir + '/*']
28
+ @original_fonts.each do |original|
29
+ new_files.should_not include(original)
30
+ end
31
+ end
32
+
33
+ it 'should not delete non-fontcustom generated files' do
34
+ File.exists?(fake_file).should be_true
35
+ end
36
+
37
+ it 'should generate different css' do
38
+ new_css = File.read(output_dir + '/fontcustom.css')
39
+ new_css.should_not equal(@original_css)
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,75 @@
1
+ require 'spec_helper'
2
+
3
+ describe Fontcustom::Generator do
4
+ let(:input_dir) { 'spec/fixtures/vectors' }
5
+ let(:output_dir) { 'tmp' }
6
+
7
+ context 'normally' do
8
+ before(:all) { Fontcustom::Generator.start([input_dir, '-o', output_dir]) }
9
+ after(:all) { cleanup(output_dir) }
10
+
11
+ it 'should create webfonts' do
12
+ exts = %w( .woff .eot .ttf .svg )
13
+ files = Dir[output_dir + '/*']
14
+ files.map! { |file| File.extname(file) }
15
+
16
+ exts.each { |ext| files.should include(ext) }
17
+ end
18
+
19
+ it 'should print font-face declarations in fontcustom.css' do
20
+ stylesheet = File.read(output_dir + '/fontcustom.css')
21
+ files = Dir[output_dir + '/*.{woff,eot,ttf,svg}']
22
+
23
+ files.each do |file|
24
+ stylesheet.should include(File.basename(file))
25
+ end
26
+ end
27
+
28
+ it 'should print icon-* CSS classes in fontcustom.css' do
29
+ stylesheet = File.read(output_dir + '/fontcustom.css')
30
+ icon_names = Dir[input_dir + '/*'].map { |file| File.basename(file)[0..-5].gsub(/\W/, '-').downcase }
31
+
32
+ icon_names.each do |name|
33
+ stylesheet.should include('.icon-' + name)
34
+ end
35
+ end
36
+ end
37
+
38
+ context 'when input_dir does not exist' do
39
+ let(:fake_input_dir) { 'does/not/exist' }
40
+
41
+ it 'should raise an error' do
42
+ results = capture(:stderr) { Fontcustom::Generator.start([fake_input_dir, '-o', output_dir]) }
43
+ results.should =~ /doesn't exist or isn't a directory/
44
+ end
45
+ end
46
+
47
+ context 'when input_dir does not contain vectors' do
48
+ let(:empty_input_dir) { 'spec/fixtures/empty' }
49
+
50
+ it 'should raise an error' do
51
+ results = capture(:stderr) { Fontcustom::Generator.start([empty_input_dir, output_dir]) }
52
+ results.should =~ /doesn't contain any vectors/
53
+ end
54
+ end
55
+
56
+ context 'when flags are passed' do
57
+ it 'should save output files with a custom name' do
58
+ Fontcustom::Generator.start([input_dir, '-o', output_dir, '-n', 'customname'])
59
+
60
+ file = Dir[File.join(output_dir, 'customname-*.ttf')].first
61
+ File.exists?(file).should be_true
62
+
63
+ cleanup(output_dir)
64
+ end
65
+
66
+ it 'should exclude the filename hash' do
67
+ Fontcustom::Generator.start([input_dir, '-o', output_dir, '--nohash'])
68
+
69
+ file = File.join(output_dir, 'fontcustom.ttf')
70
+ File.exists?(file).should be_true
71
+
72
+ cleanup(output_dir)
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,34 @@
1
+ require 'spec_helper'
2
+
3
+ describe Fontcustom do
4
+ let (:input_dir) { 'spec/fixtures/vectors' }
5
+ let (:output_dir) { 'tmp' }
6
+ let (:fontcustom) { Fontcustom }
7
+
8
+ before(:all) do
9
+ fontcustom.watch(input_dir, output_dir)
10
+ end
11
+
12
+ context '#watch' do
13
+ it 'should detect when a vector file changes' do
14
+ `mv spec/fixtures/vectors/B.svg spec/fixtures/vectors/E.svg`
15
+ sleep 1
16
+ fontcustom.should_receive(:compile).with(input_dir, output_dir)
17
+ end
18
+
19
+ it 'should detect when a vector file is added' do
20
+ end
21
+
22
+ it 'should detect when a vector file is removed' do
23
+ end
24
+
25
+ it 'should send complain if the dir has no vectors' do
26
+ end
27
+ end
28
+
29
+ after(:all) do
30
+ Fontcustom.stop
31
+ `mv spec/fixtures/vectors/E.svg spec/fixtures/vectors/B.svg`
32
+ cleanup(output_dir)
33
+ end
34
+ end
@@ -0,0 +1,29 @@
1
+ require 'spork'
2
+
3
+ Spork.prefork do
4
+ require 'rspec'
5
+ require 'fileutils'
6
+
7
+ RSpec.configure do |c|
8
+ def cleanup(dir)
9
+ FileUtils.rm_r(dir, :verbose => true) if File.exists?(dir)
10
+ end
11
+
12
+ def capture(stream)
13
+ begin
14
+ stream = stream.to_s
15
+ eval "$#{stream} = StringIO.new"
16
+ yield
17
+ result = eval("$#{stream}").string
18
+ ensure
19
+ eval("$#{stream} = #{stream.upcase}")
20
+ end
21
+
22
+ result
23
+ end
24
+ end
25
+ end
26
+
27
+ Spork.each_run do
28
+ require File.expand_path('../../lib/fontcustom.rb', __FILE__)
29
+ end
metadata ADDED
@@ -0,0 +1,261 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: fontcustomtoadstool
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.2
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Yifei Zhang
9
+ - Joshua Gross
10
+ - Dale Sande
11
+ autorequire:
12
+ bindir: bin
13
+ cert_chain: []
14
+ date: 2012-12-05 00:00:00.000000000 Z
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: json
18
+ requirement: !ruby/object:Gem::Requirement
19
+ none: false
20
+ requirements:
21
+ - - ! '>='
22
+ - !ruby/object:Gem::Version
23
+ version: '0'
24
+ type: :runtime
25
+ prerelease: false
26
+ version_requirements: !ruby/object:Gem::Requirement
27
+ none: false
28
+ requirements:
29
+ - - ! '>='
30
+ - !ruby/object:Gem::Version
31
+ version: '0'
32
+ - !ruby/object:Gem::Dependency
33
+ name: thor
34
+ requirement: !ruby/object:Gem::Requirement
35
+ none: false
36
+ requirements:
37
+ - - ! '>='
38
+ - !ruby/object:Gem::Version
39
+ version: '0'
40
+ type: :runtime
41
+ prerelease: false
42
+ version_requirements: !ruby/object:Gem::Requirement
43
+ none: false
44
+ requirements:
45
+ - - ! '>='
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ - !ruby/object:Gem::Dependency
49
+ name: listen
50
+ requirement: !ruby/object:Gem::Requirement
51
+ none: false
52
+ requirements:
53
+ - - ! '>='
54
+ - !ruby/object:Gem::Version
55
+ version: '0'
56
+ type: :runtime
57
+ prerelease: false
58
+ version_requirements: !ruby/object:Gem::Requirement
59
+ none: false
60
+ requirements:
61
+ - - ! '>='
62
+ - !ruby/object:Gem::Version
63
+ version: '0'
64
+ - !ruby/object:Gem::Dependency
65
+ name: rake
66
+ requirement: !ruby/object:Gem::Requirement
67
+ none: false
68
+ requirements:
69
+ - - ! '>='
70
+ - !ruby/object:Gem::Version
71
+ version: '0'
72
+ type: :development
73
+ prerelease: false
74
+ version_requirements: !ruby/object:Gem::Requirement
75
+ none: false
76
+ requirements:
77
+ - - ! '>='
78
+ - !ruby/object:Gem::Version
79
+ version: '0'
80
+ - !ruby/object:Gem::Dependency
81
+ name: bundler
82
+ requirement: !ruby/object:Gem::Requirement
83
+ none: false
84
+ requirements:
85
+ - - ! '>='
86
+ - !ruby/object:Gem::Version
87
+ version: '0'
88
+ type: :development
89
+ prerelease: false
90
+ version_requirements: !ruby/object:Gem::Requirement
91
+ none: false
92
+ requirements:
93
+ - - ! '>='
94
+ - !ruby/object:Gem::Version
95
+ version: '0'
96
+ - !ruby/object:Gem::Dependency
97
+ name: rspec
98
+ requirement: !ruby/object:Gem::Requirement
99
+ none: false
100
+ requirements:
101
+ - - ! '>='
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ none: false
108
+ requirements:
109
+ - - ! '>='
110
+ - !ruby/object:Gem::Version
111
+ version: '0'
112
+ - !ruby/object:Gem::Dependency
113
+ name: fakefs
114
+ requirement: !ruby/object:Gem::Requirement
115
+ none: false
116
+ requirements:
117
+ - - ! '>='
118
+ - !ruby/object:Gem::Version
119
+ version: '0'
120
+ type: :development
121
+ prerelease: false
122
+ version_requirements: !ruby/object:Gem::Requirement
123
+ none: false
124
+ requirements:
125
+ - - ! '>='
126
+ - !ruby/object:Gem::Version
127
+ version: '0'
128
+ - !ruby/object:Gem::Dependency
129
+ name: spork
130
+ requirement: !ruby/object:Gem::Requirement
131
+ none: false
132
+ requirements:
133
+ - - ! '>='
134
+ - !ruby/object:Gem::Version
135
+ version: '0'
136
+ type: :development
137
+ prerelease: false
138
+ version_requirements: !ruby/object:Gem::Requirement
139
+ none: false
140
+ requirements:
141
+ - - ! '>='
142
+ - !ruby/object:Gem::Version
143
+ version: '0'
144
+ - !ruby/object:Gem::Dependency
145
+ name: guard-spork
146
+ requirement: !ruby/object:Gem::Requirement
147
+ none: false
148
+ requirements:
149
+ - - ! '>='
150
+ - !ruby/object:Gem::Version
151
+ version: '0'
152
+ type: :development
153
+ prerelease: false
154
+ version_requirements: !ruby/object:Gem::Requirement
155
+ none: false
156
+ requirements:
157
+ - - ! '>='
158
+ - !ruby/object:Gem::Version
159
+ version: '0'
160
+ - !ruby/object:Gem::Dependency
161
+ name: guard-rspec
162
+ requirement: !ruby/object:Gem::Requirement
163
+ none: false
164
+ requirements:
165
+ - - ! '>='
166
+ - !ruby/object:Gem::Version
167
+ version: '0'
168
+ type: :development
169
+ prerelease: false
170
+ version_requirements: !ruby/object:Gem::Requirement
171
+ none: false
172
+ requirements:
173
+ - - ! '>='
174
+ - !ruby/object:Gem::Version
175
+ version: '0'
176
+ - !ruby/object:Gem::Dependency
177
+ name: rb-fsevent
178
+ requirement: !ruby/object:Gem::Requirement
179
+ none: false
180
+ requirements:
181
+ - - ~>
182
+ - !ruby/object:Gem::Version
183
+ version: 0.9.1
184
+ type: :development
185
+ prerelease: false
186
+ version_requirements: !ruby/object:Gem::Requirement
187
+ none: false
188
+ requirements:
189
+ - - ~>
190
+ - !ruby/object:Gem::Version
191
+ version: 0.9.1
192
+ description: Transforms EPS and SVG vectors into icon webfonts. Generates compatible
193
+ CSS for Toadstool framework
194
+ email:
195
+ - yz@yifei.co
196
+ - joshua@gross.is
197
+ - dale.sande@gmail.com
198
+ executables:
199
+ - fontcustom
200
+ extensions: []
201
+ extra_rdoc_files: []
202
+ files:
203
+ - .gitignore
204
+ - CHANGELOG.md
205
+ - Gemfile
206
+ - Guardfile
207
+ - LICENSES.txt
208
+ - README.md
209
+ - Rakefile
210
+ - bin/fontcustom
211
+ - fontcustomToadstool.gemspec
212
+ - lib/fontcustom.rb
213
+ - lib/fontcustom/cli.rb
214
+ - lib/fontcustom/generator.rb
215
+ - lib/fontcustom/scripts/generate.py
216
+ - lib/fontcustom/scripts/sfnt2woff
217
+ - lib/fontcustom/templates/fontcustom.css
218
+ - lib/fontcustom/templates/fontcustom.scss
219
+ - lib/fontcustom/version.rb
220
+ - lib/fontcustom/watcher.rb
221
+ - spec/fixtures/empty/no_vectors_here.txt
222
+ - spec/fixtures/vectors/C.svg
223
+ - spec/fixtures/vectors/D.svg
224
+ - spec/fixtures/vectors/a_R3ally-eXotic f1Le Name.svg
225
+ - spec/fontcustom/fontcustom_spec.rb
226
+ - spec/fontcustom/generator_spec.rb
227
+ - spec/fontcustom/watcher_spec.rb.off
228
+ - spec/spec_helper.rb
229
+ homepage: https://github.com/blackfalcon/fontcustom.sass
230
+ licenses: []
231
+ post_install_message:
232
+ rdoc_options: []
233
+ require_paths:
234
+ - lib
235
+ required_ruby_version: !ruby/object:Gem::Requirement
236
+ none: false
237
+ requirements:
238
+ - - ! '>='
239
+ - !ruby/object:Gem::Version
240
+ version: '0'
241
+ required_rubygems_version: !ruby/object:Gem::Requirement
242
+ none: false
243
+ requirements:
244
+ - - ! '>='
245
+ - !ruby/object:Gem::Version
246
+ version: '0'
247
+ requirements: []
248
+ rubyforge_project:
249
+ rubygems_version: 1.8.24
250
+ signing_key:
251
+ specification_version: 3
252
+ summary: Generate custom icon webfonts from the comfort of the command line.
253
+ test_files:
254
+ - spec/fixtures/empty/no_vectors_here.txt
255
+ - spec/fixtures/vectors/C.svg
256
+ - spec/fixtures/vectors/D.svg
257
+ - spec/fixtures/vectors/a_R3ally-eXotic f1Le Name.svg
258
+ - spec/fontcustom/fontcustom_spec.rb
259
+ - spec/fontcustom/generator_spec.rb
260
+ - spec/fontcustom/watcher_spec.rb.off
261
+ - spec/spec_helper.rb