img对象,file对象,base64,canvas对象相互转换以及图片压缩

前端:base64的作用 最近在开发中遇到文件上传采用Base64的方式上传,记得以前刚开始学http上传文件的时候,都是通过content-type为multipart/form-data方式直接上传二进制文件,我们知道都通过网络传输最终只能传输二进制流,所以毫无疑问他们本质上都是一样的,那么为什么还要先转成Base64呢?因为随着机器性能的提升,小文件通过二进制流传输和字符串传输,我们对这两种方式时间延迟的感知差异并不那么明显,因此大部分情况下我们更多考虑的是灵活性,所以采用Base64编码的情况也就比较多。 阅读详情

一、使用场景

首先想一想我们有哪些需求?大多时候我们需要将一个File对象压缩之后再变为File对象传入到远程图片服务器;有时候我们也需要将一个base64字符串压缩之后再变为base64字符串传入到远程数据库;有时候后它还有可能是一块canvas画布,或者是一个Image对象,或者直接就是一个图片的url地址,我们需要将它们压缩上传到远程;

图片.png

二、常用方法

如上图所示,七个方法,基本覆盖了JS中大部分文件类型的转换与压缩,其中:

1、urltoImage

urltoImage(url,fn) 会通过一个url加载所需要的图片对象,其中 url 参数传入图片的 url , fn 为回调方法,包含一个Image对象的参数,代码如下:

function urltoImage (url,fn){
  var img = new Image();
  img.src = url;
  img.onload = function(){
    fn(img);
  }
};

2、 imagetoCanvas

imagetoCanvas(image) 会将一个 Image 对象转变为一个 Canvas 类型对象,其中 image 参数传入一个Image对象,代码如下:

function imagetoCanvas(image){
  var cvs = document.createElement("canvas");
  var ctx = cvs.getContext('2d');
  cvs.width = image.width;
  cvs.height = image.height;
  ctx.drawImage(image, 0, 0, cvs.width, cvs.height);
  return cvs ;
};

3、 canvasResizetoFile

canvasResizetoFile(canvas,quality,fn) 会将一个 Canvas 对象压缩转变为一个 Blob 类型对象;其中 canvas 参数传入一个 Canvas 对象; quality 参数传入一个0-1的 number 类型,表示图片压缩质量; fn 为回调方法,包含一个 Blob 对象的参数;代码如下:

function canvasResizetoFile(canvas,quality,fn){
  canvas.toBlob(function(blob) {
    fn(blob);
  },'image/jpeg',quality);
};

这里的 Blob 对象表示不可变的类似文件对象的原始数据。 Blob 表示不一定是 JavaScript 原生形式的数据。 File 接口基于 Blob ,继承了 Blob 的功能并将其扩展使其支持用户系统上的文件。我们可以把它当做File类型对待,其他更具体的用法可以参考MDN文档

4、canvasResizetoDataURL

canvasResizetoDataURL(canvas,quality) 会将一个 Canvas 对象压缩转变为一个 dataURL 字符串,其中 canvas 参数传入一个 Canvas 对象; quality 参数传入一个0-1的 number 类型,表示图片压缩质量;代码如下:

methods.canvasResizetoDataURL = function(canvas,quality){
  return canvas.toDataURL('image/jpeg',quality);
};

其中的 toDataURL API可以参考MDN文档

5、 filetoDataURL

filetoDataURL(file,fn) 会将 File ( Blob )类型文件转变为 dataURL 字符串,其中 file 参数传入一个 File ( Blob )类型文件; fn 为回调方法,包含一个 dataURL 字符串的参数;代码如下:

function filetoDataURL(file,fn){
  var reader = new FileReader();
  reader.onloadend = function(e){
    fn(e.target.result);
  };
  reader.readAsDataURL(file);
};

6、 dataURLtoImage

dataURLtoImage(dataurl,fn) 会将一串 dataURL 字符串转变为 Image 类型文件,其中 dataurl 参数传入一个 dataURL 字符串, fn 为回调方法,包含一个 Image 类型文件的参数,代码如下:

function dataURLtoImage(dataurl,fn){
  var img = new Image();
  img.onload = function() {
    fn(img);
  };
  img.src = dataurl;
};

7、 dataURLtoFile

dataURLtoFile(dataurl) 会将一串 dataURL 字符串转变为 Blob 类型对象,其中 dataurl 参数传入一个 dataURL 字符串,代码如下:

function dataURLtoFile(dataurl) {
  var arr = dataurl.split(','), mime = arr[0].match(/:(.*?);/)[1],
    bstr = atob(arr[1]), n = bstr.length, u8arr = new Uint8Array(n);
  while(n--){
    u8arr[n] = bstr.charCodeAt(n);
  }
  return new Blob([u8arr], {type:mime});
};

