WebPack 图片处理

WebPack 图片处理

前言:在网页开发的过程中,经常需要处理各类图标。以前我们会使用png/jpg图片,压缩完转base64或直接使用。但是这样会出现一个重要的问题,就是我们的图标是模糊的,放大一定系数之后,这种缺陷会越发的明显。有鉴于此,取而代之的是 iconFont 以及 SVG 等技术。本文会比较各类图片处理技术,各自的使用场合,并说明如何结合 Webpack 使用它们进行网页开发。

PNG / JPG 等像素图片格式

使用

webpack

将切完的 PNG/JPG 等像素图片压缩后(tiny png)放入到项目中,利用 webpack url-loader 载入使用即可,配置如下:

{
    test: /\.(png|jpe?g|gif)(\?.*)?$/,
    loader: 'url-loader',
    options: {
        limit: 10000,
        name: utils.assetsPath('img/[name].[hash:7].[ext]')
    }
},

此处,options 配置了:

  • limit 设置让 webpack 在处理较小的图片(此处为 10 kb),将其转换成base64字符串

  • name 设置用于配置生成后的文件的命名(此处加入了长度为7的hash串)

CSS

利用 background url 引入使用即可:

/* 定义在元素上 */
.icon-logo {
    display: block;
    ...
    background: url(../assets/images/logo.png); 
}

/* 定义在伪元素上 */
.icon-logo:before {
    content: '';
    display: block;
    ...
    background: url(../assets/images/logo.png);
}

PNG

  • 适用场景:无损保存含有透明通道的像素图片(无法提供矢量图),若图片较小可直接转码为base64格式

  • 优点:无损保存像素图片

  • 缺点:文件较大,需压缩处理;像素图片在放大一定的系数后,都会显的模糊

JPG

  • 适用场景:有损保存无透明通道的像素图片(无法提供矢量图),若图片较小可直接转码为base64格式。

  • 优点:有损保存可以压缩图片大小

  • 缺点:较原图有损,同时在放大后,会显的更加模糊

Base64 编码

当图片文件较小时,可以转换成内联的base64格式来使用,使用该方式载入图片有以下优点:

  • 无需通过请求加载图片,能够减少大量的图片请求数,减少页面加载时间

  • 可用于各类预加载场景Loading图

  • 在样式类中内联使用非常方便,删除更新都非常方便,不会产生冗余图片

缺点:

  • base64字符串的大小会比原图大30%左右

  • 无法提供对应的图片预览

IconFont

IconFont 是指将多个图标合并起来转换成字体文件,然后像使用文字一样使用它们,可以对这些图标使用很多文字效果。同时IconFont 图标放大后不会模糊,是非常流行一种图片处理技术。

使用

webpack

利用 webpack url-loader 载入:

{
    test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
    loader: 'url-loader',
    options: {
        limit: 10000,
        name: utils.assetsPath('fonts/[name].[hash:7].[ext]')
    }
}

options 参数含义同上文所述。

CSS

定义 font-family 和对应的样式类来使用:

/* @font-face 定义 IconFont 字体 */
@font-face {
    font-family: 'IconFont';
    src: url('./fonts/icon-font.eot');
    src: url('./fonts/icon-font.eot') format('embedded-opentype'), url('./fonts/icon-font.woff2') format('woff2'), url('./fonts/icon-font.woff') format('woff'), url('./fonts/icon-font.ttf') format('truetype'), url('./fonts/icon-font.svg') format('svg');
    font-weight: normal;
    font-style: normal;
}

/* 定义公用样式类 */
.icon-font {
    display: inline-block;
    font: normal normal normal 14px/1 IconFont;
    font-size: inherit;
}

/* 具体图标样式类(一般在伪元素中使用) */
.icon-font-edit:before {
    content: "\f040";
}

优缺点

优点
  • 可以将多个图标 icon 合并成一个字体文件,减少图片请求次数

  • 放大不会模糊(矢量图)

  • 可以利用部分字体的样式来定制图标(如大小、颜色等)

缺点
  • 一般只用于保存各类简易的图标,不支持单个大文件图片

  • 需提供对应的矢量文件来生成字体文件,生成起来较繁琐,增删图标都需要进行重新生成

  • 不同浏览器支持的字体文件格式不一样,CSS样式中需添加多个字体文件加载源

iconfont.cn

建议多使用 iconfont.cn 网站来生成和管理 IconFont 图标字体文件。

SVG

SVG 是一种网络矢量图片格式,SVG 图片放大不会模糊,同时支持很多矢量图片的操作(如填充、描边、蒙版等),是非常流行的一种图片处理技术,同时其生成和使用非常方便,已经有取代IconFont的趋势。

使用

Vue + Webpack

使用 vue-svg-loader 将 SVG 图片加载成 Vue 组件使用:

{
    test: /\.svg$/,
    loader: 'vue-svg-loader',
    options: {
        svgo: {
            plugins: [
                {
                    cleanupIDs: {
                        minify: false
                    },
                },
                {
                    removeViewBox: false
                }
            ]
        }
    }
},

此处,options中是 vue-svg-loader 的配置信息,plugins 属性定义了使用的 svgo 模块的插件配置,此处禁用了 cleanupIDs 插件的压缩功能以及 viewBox 清除功能(会导致无法使用 width height 属性对 svg 进行缩放)。

说明:vue-svg-loader 使用 svgo 模块来优化和压缩 SVG 图片。svgo 会将 svg 图片内容转换为 js 对象(sax风格),然后利用各类定制插件对该对象进行处理,处理完毕后将该 js 对象再转换为 svg 图片,cleanupIDS 是 svgo 中 id 属性处理插件。

在 vue-svg-loader 的使用过程中,我发现了一个严重的问题,当网页上的 svg 图片较多,并且多个 svg 存在子元素有 id 属性的情况下,这些 id 属性在处理完之后会出现重复的现象,导致一些 svg 图片显示有问题,但是在 github 以及相关平台上未能找到解决方案,于是研究了一下该模块的源码,找出了对应的解决办法。

原因是 svgo 默认使用 cleanupIDs 来清理 svg 元素无用 id属性 或压缩其 id 属性为简单的字符串(如:a, b, c)。但是多个 svg 图片在压缩过程中就会出现重复的 id,在单个页面中出现多个这样的 svg 图片就会导致除了第一个 svg 显示正常以外,其它的 svg 图片无法正常显示。

所以需要禁用 cleanupIDs 插件 minify 压缩功能来确保页面显示正常。

Vue

在组件的 vue 文件中,按照以下形式使用该 SVG 组件:

<template>
    <div>
        ...
        <iconLogo class="icon-logo" />
        ...
    </div>
</template>

<script>
    import iconLogo from '../assets/images/logo.svg';
    
    export default {
        name: 'SVG',
        components: {
            iconLogo
        },
        ...
    }
</script>

<style>
    .icon-logo {
        fill: #ff4500;
    }
</style>

优缺点

优点
  • 一般会压缩后内联使用,无需发送图片请求

  • 放大不会模糊(矢量图)

  • 可以使用大量的矢量图形操作

  • 很容易从各类矢量图形设计软件中导出

  • 结合 webpack 单个文件模块化处理方便,文件管理也很方便

缺点
  • 一般只用于各类图标或简易图形,不支持单个大文件或富表现图片

  • 矢量图片压缩空间有限,一般会比像素图片大

iconfont.cn

建议多使用 iconfont.cn 网站来搜索和使用 SVG 图标文件。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值