深入浅出vue图片路径的实现


Posted in Javascript onSeptember 04, 2019

基础

1.webpack打包本质

本质就是nodejs去执行webpack脚本,由webpack脚本对项目各个文件进行必要的编译(通俗而言即字符串处理),再输出到某个目录

2.import from 和require

webpack相关脚本中的require和我们前端js文件中使用的require函数不是一回事,它的require是nodejs的关键字。

而前端js文件中,使用到的require在编译时相当于一个webpack定义的关键字,运行时则是webpack提供的一个函数。主要能力有:完成导入,参数可以省略部分后缀名(需要配置)、是目录时导入该目录下的index.js、能够使用别名(alias,需要配置)、导入图片(实际导入为base64编码后的字符串),通过编译时提供信息给各个loader处理以获得各种加载导入功能。import from是webpack提供的语法糖,可当作是const xx=require(xxxx)的组合。

3.webpack模块化处理解析配置

即webpack的resolve配置:解析(resolve) 

resolve: {
 extensions: ['.js', '.vue', '.json'],
 alias: {
  '@': resolve('src'),//此resolve通常是外面定义的一个nodejs的函数,用于生成绝对路径
  '@assets': resolve('src/assets')
 }
 },

上面require提到的别名、可省略扩展名在这里配置。

至于require函数中的路径参数,具体的解析法则如下:webpack如何解析代码模块路径

1.解析相对路径
查找相对当前模块的路径下是否有对应文件或文件夹
是文件则直接加载
是文件夹则继续查找文件夹下的 package.json 文件
有 package.json 文件则按照文件中 main 字段的文件名来查找文件
无 package.json 或者无 main 字段则查找 index.js 文件.

2.解析模块名
查找当前文件目录下,父级目录及以上目录下的 node_modules 文件夹,看是否有对应名称的模块

3.解析绝对路径
直接查找对应路径的文件

正文

1.图片处理及路径转换

一般由url-loader和file-loader处理。

url-loader

这个简单,把小图片转换成base64编码并返回该base64编码的字符串。即js代码var jpg=require('./assets/a.jpg')中,如果编译时能找到该图片且该图片大小小于规定值,那么url-loader返回该图片的base64编码,变量jpg的值将会是该图片的base64编码。

file-loader

file-loader将处理url-loader没处理的那些大图片,它会把图片复制到指定目录并返回public URL(参见file-loader文档),代表编译后运行时该图片的url路径字符串。即js代码var jpg=require('./assets/b.jpg')中,如果编译时能找到该图片,那么jpg的值将会是/img/b.jpg(具体取决于配置)

当前目录./的差异

注意css和js、html的当前路径不一致。css的./是指该css文件所在路径,而js、html中的./是指浏览器当前地址栏的url的路径目录。

2.html、js、css的处理

js中使用require函数就行,这里谈一下html和css中的处理。

html中,由vue-loader提供处理(语法糖)。其默认选项下,会把video、img、source标签的src属性放入require函数并把结果替换到原位置。也就是: vue-loader提取这些标签src属性->require函数->file-loader或url-loader处理->使用返回值进行替换。类似的,可以右转百度搜索 vue-loader transformToRequire 这个东西,你可以扩展它让其他标签的属性同样拥有该语法糖。

css中,由css-loader提供处理。类似于上面的html,css-loader会把url(./assets/b.jpg)给处理成url(/img/b.jpg),同样通过require函数获取处理结果。

注意,在html和css中,绝对路径的写法编译时将不被处理(loader判断),即url(/assets/b.jpg)编译后不变。而js中require('/assets/b.jpg')编译时将被认为是打包本地磁盘中/assets/b.jpg文件,不存在时将编译报错。

3.进阶:别名的使用

即上面提到的webpack模块化处理,js中@/assets/a.jpg这种。

html中:可直接使用,也可使用~指示webpack这是一个模块路径,即src='@/assets/a.jpg'或src='~@/assets/a.jpg'都是可行的
css中,必须使用~指示webpack这是一个模块路径,即url(~@/assets/b.jpg)

js中,不用写~,webpack一定对其使用模块路径解析。

同时注意,需要把别名字符串的部分直接包含在参数中。即

let number=1, p1='./', p2='@assets'

img.src=require(`./assets/img${number}.jpg`)//正确
img.src=require(`@assets/img${number}.jpg`)//正确
img.src=require(`${p1}assets/img${number}.jpg`)//正确

img.src=require(`${p2}/img${number}.jpg`)//错误

我也不知道这个是bug还是什么鬼了,有了解的大佬可以说下

4.hash和history模式

应该都知道,即http://localhost/#/a/b/c这样的hash模式中,html和js的./a.jpg均为http://localhost/a.jpg。而http://localhost/a/b/c这样的history模式中,html和js的./a.jpg均为http://localhost/a/b/a.jpg,此时如果设置publicPath: './',那么请注意前面提到过css中./是以css文件所在目录为起点的,而loader会把html的标签的src、css的url函数的路径统一处理,此时可能会由于html、css的当前目录./差异导致某一方找不到图片。