三、进一步封装

对于常用的将一个 File 对象压缩之后再变为 File 对象,我们可以将上面的方法再封装一下,参考如下代码:

function fileResizetoFile(file,quality,fn){
  filetoDataURL (file,function(dataurl){
    dataURLtoImage(dataurl,function(image){
      canvasResizetoFile(imagetoCanvas(image),quality,fn);
    })
  })
}

其中, file 参数传入一个 File ( Blob )类型文件; quality 参数传入一个 0-1 的 number 类型,表示图片压缩质量; fn 为回调方法,包含一个 Blob 类型文件的参数。

它使用起来就像下面这样:

var file = document.getElementById('demo').files[0];
fileResizetoFile(file,0.6,function(res){
  console.log(res);
  //拿到res,做出你要上传的操作;
})

ps:下面看下JS等比压缩图片的办法

function proDownImage(path,imgObj) { // 等比压缩图片工具
  //var proMaxHeight = 185;
  var proMaxHeight=300;
  var proMaxWidth = 175;
  var size = new Object(); 
  var image = new Image(); 
  image.src = path; 
  image.attachEvent("onreadystatechange",
  function() { // 当加载状态改变时执行此方法,因为img的加载有延迟
    if (image.readyState == "complete") { // 当加载状态为完全结束时进入
      if (image.width > 0 && image.height > 0) {
        var ww = proMaxWidth / image.width;
        var hh = proMaxHeight / image.height; 
        var rate = (ww < hh) ? ww: hh;
        if (rate <= 1) { 
          alert("imgage width*rate is:" + image.width * rate);
          size.width = image.width * rate;
          size.height = image.height * rate;
        } else {
          alert("imgage width is:" + image.width);  
          size.width = image.width;  
          size.height = image.height;   
        } 
      }
    }
    imgObj.attr("width",size.width);
    imgObj.attr("height",size.height);
  });
}

四、常用方法

file对象转base64

// file对象转base64var 
filetoDataURL = function(file,fn) {
    var reader = new FileReader();
    reader.readAsDataURL(file);
    reader.onload = function(e) {
        fn(e.target.result);
    }}

base64转file对象

// base64转file对象var base64ImgtoFile = function(dataurl,filename="file") {
    var arr = dataurl.split(','),
        mime = arr[0].match(/:(.*?);/)[1]
        suffix = mime.split('/')[1],
        bstr = atob(arr[1]),
        n = bstr.length,
        u8arr = new Uint8Array(n);
    while (n--) {
        u8arr[n] = bstr.charCodeAt(n);
    }
    return new File([u8arr], filename+"."+suffix, { type: mime });}

base64转blob

var base64Toblob = function(base64){ 
	var bstr = atob(base64),
	n = bstr.length,
	u8Arr = new Uint8Array(n);
	while(n--){
		u8Arr[n] = bstr.charCodeAt(n)
	}
	return new Blob([u8Arr])}

blob转url

URL.createObjectUrl(blob)

URL.createObjectUrl(blob):这个方法便捷,且是同步的,但需要基于当前的内存,换句话说,这个url不能拿到其他页面使用。

let url = URL.createObjectUrl(blob)img.src = url

FileReader.readAsDataURL

FileReader.readAsDataURL(blob):这个方法是异步的,转化成base64,可以放到其他页面使用。

let fr = new FileReader()fr.readAsDataURL(blob)fr.onload = function(e) {
	console.log(e.target.result)}

img对象,file对象,base64,canvas对象相互转换以及图片压缩_img base64-优快云博客

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

// canvas转dataURL:canvas对象、转换格式、图像品质

function canvasToDataURL(canvas, format, quality){

    return canvas.toDataURL(format||'image/jpeg', quality||1.0);

}

// DataURL转canvas

function dataURLToCanvas(dataurl, cb){

    var canvas = document.createElement('CANVAS');

    var ctx = canvas.getContext('2d');

    var img = new Image();

    img.onload = function(){

        canvas.width = img.width;

        canvas.height = img.height;

        ctx.drawImage(img, 0, 0);

        cb(canvas);

    };

    img.src = dataurl;

}

/*-----------------------------------------------------------------------*/

// image转canvas:图片地址

function imageToCanvas(src, cb){

    var canvas = document.createElement('CANVAS');

    var ctx = canvas.getContext('2d');

    var img = new Image();

    img.src = src;

    img.onload = function (){

        canvas.width = img.width;

        canvas.height = img.height;

        ctx.drawImage(img, 0, 0);

        cb(canvas);

    };

}

