zoukankan      html  css  js  c++  java
  • webpack4.0介绍与使用(一)

    1:webpack的基本使用:

    ##在网页中会引用那些静态资源:

      js, css, images, 字体文件和模板文件(.vue)等  

    ##网页总引用静态资源多了以后会有那些问题:

      网页加载速度慢,因为会发起很多二次请求,script标签,link标签,遇到src都会发起请求,随意一个页面要完整显示出来发送的请求数应该由资源数量决定

      处理各种依赖关系

    ##解决办法:

      合并,压缩,精灵图,图片的base64图片(第一次请求是图片转成base64字符串直接放到页面中,荷叶面一起返回,使用过于小图片)

      使用requireJs 或者webpack来解决依赖关系

    ##什么是webpack:

      webpack是一个前端项目构建工具,基于Node.js开发出来的

    ##如何完美实现上述的2中解决方案:

      1:使用Qulp,是基于task任务的

      2:使用webpack,是基于整个项目进行构建的

        +借助webpack这个前端自动化构建工具,可以完美的实现资源的合并,压缩混淆等诸多功能。

        +根据官网图片接收webpack打包过程

    ##webpack安装的而两种方式:

      1:运行 npm i webpack -g 全局安装webpack,这样能在全局使用webpack命令

      2:在项目根目录中运行 npm i webpack --save--dev 安装到项目依赖中

    ##创建根目录文件

      执行 npm init 指令会自动生成一个package.json文件

      在项目根目录中执行 npm i jQuery

    index.html:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <!--不推荐在这里引用任何包和任何css样式文件,因为会发起二次请求,所有包都在main.js中导入-->
        <script src="./main.js"></script>
    </head>
    <body>
    
        <ul>
            <li>这是第1个i</li>
            <li>这是第2个i</li>
            <li>这是第3个i</li>
            <li>这是第4个i</li>
            <li>这是第5个i</li>
            <li>这是第6个i</li>
            <li>这是第7个i</li>
            <li>这是第8个i</li>
            <li>这是第9个i</li>
            <li>这是第10个i</li>
        </ul>
    
    </body>
    </html>

    main.js:

    //这是main.js是我们项目的js入口文件

    //1:a导入jQuery,引入jQuery包用$变量接收,此方法与node中 const $ = require('jquery') 同
    //此为ES6中导入模块的方式
    //由于ES6的语法太高级,浏览器解析不了次引入方式
    import $ from 'jquery'

    $(function(){
    $('li:odd').css('backgroundColor','lightblue');
    $('li:even').css('backgroundColor',function(){
    return '#'+'D97634'
    })
    })

      会报错import语法错误,因为浏览器解析不了,所以要webpack将main.js打包到dist/bundle.js中

      执行命令 ‘webpack ./src/main.js -o ./dist/bundle.js‘(这是webpack4.0版本以上这样用,4.0以下没有其中的‘-o’)

      因为main.js中的代码,涉及到了ES6的新语法,但是浏览器不识别,所以使用webpack前端构建工具,把main.js做了处理打包,生成了一个bundle.js

      修改后的index.html:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <!--不推荐在这里引用任何包和任何css样式文件,因为会发起二次请求,所有包都在main.js中导入-->
        <!--因为main.js中的代码,涉及到了ES6的新语法,但是浏览器不识别-->
        <!--<script src="./main.js"></script>-->
        <!--解决办法,使用webpack前端构建工具,把main.js做了处理打包,生成了一个bundle.js-->
        <script src="../dist/bundle.js"></script>
    </head>
    <body>
    
        <ul>
            <li>这是第1个i</li>
            <li>这是第2个i</li>
            <li>这是第3个i</li>
            <li>这是第4个i</li>
            <li>这是第5个i</li>
            <li>这是第6个i</li>
            <li>这是第7个i</li>
            <li>这是第8个i</li>
            <li>这是第9个i</li>
            <li>这是第10个i</li>
        </ul>
    
    </body>
    </html>
    View Code

      此时效果:

    ##经过此演示,webpack可以做什么:

      1:webpack能狗处理js文件之间的复杂依赖关系

      2:webpack能够处理js的兼容问题,把高级的浏览器不识别的语法,转化为低级的浏览器识别的语法

    2:webpack最基本的配置文件的使用:(此方法【常用】替代指令【webpack ./src/main.js -o ./dist/bundle.js】生成打包文件bundle.js)

      ##首先在文件根目录下添加文件名为:webpack.config.js 的js文件

      webpack.config.js:

    const path = require('path') //node操作URL要用path模块
    
    //node语法
    //这个配置文件就是一个js文件,通过node中的模块操作,向外暴露了一个配置对象
    module.exports = {
        //在配置文件中需要主动指定入口和出口
        entry:path.join(__dirname,'./src/main.js'),//入口,表示webpack要打包那个文件
        output:{//输出文件相关配置
            path:path.join(__dirname,'./dist'),//指定,打包好的文件,输出到那个目录中去
            filename: 'bundle.js'//指定输出文件名称
        }
    }
    View Code

      然后在根目录执行命令:‘webpack’ 的道结果如下图:

      ##当在控制台直接输入 webpack 命令执行的时候,webpack 做了一下几步:

        1:首先 webpack 发现,我们并没有通过命令的形式,给它指定入口和出口;

        2: webpack 就会去项目的根目录中,查找一个叫做 ‘webpack.config.js’ 的配置文件

        3:当找到配置文件后,webpack 会去解析执行配置文件,当解析执行完配置文件后就得到了配置文件中导出的配置对象

        4:当webpack 拿到配置对象后,就拿到了配置对象中,指定的入口和出口,然后进行打包构建

    3.webpack-dev-server的基本使用:(使用此工具来实现自动打包编译的功能)

      ##执行命令在项目根目录下安装此工具:npm i webpack-dev-server

      ##安装完毕后,这个工具的用法和 webpack 命令的用法,完全一样

      ##由于,我们是在项目中,本地安装的 webpack-dev-server,所以无法把她当作脚本命令在powerhell终端中直接运行(只有那些安装到全局 -g 的工具,才能在终端中正常运行)

      ##注意:webpack-dev-server 这个工具,如果想要正常运行,要求在本地项目中必须安装 webpack,项目根目录执行命令:npm i webpack -D

    {
      "name": "bms-vue",
      "version": "1.0.0",
      "description": "",
      "main": "index.js",
      "dependencies": {
        "jquery": "^3.4.1",
        "webpack-dev-server": "^3.4.1"
      },
      "devDependencies": {},
      "scripts": {//配置一些要运行的命令
        "test": "echo "Error: no test specified" && exit 1",
        "dev":"webpack-dev-server" //当执行 npm run dev 的时候会执行辞指令
      },
      "author": "",
      "license": "ISC"
    }
    View Code

      注:如果因为重复装包而导致错误,可以将 node-nodules 删掉,执行 npm i 指令,其中 scripts 节点中用来配置一些要运行的命令,其中 "dev":"webpack-dev-server" 表示当执行 npm run dev 的时候会执行指令:webpack-dev-server

      ##到此为止执行指令:npm run dev 之后修改js文件,控制台显示确实是自动编译了,下图变是执行完指令后的控制台显示:

      如图可看到:webpack output is served from / 意为:webpack输出文件正在被根目录托管,因此 main.js 被自动打包的bundle.js 和 dist 下面的 bundle.js 并非同一文件,只是自动打包的bundle.js无法看到,但可以通过 http://localhost:8080/ 访问到

      因此也可以用script标签引用如:<script src='/bundle.js'></script>,所以要将 index.html 中的 <script src="../dist/bundle.js"></script> 替换掉即可。

      ## webpack-dev-server 帮我们打包成的bundle.js文件,并没有存放到物理磁盘上,二是直接托管到了电脑的内存中,所以我们在项目中根本找不到这个打包好的bundle.js

      ## 我们可以认为,webpack-dev-server 把打包好的文件,以一种虚拟的形式托管到了咱们的项目根目录中,虽然我们看不到它,但是可以认为和 dist     src     node_modules 平级,有一个看不见的文件叫bundle.js。(快)

    3.1 webpack-dev-server的常用命令:

      package.json文件:

      ##指令解析:空格代表传参(推荐方式)

        1:webpack-dev-server :自动打包

        2:--open 执行完 npm run dev 启动完毕后自动打开浏览器访问项目

        3:--port 3000 自定义项目启动端口为3000

        4:--contentBase src 自动打开浏览器的位置为根目录下的是src中的index.html

        5:--hot 不会重新打包,相当于打补丁,减少不必要的代码重新打包编译,并且浏览器会无刷新重载

    4 html-webpack-plugin的两个基本作用(将页面放到内存中)

      ##以上所演示的页面是本地磁盘中的index.html,下面将此HTML页面也放到内存中

        1:首先执行命令:npm i html-webpack-plugin 加载插件

        2:webpack.config.js中添加第一步:如图

                        

        3:webpack.config.js中添加第二部:如图

                        

        最后webpack.config.js文件变为:

    const path = require('path') //node操作URL要用path模块
    
    //导入在内存中生成html页面的插件
    //只要是插件都要放到plugin节点中去
    const htmlWebpackPlugin = require('html-webpack-plugin')
    
    //node语法
    //这个配置文件就是一个js文件,通过node中的模块操作,向外暴露了一个配置对象
    module.exports = {
        //在配置文件中需要主动指定入口和出口
        entry:path.join(__dirname,'./src/main.js'),//入口,表示webpack要打包那个文件
        output:{//输出文件相关配置
            path:path.join(__dirname,'./dist'),//指定,打包好的文件,输出到那个目录中去
            filename: 'bundle.js'//指定输出文件名称
        },
        plugins: [//配置插件的节点
            new htmlWebpackPlugin({//创建一个在内存中生成HTML页面的插件
                template: path.join(__dirname,'./src/index.html'),//指定模板页面,将会根据指定的页面路径,去生成内存中的页面
                filename: 'index.html',//指定生成的页面的名称
            })
    
        ]
    }
    View Code

        ##使用此插件之后,无需手动引用打包成的bundl.js,插件会将内存中的bundle.js自动添加到内存页面中

    5.页面加载样式文件

      5.1页面中加载css样式(loader 加载器)

        ##不推荐直接在页面中用link引入css文件,因为这样会发起二次请求,

        ## webpack默认只能打包处理 js 类型的文件,无法处理其他的非 js 类型的样式,如果要处理非 js 类型的文件,我们需要手动安装一些合适的第三方 loader 加载器

          1:如果想要打包处理 css 文件,需要安装:npm i style-loader css-loader -D 这两个加载器

          2:打开 webpack.config.js 这个配置文件,在里面新增一个配置节点,叫做 module,他是一个对象,在这个 module 对象身上,有个 rules 属性,这个 rules 属性是一个数组,这个数组中存放了所有第三方文件的匹配和处理规则

        ##同样和包相同要在main.js中导入样式表,不同的是js模块语法:import …… form……,而非js则只需要impot……即可。例如:impot './css/index.css'

        修改完后的 webpack.config.js :

    const path = require('path') //node操作URL要用path模块
    
    //导入在内存中生成html页面的插件
    //只要是插件都要放到plugin节点中去
    const htmlWebpackPlugin = require('html-webpack-plugin')
    
    //node语法
    //这个配置文件就是一个js文件,通过node中的模块操作,向外暴露了一个配置对象
    module.exports = {
        //在配置文件中需要主动指定入口和出口
        entry:path.join(__dirname,'./src/main.js'),//入口,表示webpack要打包那个文件
        output:{//输出文件相关配置
            path:path.join(__dirname,'./dist'),//指定,打包好的文件,输出到那个目录中去
            filename: 'bundle.js'//指定输出文件名称
        },
        plugins: [//配置插件的节点
            new htmlWebpackPlugin({//创建一个在内存中生成HTML页面的插件
                template: path.join(__dirname,'./src/index.html'),//指定模板页面,将会根据指定的页面路径,去生成内存中的页面
                filename: 'index.html',//指定生成的页面的名称
            })
    
        ],
        module:{//这个节点,用于配置所有第三方模块加载器
            rules:[//所有第三方模块的匹配规则
                { test:/.css$/, use:['style-loader','css-loader'] } //配置处理.css文件的第三方loader规则
            ]
        }
    }
    View Code

        注:在webpack打包的时候会先校验文件类型,如果是 js 文件它会直接打包,而那些非 js 文件类型,会先拿到后缀名,然后去 webpack.config.js 中的节点 module 中去找对应的匹配规则,如果能够找到,就会调用规则进行打包,如果找不到会报错

          而第三方规则的调用顺序是从右到左调用,比如上面 use 中是先调用 css-loader 得到处理结果后,将结果传到前一个loader中调用前一个 style-loader 将结果做进一步处理,如果前面没有 loader 了就直接交给 webpack 进行打包合并到 bundle.js 里去

      5.2页面加载scss样式文件

        ##执行命令 cnpm i sass-loader -D 下载第三方加载器,然后执行 cnpm i node-sass -D 此为 sass-loader 的内部依赖,无需在 webpack.config.js 中配置,但是一定要在根目录下安装

        ## 引用方式与css引用方式相同

        修改完后的webpack.config.js:

    const path = require('path') //node操作URL要用path模块
    
    //导入在内存中生成html页面的插件
    //只要是插件都要放到plugin节点中去
    const htmlWebpackPlugin = require('html-webpack-plugin')
    
    //node语法
    //这个配置文件就是一个js文件,通过node中的模块操作,向外暴露了一个配置对象
    module.exports = {
        //在配置文件中需要主动指定入口和出口
        entry:path.join(__dirname,'./src/main.js'),//入口,表示webpack要打包那个文件
        output:{//输出文件相关配置
            path:path.join(__dirname,'./dist'),//指定,打包好的文件,输出到那个目录中去
            filename: 'bundle.js'//指定输出文件名称
        },
        plugins: [//配置插件的节点
            new htmlWebpackPlugin({//创建一个在内存中生成HTML页面的插件
                template: path.join(__dirname,'./src/index.html'),//指定模板页面,将会根据指定的页面路径,去生成内存中的页面
                filename: 'index.html',//指定生成的页面的名称
            })
    
        ],
        module:{//这个节点,用于配置所有第三方模块加载器
            rules:[//所有第三方模块的匹配规则
                { test:/.css$/, use:['style-loader','css-loader'] }, //配置处理.css文件的第三方loader规则
                { test:/.scss$/, use:['style-loader','css-loader','sass-loader'] } //配置.scss文件的第三方loader规则
            ]
        }
    }
    View Code

    6. webpack中url-loader的使用(webpack 默认无法处理样式中的URL地址,不管是图片还是字体库,只要是url地址都无法处理)

      ##页面:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <!--不推荐在这里引用任何包和任何css样式文件,因为会发起二次请求,所有包都在main.js中导入-->
        <!--因为main.js中的代码,涉及到了ES6的新语法,但是浏览器不识别-->
        <!--<script src="./main.js"></script>-->
        <!--解决办法,使用webpack前端构建工具,把main.js做了处理打包,生成了一个bundle.js-->
        <!--<script src="../dist/bundle.js"></script>-->
        <script src="/bundle.js"></script>
    </head>
    <body>
    
        <div class="box"></div>
    
    </body>
    </html>
    View Code

      ##如果 .scss 中有如下所示:

    html, body{
      .box{
         220px;
        height: 120px;
        background: url('../images/kolar.jpg');
        background-size: cover;
      }
    }
    View Code

      ## main.js中引入 .scss 文件:import './css/index.scss'

      ##执行命令:cnpm i url-loader file-loader -D ; file-loader 是内部依赖所以不需要在 webpack.config.js 中配置:

        { test:/.(jpg|png|gif|bmp|jpeg)$/, use: 'url-loader'},

        经过查看图片在浏览器中显示的事base64形式的,而不是图片地址,这要减少了二次请求,如图:

                  

      ## 在第三方加载器后面可以传参数,参数名是固定的,传参方式与浏览器URL中的传参方式一样:

          1:上面图片转成 base64 字符串了,如果不想显示 base64 字符串,可以在后面传参数为 “limit”,limit 给定的值是图片的大小,单位为 ‘byte’,如果我们引用的图片大于或等于给定的limit值,则不会被转成base64格式的字符串,如果图片大小小于给定的 limit

            值,则会被转成 base64 格式的字符串。例如: { test:/.(jpg|png|gif|bmp|jpeg)$/, use: 'url-loader?limit=780831'},此时如下显示:

                           

          2:但是图片名称有变化,主要是为了防止图片重名。如何不让改名呢?============加第二个参数:{ test:/.(jpg|png|gif|bmp|jpeg)$/, use: 'url-loader?limit=780831&name=[name].[ext]'} ,其中中括号中name表示:原图片叫什么名就是什么名,后一个表示                             原图后缀

      ## 当有两张图片,相同名字,在不同的静态文件夹中,但被同一个样式表引用,那么会出现,第一个图片打包后会被另一个打包好的图片替换掉,变成现实两个相同的图片,此问题效果和解决办法如下:

        1:两个不同的图片:(两图片都叫kolar.jpg)

                  

        2:样式表中的样式:

    html, body{
      .box{
         220px;
        height: 120px;
        background: url('../images/kolar.jpg');
        background-size: cover;
      }
      .box2{
         220px;
        height: 120px;
        background: url('../images2/kolar.jpg');
        background-size: cover;
      }
    }
    View Code

        3:页面内容:

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
        <!--不推荐在这里引用任何包和任何css样式文件,因为会发起二次请求,所有包都在main.js中导入-->
        <!--因为main.js中的代码,涉及到了ES6的新语法,但是浏览器不识别-->
        <!--<script src="./main.js"></script>-->
        <!--解决办法,使用webpack前端构建工具,把main.js做了处理打包,生成了一个bundle.js-->
        <!--<script src="../dist/bundle.js"></script>-->
        <script src="/bundle.js"></script>
    </head>
    <body>
    
        <div class="box"></div>
    
        <div class="box2"></div>
    
    </body>
    </html>
    View Code

        4:两图片在项目中的位置:

        

        5:显示效果:(注:{ test:/.(jpg|png|gif|bmp|jpeg)$/, use: 'url-loader?limit=780831&name=[name].[ext]'} 此配置中的 limit 值均小于这两个图片的大小时,就会出现这种结果,如果是base64格式的字符串不会出现)

           

          注:第一张图片被打包成为kolar.jpg,然后有打包了另一张图片也为 kolar.jpg,后者在内存中,把前者覆盖掉了,因此出现了这种情况。

         6:解决办法:将图片重命名,原名称不变,在每个图片前都加上一个 hash 码,hash 值固定是32位,但这里只去前8位:

          { test:/.(jpg|png|gif|bmp|jpeg)$/, use: 'url-loader?limit=6000&name=[hash:8]-[name].[ext]'},

          这样效果就是:

              

        

  • 相关阅读:
    设计模式
    三——第二部分——第二篇论文 计划建设SQL Server镜像
    非正确使用浮点数据由项目产生BUG讨论的问题
    重写ViewPager实施单一交有关切换到这个问题,并没有缓存
    1159 Palindrome(最小插入回文串)
    CSDN-markdown编者LaTex数学公式
    找工作总结
    开展:随笔记录 OSGI的jar增加了一些小问题和注意事项
    js jquery版本号 金额千分之一转换功能(非规范,高效率)
    dom4j.jar有什么作用?
  • 原文地址:https://www.cnblogs.com/lubolin/p/10912196.html
Copyright © 2011-2022 走看看