解决ShortCutTree的一些问题

dev-VirtualTexture
wuyize 2022-10-09 23:06:54 +08:00
parent 382051e341
commit cebd41fc20
6 changed files with 37 additions and 19 deletions

View File

@ -45,9 +45,9 @@ void Line::push_back(Point now) {
} }
bool Line::isLineContained(QVector4D bound) { bool Line::isLineContained(QVector4D bound) {
double xMi = min(*vX.begin(), *vX.rbegin()), xMx = max(*vX.begin(), *vX.rbegin()); double xMin = min(*vX.begin(), *vX.rbegin()), xMax = max(*vX.begin(), *vX.rbegin());
double yMi = min(*vY.begin(), *vY.rbegin()), yMx = max(*vY.begin(), *vY.rbegin()); double yMin = min(*vY.begin(), *vY.rbegin()), yMax = max(*vY.begin(), *vY.rbegin());
if (bound.x() <= xMi && xMx <= bound.z() && bound.y() <= yMi && yMx <= bound.w()) if (bound.x() <= xMin && xMax <= bound.z() && bound.y() <= yMin && yMax <= bound.w())
return true; return true;
else return false; else return false;
} }

View File

@ -193,16 +193,18 @@ Drawable* Model::processMesh(aiMesh* mesh, const aiScene* scene, aiMatrix4x4 mod
//vector<vector<Point>> lineSet = SvgParser("M100,100C-.5,100,0,100.5,0,0L40,.07C40,59.5,39.5,60,100,60Z", 100, 100).parse(); //vector<vector<Point>> lineSet = SvgParser("M100,100C-.5,100,0,100.5,0,0L40,.07C40,59.5,39.5,60,100,60Z", 100, 100).parse();
vector<vector<Point>> lineSet = SvgParser("M308.49,212.25l23,28.38-82,78.31c-14.28,13.64-26.34-20.6-53.44,9.32l-30.24-13.4,63.56-51.59L190.71,215.6l-32.92,26.72L149.5,232.1l32.92-26.72L173.2,194l-32.91,26.72-7.38-9.08L165.83,185l-38.69-47.66L94.22,164,85,152.65l32.91-26.72-9.21-11.35L75.79,141.3l-5.53-6.81,32.92-26.72L94,96.42,61.05,123.14l-12-14.76L37.72,117.6l12,14.75L30.41,148,0,110.55,136.2,0l30.4,37.46L147.31,53.12l-12-14.76L124,47.58l12,14.75L103.05,89.05l9.21,11.35,32.92-26.72,5.52,6.81-32.91,26.72L127,118.56l32.92-26.72,9.21,11.35-32.91,26.72,38.69,47.67,32.91-26.72,7.37,9.08-32.91,26.72L191.49,198l32.92-26.72,8.29,10.22-32.92,26.71,38.7,47.68L302,204.3l6.45,7.95Z", 331.52, 328.26).parse(); vector<vector<Point>> lineSet = SvgParser("M308.49,212.25l23,28.38-82,78.31c-14.28,13.64-26.34-20.6-53.44,9.32l-30.24-13.4,63.56-51.59L190.71,215.6l-32.92,26.72L149.5,232.1l32.92-26.72L173.2,194l-32.91,26.72-7.38-9.08L165.83,185l-38.69-47.66L94.22,164,85,152.65l32.91-26.72-9.21-11.35L75.79,141.3l-5.53-6.81,32.92-26.72L94,96.42,61.05,123.14l-12-14.76L37.72,117.6l12,14.75L30.41,148,0,110.55,136.2,0l30.4,37.46L147.31,53.12l-12-14.76L124,47.58l12,14.75L103.05,89.05l9.21,11.35,32.92-26.72,5.52,6.81-32.91,26.72L127,118.56l32.92-26.72,9.21,11.35-32.91,26.72,38.69,47.67,32.91-26.72,7.37,9.08-32.91,26.72L191.49,198l32.92-26.72,8.29,10.22-32.92,26.71,38.7,47.68L302,204.3l6.45,7.95Z", 331.52, 328.26).parse();
qDebug() << lineSet.size();
for (vector<Point> line : lineSet) for (vector<Point> line : lineSet)
{ {
for (Point p : line) for (Point p : line)
p.show(); p.show();
std::cout << std::endl; std::cout << std::endl;
} }
//vector<vector<Point>> lineSet = { {Point{-1,-1}, Point{1,-1}},{Point{1,-1}, Point{1,1}}, {Point{1,1}, Point{-1,1}},{Point{-1,1}, Point{-1,-1}} }; //vector<vector<Point>> lineSet = { {Point{-1,-1}, Point{1,-1}},{Point{1,-1}, Point{1,1}}, {Point{1,1}, Point{-1,1}},{Point{-1,1}, Point{-1,-1}} };
//vector<vector<Point>> lineSet = { {Point{-1,-1}, Point{1,-1}},{Point{1,-1}, Point{1,1}}, {Point{1,1}, Point{-1,1}},{Point{-1,1}, Point{-1,-1}} }; //vector<vector<Point>> lineSet = { {Point{-1,-1}, Point{1,-1}},{Point{1,-1}, Point{1,1}}, {Point{1,1}, Point{-1,1}},{Point{-1,1}, Point{-1,-1}} };
ShortCutTree shortCutTree(100); ShortCutTree shortCutTree(3);
shortCutTree.buildShortCutTree(lineSet); shortCutTree.buildShortCutTree(lineSet);
vector<float> pointVector; vector<float> pointVector;
vector<GLuint> lineVector; vector<GLuint> lineVector;

View File

@ -736,7 +736,8 @@ bool drawElement(uint elementIndex, vec2 localUV, out vec3 color, inout vec3 deb
{ {
if (leftChild >= elementBvhLength) if (leftChild >= elementBvhLength)
{ {
debugBVH.r += 0.5; if (any(greaterThan(bound.xy+vec2(0.001), localUV)) || any(greaterThan(localUV, bound.zw-vec2(0.001))))
debugBVH.r += 1;
uint styleIndex = bvhChildren[elementBvhRoot + elementBvhIndex].y; uint styleIndex = bvhChildren[elementBvhRoot + elementBvhIndex].y;
// for(int i = 0; i<200;i++) // for(int i = 0; i<200;i++)
@ -915,7 +916,7 @@ void main()
imageStore(gBaseColor, pixelLocation, vec4(color.rgb,1)); imageStore(gBaseColor, pixelLocation, vec4(color.rgb,1));
//return; //return;
if (color.a!=-1) if (color.a!=-1&&debugBVH==vec3(0))
imageStore(gBaseColor, pixelLocation, vec4(vec3(1, 1, 0),1)); imageStore(gBaseColor, pixelLocation, vec4(vec3(1, 1, 0),1));
else else
imageStore(gBaseColor, pixelLocation, vec4(debugBVH,1)); imageStore(gBaseColor, pixelLocation, vec4(debugBVH,1));

View File

@ -1,4 +1,5 @@
#include "ShortCutTree.h" #include "ShortCutTree.h"
#include <qDebug>
void ShortCutTree::init() { void ShortCutTree::init() {
restOfTreeNodes.clear(); restOfTreeNodes.clear();
@ -92,7 +93,7 @@ bool ShortCutTree::handleShortCutNode(ShortCutNode& fa, ShortCutNode& nowTreeNod
nowTreeNode.lineSet.push_back(lineIndex); nowTreeNode.lineSet.push_back(lineIndex);
} }
} }
qDebug() << nowTreeNode.lineSet.size() ;
if (nowTreeNode.lineSet.size() <= RequiredLineMin) { if (nowTreeNode.lineSet.size() <= RequiredLineMin) {
if (nowTreeNode.lineSet.empty() && nowTreeNode.windingIncrement == 0) if (nowTreeNode.lineSet.empty() && nowTreeNode.windingIncrement == 0)
return false; return false;
@ -126,23 +127,26 @@ void ShortCutTree::simplifyLineVector() {
void ShortCutTree::spliteToShortCutTree() { void ShortCutTree::spliteToShortCutTree() {
queue<ShortCutNode> Q; queue<ShortCutNode> Q;
queue<pair<float, float> > lineBound; queue<pair<double, double> > lineBound;
ShortCutNode root; ShortCutNode root;
int nowEastGroup = 0, eastGroupSize = 1;
root.bound = QVector4D(-1, -1, 1, 1); root.bound = QVector4D(-1, -1, 1, 1);
for (int i = 0; i < allLine.size(); i++) { for (int i = 0; i < allLine.size(); i++) {
root.lineSet.push_back(i); root.lineSet.push_back(i);
} }
root.eastGroup = eastGroupSize;
Q.push(root); Q.push(root);
lineBound.push({ -1, 1 }); lineBound.push({ -1, 1 });
vector<ShortCutNode> tmpTreeNodes, generatedTreeNodes; vector<ShortCutNode> tmpTreeNodes, generatedTreeNodes;
while (!lineBound.empty()) { while (!lineBound.empty()) {
// 取出一行的所有可行方格 // 取出一行的所有可行方格
++nowEastGroup;
auto segment = lineBound.front(); auto segment = lineBound.front();
float yMid = (segment.first + segment.second) / 2; double yMid = (segment.first + segment.second) / 2;
lineBound.pop(); lineBound.pop();
while (!Q.empty()) { while (!Q.empty()) {
auto nowTreeNode = Q.front(); auto nowTreeNode = Q.front();
if (nowTreeNode.bound.y() <= segment.first && segment.second <= nowTreeNode.bound.w()) { if (nowTreeNode.eastGroup == nowEastGroup) {
tmpTreeNodes.push_back(nowTreeNode); tmpTreeNodes.push_back(nowTreeNode);
Q.pop(); Q.pop();
} }
@ -167,7 +171,7 @@ void ShortCutTree::spliteToShortCutTree() {
} }
else { else {
ShortCutNode nwTreeNode, neTreeNode; ShortCutNode nwTreeNode, neTreeNode;
float xMid = (nowTreeNode.bound.x() + nowTreeNode.bound.z()) / 2; double xMid = (nowTreeNode.bound.x() + nowTreeNode.bound.z()) / 2;
neTreeNode.bound = QVector4D(xMid, yMid, nowTreeNode.bound.z(), nowTreeNode.bound.w()); neTreeNode.bound = QVector4D(xMid, yMid, nowTreeNode.bound.z(), nowTreeNode.bound.w());
isDivided |= handleShortCutNode(nowTreeNode, neTreeNode, yMid, generatedTreeNodes, sumIncrement); isDivided |= handleShortCutNode(nowTreeNode, neTreeNode, yMid, generatedTreeNodes, sumIncrement);
nwTreeNode.bound = QVector4D(nowTreeNode.bound.x(), yMid, xMid, nowTreeNode.bound.w()); nwTreeNode.bound = QVector4D(nowTreeNode.bound.x(), yMid, xMid, nowTreeNode.bound.w());
@ -175,8 +179,10 @@ void ShortCutTree::spliteToShortCutTree() {
} }
} }
if (isDivided) { if (isDivided) {
++eastGroupSize;
lineBound.push({yMid, segment.second}); lineBound.push({yMid, segment.second});
for (auto& nowTreeNode : generatedTreeNodes) { for (auto nowTreeNode : generatedTreeNodes) {
nowTreeNode.eastGroup = eastGroupSize;
Q.push(nowTreeNode); Q.push(nowTreeNode);
} }
} }
@ -186,13 +192,18 @@ void ShortCutTree::spliteToShortCutTree() {
isDivided = false; isDivided = false;
for (auto& nowTreeNode : tmpTreeNodes) { for (auto& nowTreeNode : tmpTreeNodes) {
if (!nowTreeNode.divided) { if (!nowTreeNode.divided) {
sumIncrement += nowTreeNode.windingIncrement; for (int& lineIndex : nowTreeNode.lineSet) {
int type = allLine[lineIndex]->judgeBoundIntersection(segment.first, nowTreeNode.bound.x(), nowTreeNode.bound.z(), true);
if (type == 2)
sumIncrement++;
if (type == 3)
sumIncrement--;
}
generatedTreeNodes.push_back(nowTreeNode); generatedTreeNodes.push_back(nowTreeNode);
} }
else { else {
ShortCutNode seTreeNode, swTreeNode; ShortCutNode seTreeNode, swTreeNode;
float xMid = (nowTreeNode.bound.x() + nowTreeNode.bound.z()) / 2; float xMid = (nowTreeNode.bound.x() + nowTreeNode.bound.z()) / 2;
yMid = (nowTreeNode.bound.y() + nowTreeNode.bound.w()) / 2;
seTreeNode.bound = QVector4D(xMid, nowTreeNode.bound.y(), nowTreeNode.bound.z(), yMid); seTreeNode.bound = QVector4D(xMid, nowTreeNode.bound.y(), nowTreeNode.bound.z(), yMid);
isDivided |= handleShortCutNode(nowTreeNode, seTreeNode, segment.first, generatedTreeNodes, sumIncrement); isDivided |= handleShortCutNode(nowTreeNode, seTreeNode, segment.first, generatedTreeNodes, sumIncrement);
swTreeNode.bound = QVector4D(nowTreeNode.bound.x(), nowTreeNode.bound.y(), xMid, yMid); swTreeNode.bound = QVector4D(nowTreeNode.bound.x(), nowTreeNode.bound.y(), xMid, yMid);
@ -200,11 +211,14 @@ void ShortCutTree::spliteToShortCutTree() {
} }
} }
if (isDivided) { if (isDivided) {
++eastGroupSize;
lineBound.push({segment.first, yMid}); lineBound.push({segment.first, yMid});
for (auto& nowTreeNode : generatedTreeNodes) { for (auto nowTreeNode : generatedTreeNodes) {
nowTreeNode.eastGroup = eastGroupSize;
Q.push(nowTreeNode); Q.push(nowTreeNode);
} }
} }
tmpTreeNodes.clear();
} }
} }

View File

@ -10,7 +10,7 @@ using std::for_each;
struct ShortCutNode { struct ShortCutNode {
typedef vector<Point> vectorPoint; typedef vector<Point> vectorPoint;
int windingIncrement; int windingIncrement, eastGroup;
bool divided; bool divided;
/* type 代表进入广度优先搜索队列的节点种类: /* type 代表进入广度优先搜索队列的节点种类:
0 0
@ -20,6 +20,7 @@ struct ShortCutNode {
ShortCutNode() { ShortCutNode() {
divided = true; divided = true;
windingIncrement = 0; windingIncrement = 0;
eastGroup = 0;
lineSet.clear(); lineSet.clear();
bound = { 0, 0, 0, 0 }; bound = { 0, 0, 0, 0 };
} }

View File

@ -8,7 +8,7 @@ double StraightLine::getLineValueByT(double t, bool isY) {
} }
else { else {
valueBegin = *vX.begin(); valueBegin = *vX.begin();
valueEnd = *vY.rbegin(); valueEnd = *vX.rbegin();
} }
return t * (valueEnd - valueBegin) + valueBegin; return t * (valueEnd - valueBegin) + valueBegin;
} }
@ -40,8 +40,8 @@ int StraightLine::judgeBoundIntersection(double xy, double l, double r, bool isY
} }
return 0; return 0;
} else { } else {
if (pointBegin.y <= l && pointEnd.y < l) return 0; if (pointBegin.y <= l && pointEnd.y <= l) return 0;
if (pointBegin.y >= r && pointEnd.y > r) return 0; if (pointBegin.y >= r && pointEnd.y >= r) return 0;
return 1; return 1;
} }
return 0; return 0;