%% setParampm.m
% date: 18/12/2023
% version: 1.0.5
%%
function [paramStruct] = setParampm(paramStruct,paramName,paramValue)

flag_warning = 0;
%Testing if the input struct is motorProps or settingsMagnetostatics
if isfield(paramStruct,'stator')
    %Attention field are used in parameters that could have inconsistencies
    attentionFields = {'Winding method','Winding layers','End winding axial overhang','End winding inductance','Phase resistance'};
    % Flag warning is set to one, once a parameter is correctly assigned
    % the flag warning is set to zero. When a problem occured other
    % warnings and errors are used. 
    flag_warning = 1;
    % format paramName and delete extra spaces
    paramName = strtrim(paramName);
    paramName = lower(paramName);
    paramName(1) = upper(paramName(1));
    %Adjusting names to access imported struct from json file
    paramNamesplit = split(paramName);
    word = paramNamesplit{1};
    new_paramName = strcat(upper(word(1)),lower(word(2:end)));
    for i=2:length(paramNamesplit)
        word = paramNamesplit{i};
        new_paramName = strcat(new_paramName,upper(word(1)),lower(word(2:end)));
    end
    % Read .json file to get key and values
    jsonfileName = 'motorProps.json';
    path = getpmpath('bin/assets/scripts/');
    str = fileread([path jsonfileName]);
    data = jsondecode(str);
    % Verify if the param exists 
    if isfield(data,new_paramName)
        key = data.(new_paramName);
        keySplit = split(key,'.');
        % Verify if the parameter depends on the used topology
        if any(strcmp(attentionFields,paramName))
            %2. if motorProps.windings.layoutmethod = 'From file' and motorProps.windings.numberLayers > 2, then motorProps.windings.Lsew = 'Auto' , motorProps.windings.Rs = 'Auto' and motorProps.windings.Hsew = 'Auto'  are not allowed
            if strcmp(paramName,'Winding method')
                if  strcmp(paramStruct.windings.layoutmethod,'From file')&&((~strcmp(paramStruct.windings.numberLayers,'Double layer')&&(~strcmp(paramStruct.windings.numberLayers,'Single layer'))))
                    if strcmp(paramStruct.windings.Lsew,'Auto')
                        flag_warning = 2;
                    end
                    if strcmp(paramStruct.windings.Hsew,'Auto')
                        flag_warning = 2;
                    end
                    if strcmp(paramStruct.windings.Rs,'Auto')
                        flag_warning = 2;
                    end
                else
                    flag_warning = 0;
                    if length(keySplit) > 1
                        paramStruct.(keySplit{1}).(keySplit{2}) = paramValue;
                    else
                        paramStruct.(key) = paramValue;
                    end
                end
            end
            if (strcmp(paramName,'End winding axial overhang')) || (strcmp(paramName,'End winding inductance')) || (strcmp(paramName,'Phase resistance'))
                if ((~strcmp(paramStruct.windings.numberLayers,'Double layer')&&(~strcmp(paramStruct.windings.numberLayers,'Single layer')))) && (strcmp(paramValue,'Auto'))
                    flag_warning = 2;
                else
                    flag_warning = 0;
                    if length(keySplit) > 1
                        paramStruct.(keySplit{1}).(keySplit{2}) = paramValue;
                    else
                        paramStruct.(key) = paramValue;
                    end
                end
            end
            % 4. If motorProps.windings.numberLayers > 2 (number of winding layers is more than 2),  motorProps.windings.layoutmethod = 'From file' only
            if strcmp(paramName,'Winding layers')
                if ((~strcmp(paramStruct.windings.numberLayers,'Double layer')&&(~strcmp(paramStruct.windings.numberLayers,'Single layer'))))
                    paramStruct.windings.numberLayers = paramValue;
                    paramStruct.windings.layoutmethod = 'From file';
                else
                    flag_warning = 0;
                    if length(keySplit) > 1
                        paramStruct.(keySplit{1}).(keySplit{2}) = paramValue;
                    else
                        paramStruct.(key) = paramValue;
                    end
                end
            end
        else
            if length(keySplit) > 1
                if((strcmp(paramStruct.stator.scriptName,'from DXF')&&(strcmp('stator',keySplit{1}))))
                    flag_warning = 3;
                elseif ((strcmp(paramStruct.rotor.scriptName,'from DXF')&&(strcmp('rotor',keySplit{1}))))
                    flag_warning = 3;
                else
                    paramStruct.(keySplit{1}).(keySplit{2}) = paramValue;
                    flag_warning = 0;
                end
            else
                paramStruct.(key) = paramValue;
                flag_warning = 0;
            end
            
        end
    else
        stator = 0;
        %Assigned scriptProps parameters
        %Stator - motorProps.stator.scriptProps
        path = getpmpath('bin/assets/scripts/Stator/');
        jsonfileName = append(paramStruct.stator.scriptFile,'on');
        try
        str = fileread([path jsonfileName]);
        data = jsondecode(str);
        if isfield(data,new_paramName)
            flag_warning = 0;
            stator = 1;
            key = data.(new_paramName);
            keySplit = split(key,'.');
            paramStruct.(keySplit{1}).(keySplit{2})...
                .(keySplit{3}) = paramValue;
        end
        catch
            flag_warning = 1;
        end
        %Rotor - motorProps.rotor.scriptProps
        path = getpmpath('bin/assets/scripts/Rotor/');
        jsonfileName = append(paramStruct.rotor.scriptFile,'on');
        try
        str = fileread([path jsonfileName]);
        data = jsondecode(str);
        if isfield(data,new_paramName)
            flag_warning = 0;
            key = data.(new_paramName);
            keySplit = split(key,'.');
            paramStruct.(keySplit{1}).(keySplit{2})...
                .(keySplit{3}) = paramValue;
        end
        catch
            if(stator == 0)
                flag_warning = 1;
            end
        end
    end
    
