vg在线编辑器 https://editor.method.ac/
使用的是polygon标签
该标签能创建含有不少于三个边的图形。
如下
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <polygon points="0,10 5,2 5,7 10,0"/> </svg>
效果如下
其坐标为路径
poliline 为曲线
同样输入的为坐标
此时为了和上一个区分,将file设置为不填充,设置描边为black
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <polyline points="0,10 5,2 5,7 10,0" fill="none" stroke="black"/> </svg>
效果如下
其中 填充为非零绕数原则
path类似于笔的路径
其拥有一个属性d,该属性d由下方的单词的首字母组成。
Moveto
画笔的起点
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <path d="M10,100"/> </svg>
Lineto
该执行从画笔的起点到位置绘制一条直线
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <path d="M0 0 L0 20 L40 0 "/> </svg>
Curveto
绘制贝塞尔曲线,由三个参数组成,考虑两个控制点
直接选择画板手绘吧,实在看不懂了,貌似缺少了椭圆的一些数学知识
总结
绘制一颗心,以下是在网上找的
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <path d="M1,3 A2,2 0,0,1 5,3 A2,2 0,0,1 9,3 Q9,6 5,9 Q1,6 1,3 Z "/> </svg>
没看懂。。。
text元素
依旧当做图片处理
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <text x="0" y="20" fill="red">Hello world</text> </svg>
此为属性,定义任何类型的线条
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100"> <text x="0" y="20" stroke="black">Hello world</text> </svg>
对图片模糊
先引入图片
<image x="0" y="0" width="100%" height="300px" xlink:href="http://127.0.0.1/111.png"/>
此时图片显示
接着定义可复用的组即defs
defs 标签为可复用的组标签
使用的是file用于存放滤镜的地方
使用file标签
使用feGaussianBlur滤镜即模糊滤镜
使用的in的参数为SourceGraphic表示图形作为原始的输入
此外还有背景图,通道等
stdDeviation 表示模糊的程度
完整的如下
<defs> <filter id="f1" x="0" y="0"> <feGaussianBlur in="SourceGraphic" stdDeviation="15" /> </filter> </defs>
接着再次使用滤镜
<image filter="url(#f1)" x="0" y="0" width="100%" height="100px" xlink:href="http://127.0.0.1/111.png"/>
一个模糊
效果不错
此外还有阴影渐变,等滤镜,等就太复杂了,设计到矩阵变换等高等数学的内容,自己有心无力。
使用adobe ai 生成svg文件
创建一个画板
选择字符
添加字体
转曲
获取svg代码
画出图像
代码如下
<!DOCTYPE html> <html> <head> <title>svg页面</title> </head> <body> <p>这是一个svg</p> <!-- svg 图形的命名空间 --> <svg version="1.1" id="图层_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 1366 768" style="enable-background:new 0 0 1366 768;" xml:space="preserve"> <g> <path d="M722.2,346.5c17.1,128.1-27.4,231.2-133.3,309.2c-36.1,26.6-79.1,43.8-123.5,49.7c-109.2,14.4-200.7-14.2-274.5-85.9 c-62.1-60.1-93.1-133.1-93.1-218.8c0-103.3,45-188.2,135.1-254.6c36.1-26.6,78.9-44.2,123.3-50.2 c128.7-17.4,232.7,23.8,312.1,123.6C697.2,255.9,716,300.4,722.2,346.5z M709.2,403.7c1.8-83.1-27.7-154-88.5-212.8 c-58.6-56.5-128-84.7-208.1-84.7l-32.3,66.3l35.2,7.1l27.5-27.5l48.5,3.2l9.7,25.9L472,210.3v17.5l18.1,3.6l8.4-13.6l32-20l-1,13.6 l12,20.7l-14.2,14.9l9,8.7l-21.3,1.3l8.7,17.5l-46.2,22l7.1,26.2h-14.5l-6.5-25.9l-33.9-0.6l-6.1,10l-13.9-6.5L387,322.1l18.1,21.7 l-0.6,23.9l19.1,14.2l111.2,12.6l35.2,24.9l-4.2,61.7l-76.6,76.6c-5,5-9.8,18.7-14.5,41.4c-4.5,21.3-6.1,36.5-4.8,45.6l-11.6,13.3 c-9-17.9-20.8-45.4-35.2-82.4c-3.4-12.7-6.5-28.9-9-48.5c-1.9-16.2-3.9-32.4-5.8-48.8l-48.5-42.7l43-50.7l-17.8-25.5 c-27.4-5.6-45.1-10.6-53.3-15c-8.2-4.4-22.3-16.8-42.3-37l16.8,32.6l-11.3,4.8l-26.2-49.1l5.2-45.9l-8.1-32.3l-25.2-24.6l-18.4-4.5 l-16.2,11.3l-17.8,4.5c-49.6,57.3-74.1,123.3-73.4,197.9c0.8,76.3,32.7,151,87.1,204.4c58.1,57,128.4,85.4,210.9,85.4 c81.9,0,151.8-28.7,209.6-86C675.7,552.8,707.5,479.1,709.2,403.7z"/> </g> </svg> </body> </html>
到此,可以发挥ai的想象啦。包括绘制图形,使用滤镜,画图图标等等,哪怕使用图片导入ai,绘制出矢量图。完美的ai和html的一次结合
http://svgjs.com/ 使用该svg.js框架可以快速的操纵svg
svg-sprite-loader 是用于创建SVG精灵图的插件,通过该插件可以将导入的SVG文件自动生成为symbol标签并插入进html中
yarn add svg-sprite-loader -D
在 vue.config.js 中添加插件
const path=require("path")
module.exports={
chainWebpack(config) {
// 清除 svg loader
config.module.rule("svg").uses.clear();
// 添加 svg loader
config.module
// 排除 svg loader 对 node_modules 的操作
.rule("svg-sprite-loader")
.test(/.svg$/)
.exclude.add(/node_modules/)
.end()
// 添加 svg loader 对 icons/svg 下的 svg 图标进行操作
.test(/\.svg$/)
.include.add(path.resolve(__dirname, './src/icons/svg'))
.end()
.use("svg-sprite-loader")
.loader("svg-sprite-loader")
// 定义规则 <svg class="icon-svg"> <use xlink:href="#icon-name"></use></svg>
.options({
symbolId: "icon-[name]"
});
}
}
创建文件目录和文件
src/icons
src/icons/index.js svg 文件操作
/src/icon/svg svg 文件存放
/**
* 加载 svg
*/
function loadSvg() {
const requireAll=(requireContext)=> requireContext.keys().map(requireContext);
const req=require.context("@/icons/svg/", false, /\.svg$/);
requireAll(req);
}
<template>
<svg class="icon-svg" aria-hidden="true">
<use :xlink:href="iconName"></use>
</svg>
</template>
<script>
export default {
name: "icon-svg",
inheritAttrs: true,
props: {
name: {
type: String
},
},
computed: {
iconName() {
return `#icon-${this.name}`;
},
},
};
</script>
<style>
.icon-svg {
width: 1em;
height: 1em;
vertical-align: -0.15em;
fill: currentColor;
overflow: hidden;
}
</style>
// 基本使用
<icon-svg name="setting" />
// 通过 style 控制大小和颜色
<icon-svg name="setting" style="fontSize:18px;color:#1abc9c;"/>
// 通过 class 控制大小和颜色
<icon-svg name="setting" class="setting"/>
如果修改颜色无效的话,打开文件将里面的 fill 删除。
作背景
首先,数据分析在当前的信息时代中扮演着重要的角色。随着数据量的增加和复杂性的提高,人们对于数据分析的需求也越来越高。
其次,笔者也确确实实曾经接到过一个这样的开发需求,甲方是一个医疗方面的科研团队,有相当大的一些关于癌症治疗方面的医疗数据,通过这些数据可以分析出很多东西,最重要的是将数据通过一些科学计算后转换为可视化的数据图,并且要根据用户的检索数据实时分析展示,并且可保存为pdf或svg格式的源文件,可提供后期印刷一类的二次修改使用;最终就选择了Django和Matplotlib这两个强大的库来实现数据分析的显示和下载功能。
本文将只会浅显的探讨如何使用Django和Matplotlib,并不会对数据分析方面的知识做过多的介绍!
环境搭建
这里我假设你已经会使用django,并且已经使用django搭建起了一个可运行的demo app。
Matplotlib的安装使用和其他的Python第三方包一致,只需要通过pip命令即可快速安装!
pip install matplotlib
代码示例
1、假如我们拥有一个如下代码所示的django 类视图
# demo/views.py
from django.shortcuts import render
from django.views.generic import View
class HomeView(View):
"""
HomeView类是一个继承自View的视图类,用于处理与主页相关的请求。
Attributes:
template_name (str): 展示主页所使用的模板名称。
"""
template_name="demo/home.html"
def get(self, request, *args, **kwargs):
return render(request, self.template_name)
2、url如下所示
# 项目mysite的根urls.py
from django.urls import path
from. import views
urlpatterns=[
path('', views.HomeView.as_view(), name='index'),
]
3、demo/templates/demo目录下home.html代码如下
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
</body>
</html>
这只是一个空白的html页面,最后用来显示分析图!
那么,根据以上代码,我们可以通过django的runserver命令运行项目后看到该页面!
Matplotlib使用
1、在demo/views.py当中引入如下包
import base64
from io import BytesIO
from matplotlib.figure import Figure
from django.http import FileResponse
代码解释:
import base64 是我们导入了Python的base64模块,该模块提供了对 Base64 编码格式的支持。Base64 是一种用于编码二进制数据的方式,它将每3个字节的数据编码为4个字符,因此会将数据的大小增加约33%。这种编码格式常用于在文本中进行二进制数据的表示,尤其是在需要将二进制数据通过电子邮件等文本通道进行传输的情况下。通过导入 base64 模块,我们可以使用该模块提供的函数和类来进行 Base64 编码和解码操作。
from io import BytesIO 这一行代码是在 Python 中导入 BytesIO 类。BytesIO 类是 Python 标准库 io 模块中的一个类,用于在内存中处理二进制数据流。
BytesIO 类实现了一个缓冲区,这个缓冲区可以像文件一样进行读写操作,但实际上是在内存中进行的。因此,它可以在内存中处理和操作二进制数据,而不需要将数据写入磁盘。
通过使用 BytesIO 类,我们可以将二进制数据存储在内存中,并像处理文件一样对其进行读取、写入和其他操作。这对于处理大量数据或在内存中执行文件操作更加高效和灵活。
from matplotlib.figure import Figure 是导入matplotlib 库中的 Figure 类,Figure 类是 matplotlib 库中的一个核心类,用于创建一个图形窗口(figure window)。这个窗口可以包含各种图形元素,如坐标轴(axes)、曲线(lines)、文本(text)等。
通过导入 Figure 类,我们可以创建一个空的图形窗口,并在其中添加各种图形元素。这对于自定义图形的外观和布局非常有用。
from django.http import FileResponse是导入django为我们提供的一个响应对象,关于其作用django的官网对其有详细说明,如下所示:
2、实现在页面中显示分析图的需求
首先,我们在HomeView类中新增一个get_fig的方法,让其生成一个分析图对象:
class HomeView(View):
...
def get_fig(self):
"""
获取一个图形和轴对象
返回:
fig (matplotlib.figure.Figure): 图形对象
ax (matplotlib.axes.Axes): 轴对象
"""
fig=Figure(figsize=(5, 5)) # 创建一个大小为 5x5 的图形对象
ax=fig.subplots() # 在图形对象上创建一个子图对象
ax.plot([1, 2, 3, 4]) # 在轴对象上绘制一条线
# 标题
fig.suptitle("Hello world") # 设置图形的标题
# 坐标轴
ax.set_ylabel("Y zhou", fontdict={"size": 16, "color": "red", "weight": "bold", "family": "serif"}) # 设置轴对象的 y 轴标签
ax.set_xlabel("X zhou") # 设置轴对象的 x 轴标签
return fig, ax # 返回图形对象和轴对象
有了该图形对象之后,我们就可以用base64包将该图形对象在内存中转换为png格式的字节流,为此我们再在该视图类下新增一个img_base64_to_file的方法,让它接收一个图形对象fig作为参数!
class HomeView(View):
...
def img_base64_to_file(self, fig):
"""
将图像保存为base64编码的文件
参数:
fig:要保存的图像对象
返回值:
img:包含base64编码图像的HTML标签
"""
buf=BytesIO() # 创建字节流用于保存图像
fig.savefig(buf, format="png") # 将图像保存为png格式的字节流
data=base64.b64encode(buf.getbuffer()).decode("ascii") # 将字节流转换为base64编码的字符串
img=f"<img src='data:image/png;base64,{data}'/>" # 构建包含base64编码图像的HTML标签
return img # 返回HTML标签
做完以上两步之后,其实只需要将img_base64_to_file方法的返回值传递到get请求的上下文当中,在django的模版中通过模版过滤器safe渲染即可!其他动态筛选逻辑以及其他操作即可通过django的相关功能去实现!代码如下:
class HomeView(View):
...
def get(self, request, *args, **kwargs):
fig, ax=self.get_fig()
img=self.img_base64_to_file(fig)
return render(request, self.template_name, {"img": img})
静态html模版中如下
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
{{ img|safe }}
</body>
</html>
最终渲染图
3、实现将分析图保存为pdf或svg格式
要实现该需求其实也非常简单,只需要在该视图类中新增一个post的请求,使用django的FileResponse将数据流保存到本地即可,其中需要关注的只是fig图形对象中的savefig方法的format参数的变化,也就是保存文件的格式,这个函数本身就是支持导出pdf和svg格式的!代码如下:
class HomeView(View):
...
def download_response(self, fig, filename:str):
"""
将给定的图形对象 fig 保存为 pdf 格式的文件并下载。
参数:
self (object): 类实例对象
fig (matplotlib.figure.Figure): 绘制好的图形对象
filename (str): 保存的文件名,包含扩展名
返回值:
FileResponse: 用于文件下载的响应对象
"""
buf=BytesIO()
fig.savefig(buf, format="pdf")
buf.seek(0)
return FileResponse(
buf,
as_attachment=True,
filename=f"{filename}.pdf"
)
def post(self, request, *args, **kwargs):
fig,ax=self.get_fig()
return self.download_response(fig, "demo")
在html模版中通过post的表单请求即可下载,代码如下:
<body>
{{ img|safe }}
<form action="" method="post">
{% csrf_token %}
submit: <input type="submit" value="下载">
</form>
</body>
最终,通过点击下载按钮,发起一个post请求就实现了下载到本地的功能,当然你想动态控制下载格式的话,还可以通过django的表单系统开放给用户,让用户自由选择所需要的下载格式,需要注意的是format参数要和文件后缀格式保持一致!
*请认真填写需求信息,我们会在24小时内与您取得联系。