// canvas转image

function canvasToImage(canvas){

    var img = new Image();

    img.src = canvas.toDataURL('image/jpeg', 1.0);

    return img;

}

/*-----------------------------------------------------------------------*/

// File/Blob对象转DataURL

function fileOrBlobToDataURL(obj, cb){

    var a = new FileReader();

    a.readAsDataURL(obj);

    a.onload = function (e){

        cb(e.target.result);

    };

}

// DataURL转Blob对象

function dataURLToBlob(dataurl){

    var arr = dataurl.split(',');

    var mime = arr[0].match(/:(.*?);/)[1];

    var bstr = atob(arr[1]);

    var n = bstr.length;

    var u8arr = new Uint8Array(n);

    while(n--){

        u8arr[n] = bstr.charCodeAt(n);

    }

    return new Blob([u8arr], {type:mime});

}

/*-----------------------------------------------------------------------*/

// Blob转image

function blobToImage(blob, cb){

    fileOrBlobToDataURL(blob, function (dataurl){

        var img = new Image();

        img.src = dataurl;

        cb(img);

    });

}

// image转Blob

function imageToBlob(src, cb){

    imageToCanvas(src, function (canvas){

        cb(dataURLToBlob(canvasToDataURL(canvas)));

    });

}

/*-----------------------------------------------------------------------*/

// Blob转canvas

function BlobToCanvas(blob, cb){

    fileOrBlobToDataURL(blob, function (dataurl){

        dataURLToCanvas(dataurl, cb);

    });

}

// canvas转Blob

function canvasToBlob(canvas, cb){

    cb(dataURLToBlob(canvasToDataURL(canvas)));

}

/*-----------------------------------------------------------------------*/

// image转dataURL

function imageToDataURL(src, cb){

    imageToCanvas(src, function (canvas){

        cb(canvasToDataURL(canvas));

    });

}

// dataURL转image,这个不需要转,直接给了src就能用

function dataURLToImage(dataurl){

    var img = new Image();

    img.src = d;

    return img;

}

Vcenter虚拟机磁盘转换实战:如何用StarWind V2V将vmdk转为qcow2(附空间优化技巧) 本文详细介绍了如何使用StarWind V2V Converter将Vcenter中的vmdk虚拟机磁盘高效转换为qcow2格式,并提供了空间优化技巧。从准备工作、导出vmdk文件到转换过程中的性能调优,帮助管理员在迁移虚拟机时减少资源消耗,确保数据完整性和性能。 阅读详情

相关推荐

Mamba-ST实战:用状态空间模型实现艺术风格迁移的5个关键步骤

本文详细介绍了如何使用Mamba-ST状态空间模型实现高效的艺术风格迁移,涵盖环境配置、数据预处理、模型架构、训练策略和推理优化等5个关键步骤。Mamba-ST基于SSM(状态空间模型)构建,在保持生成质量的同时显著降低计算复杂度,为风格迁移领域提供了新的解决方案。

weixin_29163581的博客 353

HTML中img标签base64显示图片

在浏览网页的时候大家可能会注意到一个奇怪的现象,有的图片的路径后面是一串很长的字符串,例如: data:image/jpg;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAAkCAYAAABIdFAMAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHhJREFUeNo8zjsOxCAMAAAABJ...

象在舞的技术专栏 5万+

手把手教你玩转Infoseek舆情监测系统:从数据爬取到智能分析实战

别只会监测品牌名!一个有效的监测体系应该包括:// 完整的监测关键词策略brand: ["品牌名", "产品名", "缩写"],executives: ["CEO姓名", "高管姓名"],campaign: ["当前营销活动名称"],competitors: ["竞品A", "竞品B"],industry: ["行业通用关键词"],// 别忘了常见拼写错误和黑称defensive: ["常见的错误拼写", "用户起的黑称"]产品优化:从用户吐槽中发现改进点市场洞察。

2501_93332955的博客 755

【JS】img标签使用base64图片以及如何将图片转为base64格式

首先获取file对象,然后创建一个FileReader对象。监听FileReader对象的load事件,在load事件被触发时,我们就可以通过reader.result获取到Base64字符串。最后调用readAsDataURL方法将文件读取成data URL。

owo_ovo的博客 1万+

DBeaver连接IoTDB避坑指南:手动配置JDBC驱动的完整流程(附问题排查)

本文提供了在DBeaver中手动配置Apache IoTDB JDBC驱动的完整流程与避坑指南。详细解析了从驱动创建、库文件添加(关键是指向整个lib目录)到连接测试的每一步,并重点针对常见的ClassNotFoundException、连接拒绝等错误提供了深度排查方案,帮助用户高效建立图形化管理连接。

