您的当前位置:首页正文

webpack中如何使用雪碧图的示例代码

2020-11-27 来源:筏尚旅游网

一、什么是雪碧图?

CSS雪碧 即CSS Sprite,也有人叫它CSS精灵,是一种CSS图像合并技术,该方法是将小图标和背景图像合并到一张图片上,然后利用css的背景定位来显示需要显示的图片部分。

二:为什么要用雪碧图

结合我们公司的需求来说,因为有很多组件,每个组件下有大概50张图片,每张图片是一个请求,也就是发了300多个请求,这样是很可怕的,所以为了优化性能,减少http请求,决定采用雪碧图的形式。

雪碧图是将你想要的很多张图片整理成一张图片,然后通过background-*来进行图片识别和定位来达到之前的效果。

三:如何使用雪碧图

雪碧图在之前有很多方式,如ps之类,现在最佳的方案还是在webpack-spritesmith。

我其实对webpack并不是很了解,我现在列出使用方法和我在使用webpack时候遇到的问题。

1.安装

执行命令行:npm install --save-dev webpack-spritesmith

2.在webpack.config.js中写入

 var path = require('path')

 var SpritesmithPlugin = require('webpack-spritesmith')

 //自定义样式
 var templateFunction = function (data) {
 var shared = '.ico { background-size: TWpx THpx }'
 .replace('TW', data.sprites[0].total_width / 2)
 .replace('TH', data.sprites[0].total_height / 2)

 var perSprite = data.sprites.map(function (sprite) {
 return '&.element-N {\n width: Wpx;\n height: Hpx;\n background-position: Xpx Ypx;\n}'
 .replace('N', sprite.name)
 .replace('W', sprite.width / 2)
 .replace('H', sprite.height / 2)
 .replace('X', sprite.offset_x / 2)
 .replace('Y', sprite.offset_y / 2)
 .replace('TW', sprite.total_width / 2)
 .replace('TH', sprite.total_height / 2)
 }).join('\n')

 return shared + '\n' + perSprite
 }

 module.exports = {
 ...
 module: {
 rules: [
 {test: /\.styl$/, use: [
 'style-loader',
 'css-loader',
 'stylus-loader'
 ]},
 {test: /\.png$/, use: [
 'file-loader?name=i/[hash].[ext]'
 ]}
 ]
 },
 resolve: {
 modules: ['node_modules', 'spritesmith-generated']
 },
 plugins: [
 new SpritesmithPlugin({
 src: { //引入路径
 cwd: path.resolve(__dirname, 'src/images/ios/'),
 glob: '*.png'
 },
 target: { //
输出路径 image: path.resolve(__dirname, 'src/spritesmith-generated/ios.png'), css: [ [path.resolve(__dirname, 'src/spritesmith-generated/sprite-1.css'), { format: 'function_based_template' }], [path.resolve(__dirname, 'src/spritesmith-generated/sprite-2.css'), { format: 'handlebars_based_template' }] ] }, customTemplates: { 'function_based_template': templateFunction, //自定义输出什么样的css样式 }, apiOptions: { cssImageRef: 'ios.png' } }) ] }

3.根据地址更改后执行命令

wbpack

其实这样已经满足了大部分需求,根据需要将你所在的输入和输出地址进行更改即可,可以设置自己想要设置的的css(style-components、styl等),然后直接复制在自己的项目css文件,很有灵活性。

四:需要注意的点

我有的时候指定不同文件下的图片合成一张雪碧图,那该如何呢

例如我的需求是:

  • resources
  • ios
  • images
  • ant
  • images
  • ios
  • images
  • ...
  • 翻译: resources下有几个文件夹(ios、ant、ios),相对应下面images文件夹放着各自对应的图片。

    需要注意下,它是支持glob的

    src: { 
     //引入路径
     cwd: path.resolve(__dirname, 'src/images/ios/'),
     glob: '*.png' //这里进行更改
    },

    这里可以参考在这里根据需求进行设置:http://www.globtester.com/

    把glob改成

    @(wechat|element|ios)/images/*.png

    效果

    五:更深层次的需求

    我其实是想在各自的文件夹下的图片,生成各自文件夹下的雪碧图和css,那该如何实现呢,我写了一部分,还没有写完,感觉遇到了技术难点,我呈现出代码,会继续优化来实现

    var path = require('path')
    var SpritesmithPlugin = require('webpack-spritesmith')
    
    var platforms = ['android', 'ant', 'element', 'ios', 'wechat']//, 'windows']
    
    // var url = 'ant'
    const TARGET = process.env.TARGET
    
    console.log({ TARGET })
    
    module.exports = [TARGET].map(l => {
     console.log(l)
     const url = l
    
     const fn = (data) => {
     console.log(url)
     var shared = 'background-size: TWpx THpx\n'
     .replace('TW', data.sprites[0].total_width / 2)
     .replace('TH', data.sprites[0].total_height / 2)
    
     var perSprite = data.sprites.map(function (sprite) {
     return `&.${url}-N {\n width: Wpx;\n height: Hpx;\n background-position: Xpx Ypx;\n}\n`
     .replace('N', sprite.name)
     .replace('W', sprite.width / 2)
     .replace('H', sprite.height / 2)
     .replace('X', sprite.offset_x / 2)
     .replace('Y', sprite.offset_y / 2)
     .replace('TW', sprite.total_width / 2)
     .replace('TH', sprite.total_height / 2)
     }).join('\n')
    
     return shared + '\n' + perSprite
     }
    
     return {
     module: {
     rules: [
     {test: /\.styl$/, use: [
     'style-loader',
     'css-loader',
     'stylus-loader'
     ]},
     {test: /\.png$/, use: [
     'file-loader?name=i/[hash].[ext]'
     ]}
     ]
     },
     entry: {
     [url]: path.join(__dirname, url),
     },
     output: {
     path: path.join(__dirname, '../parsed/', url),
     filename: '[name].css'
     },
     resolve: {
     modules: ['node_modules', 'spritesmith-generated']
     },
     plugins: [
     new SpritesmithPlugin({
     src: {
     cwd: path.resolve(__dirname, 'images/'+url+'/'),
     glob: '*.png' // '@(android|ant|element|ios|wechat|windows)/*.png'
     },
     target: {
     image: path.resolve(__dirname, '../parsed/'+url+'/'+url+'.png'),
     css: [
     [path.resolve(__dirname, '../parsed/'+url+'/'+url+'.css'), {
     format: 'function_based_template'
     }]
     ]
     },
     customTemplates: {
     'function_based_template': fn
     }
     })
     ]
     }
    })
    显示全文