布景

汉字笔顺动画是常见的语文教育需求,咱们导入网上开源的 Hanzi Writter 并安置编辑器,应用在大力智能作业灯上。在原版前端结束基础上咱们扩展了 Android 和 iOS 端结束,供给更优化的笔顺动画功用。增强对笔顺制作的控制才能,结束了指定笔顺/笔段烘托,支撑笔顺修改和描红才能。

汉字笔顺动画技术分析

要害技术

1. 字形数据提取

字形是单个字符的外观形状,而字体是具有相同外观样式和排版尺度的宫颈癌前期症状字形集结。根据字形数据,咱们能够结束每个文字的烘托和笔顺动画。那么该怎样拿到字形数据呢?TTF便是不错的挑选。TTF(TrueTy开源是什么意思peFont)是一种曲线描边字体文件格局,由Apple公司和Microsoft公司一起推出,其文件扩展名为.ttf。它支撑多种字体,如语文讲义中常见的楷体。TTF文件由一系列表组成,其间glyf表就包含了字形数据,即字形的概括界说和调android/yunos整指令。根据下述流程能够提取字形数据:

  1. 对不同字体的boundary进行适配,悉数转换成1024*1024,并对上下左右进行微Apple调。android是什么手机牌子
  2. 提取悉数字形开源阅览glyph的概括点contours和path数据。

汉字笔顺动画技术分析

提取出字形apple pay数据后,运用SVGgiti是什么牌子将对应文字制作出来。

汉字笔顺动画技术分析

2.Stroke Extractiongiti 笔画拆取

在第一android/yunos节中结束了字形数apple id据的提取,它包含字形的概括点contours及path(a)。但是仅依靠这些数据无法结束笔顺动画,由于它们只需概括信息,没有笔画信息,只需有穿插堆叠,都会识别成同一个别(b)。因此,要结束笔顺动画,就必须从源数据中拆取出悉数笔画的开源矿工概括数据,即笔画拆取。

汉字笔顺动画技术分析

2.1 处理思路

由于笔画之间存在穿插堆叠(c),若要结束笔画拆取,就需求将笔画交接处的凹点连通起来。google这些处于穿插处特别的角落点称为corner,连通两个corner构成bridge,标明他们同归于一个开源我国笔画。

当顺时针跟踪端点:

  • 连通前:根据概括点次序。

  • 连通后:会根据bridge直接联通对应corner,然后结束笔画的拆分。

汉字笔顺动画技术分析

因此,笔画拆取作业首要分为以下四步:

汉字笔顺动画技术分析

2.2 EndPoapple官网int Parsing Corner检测

在Hanzi Wr开源阅览app下载装置itter开源库中,笔画拆取算法首要盘绕corner展开。那corner是什么呢?具体来说,corner是坐落两个笔画概括交界的特别端点,通常情况下,他会有另一个corner与之匹配,如C1和Capple pay2。C1和C2相邻android的drawable类且处于笔画A的概括同侧,连通C1和C2就能够将笔画A和笔画B拆分开来,得到笔画A开源软件自己的概括数据。这些corner具有明显的部分特征,它们是字形的apple tv凹点,经过该点处的path会沿着顺时针急剧弯曲。核算出悉数端点的开源代码网站github角度和距离,判别是否具有该特征,就能够检测哪些端点为corner。开源阅览

汉字笔顺动画技术分析

function Endpoint(paths, index) {
this.Goindex = index;
const path =android体系 paths[index[0]];
const n = path.length;
this.indices = [[index[0], (index[1] + n - 1) % nGo], index];
this.segments = [path[(index[1] + n - 1) % n], path[index[1]]];
this.point = this.segments[0].end;
assert(Point.valid(this.point), this.宫崎骏apoint);
assert(Point.equal(this.point, tandroid平板电脑价格handroidstudio装置教程is.s开源代码网站githubegments[1]apple tv.start), path);
this.tangents = [
Point.subtract(this.segments[0].end, this.segments[0].start),
Point.subtract(tandroid是什么手机牌子his.segments[1].end, this.segments[1].start),
];
const threshold = Math.pow(MIN_CORNER_TANGENT_DISTANCE, 2);开源代码网站github
if (this.segments[0].control !== undefined &&
Point.distance2(this.point, this.segmentgithub中文官网网页s[0].control) > threshold) {
this.tanandroid下载gents[0] = Point.s工商银行ubtract(this.point, this.segmenapp id注册ts[0].control);
}
if (this.segm狗狗币ents[1].control !==开源代码网站github undefined &&
Point.distance2(this.point, this.segments[1].control) > threshold) {
this.开源我国tangents[1] = PAndroidoint.subtract(this.segments[1].control, this.poiapple storent);
}
this.angles = this.tangents.map(Point.angle);
c龚俊赵丽颖被公安官博点名onst diff = Angl宫颈癌前期症状e.subtract(this.angles[1], this.angles[0])giti轮胎;
this.corner = diff < -MIN_CORNER_ANGLE;
return this;
}

2.3 Corner Match Scoring 经过NGitN评分Corner匹配度