weixin_28327051的博客 393

星光、黑光、全彩夜视摄像头技术解析与实战选型指南

本文深入解析了星光、黑光、全彩与红外等主流夜视摄像头技术的工作原理与核心差异。针对不同监控场景与预算,提供了实战选型指南,帮助用户在安防项目中做出明智决策,实现夜间监控效果最大化。

weixin_29179311的博客 345

img图片转码base64使用(简单版)

前端图片转base64实操代码。

Jar_plo的博客 1万+

【工控基础】UVW平台踩坑

1 每个轴按顺时针或逆时针走一个距离,就是旋转。 2 图中W动,U轴V轴不动,就是X方向的平移 3 图中U轴V轴同时动,X不动,就是Y方向的平移。

songhuangong123的博客 6942

img显示base64图片

img显示base64图片

qq_54780032的博客 9655

包成功安装tiny-cuda-nn,记录安装过程中的问题解决,附带pytorch3d安装【踩坑指南】

该包可以显著提高NeRF训练速度,是和NeRFstudio等框架中,必须使用的。本文提供tiny-cuda-nn可以安装的完整包的下载链接,可以直接上传到项目中安装。附带笔者遇到的问题的解决方案。

zik的博客 7029

【YOLOv11】087、YOLOv11多任务学习:检测、分割、分类联合学习

摘要: 工业质检场景中,多任务模型(检测、分类、分割)的需求日益增长。针对边缘设备部署的挑战,本文提出基于YOLOv11的多任务学习方案。通过共享主干网络和设计分支头(检测、分割、分类),实现高效推理;采用动态权重平衡策略解决多任务损失不平衡问题;并优化数据流处理(支持部分标注)和推理剪裁(按需启用分支)。实验表明,该方法在Jetson Orin上帧率提升3倍,内存占用减少40%,为工业质检提供了轻量高效的解决方案。

企鹅码农的专属播客,分享10多年的实战案例和经验解读,包含YOLO、RT-DETR、AI等各个工作领域。 445

img对象,file对象,base64,canvas对象相互转换以及图片压缩

img对象,file对象,base64,canvas对象相互转换以及图片压缩 </h1> <div class="clear"></div> <div class="postBody"> 先上一张图:   以上图片是js几乎所有图片类型的转换方式了。接下来讲讲几种常用的类型转换: 1、 urltoImage(url,fn) 会通过一...

叶子先生的博客 681

【车载以太网】【SOMEIP】Wireshark测试someip

一、 Wireshark SOMEIP plugin 1.1 插件安装 Wireshark插件目录:Help -> About Wireshark -> Folders/Pluginshttps://github.com/jamores/eth-ws-someip 解压后,将所有后缀是lua的文件拷贝到Wireshark安装目录plugins/2.4.10/下。 1.2时间戳调整为UTC显示格式 View -> Time Display Format -> Date and Tim.

专注汽车软件开发、AutoSAR、车载以太网、SOA、EE架构。 9723

图片转换js (img对象,file对象,base64,canvas对象),以及图片压缩方式

首先想一想我们有哪些需求?大多时候我们需要将一个File对象压缩之后再变为File对象传入到远程图片服务器;有时候我们也需要将一个base64字符串压缩之后再变为base64字符串传入到远程数据库;有时候后它还有可能是一块canvas画布,或者是一个Image对象,或者直接就是一个图片的url地址,我们需要将它们压缩上传到远程;二、解决办法如上图所示,七个方法,基本覆盖了JS中大部分文件类型的转换...

twtcqw2008的博客 3万+

visio安装包

Microsoft Office Visio 是一款专业的制图软件。利用经过更新的形状、协作工具和数据链接图表,创建专业级图表以简化复杂的信息。

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

js canvas 图片压缩 并转换为 file 类型文件

<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title></title> <script src="js/jquery-3.1.1.min.js"></script> <style type="text/css"&...

guohao326的博客 6995

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

【VUE】将图片的url或file类型转换成base64,并压缩图片大小

