function [c,s] = wavedec2(x,n,IN3,IN4)
%MATLAB Code Generation Library Function

%   Limitations:
%   * With three inputs, i.e. when suppling a "wname", the third input must
%     be constant.
%   * Variable sizing is required.

%   Copyright 1995-2022 The MathWorks, Inc.
%#codegen

% Check arguments.
narginchk(3,4);
if nargin == 3
    coder.internal.prefer_const(IN3);
    [Lo_D,Hi_D] = wfiltersConst(char(IN3),'d');
else
    Lo_D = IN3;
    Hi_D = IN4;
end
validateattributes(x,{'numeric','logical'},{'3d'},'wavedec2','X');

xdouble = double(x);
% GPU enabled condition is added here
if coder.gpu.internal.isGpuEnabled
    % If 'level' is not constant, added compile time warning message here.
    if ~coder.internal.isConst(n)
        coder.internal.compileWarning('gpucoder:common:Wavedec2LevelIsNotConstant');
    end
    % GPU specific implementation for 'wavedec2' is called here.
    [c, s] = wavelet.internal.gpu.wavedec2(xdouble,n,Lo_D,Hi_D);
    return
end

% Initialization.
coder.varsize('c');
coder.varsize('xv');
nd = coder.internal.ndims(x);
s = zeros(n + 2,nd);
c = zeros(1,0);
if isempty(xdouble)
    return
end
xv = xdouble;
for j = 1:nd
    s(n + 2,j) = size(xv,j);
end
for k = 1:n
    [xv,h,v,d] = dwt2(xv,Lo_D,Hi_D); % decomposition
    c = [h(:).',v(:).',d(:).',c]; %#ok<AGROW> % store details
    for j = 1:nd
        s(n - k + 2,j) = size(xv,j); % store size
    end
end

% Last approximation.
c = [xv(:).',c];
for j = 1:nd
    s(1,j) = size(xv,j); % store size
end
