上节课,我们通过自定义的神经网络,从头训练实现了曲线拟合的例子。
今天我们要来学用ml5.js来做一个风格迁移的例子。风格迁移是将一类风格应用到一张图片上,改变这张图片的风格。风格迁移的原理是通过从一类风格的图片通过卷积网络训练抽取出风格,再将目标图像抽取出来的内容数据混合在一起,这就形成了带特定风格的图像。所以风格迁移主要有两个步骤,一是在一种特定样式上训练模型,二是将此样式应用于另一张图像。
和其它许多神经网络模型一样,ml5已经将相对成熟的神经网络移植过来,用别人已经训练好的模型数据,可以直接在浏览器里面运行。
观看本教程的视频:https://www.bilibili.com/video/BV1az4y1Z742?p=5
<html lang="en">
<head>
<meta charset=utf-8 />
<script src='js/ml5.min.js'>script>
head>
<body>
<input type='file' id='file' style='width: 200px; height: 100px; border: dashed'/><br/>
<img id='image1' style='border: solid 1px grey; min-width: 200px; min-height: 200px;' />
<img id='image2' style='border: solid 1px grey; min-width: 200px; min-height: 200px;' /><br/>
<input type='button' value='转换' onclick='transfer()'/>
<div id='result'>div>
<script>
let fileElem = document.getElementById('file');
fileElem.addEventListener('change', fileChanged, false);
function fileChanged(evt) {
let file = evt.target.files[0];
if(!file) return;
var reader = new FileReader();
reader.onload = function(e) {
document.getElementById('image1').setAttribute('src', e.target.result);
}
reader.readAsDataURL(file);
}
log('加载中...');
// let styler = ml5.styleTransfer('data/model/style-transfer/wave', function() {
let styler = ml5.styleTransfer('data/model/style-transfer/udnie', function() {
log('加载成功...');
})
function transfer() {
log('转换中...');
let inImg = document.getElementById('image1');
let outImg = document.getElementById('image2');
setTimeout(function() {
styler.transfer(inImg, function(err, result) {
outImg.setAttribute('src', result.src);
})
log('');
}, 10);
}
function log(c) {
document.getElementById('result').innerHTML = c;
}
script>
body>
html>
我们先来看看页面上的UI元素:
<input type='file' id='file' style='width: 200px; height: 100px; border: dashed'/><br/>
<img id='image1' style='border: solid 1px grey; min-width: 200px; min-height: 200px;' />
<img id='image2' style='border: solid 1px grey; min-width: 200px; min-height: 200px;' /><br/>
<input type='button' value='转换' onclick='transfer()'/>
<div id='result'>div>
页面上两个元素,分别用来显示被转换的图片和转换后的结果。
页面上有一个文件选择器,当用户选择了文件,我们将文件的内容读出来显示到img元素中,注意这个过程都是在浏览器里面完成,文件并没有传送到服务器。这里FileReader.readAsDataURL()
就是将文件内容读成dataUrl的格式,这种格式是二进制文件进行base64
编码,让内容可以在html里面使用。
DataURL的定义:
data:[
DataURL的一个例子:
data:text/plain;base64,SGVsbG8sIFdvcmxkIQ==
let styler = ml5.styleTransfer('data/model/style-transfer/udnie', function() {
log('加载成功...');
})
进行风格转换,我们需要通过ml5.styleTransfer()
生成一个styleTransfer
对象,这个方法有两个参数:
参数一:模型地址。这是一个路径,ml5会自动在这个路径下面找需要的内容。这个路径下面需要有一个manifest.json
清单文件,用来表示数据文件的位置,然后就是这些数据文件。
参数二:初始化结果的回调函数
要开始风格转换,代码如下:
styler.transfer(inImg, function(err, result) {
outImg.setAttribute('src', result.src);
})
styler就是我们刚才创建的styleTransfer
对象,styler.transfer()
两个参数,一个是输入图片的元素,一个是执行结果的回调函数,在回调里面我们直接将转移的结果result显示到另一个页面元素里面。
因为styler.transfer()
是一个同步方法,调用过后页面的线程就被阻塞,状态内容并没有刷新到页面上。我们就用setTimeout
先更新状态,再来开始转换过程。
当然我么也可以训练自己的风格,训练风格需要更强的计算能力和内存,所以在浏览器里面就不太合适,具体的操作步骤可以参见官方的教程。
https://blog.paperspace.com/creating-your-own-style-transfer-mirror/
ml5.js基于tensorflow.js为我们提供了一个在浏览器里面运行的深度学习神经网络的库,这个库使用相对简单,也不需要特殊的计算机与配置。适合初学者体验和入门。它也实现了许多成熟的网络,可以实现一些有用的功能,有的可以实现图像分类,有的可以识别人体的姿态,有的可以生成草图,有的可以检测人脸,还可以声音识别,文本分段等等。。。
具体的例子可以在下面这些网址找到:
https://ml5js.org/community/
https://examples.ml5js.org/
https://ml4a.github.io/demos/
好了,ml5.js系列的入门介绍就告一段落。如果大家有任何意见,建议,idea,或者在编码过程中遇到任何问题,欢迎在下边留言,我看到会一一回复各位。谢谢大家!