GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: src/unrrdu/axinsert.c Lines: 24 63 38.1 %
Date: 2017-05-26 Branches: 1 34 2.9 %

Line Branch Exec Source
1
/*
2
  Teem: Tools to process and visualize scientific data and images             .
3
  Copyright (C) 2013, 2012, 2011, 2010, 2009  University of Chicago
4
  Copyright (C) 2008, 2007, 2006, 2005  Gordon Kindlmann
5
  Copyright (C) 2004, 2003, 2002, 2001, 2000, 1999, 1998  University of Utah
6
7
  This library is free software; you can redistribute it and/or
8
  modify it under the terms of the GNU Lesser General Public License
9
  (LGPL) as published by the Free Software Foundation; either
10
  version 2.1 of the License, or (at your option) any later version.
11
  The terms of redistributing and/or modifying this software also
12
  include exceptions to the LGPL that facilitate static linking.
13
14
  This library is distributed in the hope that it will be useful,
15
  but WITHOUT ANY WARRANTY; without even the implied warranty of
16
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17
  Lesser General Public License for more details.
18
19
  You should have received a copy of the GNU Lesser General Public License
20
  along with this library; if not, write to Free Software Foundation, Inc.,
21
  51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
22
*/
23
24
#include "unrrdu.h"
25
#include "privateUnrrdu.h"
26
27
#define INFO "Add a \"stub\" (length 1) axis to a nrrd"
28
static const char *_unrrdu_axinsertInfoL =
29
(INFO
30
 ". The underlying linear ordering of the samples is "
31
 "unchanged, and the information about the other axes is "
32
 "shifted upwards as needed.\n "
33
 "* Uses nrrdAxesInsert, and with \"-s\", nrrdPad_nva");
34
35
int
36
unrrdu_axinsertMain(int argc, const char **argv, const char *me,
37
                    hestParm *hparm) {
38
2
  hestOpt *opt = NULL;
39
1
  char *out, *err, *label;
40
1
  Nrrd *nin, *nout;
41
1
  int pret, kind, center;
42
1
  unsigned int axis, size, opi, centOptIdx;
43
1
  double mm[2];
44
  airArray *mop;
45
1
  NrrdBoundarySpec *bspec;
46
47
1
  hparm->elideSingleOtherDefault = AIR_FALSE;
48
1
  OPT_ADD_AXIS(axis, "dimension (axis index) at which to insert the new axis");
49
1
  hestOptAdd(&opt, "l,label", "label", airTypeString, 1, 1, &label, "",
50
             "label to associate with new axis");
51
1
  opi = hestOptAdd(&opt, "k,kind", "kind", airTypeEnum, 1, 1, &kind, "stub",
52
1
                   "axis kind to associate with new axis", NULL, nrrdKind);
53
1
  hestOptAdd(&opt, "mm,minmax", "min max", airTypeDouble, 2, 2, mm, "nan nan",
54
             "min and max values along new axis");
55
  centOptIdx =
56
1
    hestOptAdd(&opt, "c,center", "center", airTypeEnum, 1, 1, &center, "cell",
57
               "centering of inserted axis: \"cell\" or \"node\"",
58
1
               NULL, nrrdCenter);
59
1
  hestOptAdd(&opt, "s,size", "size", airTypeUInt, 1, 1, &size, "1",
60
             "after inserting stub axis, also pad out to some length, "
61
             "according to the \"-b\" option");
62
1
  hestOptAdd(&opt, "b,boundary", "behavior", airTypeOther, 1, 1, &bspec,
63
             "bleed",
64
             "How to handle samples beyond the input bounds:\n "
65
             "\b\bo \"pad:<val>\": use specified value\n "
66
             "\b\bo \"bleed\": extend border values outward\n "
67
             "\b\bo \"mirror\": repeated reflections\n "
68
             "\b\bo \"wrap\": wrap-around to other side",
69
1
             NULL, NULL, nrrdHestBoundarySpec);
70
1
  OPT_ADD_NIN(nin, "input nrrd");
71
1
  OPT_ADD_NOUT(out, "output nrrd");
72
73
1
  mop = airMopNew();
74
1
  airMopAdd(mop, opt, (airMopper)hestOptFree, airMopAlways);
75
76
2
  USAGE(_unrrdu_axinsertInfoL);
77
  PARSE();
78
  airMopAdd(mop, opt, (airMopper)hestParseFree, airMopAlways);
79
80
  nout = nrrdNew();
81
  airMopAdd(mop, nout, (airMopper)nrrdNuke, airMopAlways);
82
83
  if (nrrdAxesInsert(nout, nin, axis)) {
84
    airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
85
    fprintf(stderr, "%s: error inserting axis:\n%s", me, err);
86
    airMopError(mop);
87
    return 1;
88
  }
89
  if (hestSourceUser == opt[centOptIdx].source) {
90
    nout->axis[axis].center = center;
91
  }
92
  if (1 < size) {
93
    /* we also do padding here */
94
    ptrdiff_t min[NRRD_DIM_MAX], max[NRRD_DIM_MAX];
95
    unsigned int ai;
96
    Nrrd *npad;
97
    for (ai=0; ai<nout->dim; ai++) {
98
      min[ai] = 0;
99
      max[ai] = nout->axis[ai].size - 1;
100
    }
101
    max[axis] = size-1;
102
    npad = nrrdNew();
103
    airMopAdd(mop, npad, (airMopper)nrrdNuke, airMopAlways);
104
    if (nrrdPad_nva(npad, nout, min, max,
105
                    bspec->boundary, bspec->padValue)) {
106
      airMopAdd(mop, err = biffGetDone(NRRD), airFree, airMopAlways);
107
      fprintf(stderr, "%s: error padding:\n%s", me, err);
108
      airMopError(mop);
109
      return 1;
110
    }
111
    /* sneaky, but ok; nothing changes in the mops */
112
    nout = npad;
113
    /* only set output kind if explicitly requested
114
       (since the default is not appropriate) */
115
    if (hestSourceUser == opt[opi].source) {
116
      nout->axis[axis].kind = kind;
117
    }
118
  } else {
119
    /* no request to pad; setting the default "stub" kind is sensible */
120
    nout->axis[axis].kind = kind;
121
  }
122
  if (strlen(label)) {
123
    nout->axis[axis].label = (char *)airFree(nout->axis[axis].label);
124
    nout->axis[axis].label = airStrdup(label);
125
  }
126
  if (AIR_EXISTS(mm[0])) {
127
    nout->axis[axis].min = mm[0];
128
  }
129
  if (AIR_EXISTS(mm[1])) {
130
    nout->axis[axis].max = mm[1];
131
  }
132
133
  SAVE(out, nout, NULL);
134
135
  airMopOkay(mop);
136
  return 0;
137
1
}
138
139
UNRRDU_CMD(axinsert, INFO);