commit aff12ec445b19c0effbcaed0e5b462b72d691602
parent d1b2c2a80248409f0fc12b05981191e857bab4ad
Author: Vincent Forest <vincent.forest@meso-star.com>
Date: Wed, 26 Jul 2017 15:13:30 +0200
Write the primary and receiver data to the output VTKs of solvtk
Diffstat:
| M | src/Makefile | | | 14 | ++++---------- |
| M | src/solpp.h | | | 137 | +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++-- |
| M | src/solvtk.c | | | 191 | ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++------------------- |
3 files changed, 284 insertions(+), 58 deletions(-)
diff --git a/src/Makefile b/src/Makefile
@@ -19,7 +19,7 @@ NPATHS=1000
SUN_DIRS=270,45
RCV_FILE=themis-rcv.yaml
-CFLAGS = -O2 -std=c99 -pedantic -Wall
+CFLAGS = -g -std=c99 -pedantic -Wall
SCRIPT = themis.c solsplit.c solpp.c solvtk.c
PROG = $(SCRIPT:%.c=%)
PATH := $(PATH):$(STAR_ENGINE)/bin:.
@@ -31,17 +31,11 @@ all: $(PROG)
input: $(PROG)
@./themis
-.PHONY: output
-output: receiver
- @themis | solstice -q -n$(NEXPERIMENTS) -D$(SUN_DIRS) -R $(RCV_FILE)
-
-.PHONY: obj
-obj: $(PROG)
- themis | solstice -D$(SUN_DIRS) -qg format=obj:split=geometry | solsplit
-
.PHONY: run
run: $(PROG) receiver
- themis | solstice -q -n$(NEXPERIMENTS) -D$(SUN_DIRS) -R $(RCV_FILE) | solpp
+ themis | solstice -D$(SUN_DIRS) -q -n$(NEXPERIMENTS) -R $(RCV_FILE) -fo simul
+ themis | solstice -D$(SUN_DIRS) -qg format=obj:split=none -fo geom
+ solvtk geom simul
.PHONY: clean
clean:
diff --git a/src/solpp.h b/src/solpp.h
@@ -30,6 +30,10 @@ struct mc {
double SE; /* Standard Error */
};
+#define DARRAY_NAME mc
+#define DARRAY_DATA struct mc
+#include <rsys/dynamic_array.h>
+
static INLINE char*
read_line(char** b, FILE* stream)
{
@@ -54,6 +58,7 @@ struct rcv {
struct mc reflectivity_loss[2];
struct mc absorptivity_loss[2];
struct mc efficiency[2];
+ struct darray_mc map[2];
struct str name;
size_t id;
double area;
@@ -64,12 +69,16 @@ rcv_init(struct mem_allocator* allocator, struct rcv* rcv)
{
memset(rcv, 0, sizeof(struct rcv));
str_init(allocator, &rcv->name);
+ darray_mc_init(allocator, &rcv->map[0]);
+ darray_mc_init(allocator, &rcv->map[1]);
}
static INLINE void
rcv_release(struct rcv* rcv)
{
str_release(&rcv->name);
+ darray_mc_release(&rcv->map[0]);
+ darray_mc_release(&rcv->map[1]);
}
static INLINE res_T
@@ -83,6 +92,7 @@ rcv_copy(struct rcv* dst, const struct rcv* src)
dst->reflectivity_loss[i] = src->reflectivity_loss[i];
dst->absorptivity_loss[i] = src->absorptivity_loss[i];
dst->efficiency[i] = src->efficiency[i];
+ CHECK(darray_mc_copy(&dst->map[i], &src->map[i]), RES_OK);
}
dst->area = src->area;
CHECK(str_copy(&dst->name, &src->name), RES_OK);
@@ -100,6 +110,7 @@ rcv_copy_and_release(struct rcv* dst, struct rcv* src)
dst->reflectivity_loss[i] = src->reflectivity_loss[i];
dst->absorptivity_loss[i] = src->absorptivity_loss[i];
dst->efficiency[i] = src->efficiency[i];
+ CHECK(darray_mc_copy_and_release(&dst->map[i], &src->map[i]), RES_OK);
}
dst->area = src->area;
CHECK(str_copy_and_release(&dst->name, &src->name), RES_OK);
@@ -257,6 +268,79 @@ simul_copy_and_release(struct simul* dst, struct simul* src)
#define DARRAY_FUNCTOR_COPY_AND_RELEASE simul_copy_and_release
#include <rsys/dynamic_array.h>
+static void
+read_receiver_map_side_data(struct rcv* rcv, const size_t n, FILE* input)
+{
+ char* buf = NULL;
+ char* line = NULL;
+ size_t i;
+ enum side side;
+
+ NCHECK(line = read_line(&buf, input), NULL);
+ if(!strncmp(line+8, "Front_faces", 5)) side = FRONT;
+ else if(!strncmp(line+8, "Back_faces",4)) side = BACK;
+ else FATAL("Unexpected side name\n");
+
+ NCHECK(read_line(&buf, input), NULL); /* LUT */
+
+ CHECK(darray_mc_resize(&rcv->map[side], n), RES_OK);
+ FOR_EACH(i, 0, n) {
+ struct mc* mc = darray_mc_data_get(&rcv->map[side])+i;
+ NCHECK(line = read_line(&buf, input), NULL);
+ CHECK(sscanf(line, "%lf %lf", &mc->E, &mc->SE), 2);
+ }
+
+ sa_release(buf);
+}
+
+static void
+read_receiver_map(struct simul* simul, FILE* input)
+{
+ struct rcv* rcv;
+ char* buf = NULL;
+ char* line = NULL;
+ size_t i, n;
+ long fp;
+
+ NCHECK(line = read_line(&buf, input), NULL);
+ FOR_EACH(i, 0, darray_rcv_size_get(&simul->rcvs)) {
+ rcv = darray_rcv_data_get(&simul->rcvs)+i;
+ if(!strcmp(str_cget(&rcv->name), line)) break;
+ rcv = NULL;
+ }
+ NCHECK(rcv, NULL);
+
+ /* Skip header */
+ NCHECK(read_line(&buf, input), NULL);
+ NCHECK(read_line(&buf, input), NULL);
+
+ /* Skip vertices */
+ NCHECK(line = read_line(&buf, input), NULL);
+ CHECK(sscanf(line, "POINTS %zu float", &n), 1);
+ FOR_EACH(i, 0, n) NCHECK(read_line(&buf, input), NULL);
+
+ /* Skip polygons */
+ NCHECK(line = read_line(&buf, input), NULL);
+ CHECK(sscanf(line, "POLYGONS %zu %*u", &n), 1);
+ FOR_EACH(i, 0, n) NCHECK(read_line(&buf, input), NULL);
+
+ /* Read the map data of one side */
+ NCHECK(line = read_line(&buf, input), NULL);
+ CHECK(sscanf(line, "CELL_DATA %zu", &n), 1);
+
+ read_receiver_map_side_data(rcv, n, input);
+ fp = ftell(input);
+
+ /* Read the optionnal map data of the other side */
+ line = read_line(&buf, input);
+ fseek(input, fp, SEEK_SET);
+ if(line && !strncmp(line, "SCALAR", 6)) {
+ read_receiver_map_side_data(rcv, n, input);
+ }
+
+ sa_release(buf);
+}
+
static INLINE void
read_simulation(struct simul* simul, FILE* input)
{
@@ -353,6 +437,20 @@ read_simulation(struct simul* simul, FILE* input)
GET(BACK, absorptivity_loss)), 18);
#undef GET
}
+
+ /* Read receiver maps */
+ for(;;) {
+ const long fp = ftell(input);
+ line = read_line(&buf, input);
+
+ if(line && !strncmp(line, "# vtk", 5)) {
+ read_receiver_map(simul, input);
+ } else {
+ fseek(input, fp, SEEK_SET);
+ break;
+ }
+ }
+
sa_release(buf);
}
@@ -360,24 +458,59 @@ static INLINE const struct prim*
find_primary(const struct simul* simul, const char* name)
{
size_t i;
- for(i=0; i<darray_prim_size_get(&simul->prims); ++i) {
+ FOR_EACH(i, 0, darray_prim_size_get(&simul->prims)) {
const struct prim* prim = darray_prim_cdata_get(&simul->prims)+i;
if(!strcmp(str_cget(&prim->name), name)) return prim;
}
return NULL;
}
+static INLINE const struct prim*
+find_primary_by_id(const struct simul* simul, const size_t id)
+{
+ size_t i;
+ FOR_EACH(i, 0, darray_prim_size_get(&simul->prims)) {
+ const struct prim* prim = darray_prim_cdata_get(&simul->prims)+i;
+ if(prim->id == id) return prim;
+ }
+ return NULL;
+}
+
static INLINE const struct rcv*
find_receiver(const struct simul* simul, const char* name)
{
size_t i;
- for(i=0; i<darray_rcv_size_get(&simul->rcvs); ++i) {
+ FOR_EACH(i, 0, darray_rcv_size_get(&simul->rcvs)) {
const struct rcv* rcv = darray_rcv_cdata_get(&simul->rcvs)+i;
if(!strcmp(str_cget(&rcv->name), name)) return rcv;
}
return NULL;
}
+static INLINE const struct rcv*
+find_receiver_by_id(const struct simul* simul, const size_t id)
+{
+ size_t i;
+ FOR_EACH(i, 0, darray_rcv_size_get(&simul->rcvs)) {
+ const struct rcv* rcv = darray_rcv_cdata_get(&simul->rcvs)+i;
+ if(rcv->id == id) return rcv;
+ }
+ return NULL;
+}
+
+static INLINE const struct rcvXprim*
+find_rcvXprim
+ (const struct simul* simul, const size_t rcv_id, const size_t prim_id)
+{
+ size_t i;
+ FOR_EACH(i, 0, darray_rcvXprim_size_get(&simul->rcvXprims)) {
+ const struct rcvXprim* rcvXprim;
+ rcvXprim = darray_rcvXprim_cdata_get(&simul->rcvXprims)+i;
+ if(rcvXprim->rcv_id == rcv_id && rcvXprim->prim_id == prim_id)
+ return rcvXprim;
+ }
+ return NULL;
+}
#endif /* SOLPP_H */
diff --git a/src/solvtk.c b/src/solvtk.c
@@ -80,6 +80,119 @@ mesh_write_obj(FILE* output, struct mesh* msh)
}
}
+static void
+mesh_write_prim_data_vtk
+ (FILE* output, const struct mesh* msh, const struct simul* simul)
+{
+ const struct prim* prim;
+ const struct rcvXprim* rcvXprim;
+ size_t ircv;
+ size_t iprim;
+ size_t icell;
+ size_t n;
+
+ n = sa_size(msh->ids) / 3;
+ fprintf(output, "CELL_DATA %zu\n", n);
+
+ fprintf(output, "FIELD PrimaryData %zu\n",
+ 2 + darray_rcv_size_get(&simul->rcvs)*8);
+ fprintf(output, "cos_factor 2 %zu float\n", n);
+ FOR_EACH(iprim, 0, sa_size(msh->entities)) {
+ NCHECK(prim = find_primary_by_id(simul, msh->entities[iprim]), NULL);
+ FOR_EACH(icell, 0, msh->ncells[iprim]) {
+ fprintf(output, "%g %g\n", prim->cos_factor.E, prim->cos_factor.SE);
+ }
+ }
+
+ fprintf(output, "shadow_loss 2 %zu float\n", n);
+ FOR_EACH(iprim, 0, sa_size(msh->entities)) {
+ NCHECK(prim = find_primary_by_id(simul, msh->entities[iprim]), NULL);
+ FOR_EACH(icell, 0, msh->ncells[iprim]) {
+ fprintf(output, "%g %g\n", prim->shadow_loss.E, prim->shadow_loss.SE);
+ }
+ }
+
+ #define WRITE(Side, Name) { \
+ fprintf(output, "%s_"STR(Side)"_"STR(Name)" 2 %zu float\n", \
+ str_cget(&rcv->name), n); \
+ FOR_EACH(iprim, 0, sa_size(msh->entities)) { \
+ rcvXprim = find_rcvXprim(simul, rcv->id, msh->entities[iprim]); \
+ NCHECK(rcvXprim, NULL); \
+ FOR_EACH(icell, 0, msh->ncells[iprim]) { \
+ fprintf(output, "%g %g\n", \
+ rcvXprim->Name[Side].E, \
+ rcvXprim->Name[Side].SE); \
+ } \
+ } \
+ } (void)0
+ FOR_EACH(ircv, 0, darray_rcv_size_get(&simul->rcvs)) {
+ const struct rcv* rcv = darray_rcv_cdata_get(&simul->rcvs)+ircv;
+ WRITE(FRONT, absorbed_irradiance);
+ WRITE(FRONT, irradiance);
+ WRITE(FRONT, reflectivity_loss);
+ WRITE(FRONT, absorptivity_loss);
+ WRITE(BACK, absorbed_irradiance);
+ WRITE(BACK, irradiance);
+ WRITE(BACK, reflectivity_loss);
+ WRITE(BACK, absorptivity_loss);
+ }
+ #undef WRITE
+}
+
+static void
+mesh_write_rcv_data_vtk
+ (FILE* output, const struct mesh* msh, const struct simul* simul)
+{
+ const struct rcv* rcv;
+ size_t ircv;
+ size_t icell;
+ size_t n;
+
+ n = sa_size(msh->ids)/3;
+ fprintf(output, "CELL_DATA %zu\n", n);
+
+ fprintf(output, "FIELD PrimaryData 12\n");
+
+ #define WRITE(Side, Name) { \
+ fprintf(output, STR(Side)"_"STR(Name)" 2 %zu float\n", n); \
+ FOR_EACH(ircv, 0, sa_size(msh->entities)) { \
+ NCHECK(rcv = find_receiver_by_id(simul, msh->entities[ircv]), NULL); \
+ FOR_EACH(icell, 0, msh->ncells[ircv]) { \
+ fprintf(output, "%g %g\n", rcv->Name[Side].E, rcv->Name[Side].SE); \
+ } \
+ } \
+ } (void)0
+ WRITE(FRONT, absorbed_irradiance);
+ WRITE(FRONT, irradiance);
+ WRITE(FRONT, reflectivity_loss);
+ WRITE(FRONT, absorptivity_loss);
+ WRITE(FRONT, efficiency);
+ WRITE(BACK, absorbed_irradiance);
+ WRITE(BACK, irradiance);
+ WRITE(BACK, reflectivity_loss);
+ WRITE(BACK, absorptivity_loss);
+ WRITE(BACK, efficiency);
+ #undef WRITE
+
+ #define WRITE_MAP(Side) { \
+ fprintf(output, STR(Side)"_map 2 %zu float\n", n); \
+ FOR_EACH(ircv, 0, sa_size(msh->entities)) { \
+ NCHECK(rcv = find_receiver_by_id(simul, msh->entities[ircv]), NULL); \
+ if(!darray_mc_size_get(&rcv->map[Side])) { \
+ FOR_EACH(icell, 0, msh->ncells[ircv]) fprintf(output, "-1 -1\n"); \
+ } else { \
+ FOR_EACH(icell, 0, msh->ncells[ircv]) { \
+ const struct mc* mc = darray_mc_cdata_get(&rcv->map[Side])+icell; \
+ fprintf(output, "%g %g\n", mc->E, mc->SE); \
+ } \
+ } \
+ } \
+ } (void)0
+ WRITE_MAP(FRONT);
+ WRITE_MAP(BACK);
+ #undef WRITE_MAP
+}
+
int
main(int argc, char** argv)
{
@@ -99,7 +212,8 @@ main(int argc, char** argv)
char* line = NULL;
char* buf = NULL;
char* str = NULL;
- size_t ntris = 0, nverts = 0;
+ size_t ntris_grp = 0, nverts_grp = 0;
+ size_t nverts_obj = 0, offset_obj = 0;
float azim, elev;
int err = 0;
@@ -126,12 +240,23 @@ main(int argc, char** argv)
CHECK(sscanf(line+19, "%f %f (%*f %*f %*f)", &azim, &elev), 2);
} else if(!strncmp(line, "g ", 2)) {
CHECK(str_set(&name, line+2), RES_OK);
+ if(prim) {
+ sa_push(msh_prim.ncells, ntris_grp);
+ msh_prim.voffset += nverts_grp;
+ }
+ if(rcv) {
+ sa_push(msh_rcv.ncells, ntris_grp);
+ msh_rcv.voffset += nverts_grp;
+ }
+ if(!prim && !rcv) msh_misc.voffset += nverts_grp;
prim = find_primary(&simul, line+2);
rcv = find_receiver(&simul, line+2);
if(prim) sa_push(msh_prim.entities, prim->id);
if(rcv) sa_push(msh_rcv.entities, rcv->id);
- ntris = 0;
- nverts = 0;
+ ntris_grp = 0;
+ nverts_grp = 0;
+ offset_obj = nverts_obj;
+
} else if(!strncmp(line, "v ", 2)) {
double pos[3];
CHECK(sscanf(line+2, "%lf %lf %lf", pos+0, pos+1, pos+2), 3);
@@ -150,75 +275,49 @@ main(int argc, char** argv)
sa_push(msh_misc.coords, pos[1]);
sa_push(msh_misc.coords, pos[2]);
}
- ++nverts;
+ ++nverts_grp;
+ ++nverts_obj;
} else if(!strncmp(line, "f ", 2)) {
size_t tri[3];
CHECK(sscanf(line+2, "%zu %zu %zu", tri+0, tri+1, tri+2), 3);
if(prim) {
- sa_push(msh_prim.ids, tri[0] - 1 + msh_prim.voffset);
- sa_push(msh_prim.ids, tri[1] - 1 + msh_prim.voffset);
- sa_push(msh_prim.ids, tri[2] - 1 + msh_prim.voffset);
+ sa_push(msh_prim.ids, tri[0] - 1 + msh_prim.voffset - offset_obj);
+ sa_push(msh_prim.ids, tri[1] - 1 + msh_prim.voffset - offset_obj);
+ sa_push(msh_prim.ids, tri[2] - 1 + msh_prim.voffset - offset_obj);
}
if(rcv) {
- sa_push(msh_rcv.ids, tri[0] - 1 + msh_rcv.voffset);
- sa_push(msh_rcv.ids, tri[1] - 1 + msh_rcv.voffset);
- sa_push(msh_rcv.ids, tri[2] - 1 + msh_rcv.voffset);
+ sa_push(msh_rcv.ids, tri[0] - 1 + msh_rcv.voffset - offset_obj);
+ sa_push(msh_rcv.ids, tri[1] - 1 + msh_rcv.voffset - offset_obj);
+ sa_push(msh_rcv.ids, tri[2] - 1 + msh_rcv.voffset - offset_obj);
}
if(!prim && !rcv) {
- sa_push(msh_misc.ids, tri[0] - 1 + msh_misc.voffset);
- sa_push(msh_misc.ids, tri[1] - 1 + msh_misc.voffset);
- sa_push(msh_misc.ids, tri[2] - 1 + msh_misc.voffset);
+ sa_push(msh_misc.ids, tri[0] - 1 + msh_misc.voffset - offset_obj);
+ sa_push(msh_misc.ids, tri[1] - 1 + msh_misc.voffset - offset_obj);
+ sa_push(msh_misc.ids, tri[2] - 1 + msh_misc.voffset - offset_obj);
}
- ++ntris;
+ ++ntris_grp;
} else if(!strcmp(line, "---")) {
- if(prim) {
- sa_push(msh_prim.ncells, ntris);
- msh_prim.voffset += nverts;
- }
- if(rcv) {
- sa_push(msh_rcv.ncells, ntris);
- msh_rcv.voffset += nverts;
- }
- if(!prim && !rcv) {
- msh_misc.voffset += nverts;
- }
- prim = NULL;
- rcv = NULL;
+ nverts_obj = 0;
}
}
+ if(prim) sa_push(msh_prim.ncells, ntris_grp);
+ if(rcv) sa_push(msh_rcv.ncells, ntris_grp);
fclose(input);
NCHECK(output = fopen("primaries.vtk", "w"), NULL);
mesh_write_vtk(output, &msh_prim);
+ mesh_write_prim_data_vtk(output, &msh_prim, &simul);
fclose(output);
NCHECK(output = fopen("receivers.vtk", "w"), NULL);
mesh_write_vtk(output, &msh_rcv);
+ mesh_write_rcv_data_vtk(output, &msh_rcv, &simul);
fclose(output);
NCHECK(output = fopen("miscellaneous.obj", "w"), NULL);
mesh_write_obj(output, &msh_misc);
fclose(output);
-#if 0
- fprintf(output, "CELL_DATA %zu\n", n);
- fprintf(output, "FIELD PrimaryData 2\n");
- fprintf(output, "cos_factor 2 %zu float\n", n);
- FOR_EACH(i, 0, sa_size(prim_ids)) {
- FOR_EACH(j, 0, ncells[i]) {
- fprintf(output, "%g %g\n",
- prims[prim_ids[i]].cos_factor.E,
- prims[prim_ids[i]].cos_factor.SE);
- }}
- fprintf(output, "shadow_loss 2 %zu float\n", n);
- FOR_EACH(i, 0, sa_size(prim_ids)) {
- FOR_EACH(j, 0, ncells[i]) {
- fprintf(output, "%g %g\n",
- prims[prim_ids[i]].shadow_loss.E,
- prims[prim_ids[i]].shadow_loss.SE);
- }}
-#endif
-
exit:
mesh_release(&msh_prim);
mesh_release(&msh_rcv);