1########################################################################
2##
3## Copyright (C) 1994-2021 The Octave Project Developers
4##
5## See the file COPYRIGHT.md in the top-level directory of this
6## distribution or <https://octave.org/copyright/>.
7##
8## This file is part of Octave.
9##
10## Octave is free software: you can redistribute it and/or modify it
11## under the terms of the GNU General Public License as published by
12## the Free Software Foundation, either version 3 of the License, or
13## (at your option) any later version.
14##
15## Octave is distributed in the hope that it will be useful, but
16## WITHOUT ANY WARRANTY; without even the implied warranty of
17## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18## GNU General Public License for more details.
19##
20## You should have received a copy of the GNU General Public License
21## along with Octave; see the file COPYING.  If not, see
22## <https://www.gnu.org/licenses/>.
23##
24########################################################################
25
26## private function for the ind2XXX functions which have a lot of code in common
27
28function [x, map] = ind2x (caller, x, map)
29
30  ## Check if X is an indexed image.
31  ## An indexed image is defined has having only 2D, and that's how Matlab
32  ## behaves.  But we want to support ND images, so we will allow up to 4D
33  ## and check that the 3rd dimension is a singleton.
34  if (all (ndims (x) != [2 4]) || size (x, 3) != 1
35      || iscomplex (x) || issparse (x)
36      || ! (isfloat (x) && all (x(:) == fix (x(:)))
37            || (isinteger (x) && intmin (x) == 0)))
38    error ("%s: X must be an indexed image", caller);
39  endif
40
41  ## Check if map is a valid colormap.
42  if (! iscolormap (map))
43    error ("%s: MAP must be a valid colormap", caller);
44  endif
45
46  ## Any color indices below the lower bound of the color map are modified
47  ## to point to the first color in the map (see bug #41851).
48  if (isfloat (x))
49    invalid_idx = x < 1;
50    if (any (invalid_idx(:)))
51      warning (["Octave:" caller ":invalid-idx-img"],
52               [caller ": indexed image contains colors outside of colormap"]);
53      x(invalid_idx) = 1;
54    endif
55  endif
56
57  ## Switch to using 1-based indexing.
58  ## It is possible that an integer storage class may not have enough room
59  ## to make the switch, in which case we convert the data to single.
60  maxidx = max (x(:));
61  if (isinteger (x))
62    if (maxidx == intmax (x))
63      x = single (x);
64    endif
65    x      += 1;
66    maxidx += 1;
67  endif
68
69  ## When there are more colors in the image, than there are in the map,
70  ## pad the colormap with the last color in the map for Matlab compatibility.
71  num_colors = rows (map);
72  if (num_colors < maxidx)
73    warning (["Octave:" caller ":invalid-idx-img"],
74             [caller ": indexed image contains colors outside of colormap"]);
75    pad = repmat (map(end,:), maxidx - num_colors, 1);
76    map(end+1:maxidx, :) = pad;
77  endif
78
79endfunction
80