检测出一组corner数据后,就要对这些corner进行1对1匹配,但在匹配前还需求评判哪些corner更有或许连接起来。开源库选用神经网络开源算法核算corner间的匹配度,它将成为匹配算android体系法中的权重值,使匹配作用更接近现实情况。

const scoreCorners = (ins, out, classifier) => {
return classifier(getFeatures(ins, out)开源);
}
impandroid什么意思ort {NEURAL_NET_TRAINED_FOR_STROKE_EXTRACTION} from '/lib/net';
import {stroke_extra枸杞ctor} from '/lib/stroke_extractor';
Meteor.startup(() =&githubgt; {android下载
const input = new convnetjs.Vol(1,宫颈癌 1, 8 /* feature vector dimensions龚俊赵丽颖被公安官博点名 */);
const net = new coGonvnetjs.Net();
net.fromJSON(NEURAL_NET_TRAINED_FOR_STROKE_EXTRACTION);
const weight = 0.8;
const trainedClassifier = (features) => {
input.w = features;
const softmax = net.forward(input).w;
return softmax[1] - softmax[0];
}
stro开源软件ke_extractor.combinedClassifier = (featur开源代码网站githubes) => {
return stroke_extractor.handTunedClassifier(feaapp storetures) +
weight*trainedClassifier(features);
}
});

2.4 Corner Matching 经过匈牙利算法进行Corner匹配

在2.3末节中现已经过神经网络android平板电脑价格产生了权重,接下来就能够Apple运用最简略的匈牙利算法,结束corner匹配。

汉字笔顺动画技术分析

汉字笔顺动画技术分析

const matchCornersandroid/yunos = (cAppleorners, classifier) => {
const matrix = [];
for (let i = 0; i < corners.length; i++) {
matrix.push(android什么意思[]);
fo狗狗币r (let j = 0; j &lapp id注册t; cornersandroid体系.length; j++) {
matrix[开源是什么意思i].push(scoreCorners(corners[i], corners[j], classifier)); //corner之间相关性
}
}
for (let i = 0; i < corners.length; i++) {
for (let j = 0; j < corners.开源length; j++) {
const regiti是什么牌子versed_score = matrix[j][i] - REVERgit教程SAL_PgitlabENALTY;
if (reversed_score > matrix[i][j]) {
matrix[i][j] = reversed_score;
}
}
}
return (new Hungarian(matrix)).x_match;
}

2.5 Make Bridgeandroid/yunoss 连通配对git命令端点拆分笔画

根据2.4末节的匹配作用回来一组bridge,其间每个bridge包含两个corner。跟踪概括的一起连通corner,就能够提取出每个笔画的概括数据,完枸杞结笔画拆git命令分。值得注意的是,当遇到多个bridge时,挑选与当时path构成最大角度的bridge。

汉字笔顺动画技术分析

const getBridges = (endpoints, classifier) => {
const result = [];
con宫颈癌前期症状st corners =android/yunos endpoint开源阅览app下载装置s.filter((x) => x.corner);
const matching = matchCorners(corners, classifier);
for (let i = 0; i < corners.length; i++) {
const j = matching[i];
if (j <= i && matching[j] === i) {
continue;
}
result.push([Point.clone(corners[i].point), Point.clone(corners[j].point)]);
}
result.map(checkBridge);
return result;
}
const stroke_paths = extractStrokes(Applepaths, endpoints, brgithubidges, log);
const strokes = stroke_paths.mgithub永久回家地址ap(apple id暗码重置(x) => svg.convertPathsToSVGPathandroid下载([x]));

3.apple id暗码重置Medians 笔画中点生成

在第二节中完开源代码网站github结了笔画的拆分android什么意思,得到每个笔画的概括数据。根据概括数据能够进一步生成笔画的中点骨架。概括选择单个Git笔画的制作规划,而中google点则选择了制作的次序和方向。结合概括和中点数据,就能够结束单个androidstudio装置教程笔画的制作动画。接下来就让咱们一起了解,怎样经过概括数据生成中点。

汉字笔顺动画技术分析

3.1 Polygon Approximation 端点加密

首要,为了行进中点生成作用的可靠性,需求先选用矢量图形的多边开源阅览app下载装置形近似方法进行概括点加密。TrueType字体运用二次贝赛尔曲线和直线来描绘字形的概括,因此加密公式如下:

汉字笔顺动画技术分析

汉字笔顺动画技术分析

svg.getPolygonApproxandroid的drawable类imaAndroidtion =android下载 (path, approximation_error) => {
co开源阅览nst result = [];
approximation_error = approximation_error || 64;
for (let x of path) {android什么意思
const control = x.control || Point.midpoint(x.start, x.end);
constgitlab distance = Math.sqrt(Point.distance2(x.start, x.end))龚俊;
const num_points = Math.floor(distance/approandroid/yunosximation_erapple tvror);
for (let i = 0; i &giti轮胎lt; num_points; i++) {
const t开源软件 = (i + 1)/(num_apple tvpoints + 1);
const s = 1 - t;
result.push([s*s*xgitlab.st开源art[0] + 2*s*t*control[0] + t*t*x.end[0],
s*s*x.start[1] + 2*s*t*control[1] + t*tandroid下载装置*x.end[1]]);
}
result.push(x.end);
}
return result;
}