解决方案简单,history模式时publicPath不要用相对路径、html或css其中一方手动注意代码写法绕开loader的处理即可,逻辑搞清即可,处理方法多样。

5.常见问题

不了解@vue/cli项目中file-loader的选项设置、不了解webpack各模板中如何间接设置file-loader的选项设置。
解决靠自己了,或者右转百度,说不定直接抄过来给file-loader设置publicPath: './'恰好对上项目结构而解决问题

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
IE 当eval遇上function的处理
Aug 09 Javascript
jquery插件珍藏(图片局部放大/信息提示框)
Jan 08 Javascript
Extjs实现进度条的两种便捷方式
Sep 26 Javascript
禁用JavaScript控制台调试的方法
Mar 07 Javascript
JavaScript验证图片类型(扩展名)的函数分享
May 05 Javascript
基于JavaScript实现div层跟随滚动条滑动
Jan 12 Javascript
JQuery validate插件验证用户注册信息
May 11 Javascript
javascript日期比较方法实例分析
Jun 17 Javascript
AngularJs用户输入动态模板XSS攻击示例详解
Apr 21 Javascript
Angularjs Ng_repeat中实现复选框选中并显示不同的样式方法
Sep 12 Javascript
JavaScript 引用类型实例详解【数组、对象、严格模式等】
May 13 Javascript
Vuex中的Mutations的具体使用方法
Jun 01 Javascript
webpack 如何解析代码模块路径的实现
Sep 04 #Javascript
layui使用button按钮 点击出现弹层 弹层中加载表单的实例
Sep 04 #Javascript
微信小程序 自定义复选框实现代码实例
Sep 04 #Javascript
layui弹出框Tab选项卡的示例代码
Sep 04 #Javascript
在layui tab控件中载入外部html页面的方法
Sep 04 #Javascript
微信自定义分享链接信息(标题,图片和内容)实现过程详解
Sep 04 #Javascript
微信小程序按钮点击动画效果的实现
Sep 04 #Javascript
You might like
简单易用的计数器(数据库)
2006/10/09 PHP
thinkphp实现数组分页示例
2014/04/13 PHP
浅谈php优化需要注意的地方
2014/11/27 PHP
php处理json格式数据经典案例总结
2016/05/19 PHP
基于PHP生成简单的验证码
2016/06/01 PHP
PHP定时任务获取微信access_token的方法
2016/10/10 PHP
thinkphp隐藏index.php/home并允许访问其他模块的实现方法
2016/10/13 PHP
JS中字符问题(二进制/十进制/十六进制及ASCII码之间的转换)
2008/11/03 Javascript
javascript学习笔记(十七) 检测浏览器插件代码
2012/06/20 Javascript
表单元素与非表单元素刷新区别详细解析
2013/11/06 Javascript
通过url查找a元素并点击
2014/04/09 Javascript
js显示当前日期时间和星期几
2015/10/22 Javascript
基于javascript实现全国省市二级联动下拉选择菜单
2016/01/28 Javascript
jquery配合.NET实现点击指定绑定数据并且能够一键下载
2016/10/28 Javascript
AngularJS创建一个上传照片的指令实例代码
2018/02/24 Javascript
解决vue-cli + webpack 新建项目出错的问题
2018/03/20 Javascript
vue打包npm run build时候界面报错的解决
2020/08/13 Javascript
[02:55]含熏伴清风,风行者至宝、屠夫身心及典藏宝瓶二展示
2020/09/08 DOTA
使用Python脚本生成随机IP的简单方法
2015/07/30 Python
Python批量修改文本文件内容的方法
2016/04/29 Python
Python的消息队列包SnakeMQ使用初探
2016/06/29 Python
python bluetooth蓝牙信息获取蓝牙设备类型的方法
2019/11/29 Python
python实现银行实战系统
2020/02/26 Python
python中zip()函数遍历多个列表方法
2021/02/18 Python
驴妈妈旅游网:中国新型的B2C旅游电子商务网站
2016/08/16 全球购物
意大利香水和化妆品购物网站:Parfimo.it
2019/10/06 全球购物
瑞士最大的图书贸易公司:Orell Füssli
2019/12/28 全球购物
德尔福集团DELPHI的笔试题
2012/02/22 面试题
办公室主任主任岗位责任制
2014/02/11 职场文书
农民工工资支付承诺函
2014/03/31 职场文书
诚信承诺书模板
2014/05/26 职场文书
三八妇女节演讲稿
2014/05/27 职场文书
百日安全生产活动总结
2014/07/05 职场文书
个人师德师风自我剖析材料
2014/09/29 职场文书
小学教育见习总结
2015/06/23 职场文书
2017新年晚会开幕词
2016/03/03 职场文书