elseif isfield(paramStruct,'MS_solvertype')
    %settingsMagnetostatic parameters
    
    %Adjusting the names to access imported struct from json file
    paramNamesplit = split(paramName);
    word = paramNamesplit{1};
    if strcmp(word,'RMS') || strcmp(word,'DC')
        new_paramName = strcat(upper(word));
    else
        new_paramName = strcat(upper(word(1)),lower(word(2:end)));
    end
    for i=2:length(paramNamesplit)
        word = paramNamesplit{i};
        new_paramName = strcat(new_paramName,upper(word(1)),lower(word(2:end)));
    end
% Fields that have to be verified to be compatible with other parameters
    attentionFields = {'RMS supply current','Peak supply current',...
        'RMS current density','RMS phase current','DC supply current',...
        'Current waveform'};
    path = getpmpath('bin/assets/scripts/');
    jsonfileName = 'settingsMagnetostatic.json';
    str = fileread([path jsonfileName]);
    data = jsondecode(str);
    if isfield(data,new_paramName)
        if any(strcmp(attentionFields,paramName))
            lower_paramName = lower(new_paramName);
            % Validation of current waveform and current input method 
            if strcmp(lower_paramName, 'currentwaveform')
                if strcmp(paramValue, 'Trapezoidal')
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                    if strcmp(paramStruct.MS_currentinputmethod,'RMS supply current')
                        paramStruct.MS_currentinputmethod = 'RMS phase current';
                    elseif strcmp(paramStruct.MS_currentinputmethod,'Peak supply current')
                        paramStruct.MS_currentinputmethod = 'RMS phase current';
                    end
                elseif strcmp(paramValue, 'Sinusoidal')
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                    if strcmp(paramStruct.MS_currentinputmethod,'RMS phase current')
                        paramStruct.MS_currentinputmethod = 'RMS supply current';                       
                    elseif strcmp(paramStruct.MS_currentinputmethod,'DC supply current')
                        paramStruct.MS_currentinputmethod = 'RMS supply current';                       
                    end
                end
            % Sinusoidal                
            elseif strcmp(paramStruct.MS_currentwaveform, 'Sinusoidal')
                if strcmp(lower_paramName,'rmssupplycurrent')
                    paramStruct.MS_currentinputmethod = 'RMS supply current';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                elseif strcmp(lower_paramName,'peaksupplycurrent')
                    paramStruct.MS_currentinputmethod = 'Peak supply current';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                elseif strcmpi(lower_paramName,'rmscurrentdensity')
                    paramStruct.MS_currentinputmethod = 'RMS current density';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                else
                    flag_warning = 6;
                end
            % Trapezoidal
            elseif strcmp(paramStruct.MS_currentwaveform, 'Trapezoidal')
                if strcmp(lower_paramName,'rmsphasecurrent')
                    paramStruct.MS_currentinputmethod = 'RMS phase current';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                elseif strcmp(lower_paramName,'dcsupplycurrent')
                    paramStruct.MS_currentinputmethod = 'DC supply current';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                elseif strcmp(lower_paramName,'rmscurrentdensity')
                    paramStruct.MS_currentinputmethod = 'RMS current density';
                    key = data.(new_paramName);
                    paramStruct.(key) = paramValue;
                else
                    flag_warning = 6;
                end
                             
            end
        else
            key = data.(new_paramName);
            paramStruct.(key) = paramValue;
        end
    else
        flag_warning = 5;
    end
else
    flag_warning = 4;
    
end

% Warning messages
warning_message(1) = string(sprintf('The parameter - %s - does not exist in motorProps or cannot be set because the geometry is imported from a dxf-file.\n',paramName));
warning_message(2) = string(sprintf('The parameter - %s - cannot be set as Auto.\n',paramName));
warning_message(3) = string(sprintf('The parameter - %s - cannot be set because the geometry is imported from a dxf-file .\n',paramName));
warning_message(4) = string(sprintf('Incorrect input structure, only motorProps or settingsMagnetostatics are valid.\n'));
warning_message(5) = string(sprintf('The parameter - %s - does not exist in settingsMagnetostatic.json\n',paramName));
warning_message(6) = string(sprintf('The parameter - %s - cannot be assigned for this current waveform.\n',paramName));

if(flag_warning>0)
    error(warning_message(flag_warning));
end

end