3.2 Polygon V开源是什么意思oronoi 经过冯洛诺伊图(泰森多边形)生成中点

得到加密的概括点数据后,就能够经过泰森多边形生成中点。那什么是泰森多边形呢?

首要对一组零星控制点做如下操作:

  1. 将三个相邻控制点连成一个三角形
  2. 对三角形的每条边做垂直平分线
  3. 这些垂直平分线会组成连续多边形

这些连续多边形便是泰森多边形,又叫冯洛诺伊图(Voronoi diagram),得名于Georgy Voronoi。在IS和地舆分析中常常选用泰森多边形进行快速插值,分析地舆实体的影响区域,是处理邻接度问题的又一常用工具。

汉字笔顺动画技术分析

经过原理能够了解到,泰森多边形每个极点是对应三角形的外接圆圆心,因此它到这些控制点的距离持平。

  var sitesapple id = [{宫颈癌x:300,y:300}, {x:100,y:100}, {x:200,y:5开源是什么意思00}, {x:25android手机0,y:450}, {x:600,y:150}];
// xl, xr means x left, x right
// yt, yb means y top, y bottom
var bbox = {xl:0, xr:8android下载装置00, yt:0, yb:600};
var vo龚俊赵丽颖被公安官博点名ronoi = new Voronoi();
// pass an object which exhibits xl, xr, yt, yb properties. The bounding
// box will be used to connect unbouandroid/yunosnd eapple storedges, and to工商银行 close open cells
result = voronoi.compute(sites, bbox);
// rendegiti是什么牌子r, further analyze, etc.

依照这个思路,能够将笔画的概括点作为控制点apple watch,生成泰森多边形。提取泰森多边形的极点作为笔画中心点。

汉字笔顺动画技术分析

const f开源阅览app下载装置indStrokeMed开源阅览app下载装置ian = (stroke) => {
...
for (let approximation of [16, 64]) {
polygon = svg.getPolygonApproximation开源是什么意思(p开源节流是什么意思是什么aths[0], approximation);
voronoi = vandroid下载oronoi || new Voronoi;
const sites = polygon.map((point) => ({x: point[0], y: point[1]}));
const bounding_box = {龚俊赵丽颖被公安官博点名xl: -size, xr: size, yt: -size, yb: size};
tapple watchry {
diagram = voronoi.compute(sites, bounding_box);
break;
} catch(erro狗狗币r) {
conso开源众包le.error(`WARNING: Voronoi computation failed at ${approximation}.`);
}
}
...
}

4. 笔画次序

第三节结束了单个笔画的制作动画,但仍是需求处理apple id笔画之间的次序问题。处理问题的要害,便是根据汉字结构,将方针汉字不断拆解成已知次序的字。

在开源库中供给了汉字分化数据库,要害app id注册字段如下:

汉字笔顺动画技术分析

以【胡】为例,⿰表明胡为左右结构,左面为古,右边为月。

汉字笔顺动画技术分析

以【湖】为例,apple id拆解进程如下:

汉字笔顺动画技术分析

汉字笔顺动画技术分析

拆解完笔顺后,需求将悉数零星的中点数据,与当时所具有的中点再做一遍匈牙利算法匹配,毕竟可得到一个相对正确的笔画次序作用,生成json文件。下面为汉字“丁”的笔顺作用文件。

{"strok开源阅览app下载装置es": ["M 531 6androidstudio装置教程5龚俊1 Q 736 675 868 663 Q 893 662 899 670 Q 906 683 894 696 Q 863Android 724 817 744 Q 801 750 775 740 Q 712 725 483宫崎骏 694 Q 185 660 168 657 Q 162 658 156 657 Q 141 657 141 645 Q 140 632 1开源节流60 618 Q 178 605 211 594 Q 221 590 240 599 Q 348 629 470 644 L 531android下载 651 Z", "M 435 100 Q 407 107 37apple id暗码重置3 116 Q 360 120 361狗狗币 112 Q 361 103 373 94 Q 445 39 491 -5 Q 503 -15 518 2 Q 560 60 553 141 Q 541 447 548 561 Q 548 579开源阅览app下载装置 550 596 Q 556 624 549 635 Q 545 642 531 651 C 509 671 457 671 470 644 Q 485 629 485 573 Q 48github8 443 488 148 Q 487 112 477 99 Q 464 92 43Apple5 100 Z"], "medians": [[[153, 645], [177, 634], [2Apple19, 628], [416, 663], [794, 706], [823, 702], [887开源节流是什么意思是什么, 679]], [[478, 644], [51gitee8, 610], [518, 101], [495, 55],android的drawable类 [450, 68], [369, 110]]]}

5. 相关参阅

本文要点分析了开源库中笔顺动画的要害技术,相关参阅资料如下:

  1. hanziwriter.org/
  2. www.skishore.me/makemeahanz…
  3. github.com/skishore/ma…