Implementation code for our paper "Integer-Only Cross Field Computation" (SIGGRAPH 2018). It computes a smooth cross field on a triangle mesh using an efficient grid search algorithm for finding the cone singularities. Cross fields are a type of a direction field in which four unit vectors are defined at each point (unlike a regular vector field which has only one vector at each point). They are used in many applications in geometry processing, from quad remeshing to non-photorealistic rendering. See this for a really nice introduction to the subject.
If you use this code, please cite our paper:
xxxxxxxxxx
@article{farchi2018integer,
title={Integer-Only Cross Field Computation},
author={Nahum Farchi and Ben-Chen, Mirela},
journal={ACM Transactions on Graphics (TOG)},
volume={37},
number={4},
pages={},
year={2018},
publisher={ACM}
}
We also provide (windows) binaries for the full mesh quadrangulation pipeline, for vector field visualization, and an MIQ implementation (using libQEx and libigl).
First, compile the CUDA kernel:
Alternatively, a precompiled .ptx is included. To use it, just run setup.m.
Just run setup.m and then try one of the examples.
To load a mesh and compute a cross field on it, just run:
xxxxxxxxxx
m = Mesh('./data/bunny.off');
[alpha, beta, x, theta, CF, stats] = IOQ(m);
figure; m.draw(CF, alpha)
IOQ has a couple of options that you can play around with, the most important of which is whether or not to use the GPU, and whether to use the resistance distance approximation. For best results, use both (this is the default).
See the examples folder for more.
We also provide binaries for libQEx and and wrappers for a couple libigl methods. You can use these to quadrangulate a tri mesh:
xxxxxxxxxx
tri_to_quad('.\data\bunny.off', 'GradSize', 30, 'OutFolder', 'results\quads\', 'Method', 'IOQ');
run the MIQ [Bommes et al. 2009] cross field computation:
xxxxxxxxxx
F0 = 1; V0 = [1, 0, 0]; DEGREE = 4;
fp = '.\data\bunny.off';
m = Mesh(fp);
[theta, p, alpha, CF, E, elapsed] = MIQ(fp, F0, V0, DEGREE);
and visualize the cross field:
xxxxxxxxxx
R = CF(1:m.nf, :); % only need the first vector from each cross
vis_vector_field(m.path, R, alpha);
The main limitation is that directional constraints are currently not supported. Another limitation is that for best performance you need a GPU with a lot of RAM.
Also, note that the code was tested on Windows 10 only, though most of it should probably work on other platforms as well (excluding the binaries of course).