话不多,看代码! 1、将图片的url转换成base64 urlTobase64(url) { var that = this var img = new Image() img.src = url + '?time=' + new Date().valueOf() // 加上时间结尾,处理缓存 //支持http跨域图片。需要后端设置图片支持跨域为*(如果后端不处理,加上这行会无法显示图片,导致拿不到base64) img.setAttribute('crossOrigin', '

LuviaWu的博客 7973

Outlook Express 6 (OE6) for Win7/Win8/Win10

英文版 Outlook Express6.0, 兼容Win7/Win10/WinXP,解压就可用。

前端必看:用Canvas轻松压缩图片并玩转Base64与File互转

一条“File → Canvas → File”的完整流水线;一套“尺寸/品质/格式”三维可调的黄金参数表;一张“兼容性坑位”的排雷地图;一把“调试 + 定位”的尺子;还有无数“裁剪、离线、Worker、雪碧图”的骚操作。下次再遇到“图片太大”的警告,你就可以淡定地喝一口咖啡,敲下,然后对产品经理说:“放心,我已经把 10MB 砍到 800KB,画质还比朋友圈高。这就是前端人的浪漫——用一行代码,帮用户省下一兆流量;用一张画布,把世界看得更清晰。(完整可运行仓库已放在。

一个做过前端开发的产品经理,经历过睿智产品的折磨导致脱发之后,励志要翻身"农奴"把歌唱,一边打入敌人内部一边持续提升自己,为我们广大开发同胞谋福祉,坚决抵制睿智产品折磨我们码农兄弟! 1079

canvas实现浏览器图片压缩(base64和file对象的相互转换)

/** * 图片压缩,默认同比例压缩 * @param {Object} path * pc端传入的路径可以为相对路径,但是在移动端上必须传入的路径是照相图片储存的绝对路径 * @param {Object} obj * obj 对象 有 width, height, quality(0-1) * @param {Object} callback * 回调函数有一个参数,...

黄彪博客 821

前端JS利用canvas的drawImage()对图片进行压缩

对于大尺寸图片的上传,在前端进行压缩除了省流量外,最大的意义是极大的提高了用户体验。 这种体验包括两方面: 1、由于上传图片尺寸比较小,因此上传速度会比较快,交互会更加流畅,同时大大降低了网络异常导致上传失败风险。 2、最重要的体验改进点:省略了图片的再加工成本。很多网站的图片上传功能都会对图片的大小进行限制,尤其是头像上传,限制5M或者2M以内是非常常见的。然后现在的数码设备拍摄功能都非常出众,...

我是谁的博客 8249

前端人别硬扛:Canvas搞定图片压缩与Base64互转实战

场景多了去了:要存localStorage得转Base64,要formData上传得转File,要预览直接塞img标签src,有时候Base64更方便,有时候File更正宗。你打开控制台一看,好家伙,一张自拍8MB,还是HEIC格式转过来的。所以啊,前端压缩这事儿,真不是咱们吃饱了撑的非要炫技。前端统一压缩到每张500KB以内,后端接口完全不用改,因为收到的还是File对象,只是体积小了很多。的quality参数,对于JPEG是0-1的质量系数,0.7通常是个甜点,体积能省60%以上,肉眼基本看不出损失。

一个做过前端开发的产品经理,经历过睿智产品的折磨导致脱发之后,励志要翻身"农奴"把歌唱,一边打入敌人内部一边持续提升自己,为我们广大开发同胞谋福祉,坚决抵制睿智产品折磨我们码农兄弟! 728

前端:Blob及使用场景 / 积累 / 分片上传 / 下载数据 / 用作URL / url、base64、blob相互转换 / 图片压缩 / 生产pdf ... / Web 二进制数据体系

在Web中,Blob类型的对象表示不可变的类似文件对象的原始数据,通俗点说,就是Blob对象是二进制数据,但它是类似文件对象的二进制数据,因此可以像操作File对象一样操作Blob对象,实际上,File继承自Blob。在web领域,Blob对象表示一个只读原始数据的类文件对象,虽然是二进制原始数据但是类似文件的对象,因此可以像操作文件对象一样操作Blob对象。当上传的需求要求可预览、显示上传进度、中断上传过程、大文件分片上传等等,这时传统的表单上传很难实现这些功能,我们可以借助现有插件完成。

snow的博客 8319

通过JS将图片File转为base64并压缩

后端为了方便需要直接将图片存储为base64,但图片过大时转出的base64过长,因此前端需要对转后的base64进行压缩 话不多说,直接上代码 /** * * @param {需要转换的图片file} file * @param {是否返回压缩后的base64} isCompression * @param {转换成功后通过回调函数将结果返回} callback */ export function imageToBase64(file, isCompression, callbac.

sinat_21902709的博客 1578

[JavaScript] 图片文件转Base64,Base64转Blob,Blob转File对象

待写

iChangebaobao的博客 1250
上一篇: vue组件内引入外部js, 外部js调用组件内的方法
下一篇: mysql-binlog
springdk2009
博客等级 码龄17年 1835粉丝 257原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值