I made Gruntfile.js like this:
'use strict';
module.exports = function (grunt) {
grunt.loadNpmTasks('grunt-favicons');
grunt.loadNpmTasks('grunt-contrib-imagemin');
grunt.loadNpmTasks('grunt-bake');
grunt.loadNpmTasks('grunt-contrib-htmlmin');
grunt.loadNpmTasks('grunt-contrib-less');
grunt.loadNpmTasks('grunt-autoprefixer');
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-uglify');
grunt.loadNpmTasks('grunt-cwebp');
grunt.loadNpmTasks('grunt-responsive-images');
grunt.loadNpmTasks('grunt-retinafy');
grunt.loadNpmTasks('grunt-spritesmith');
grunt.loadNpmTasks('grunt-notify');
grunt.loadNpmTasks('grunt-contrib-watch');
require('load-grunt-tasks')(grunt);
grunt.initConfig({
pkg : grunt.file.readJSON('package.json'),
watch: {
html: {
files: ['./assets/**/*.html'],
tasks: ['html'],
options: {
spawn: false,
livereload: true,
},
},
less: {
files: ['./assets/less/**/*.less'],
tasks: ['less_files'],
options: {
spawn: false,
livereload: true,
},
},
js: {
files: ['./assets/js/**/*.js'],
tasks: ['js'],
options: {
spawn: false,
livereload: true,
},
},
img: {
files: ['./assets/images/**/*.png'],
tasks: ['img'],
options: {
spawn: false,
livereload: true,
},
},
favicon: {
files: ['./assets/favicon/favicon.png'],
tasks: ['favicon'],
options: {
spawn: false,
livereload: true,
},
},
icons: {
files: ['./assets/sprites/**/*.png'],
tasks: ['icons'],
options: {
spawn: false,
livereload: true,
},
},
},
shell: {
can_i_use_update: {
command: 'npm update caniuse-db'
}
},
favicons: {
options: {},
icons: {
src: 'assets/favicon/favicon.png',
dest: 'dist/favicons/'
}
},
imagemin: {
images: {
options: {
optimizationLevel: 4,
progressive: true,
interlaced: true
},
files: [{
expand: true,
cwd: './dist/images',
src: ['**/*.{png,jpg,jpeg,gif}'],
dest: './dist/images/'
}]
},
favicons: {
options: {
optimizationLevel: 4,
progressive: true,
interlaced: true
},
files: [{
expand: true,
cwd: './dist/favicons',
src: ['**/*.{png,jpg,jpeg,gif}'],
dest: './dist/favicons/'
}]
},
sprite: {
options: {
optimizationLevel: 4,
progressive: true,
interlaced: true
},
files: {
'./dist/images/sprite.png': './dist/images/sprite.png',
}
},
},
bake: {
build: {
options: {},
files: [{
expand: true,
cwd: './assets/',
src: ['*.html'],
dest: './dist/',
ext: '.html'
}]
}
},
htmlmin: {
dist: {
options: {
removeComments: true,
collapseWhitespace: true,
conservativeCollapse: true,
preserveLineBreaks: true
},
files: [{
expand: true,
cwd: './dist/',
src: ['**/*.html'],
dest: './dist/'
}]
}
},
less: {
build: {
options: {
compress: true,
ieCompat: true,
sourceMap: true,
sourceMapFilename: './dist/css/style.map',
sourceMapURL: 'css/style.map'
},
files: {
"./dist/css/style.css": "./assets/less/style.less"
}
}
},
autoprefixer: {
options: {
browsers: ['last 5 versions', 'ie 8', 'ie 9', '> 5%']
},
build: {
"./dist/css/style.css":"./dist/css/style.css"
},
},
concat: {
options: {},
dist: {
src: ['./assets/js/*.js'],
dest: './dist/js/script.js',
},
},
uglify: {
build: {
options: { compress: true },
files: { "./dist/js/script.js":"./dist/js/script.js" }
}
},
cwebp: {
build: {
options: {
q: 80,
alpha_q: 80
},
files: [{
expand: true,
cwd: './dist/images/',
src: ['**/*.{png,jpg,jpeg,gif}'],
dest: './dist/images/webp'
}]
}
},
responsive_images: {
build: {
options: {
engine:"im",
sizes: [{
width: 640,
},{
width: 1024,
},{
width: 1920
}]
},
files: [{
expand: true,
src: ['**.{jpg,gif,png}'],
cwd: './assets/images/',
custom_dest: './dist/images/responsive/{%= width %}/'
}]
}
},
retinafy: {
build: {
options: {
sizes: {
'75%': { suffix: '@1.5x' },
'100%': { suffix: '@2x' }
}
},
files: [{
expand: true,
cwd: './dist/images/',
src: ['**/*.{jpg,jpeg,gif,png}'],
dest: './dist/images/'
}],
}
},
sprite:{
all: {
src: './assets/sprites/*.png',
dest: './dist/images/sprite.png',
destCss: './assets/less/sprite.less'
}
},
notify_hooks: {
options: {
enabled: true,
max_jshint_notifications: 5, // maximum number of notifications from jshint output
title: "Project Name", // defaults to the name in package.json, or will use project directory's name
success: true, // whether successful grunt executions should be notified automatically
duration: 2 // the duration of notification in seconds, for `notify-send only
}
}
});
grunt.task.run('notify_hooks');
grunt.registerTask('html', ['bake', 'htmlmin']);
grunt.registerTask('less_files', ['less', 'autoprefixer']);
grunt.registerTask('js', ['concat', 'uglify']);
grunt.registerTask('img', ['responsive_images', 'retinafy', 'imagemin:images', 'cwebp']);
grunt.registerTask('favicon', ['favicons', 'imagemin:favicons']);
grunt.registerTask('icons', ['sprite', 'imagemin:sprite']);
grunt.registerTask('default', ['html','less_files','js','img','favicon','icons','watch']);
};
Everything works, even grunt-contrib watch, but only for old and modified files. It doesn't see any new files in watched folders. It doesn't work on different versions of grunt-contrib-watch. Any ideas?
node -v v0.12.7
npm -v 2.11.3
OSX 10.10.4 Yosemite
I think you should strip the ./
at the beginning. It never needs to be prepended. It could be related to this issue when ./
is prepended, it breaks some of the events.
Try also setting the options to be:
options: {
event: ['changed', 'added', 'deleted']
}
The default setting is set to all
but it has been reported that sometimes it doesn't work.
If all failed, there is an alternative solution. Drop grunt-contrib-watch
and try grunt-simple-watch
. Here you can find why grunt-contrib-watch
is causing troubles.
Side note: I realized that you are loading all the tasks manually then using load-grunt-task
like this:
grunt.loadNpmTasks('grunt-favicons');
grunt.loadNpmTasks('grunt-contrib-imagemin');
grunt.loadNpmTasks('grunt-bake');
grunt.loadNpmTasks('grunt-contrib-htmlmin');
grunt.loadNpmTasks('grunt-contrib-less');
grunt.loadNpmTasks('grunt-autoprefixer');
grunt.loadNpmTasks('grunt-contrib-concat');
grunt.loadNpmTasks('grunt-contrib-uglify');
grunt.loadNpmTasks('grunt-cwebp');
grunt.loadNpmTasks('grunt-responsive-images');
grunt.loadNpmTasks('grunt-retinafy');
grunt.loadNpmTasks('grunt-spritesmith');
grunt.loadNpmTasks('grunt-notify');
grunt.loadNpmTasks('grunt-contrib-watch');
require('load-grunt-tasks')(grunt);
For your information; you don't need to load all the tasks because load-grunt-tasks
do it for you automatically. load-grunt-tasks
scan the packages.json
file for the tasks that you have and automatically load them. You can safely remove all the grunt.loadNpmTasks(xxx)
and that task will be loaded (as long as it is mentioned in packages.json
)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With