cleaning.
This commit is contained in:
parent
a99a702c9c
commit
80ddbed065
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.9 2005/02/20 00:43:23 ponchio
|
||||
Less memory x extraction. (removed frags)
|
||||
|
||||
Revision 1.8 2005/02/19 16:22:45 ponchio
|
||||
Minor changes (visited and Cell)
|
||||
|
||||
|
@ -64,7 +67,9 @@ void Extraction::Extract(NexusMt *_mt) {
|
|||
|
||||
//first we clear the visited flags
|
||||
visited.clear();
|
||||
visited.resize(mt->history.n_nodes(), 0);
|
||||
visited.resize(mt->history.n_nodes(), false);
|
||||
visible.clear();
|
||||
visible.resize(mt->size(), true);
|
||||
|
||||
heap.clear();
|
||||
|
||||
|
@ -96,34 +101,28 @@ void Extraction::Init() {
|
|||
Node *nodes = mt->history.nodes;
|
||||
for(unsigned int i = 0; i < visited.size(); i++) {
|
||||
if(!visited[i]) continue;
|
||||
// if(!visited[i]) continue;
|
||||
Node &node = nodes[i];
|
||||
|
||||
bool cancoarse = true;
|
||||
|
||||
Node::iterator n;
|
||||
for(n = node.out_begin(); n != node.out_end(); n++) {
|
||||
if(!Visited((*n).node)) {
|
||||
// if(!visited[(*n).node - root]) {
|
||||
float maxerror = -1;
|
||||
|
||||
Link &link = *n;
|
||||
for(Link::iterator k = link.begin(); k != link.end(); k++) {
|
||||
// unsigned int patch = *k;
|
||||
unsigned int patch = k;
|
||||
Entry &entry = (*mt)[patch];
|
||||
|
||||
bool visible;
|
||||
float error = metric->GetError(entry, visible);
|
||||
|
||||
if(error > maxerror) maxerror = error;
|
||||
|
||||
cost.extr += entry.ram_size;
|
||||
//TODO if(frustum) else
|
||||
//if(visible)
|
||||
// cost.draw += entry.ram_size;
|
||||
|
||||
vcg::Sphere3f &sphere = entry.sphere;
|
||||
if(!frustum.IsOutside(sphere.Center(), sphere.Radius()))
|
||||
SetVisible(patch, visible);
|
||||
if(visible)
|
||||
cost.draw += entry.ram_size;
|
||||
|
||||
if(!entry.patch)
|
||||
|
@ -135,7 +134,7 @@ void Extraction::Init() {
|
|||
} else
|
||||
cancoarse = false;
|
||||
}
|
||||
if(cancoarse && &node != root) {
|
||||
if(cancoarse && (&node != root)) {
|
||||
float error = GetRefineError(&node);
|
||||
back.push_back(HeapNode(&node, error));
|
||||
}
|
||||
|
@ -157,31 +156,48 @@ void Extraction::Update(NexusMt *_mt) {
|
|||
if(!visited.size()) {
|
||||
visited.resize(mt->history.n_nodes(), false);
|
||||
SetVisited(root, true);
|
||||
}
|
||||
}
|
||||
visible.clear();
|
||||
visible.resize(mt->size(), true);
|
||||
|
||||
Init();
|
||||
|
||||
bool no_draw = false;
|
||||
bool no_disk = false;
|
||||
|
||||
//TODO big problem: nodes a (error 10) with parent b (error -1)
|
||||
//i try to refine a, refine b (recursive) but fail to refine a
|
||||
//next step i coarse b whis cause a cycle.
|
||||
|
||||
/* Updateing strategy:
|
||||
if i can refine (not at leaves, have draw and extr buffer, not past target_error)
|
||||
i try to refine BUT
|
||||
i can fail because i finish some buffer (exp. while recursively refine)
|
||||
(then i put the operation back on the stack)
|
||||
if i have finished disk i should just quit
|
||||
if i cannot refine i consider coarsening:
|
||||
i need 1) not be at root (eheh)
|
||||
2) have finished draw and extr buffer
|
||||
3) do not make global error worse (unless it is < target_error...)
|
||||
4) check it is not a recursive coarsening (drop it otherwise)
|
||||
i try to coarse BUT
|
||||
i can fail because i need disk
|
||||
(then i put the operation back on the stack)
|
||||
if i cannot coarse i just quit
|
||||
*/
|
||||
|
||||
while(1) {
|
||||
if(!no_draw && //we have buffer
|
||||
front.size() && //we are not at max level
|
||||
front[0].error > target_error) { //we are not already target_error
|
||||
front[0].error > target_error) { //we are not already at target_error
|
||||
|
||||
max_error = front[0].error;
|
||||
pop_heap(front.begin(), front.end());
|
||||
HeapNode hnode = front.back();
|
||||
front.pop_back();
|
||||
if(!Visited(hnode.node)) {
|
||||
if(!Refine(hnode)) {
|
||||
|
||||
if(!Visited(hnode.node) && !Refine(hnode))
|
||||
no_draw = true;
|
||||
}
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
|
@ -191,6 +207,7 @@ void Extraction::Update(NexusMt *_mt) {
|
|||
}
|
||||
|
||||
if(no_draw) { //suppose i have no more buffer
|
||||
//TODO see point 3
|
||||
//if i do error damages coarsening better get out
|
||||
if(front.size() && ((back.front().error + 0.001) >= front.front().error)) {
|
||||
//cerr << "Balanced cut\n";
|
||||
|
@ -219,10 +236,10 @@ void Extraction::Update(NexusMt *_mt) {
|
|||
Node *child = (*i).node;
|
||||
if(Visited(child)) recursive = true;
|
||||
}
|
||||
if(!recursive && !Coarse(hnode)) { //no more disk so.. push back on heap the heapnode
|
||||
back.push_back(hnode);
|
||||
push_heap(back.begin(), back.end(), greater<HeapNode>());
|
||||
break;
|
||||
if(!recursive && !Coarse(hnode)) { //no more disk so. push back on heap the heapnode
|
||||
back.push_back(hnode);
|
||||
push_heap(back.begin(), back.end(), greater<HeapNode>());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -244,8 +261,6 @@ void Extraction::Update(NexusMt *_mt) {
|
|||
for(l = node->out_begin(); l != node->out_end(); l++) {
|
||||
Link &link = (*l);
|
||||
for(Link::iterator k = link.begin(); k != link.end(); k++) {
|
||||
// selected.push_back(Item(*k, i));
|
||||
// errors[*k] = i;
|
||||
selected.push_back(Item(k, i));
|
||||
errors[k] = i;
|
||||
}
|
||||
|
@ -259,8 +274,6 @@ void Extraction::Update(NexusMt *_mt) {
|
|||
for(l = node->in_begin(); l != node->in_end(); l++) {
|
||||
Link &link = (*l);
|
||||
for(Link::iterator k = link.begin(); k != link.end(); k++) {
|
||||
// selected.push_back(Item(*k, i));
|
||||
// errors[*k] = i;
|
||||
selected.push_back(Item(k, i));
|
||||
errors[k] = i;
|
||||
}
|
||||
|
@ -279,6 +292,7 @@ float Extraction::GetRefineError(Node *node) {
|
|||
bool visible;
|
||||
float error = metric->GetError(entry, visible);
|
||||
if(error > maxerror) maxerror = error;
|
||||
SetVisible(p, visible);
|
||||
}
|
||||
}
|
||||
return maxerror;
|
||||
|
@ -399,11 +413,6 @@ void Extraction::Select() {
|
|||
unsigned int n_out = (*n).node - root;
|
||||
if(!visited[n_out]) {
|
||||
Link &link = *n;
|
||||
/* for(Link::iterator k = link.begin(); k != link.end(); k++) {
|
||||
unsigned int patch = *k;
|
||||
selected.push_back(Item(patch,0));
|
||||
errors[patch] = 0.0f;
|
||||
}*/
|
||||
for(Link::iterator p= link.begin(); p != link.end(); p++) {
|
||||
selected.push_back(Item(p, 0));
|
||||
errors[p] = 0.0f;
|
||||
|
@ -438,6 +447,7 @@ void Extraction::Visit(Node *node) {
|
|||
bool visible;
|
||||
float error = metric->GetError(entry, visible);
|
||||
if(error > maxerror) maxerror = error;
|
||||
SetVisible(p, visible);
|
||||
}
|
||||
//TODO this check may be dangerous for non saturating things...
|
||||
if(maxerror > target_error) {
|
||||
|
@ -462,9 +472,8 @@ void Extraction::Diff(Node *node, Cost &cost) {
|
|||
for(Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
Entry &entry = (*mt)[p];
|
||||
cost.extr -= entry.ram_size;
|
||||
vcg::Sphere3f &sphere = entry.sphere;
|
||||
if(!frustum.IsOutside(sphere.Center(), sphere.Radius()))
|
||||
cost.draw -= entry.ram_size;
|
||||
if(Visible(p)) cost.draw -= entry.ram_size;
|
||||
|
||||
if(!entry.patch)
|
||||
cost.disk -= entry.disk_size;
|
||||
}
|
||||
|
@ -475,9 +484,8 @@ void Extraction::Diff(Node *node, Cost &cost) {
|
|||
for(Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
Entry &entry = (*mt)[p];
|
||||
cost.extr += entry.ram_size;
|
||||
vcg::Sphere3f &sphere = entry.sphere;
|
||||
if(!frustum.IsOutside(sphere.Center(), sphere.Radius()))
|
||||
cost.draw += entry.ram_size;
|
||||
if(Visible(p)) cost.draw += entry.ram_size;
|
||||
|
||||
if(!entry.patch)
|
||||
cost.disk += entry.disk_size;
|
||||
}
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.8 2005/02/19 16:22:45 ponchio
|
||||
Minor changes (visited and Cell)
|
||||
|
||||
Revision 1.7 2005/02/10 09:18:20 ponchio
|
||||
Statistics.
|
||||
|
||||
|
@ -81,12 +84,9 @@ class Extraction {
|
|||
};
|
||||
|
||||
Metric *metric;
|
||||
|
||||
//TODO make a pointer so no need to doubl check visibility...!
|
||||
vcg::Frustumf frustum;
|
||||
|
||||
float target_error;
|
||||
float max_error;
|
||||
|
||||
float max_error; //actual error at end of extraction
|
||||
unsigned int extr_used, extr_max;
|
||||
unsigned int draw_used, draw_max;
|
||||
unsigned int disk_used, disk_max;
|
||||
|
@ -98,7 +98,7 @@ class Extraction {
|
|||
std::vector<Item> selected;
|
||||
unsigned int draw_size; //first in selected should be drawn
|
||||
|
||||
std::vector<HeapNode> heap; //no realtime extraxtion
|
||||
std::vector<HeapNode> heap; //no realtime extraxtion TODO (use front)
|
||||
|
||||
//nodes that i can expand to
|
||||
std::vector<HeapNode> front;
|
||||
|
@ -114,6 +114,8 @@ class Extraction {
|
|||
void Update(NexusMt *mt);
|
||||
|
||||
|
||||
bool Visible(unsigned int p) { return visible[p]; }
|
||||
void SetVisible(unsigned int p, bool v) { visible[p] = v; }
|
||||
protected:
|
||||
|
||||
void Select();
|
||||
|
@ -126,16 +128,15 @@ class Extraction {
|
|||
bool Coarse(HeapNode node);
|
||||
|
||||
void Init();
|
||||
|
||||
bool Visited(Node *node) { return visited[node - root]; }
|
||||
void SetVisited(Node *node, bool v) { visited[node - root] = v; }
|
||||
|
||||
private:
|
||||
NexusMt *mt;
|
||||
Node *root;
|
||||
Node *sink;
|
||||
|
||||
bool Visited(Node *node) { return visited[node - root]; }
|
||||
void SetVisited(Node *node, bool v) { visited[node - root] = v; }
|
||||
bool Visible(Node *node) { return visible[node - root]; }
|
||||
void SetVisible(Node *node, bool v) { visible[node - root] = v; }
|
||||
|
||||
float GetRefineError(Node *node);
|
||||
};
|
||||
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.5 2005/02/19 16:22:45 ponchio
|
||||
Minor changes (visited and Cell)
|
||||
|
||||
Revision 1.4 2005/02/08 12:43:03 ponchio
|
||||
Added copyright
|
||||
|
||||
|
@ -43,22 +46,25 @@ namespace nxs {
|
|||
|
||||
class Metric {
|
||||
public:
|
||||
virtual void GetView() {}
|
||||
vcg::Frustumf frustum;
|
||||
bool culling;
|
||||
|
||||
Metric(): culling(true) {}
|
||||
virtual void GetView() { frustum.GetView(); }
|
||||
virtual float GetError(Entry &entry, bool &visible) = 0;
|
||||
|
||||
};
|
||||
|
||||
class FlatMetric: public Metric {
|
||||
public:
|
||||
float GetError(Entry &entry, bool &visible) {
|
||||
visible = true;
|
||||
return entry.error; }
|
||||
return entry.error;
|
||||
}
|
||||
};
|
||||
|
||||
class FrustumMetric: public Metric {
|
||||
public:
|
||||
vcg::Frustumf frustum;
|
||||
|
||||
virtual void GetView() { frustum.GetView(); }
|
||||
float GetError(Entry &entry, bool &visible) {
|
||||
visible = true;
|
||||
vcg::Sphere3f &sph = entry.sphere;
|
||||
|
@ -66,12 +72,16 @@ namespace nxs {
|
|||
|
||||
if(dist < 0) return 1e20f;
|
||||
|
||||
float remote = frustum.Remoteness(sph.Center(), sph.Radius());
|
||||
float error = entry.error/frustum.Resolution(dist);
|
||||
if(remote > 0) {
|
||||
visible = false;
|
||||
error /= remote;
|
||||
}
|
||||
if(culling) {
|
||||
float remote = frustum.Remoteness(sph.Center(), sph.Radius());
|
||||
if(remote > 0) {
|
||||
visible = false;
|
||||
error /= remote;
|
||||
} else if(entry.cone.Backface(sph, frustum.ViewPoint())) {
|
||||
visible = false;
|
||||
}
|
||||
}
|
||||
return error;
|
||||
}
|
||||
};
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.33 2005/02/20 00:43:23 ponchio
|
||||
Less memory x extraction. (removed frags)
|
||||
|
||||
Revision 1.32 2005/02/19 12:06:53 ponchio
|
||||
Debug...
|
||||
|
||||
|
@ -129,7 +132,6 @@ bool NexusMt::InitGL(bool vbo) {
|
|||
|
||||
void NexusMt::Render(DrawContest contest) {
|
||||
Extraction extraction;
|
||||
extraction.frustum.GetView();
|
||||
extraction.metric->GetView();
|
||||
extraction.Extract(this);
|
||||
Render(extraction, contest);
|
||||
|
@ -162,11 +164,9 @@ void NexusMt::Render(Extraction &extraction, DrawContest &contest,
|
|||
for(unsigned int i = 0; i < extraction.draw_size; i++) {
|
||||
unsigned int patch = extraction.selected[i].id;
|
||||
Entry &entry = operator[](patch);
|
||||
vcg::Sphere3f &sphere = entry.sphere;
|
||||
|
||||
if(stats) stats->extr += 2*entry.nvert;
|
||||
|
||||
if(extraction.frustum.IsOutside(sphere.Center(), sphere.Radius()))
|
||||
if(!extraction.Visible(patch))
|
||||
continue;
|
||||
|
||||
if(stats) stats->tri += 2*entry.nvert;
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.42 2005/02/20 00:43:24 ponchio
|
||||
Less memory x extraction. (removed frags)
|
||||
|
||||
Revision 1.41 2005/02/19 12:06:55 ponchio
|
||||
Debug...
|
||||
|
||||
|
@ -314,9 +317,6 @@ int main(int argc, char *argv[]) {
|
|||
return -1;
|
||||
}
|
||||
|
||||
|
||||
// FrustumPolicy frustum_policy;
|
||||
|
||||
cerr << "Commands: \n"
|
||||
" q : quit\n"
|
||||
" t : toggle statistics\n"
|
||||
|
@ -408,7 +408,6 @@ int main(int argc, char *argv[]) {
|
|||
case SDLK_0: extraction.extr_max *= 1.3; break;
|
||||
case SDLK_9: extraction.extr_max *= 0.8; break;
|
||||
|
||||
// case SDLK_s: metric = NexusMt::FRUSTUM; break;
|
||||
case SDLK_p: contest.mode = DrawContest::POINTS; break;
|
||||
case SDLK_d: contest.mode = DrawContest::PATCHES; break;
|
||||
case SDLK_f: contest.mode = DrawContest::FLAT; break;
|
||||
|
@ -517,7 +516,8 @@ int main(int argc, char *argv[]) {
|
|||
glColor3f(0.8f, 0.8f, 0.8f);
|
||||
|
||||
if(extract) {
|
||||
extraction.frustum.GetView();
|
||||
// Sould we want a different view from metric and extraction
|
||||
// extraction.frustum->GetView();
|
||||
extraction.metric->GetView();
|
||||
if(!realtime) {
|
||||
extraction.Extract(&nexus);
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.20 2005/02/19 10:45:04 ponchio
|
||||
Patch generalized and small fixes.
|
||||
|
||||
Revision 1.19 2005/02/18 13:04:12 ponchio
|
||||
Added patch reordering.
|
||||
|
||||
|
@ -57,6 +60,57 @@ using namespace vcg;
|
|||
#include "tristripper/tri_stripper.h"
|
||||
using namespace triangle_stripper;
|
||||
|
||||
|
||||
void nxs::TightSphere(vcg::Sphere3f &sphere,
|
||||
std::vector<vcg::Point3f> &points) {
|
||||
//test:
|
||||
//assumes radius is ok.... and try to optimize moving center.
|
||||
//TODO using a gradiend descent? really a mess.
|
||||
Point3f center;
|
||||
float radius;
|
||||
Point3f pert[14];
|
||||
while(1) {
|
||||
radius = sphere.Radius();
|
||||
float step = radius/40;
|
||||
pert[0] = Point3f(step, 0, 0);
|
||||
pert[1] = -pert[0];
|
||||
pert[2] = Point3f(0, step, 0);
|
||||
pert[3] = -pert[2];
|
||||
pert[4] = Point3f(0, 0, step);
|
||||
pert[5] = -pert[4];
|
||||
pert[6] = Point3f(step, step, step);
|
||||
pert[7] = Point3f(step, step, -step);
|
||||
pert[8] = Point3f(step, -step, step);
|
||||
pert[9] = Point3f(step, -step, -step);
|
||||
pert[10] = Point3f(-step, step, step);
|
||||
pert[11] = Point3f(-step, step, -step);
|
||||
pert[12] = Point3f(-step, -step, step);
|
||||
pert[13] = Point3f(-step, -step, -step);
|
||||
|
||||
unsigned int best = 14;
|
||||
float best_radius = sphere.Radius();
|
||||
|
||||
for(unsigned int k = 0; k < 14; k++) {
|
||||
center = sphere.Center() + pert[k];
|
||||
radius = 0;
|
||||
for(unsigned int i = 0; i < points.size(); i++) {
|
||||
float r = 1.01 * Distance(center, points[i]);
|
||||
if(r > radius)
|
||||
radius = r;
|
||||
}
|
||||
if(radius < best_radius) {
|
||||
best = k;
|
||||
best_radius = radius;
|
||||
}
|
||||
}
|
||||
if(best == 14) break;
|
||||
sphere.Center() = sphere.Center() + pert[best];
|
||||
sphere.Radius() = best_radius;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void nxs::ComputeNormals(Nexus &nexus) {
|
||||
assert(nexus.signature.vnorm);
|
||||
|
||||
|
@ -74,9 +128,8 @@ void nxs::ComputeNormals(Nexus &nexus) {
|
|||
exit(0);
|
||||
}
|
||||
|
||||
//TODO optimize! it is not necessary to read all the borders.
|
||||
for(unsigned int p = 0; p < nexus.size(); p++) {
|
||||
Border &border = nexus.GetBorder(p);
|
||||
Border &border = nexus.borders[p];
|
||||
tmpb_start.push_back(tmpb_offset);
|
||||
tmpb_offset += border.Size();
|
||||
}
|
||||
|
@ -131,6 +184,10 @@ void nxs::ComputeNormals(Nexus &nexus) {
|
|||
normals[f[2]] += norm;
|
||||
}
|
||||
|
||||
//compute normalscone (done in building...
|
||||
// ANCone3f cone;
|
||||
// cone.AddNormals(normals, cone_threshold);
|
||||
// nexus[p].cone.Import(cone);
|
||||
if(nexus.signature.vnorm == Encodings::SHORT4) {
|
||||
short *n = (short *)patch.VNormBegin();
|
||||
for(unsigned int i = 0; i < patch.nv; i++, n += 4) {
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.6 2005/02/19 10:45:04 ponchio
|
||||
Patch generalized and small fixes.
|
||||
|
||||
Revision 1.5 2005/02/18 13:04:13 ponchio
|
||||
Added patch reordering.
|
||||
|
||||
|
@ -38,12 +41,14 @@ Added copyright
|
|||
|
||||
#include <vector>
|
||||
#include "patch.h"
|
||||
#include <vcg/space/sphere3.h>
|
||||
|
||||
namespace nxs {
|
||||
|
||||
class Nexus;
|
||||
class Patch;
|
||||
|
||||
|
||||
struct ZEntry {
|
||||
unsigned int id;
|
||||
unsigned int pos;
|
||||
|
@ -57,6 +62,7 @@ namespace nxs {
|
|||
void Unify(Nexus &nexus, float threshold);
|
||||
void ZSort(Nexus &nexus, std::vector<unsigned int> &forward,
|
||||
std::vector<unsigned int> &backward);
|
||||
void TightSphere(vcg::Sphere3f &sphere, std::vector<vcg::Point3f> &points);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.18 2005/02/20 00:43:24 ponchio
|
||||
Less memory x extraction. (removed frags)
|
||||
|
||||
Revision 1.17 2005/02/19 17:14:02 ponchio
|
||||
History quick by default.
|
||||
|
||||
|
@ -338,7 +341,8 @@ void ThirdStep(const string &crudefile, const string &output,
|
|||
assert(vcount == vertices.size());
|
||||
assert(fcount == faces.size());
|
||||
|
||||
//TODO deal with this case adding another patch at the end... its not that difficult!
|
||||
//TODO deal with this case adding another patch at the end...
|
||||
//its not that difficult!
|
||||
|
||||
//This can happen on degenerate cases when we have a lot of detached faces....
|
||||
if(vcount > 65000 && fcount > 65000) {
|
||||
|
@ -359,6 +363,23 @@ void ThirdStep(const string &crudefile, const string &output,
|
|||
sphere.Add(vertices[i]);
|
||||
sphere.Radius() *= 1.01;
|
||||
|
||||
TightSphere(sphere, vertices);
|
||||
|
||||
vector<Point3f> normals;
|
||||
for(unsigned int i = 0; i < patch.nf; i++) {
|
||||
unsigned short *f = patch.Face(i);
|
||||
Point3f &v0 = patch.Vert3f(f[0]);
|
||||
Point3f &v1 = patch.Vert3f(f[1]);
|
||||
Point3f &v2 = patch.Vert3f(f[2]);
|
||||
|
||||
Point3f norm = (v1 - v0) ^ (v2 - v0);
|
||||
normals.push_back(norm.Normalize());
|
||||
}
|
||||
ANCone3f cone;
|
||||
cone.AddNormals(normals, 0.99f);
|
||||
nexus[patch_idx].cone.Import(cone);
|
||||
|
||||
|
||||
#ifndef NDEBUG
|
||||
for(int i = 0; i < vertices.size(); i++) {
|
||||
assert(sphere.IsIn(vertices[i]));
|
||||
|
@ -836,6 +857,7 @@ void SaveFragment(Nexus &nexus, VChain &chain,
|
|||
nexus.sphere.Add(outpatch.vert[v]);
|
||||
}
|
||||
entry.sphere.Radius() *= 1.01;
|
||||
TightSphere(entry.sphere, outpatch.vert);
|
||||
|
||||
//remap internal borders
|
||||
for(unsigned int k = 0; k < outpatch.bord.size(); k++) {
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
History
|
||||
|
||||
$Log: not supported by cvs2svn $
|
||||
Revision 1.22 2005/02/20 00:43:24 ponchio
|
||||
Less memory x extraction. (removed frags)
|
||||
|
||||
Revision 1.21 2005/02/19 17:14:02 ponchio
|
||||
History quick by default.
|
||||
|
||||
|
@ -86,21 +89,25 @@ string getSuffix(Signature &signature) {
|
|||
return suff;
|
||||
}
|
||||
|
||||
void printInfo(Nexus &nexus, bool verbose, bool dump_history);
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
|
||||
string input;
|
||||
string output;
|
||||
string plysource;
|
||||
|
||||
bool info = false;
|
||||
bool verbose = false;
|
||||
bool dump_history = false;
|
||||
|
||||
unsigned int ram_size = 128000000;
|
||||
unsigned int chunk_size = 0;
|
||||
|
||||
bool add = false;
|
||||
bool add_strips = false;
|
||||
bool add_colors = false;
|
||||
bool add_normals = false;
|
||||
unsigned char add_normals = 0;
|
||||
bool add_textures = false;
|
||||
bool add_data = false;
|
||||
|
||||
|
@ -113,45 +120,32 @@ int main(int argc, char *argv[]) {
|
|||
|
||||
bool compress = false;
|
||||
bool uncompress = false;
|
||||
bool zsort = false;
|
||||
|
||||
float qvertex = 0;
|
||||
float qnormal = 0;
|
||||
float qcolor = 0;
|
||||
float qtexture = 0;
|
||||
bool zsort = false;
|
||||
float cone_threshold = 0;
|
||||
|
||||
int option;
|
||||
while((option = getopt(argc, argv, "ilho:a:r:zxsv:n:k:t:b:c:")) != EOF) {
|
||||
while((option = getopt(argc, argv, "ilho:a:r:zxsv:n:k:t:b:c:V:")) != EOF) {
|
||||
switch(option) {
|
||||
case 'i': info = true; break;
|
||||
case 'l': verbose = true; break;
|
||||
case 'h': dump_history = true; break;
|
||||
case 'o': output = optarg; break;
|
||||
case 'p': plysource = optarg; break;
|
||||
|
||||
case 'a': {
|
||||
if(strstr(optarg, "strips")) {
|
||||
add_strips = true;
|
||||
add = true;
|
||||
// add |= NXS_STRIP;
|
||||
// remove |= NXS_FACES;
|
||||
}
|
||||
if(strstr(optarg, "colors")) {
|
||||
add_colors = true;
|
||||
add = true;
|
||||
// add |= NXS_COLORS;
|
||||
}
|
||||
if(strstr(optarg, "normals")) {
|
||||
add_normals = true;
|
||||
add = true;
|
||||
// add |= NXS_NORMALS_SHORT;
|
||||
}
|
||||
if(strstr(optarg, "textures")) {
|
||||
add_textures = true;
|
||||
add = true;
|
||||
// add |= NXS_TEXTURES_SHORT;
|
||||
}
|
||||
if(strstr(optarg, "data")) {
|
||||
add_data = true;
|
||||
// add |= NXS_DATA32;
|
||||
}
|
||||
if(strstr(optarg, "strips")) { add_strips = true; add = true; }
|
||||
if(strstr(optarg, "colors")) { add_colors = true; add = true; }
|
||||
if(strstr(optarg, "normals")) {
|
||||
add_normals = Encodings::SHORT4; add = true; }
|
||||
if(strstr(optarg, "normalf")) {
|
||||
add_normals = Encodings::FLOAT3; add = true; }
|
||||
if(strstr(optarg, "textures")) { add_textures = true; add = true; }
|
||||
if(strstr(optarg, "data")) { add_data = true; add = true; }
|
||||
if(add == false) {
|
||||
cerr << "Invalid -a argument: " << optarg << "\n"
|
||||
<< "Valid options are: strips, colors, normals, textures, data\n";
|
||||
|
@ -159,50 +153,31 @@ int main(int argc, char *argv[]) {
|
|||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case 'r': {
|
||||
if(strstr(optarg, "strips")) {
|
||||
cerr << "Strips removing not supported!\n";
|
||||
return -1;
|
||||
remove_strips = true;
|
||||
remove = true;
|
||||
add = true;
|
||||
// add |= NXS_FACES;
|
||||
// remove |= NXS_STRIP;
|
||||
}
|
||||
if(strstr(optarg, "colors")) {
|
||||
remove_colors = true;
|
||||
remove = true;
|
||||
// remove |= NXS_COLORS;
|
||||
}
|
||||
if(strstr(optarg, "normals")) {
|
||||
remove_normals = true;
|
||||
remove = true;
|
||||
// remove |= NXS_NORMALS_SHORT;
|
||||
}
|
||||
if(strstr(optarg, "textures")) {
|
||||
remove_textures = true;
|
||||
remove = true;
|
||||
// remove |= NXS_TEXTURES_SHORT;
|
||||
}
|
||||
if(strstr(optarg, "data")) {
|
||||
remove_data = true;
|
||||
remove = true;
|
||||
// remove |= NXS_DATA32;
|
||||
}
|
||||
if(strstr(optarg, "colors")) { remove_colors = true; remove = true; }
|
||||
if(strstr(optarg, "normals")) { remove_normals = true; remove = true; }
|
||||
if(strstr(optarg, "textures")) { remove_textures = true; remove = true; }
|
||||
if(strstr(optarg, "data")) { remove_data = true; remove = true; }
|
||||
if(remove == false) {
|
||||
cerr << "Invalid -a argument: " << optarg << "\n"
|
||||
<< "Valid options are: strip, colors, normals, textures, data\n";
|
||||
<< "Valid options are: strip, colors, normals, normalf, "
|
||||
<< "textures, data\n";
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case 'p': plysource = optarg; break;
|
||||
|
||||
|
||||
case 'z': compress = true; break;
|
||||
case 'x': uncompress = true; break;
|
||||
case 's': zsort = true; break;
|
||||
|
||||
case 'V': cone_threshold = atof(optarg); break;
|
||||
case 'v': qvertex = (float)atof(optarg);
|
||||
if(qvertex == 0) {
|
||||
cerr << "Invalid value for quantization: " << optarg << endl;
|
||||
|
@ -227,6 +202,7 @@ int main(int argc, char *argv[]) {
|
|||
return -1;
|
||||
}
|
||||
break;
|
||||
|
||||
case 'b': ram_size = atoi(optarg);
|
||||
if(ram_size == 0) {
|
||||
cerr << "Invalid ram_size: " << optarg << endl;
|
||||
|
@ -244,18 +220,13 @@ int main(int argc, char *argv[]) {
|
|||
}
|
||||
}
|
||||
|
||||
if(compress && uncompress) {
|
||||
cerr << "x and z are obviously exclusive :P\n";
|
||||
return -1;
|
||||
}
|
||||
|
||||
if(optind != argc - 1) {
|
||||
cerr << "Usage: " << argv[0] << " <nexus file> [options]\n"
|
||||
<< " -i : display some info about nexus file\n"
|
||||
<< " -l : list nodes\n"
|
||||
<< " -h : list history\n"
|
||||
<< " -o <file>: output filename (default is adding 00 to nexus)\n"
|
||||
<< " -a <what>: Add [colors|normals|strips|textures|data|borders]\n"
|
||||
<< " -a <what>: Add [colors|normals|normalf|strips|textures|data|borders]\n"
|
||||
<< " -r <what>: As add...\n"
|
||||
<< " -p <ply> : Ply source for colors or textures or data\n"
|
||||
<< " -z : compress\n"
|
||||
|
@ -264,12 +235,34 @@ int main(int argc, char *argv[]) {
|
|||
<< " -v<float>: Vertex quantization (float is the 0 level amount)\n"
|
||||
<< " -n<float>: Normal quantization\n"
|
||||
<< " -c<float>: Color quantization\n"
|
||||
<< " -t<float>: Texture quantization\n\n";
|
||||
<< " -t<float>: Texture quantization\n"
|
||||
<< " -V<float>: Normal cone threshold [0, 1] (0.95 default)\n\n"
|
||||
<< " This option will not create a new nexus file\n";
|
||||
return -1;
|
||||
}
|
||||
input = argv[optind];
|
||||
|
||||
//Sanity test of options...
|
||||
|
||||
if(compress && uncompress) {
|
||||
cerr << "x and z are obviously exclusive :P\n";
|
||||
return -1;
|
||||
}
|
||||
|
||||
if(add_normals && compress) {
|
||||
cerr << "Its not possible to add normals and compress in the same step\n"
|
||||
<< "Because normals requires 2 passes to be calculated\n\n";
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool compute_cones = false;
|
||||
if(!add && !remove && !compress && !uncompress && !zsort &&
|
||||
!qvertex && !qcolor && !qnormal && !qtexture && cone_threshold != 0)
|
||||
compute_cones = true;
|
||||
|
||||
|
||||
Nexus nexus;
|
||||
|
||||
if(!nexus.Load(input, true)) {
|
||||
|
@ -301,6 +294,26 @@ int main(int argc, char *argv[]) {
|
|||
return -1;
|
||||
}
|
||||
|
||||
if(add_strips && (nexus.signature.face == Signature::STRIPS)) {
|
||||
cerr << "Nexus file already has strips\n";
|
||||
return -1;
|
||||
}
|
||||
if(add_colors && nexus.signature.vcolor) {
|
||||
cerr << "Nexus file already has colors\n";
|
||||
return -1;
|
||||
}
|
||||
if(add_normals && nexus.signature.vnorm) {
|
||||
cerr << "Nexus file already has normals\n";
|
||||
return -1;
|
||||
}
|
||||
if(add_textures && nexus.signature.vtext) {
|
||||
cerr << "Nexus file already has textures\n";
|
||||
return -1;
|
||||
}
|
||||
if(add_data && nexus.signature.vdata) {
|
||||
cerr << "Nexus file already has data\n";
|
||||
return -1;
|
||||
}
|
||||
|
||||
if(nexus.IsCompressed() && compress) {
|
||||
cerr << "File already compressed.\n";
|
||||
|
@ -314,91 +327,29 @@ int main(int argc, char *argv[]) {
|
|||
|
||||
|
||||
if(info) {
|
||||
//perform locality statistics
|
||||
double meandist = 0;
|
||||
vcg::Sphere3f last = nexus[0].sphere;
|
||||
for(unsigned int i = 1; i < nexus.size(); i++) {
|
||||
vcg::Sphere3f &sphere = nexus[i].sphere;
|
||||
double dist = vcg::Distance(last.Center(), sphere.Center());
|
||||
meandist += dist;
|
||||
last = sphere;
|
||||
}
|
||||
meandist /= nexus.size() -1;
|
||||
cout << "Nexus file: " << input << "\n"
|
||||
<< "\n\tCompressed: " << nexus.IsCompressed()
|
||||
<< "\n\tStripped: "
|
||||
<< (int)(nexus.signature.face == Signature::STRIPS)
|
||||
<< "\n\tColor : " << (int)(nexus.signature.vcolor !=0)
|
||||
<< "\n\tNormal : " << (int)((nexus.signature.vnorm) !=0)
|
||||
<< "\n\tTexture : " << (int)((nexus.signature.vtext) !=0)
|
||||
<< "\n\tData : " << (int)((nexus.signature.vdata) !=0)
|
||||
<< "\n\n\tVertices: " << nexus.totvert
|
||||
<< "\tFaces: " << nexus.totface
|
||||
<< "\tPatches: " << nexus.size()
|
||||
<< "\n\tSphere: "
|
||||
<< nexus.sphere.Center()[0] << " "
|
||||
<< nexus.sphere.Center()[1] << " "
|
||||
<< nexus.sphere.Center()[2] << " R: "
|
||||
<< nexus.sphere.Radius()
|
||||
<< "\n\tAverage distance: " << meandist
|
||||
<< "\n\tChunk size " << nexus.chunk_size << endl;
|
||||
|
||||
if(dump_history) {
|
||||
if(nexus.history.IsQuick()) {
|
||||
cout << "Quick format\n";
|
||||
for(unsigned int i = 0; i < nexus.history.n_nodes(); i++) {
|
||||
cout << "Node: " << i << " out: ";
|
||||
History::History::Node node = nexus.history.nodes[i];
|
||||
for(History::Node::iterator l = node.out_begin(); l != node.out_end(); l++) {
|
||||
cout << ".";
|
||||
History::Link &link = *l;
|
||||
for(History::Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
cout << p << " ";
|
||||
}
|
||||
}
|
||||
cout << " in: ";
|
||||
for(History::Node::iterator j = node.in_begin(); j != node.in_end(); j++) {
|
||||
cout << ".";
|
||||
History::Link &link = *j;
|
||||
for(History::Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
cout << p << " ";
|
||||
}
|
||||
}
|
||||
cout << endl;
|
||||
}
|
||||
|
||||
} else {
|
||||
cout << "Update format\n";
|
||||
for(unsigned int i = 0; i < nexus.history.updates.size(); i++) {
|
||||
History::Update &update = nexus.history.updates[i];
|
||||
cout << "Created: ";
|
||||
for(unsigned int k = 0; k < update.created.size(); k++) {
|
||||
cout << update.created[k] << " ";
|
||||
}
|
||||
cout << "\nErased: ";
|
||||
for(unsigned int k = 0; k < update.erased.size(); k++) {
|
||||
cout << update.erased[k] << " ";
|
||||
}
|
||||
cout << "\n\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(verbose) {
|
||||
for(unsigned int i = 0; i < nexus.size(); i++) {
|
||||
Entry &entry = nexus[i];
|
||||
cout << i << " -> nv: " << entry.nvert << " nf: " << entry.nface
|
||||
<< " error: " << entry.error
|
||||
<< " disk_size: " << entry.disk_size
|
||||
<< " start: " << entry.patch_start << endl;
|
||||
}
|
||||
cout << endl;
|
||||
}
|
||||
cout << "Nexus file: " << input << "\n";
|
||||
printInfo(nexus, verbose, dump_history);
|
||||
}
|
||||
|
||||
|
||||
//determine if we must proceed:
|
||||
if(!add && !remove && !compress && !uncompress && !zsort &&
|
||||
qvertex == 0 && qnormal == 0 && qcolor == 0 && qtexture == 0) {
|
||||
qvertex == 0 && qnormal == 0 && qcolor == 0 && qtexture == 0 &&
|
||||
cone_threshold == 0) {
|
||||
nexus.Close();
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(compute_cones) {//just recalculate normal cones
|
||||
cerr << "Unimplemented at the moment...\n";
|
||||
|
||||
/*vector<NCone3s> cones;
|
||||
// ComputeCones(Nexus &nexus, float cone_threshold);
|
||||
nexus.Close();
|
||||
nexus.Load(intput, false);
|
||||
for(unsigned int i = 0; i < nexus.size(); i++) {
|
||||
nexus[i].cone = cones[i];
|
||||
}*/
|
||||
nexus.Close();
|
||||
return 0;
|
||||
}
|
||||
|
@ -422,15 +373,9 @@ int main(int argc, char *argv[]) {
|
|||
grid.Set(mesh.face);
|
||||
}
|
||||
|
||||
if(add_normals && compress) {
|
||||
cerr << "Its not possible to add normals and compress in the same step\n"
|
||||
<< "Because normals requires 2 passes to be calculated\n\n";
|
||||
return -1;
|
||||
}
|
||||
|
||||
Signature signature = nexus.signature;
|
||||
if(add_strips) signature.face = Signature::STRIPS;
|
||||
if(add_normals) signature.vnorm = Encodings::SHORT4;
|
||||
if(add_normals) signature.vnorm = add_normals;
|
||||
if(add_colors) signature.vcolor = Encodings::BYTE4;
|
||||
|
||||
if(remove_normals) signature.vnorm = 0;
|
||||
|
@ -442,6 +387,7 @@ int main(int argc, char *argv[]) {
|
|||
if(!output.size()) output = input + getSuffix(signature);
|
||||
if(output == input) {
|
||||
cerr << "Output and input files are the same.\n"
|
||||
<< "Use option -o <filename>\n"
|
||||
<< "You do not want to overwrite your data. Trust me.\n";
|
||||
return -1;
|
||||
}
|
||||
|
@ -576,7 +522,7 @@ int main(int argc, char *argv[]) {
|
|||
//copying entry information;
|
||||
dst_entry.sphere = src_entry.sphere;
|
||||
dst_entry.error = src_entry.error;
|
||||
//WARNING copy also normals cone
|
||||
dst_entry.cone = src_entry.cone;
|
||||
|
||||
out.borders.ResizeBorder(p, src_border.Size());
|
||||
Border &dst_border = out.GetBorder(p);
|
||||
|
@ -623,3 +569,87 @@ int main(int argc, char *argv[]) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void printInfo(Nexus &nexus, bool verbose, bool dump_history) {
|
||||
//perform locality statistics
|
||||
double meandist = 0;
|
||||
vcg::Sphere3f last = nexus[0].sphere;
|
||||
for(unsigned int i = 1; i < nexus.size(); i++) {
|
||||
vcg::Sphere3f &sphere = nexus[i].sphere;
|
||||
double dist = vcg::Distance(last.Center(), sphere.Center());
|
||||
meandist += dist;
|
||||
last = sphere;
|
||||
}
|
||||
meandist /= nexus.size() -1;
|
||||
cout << "\n\tCompressed: " << nexus.IsCompressed()
|
||||
<< "\n\tStripped: "
|
||||
<< (int)(nexus.signature.face == Signature::STRIPS)
|
||||
<< "\n\tColor : " << (int)(nexus.signature.vcolor !=0)
|
||||
<< "\n\tNormal : " << (int)((nexus.signature.vnorm) !=0)
|
||||
<< "\n\tTexture : " << (int)((nexus.signature.vtext) !=0)
|
||||
<< "\n\tData : " << (int)((nexus.signature.vdata) !=0)
|
||||
<< "\n\n\tVertices: " << nexus.totvert
|
||||
<< "\tFaces: " << nexus.totface
|
||||
<< "\tPatches: " << nexus.size()
|
||||
<< "\n\tSphere: "
|
||||
<< nexus.sphere.Center()[0] << " "
|
||||
<< nexus.sphere.Center()[1] << " "
|
||||
<< nexus.sphere.Center()[2] << " R: "
|
||||
<< nexus.sphere.Radius()
|
||||
<< "\n\tAverage distance: " << meandist
|
||||
<< "\n\tChunk size " << nexus.chunk_size << endl;
|
||||
|
||||
if(dump_history) {
|
||||
if(nexus.history.IsQuick()) {
|
||||
cout << "Quick format\n";
|
||||
for(unsigned int i = 0; i < nexus.history.n_nodes(); i++) {
|
||||
cout << "Node: " << i << " out: ";
|
||||
History::History::Node node = nexus.history.nodes[i];
|
||||
for(History::Node::iterator l = node.out_begin();
|
||||
l != node.out_end(); l++) {
|
||||
cout << ".";
|
||||
History::Link &link = *l;
|
||||
for(History::Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
cout << p << " ";
|
||||
}
|
||||
}
|
||||
cout << " in: ";
|
||||
for(History::Node::iterator j = node.in_begin();
|
||||
j != node.in_end(); j++) {
|
||||
cout << ".";
|
||||
History::Link &link = *j;
|
||||
for(History::Link::iterator p = link.begin(); p != link.end(); p++) {
|
||||
cout << p << " ";
|
||||
}
|
||||
}
|
||||
cout << endl;
|
||||
}
|
||||
|
||||
} else {
|
||||
cout << "Update format\n";
|
||||
for(unsigned int i = 0; i < nexus.history.updates.size(); i++) {
|
||||
History::Update &update = nexus.history.updates[i];
|
||||
cout << "Created: ";
|
||||
for(unsigned int k = 0; k < update.created.size(); k++) {
|
||||
cout << update.created[k] << " ";
|
||||
}
|
||||
cout << "\nErased: ";
|
||||
for(unsigned int k = 0; k < update.erased.size(); k++) {
|
||||
cout << update.erased[k] << " ";
|
||||
}
|
||||
cout << "\n\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(verbose) {
|
||||
for(unsigned int i = 0; i < nexus.size(); i++) {
|
||||
Entry &entry = nexus[i];
|
||||
cout << i << " -> nv: " << entry.nvert << " nf: " << entry.nface
|
||||
<< " error: " << entry.error
|
||||
<< " disk_size: " << entry.disk_size
|
||||
<< " start: " << entry.patch_start << endl;
|
||||
}
|
||||
cout << endl;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue