/*
 * pm_motor_2d_introduction.java
 */

import com.comsol.model.*;
import com.comsol.model.util.*;

/** Model exported on May 15 2026, 08:30 by COMSOL 6.4.0.421. */
public class pm_motor_2d_introduction {

  public static Model run() {
    Model model = ModelUtil.create("Model");

//    From the File menu, choose New.
//    In the New window, click Model Wizard.
//    In the Model Wizard window, click 2D.
//    In the Select Physics tree, select AC/DC > Electromagnetics and Mechanics > Rotating Machinery, Magnetic (rmm).
//    Click Add.
//    Click Study.
//    In the Select Study tree, select General Studies > Stationary.
//    Click Done.

    model.component().create("comp1", true);

    model.component("comp1").geom().create("geom1", 2);

    model.component("comp1").mesh().create("mesh1");

    model.component("comp1").physics().create("rmm", "RotatingMachineryMagnetic", "geom1");

    model.study().create("std1");
    model.study("std1").create("stat", "Stationary");

//    Begin by specifying a number of general parameters that will be used in the model.
//    In the Model Builder window, under Global Definitions, click Parameters 1.
//    In the Settings window for Parameters, locate the Parameters section.
//    In the table, enter the following settings:

    model.param().set("L", "200[mm]");
    model.param().descr("L", "Out-of-plane thickness of motor");
    model.param().set("init_ang", "0[deg]");
    model.param().descr("init_ang", "Initial electrical angle");
    model.param().set("Np", "10");
    model.param().descr("Np", "Number of poles");
    model.param().set("Ns", "12");
    model.param().descr("Ns", "Number of slots");
    model.param().set("w_rot", "600[rpm]");
    model.param().descr("w_rot", "Rotational speed");
    model.param().set("f_el", "w_rot*(Np/2)");
    model.param().descr("f_el", "Electrical frequency");
    model.param().set("I0", "10[A]");
    model.param().descr("I0", "Peak current");
    model.param().set("Nturn", "10");
    model.param().descr("Nturn", "Number of wire turns in slot");
    model.param().set("ff_slot", "0.8");
    model.param().descr("ff_slot", "Slot filling factor");

//    Next, build the motor using rotor and stator parts from the geometry part library. Initialize the parts, and tick the selections that are predefined to make it convenient to assign material properties and magnetization direction.
//    In the Home toolbar, click Windows and choose Part Libraries.
//    In the Part Libraries window, select AC/DC Module > Rotating Machinery 2D > Rotors > Internal > surface_mounted_magnet_internal_rotor_2d in the tree.
//    Click Add to Geometry.

    model.geom()
         .load(new String[]{"part1"}, "ACDC_Module\\Rotating_Machinery_2D\\Rotors\\Internal\\surface_mounted_magnet_internal_rotor_2d.mph", new String[]{"part1"});
    model.component("comp1").geom("geom1").create("pi1", "PartInstance");
    model.component("comp1").geom("geom1").feature("pi1").set("selkeepnoncontr", false);
    model.component("comp1").geom("geom1").feature("pi1").set("part", "part1");

//    In the Model Builder window, under Component 1 (comp1) > Geometry 1, click Internal Rotor – Surface Mounted Magnets 1 (pi1).
//    In the Settings window for Part Instance, locate the Input Parameters section.
//    In the table, enter the following settings:

    model.component("comp1").geom("geom1").feature("pi1").setEntry("inputexpr", "number_of_poles", "Np");
    model.component("comp1").geom("geom1").feature("pi1").setEntry("inputexpr", "number_of_modeled_poles", "Np");

//    Click to expand the Domain Selections section.
//    In the table, enter the following settings:

    model.component("comp1").geom("geom1").feature("pi1").setEntry("selkeepdom", "pi1_shaft.dom", true);
    model.component("comp1").geom("geom1").feature("pi1").setEntry("selkeepdom", "pi1_rotor_iron.dom", true);
    model.component("comp1").geom("geom1").feature("pi1").setEntry("selkeepdom", "pi1_rotor_magnets", true);
    model.component("comp1").geom("geom1").feature("pi1").setEntry("selkeepdom", "pi1_all.dom", true);

//    Click to expand the Boundary Selections section.
//    In the table, enter the following settings:

    model.component("comp1").geom("geom1").feature("pi1").setEntry("selkeepbnd", "pi1_exterior", true);

//    In the Home toolbar, click Windows and choose Part Libraries.
//    In the Part Libraries window, select AC/DC Module > Rotating Machinery 2D > Stators > External > slotted_external_stator_2d in the tree.
//    Click Add to Geometry.

    model.geom()
         .load(new String[]{"part2"}, "ACDC_Module\\Rotating_Machinery_2D\\Stators\\External\\slotted_external_stator_2d.mph", new String[]{"part1"});
    model.component("comp1").geom("geom1").run("pi1");
    model.component("comp1").geom("geom1").create("pi2", "PartInstance");
    model.component("comp1").geom("geom1").feature("pi2").set("selkeepnoncontr", false);
    model.component("comp1").geom("geom1").feature("pi2").set("part", "part2");

//    Specify number of slots and select a radial partition for the slot winding type.
//    In the Model Builder window, under Component 1 (comp1) > Geometry 1, click External Stator – Slotted 1 (pi2).
//    In the Settings window for Part Instance, locate the Input Parameters section.
//    In the table, enter the following settings:

    model.component("comp1").geom("geom1").feature("pi2").setEntry("inputexpr", "number_of_slots", "Ns");
    model.component("comp1").geom("geom1").feature("pi2").setEntry("inputexpr", "number_of_modeled_slots", "Ns");
    model.component("comp1").geom("geom1").feature("pi2").setEntry("inputexpr", "slot_winding_type", 2);

//    Locate the Domain Selections section.
//    In the table, enter the following settings:

    model.component("comp1").geom("geom1").feature("pi2").setEntry("selkeepdom", "pi2_stator_iron.dom", true);
    model.component("comp1").geom("geom1").feature("pi2").setEntry("selkeepdom", "pi2_stator_slots", true);
    model.component("comp1").geom("geom1").feature("pi2").setEntry("selkeepdom", "pi2_all.dom", true);

//    Create an assembly from the two geometry objects, connected by a pair boundary.
//    In the Model Builder window, under Component 1 (comp1) > Geometry 1, click Form Union (fin).
//    In the Settings window for Form Union/Assembly, locate the Form Union/Assembly section.
//    From the Action list, select Form an assembly.

    model.component("comp1").geom("geom1").feature("fin").set("action", "assembly");

//    In the Home toolbar, click Build All.

    model.component("comp1").geom("geom1").run("fin");

//    Click the Zoom Extents button in the Graphics toolbar.
//    In the Model Builder window, click Geometry 1.
//    Create union selections for the motor iron parts.
//    In the Definitions toolbar, click Union.

    model.component("comp1").selection().create("uni1", "Union");

//    In the Settings window for Union, type Iron in the Label text field.

    model.component("comp1").selection("uni1").label("Iron");

//    Locate the Input Entities section.
//    Under Selections to add, click Add.
//    In the Add dialog, select Rotor iron (Internal Rotor – Surface Mounted Magnets 1), Stator iron (External Stator – Slotted 1) in the Selections to add list.
//    Click OK.

    model.component("comp1").selection("uni1")
         .set("input", new String[]{"geom1_pi1_rotor_iron_dom", "geom1_pi2_stator_iron_dom"});

//    Next, add materials and assign them to their appropriate domain selections.
//    In the Materials toolbar, click Add Material to open the Add Material window.
//    In the tree, select Built-in > Air.
//    Click Add to Component in the window toolbar.

    model.component("comp1").material().create("mat1", "Common");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("eta", "Piecewise");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("Cp", "Piecewise");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("rho", "Analytic");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("k", "Piecewise");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("cs", "Analytic");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("an1", "Analytic");
    model.component("comp1").material("mat1").propertyGroup("def").func().create("an2", "Analytic");
    model.component("comp1").material("mat1").propertyGroup()
         .create("RefractiveIndex", "RefractiveIndex", "Refractive index");
    model.component("comp1").material("mat1").propertyGroup()
         .create("NonlinearModel", "NonlinearModel", "Nonlinear model");
    model.component("comp1").material("mat1").propertyGroup().create("idealGas", "idealGas", "Ideal gas");
    model.component("comp1").material("mat1").propertyGroup("idealGas").func().create("Cp", "Piecewise");
    model.component("comp1").material("mat1").label("Air");
    model.component("comp1").material("mat1").set("family", "air");
    model.component("comp1").material("mat1").propertyGroup("def").func("eta").set("arg", "T");
    model.component("comp1").material("mat1").propertyGroup("def").func("eta")
         .set("pieces", new String[][]{{"200.0", "1600.0", "-8.38278E-7+8.35717342E-8*T^1-7.69429583E-11*T^2+4.6437266E-14*T^3-1.06585607E-17*T^4"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("eta").set("argunit", "K");
    model.component("comp1").material("mat1").propertyGroup("def").func("eta").set("fununit", "Pa*s");
    model.component("comp1").material("mat1").propertyGroup("def").func("Cp").set("arg", "T");
    model.component("comp1").material("mat1").propertyGroup("def").func("Cp")
         .set("pieces", new String[][]{{"200.0", "1600.0", "1047.63657-0.372589265*T^1+9.45304214E-4*T^2-6.02409443E-7*T^3+1.2858961E-10*T^4"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("Cp").set("argunit", "K");
    model.component("comp1").material("mat1").propertyGroup("def").func("Cp").set("fununit", "J/(kg*K)");
    model.component("comp1").material("mat1").propertyGroup("def").func("rho")
         .set("expr", "pA*0.02897/R_const[K*mol/J]/T");
    model.component("comp1").material("mat1").propertyGroup("def").func("rho").set("args", new String[]{"pA", "T"});
    model.component("comp1").material("mat1").propertyGroup("def").func("rho").set("fununit", "kg/m^3");
    model.component("comp1").material("mat1").propertyGroup("def").func("rho")
         .set("argunit", new String[]{"Pa", "K"});
    model.component("comp1").material("mat1").propertyGroup("def").func("rho")
         .set("plotaxis", new String[]{"off", "on"});
    model.component("comp1").material("mat1").propertyGroup("def").func("rho")
         .set("plotfixedvalue", new String[]{"101325", "273.15"});
    model.component("comp1").material("mat1").propertyGroup("def").func("rho")
         .set("plotargs", new String[][]{{"pA", "101325", "101325"}, {"T", "273.15", "293.15"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("k").set("arg", "T");
    model.component("comp1").material("mat1").propertyGroup("def").func("k")
         .set("pieces", new String[][]{{"200.0", "1600.0", "-0.00227583562+1.15480022E-4*T^1-7.90252856E-8*T^2+4.11702505E-11*T^3-7.43864331E-15*T^4"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("k").set("argunit", "K");
    model.component("comp1").material("mat1").propertyGroup("def").func("k").set("fununit", "W/(m*K)");
    model.component("comp1").material("mat1").propertyGroup("def").func("cs")
         .set("expr", "sqrt(1.4*R_const[K*mol/J]/0.02897*T)");
    model.component("comp1").material("mat1").propertyGroup("def").func("cs").set("args", new String[]{"T"});
    model.component("comp1").material("mat1").propertyGroup("def").func("cs").set("fununit", "m/s");
    model.component("comp1").material("mat1").propertyGroup("def").func("cs").set("argunit", new String[]{"K"});
    model.component("comp1").material("mat1").propertyGroup("def").func("cs")
         .set("plotfixedvalue", new String[]{"273.15"});
    model.component("comp1").material("mat1").propertyGroup("def").func("cs")
         .set("plotargs", new String[][]{{"T", "273.15", "373.15"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("an1").set("funcname", "alpha_p");
    model.component("comp1").material("mat1").propertyGroup("def").func("an1")
         .set("expr", "-1/rho(pA,T)*d(rho(pA,T),T)");
    model.component("comp1").material("mat1").propertyGroup("def").func("an1").set("args", new String[]{"pA", "T"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an1").set("fununit", "1/K");
    model.component("comp1").material("mat1").propertyGroup("def").func("an1")
         .set("argunit", new String[]{"Pa", "K"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an1")
         .set("plotaxis", new String[]{"off", "on"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an1")
         .set("plotfixedvalue", new String[]{"101325", "273.15"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an1")
         .set("plotargs", new String[][]{{"pA", "101325", "101325"}, {"T", "273.15", "373.15"}});
    model.component("comp1").material("mat1").propertyGroup("def").func("an2").set("funcname", "muB");
    model.component("comp1").material("mat1").propertyGroup("def").func("an2").set("expr", "0.6*eta(T)");
    model.component("comp1").material("mat1").propertyGroup("def").func("an2").set("args", new String[]{"T"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an2").set("fununit", "Pa*s");
    model.component("comp1").material("mat1").propertyGroup("def").func("an2").set("argunit", new String[]{"K"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an2")
         .set("plotfixedvalue", new String[]{"200"});
    model.component("comp1").material("mat1").propertyGroup("def").func("an2")
         .set("plotargs", new String[][]{{"T", "200", "1600"}});
    model.component("comp1").material("mat1").propertyGroup("def").set("thermalexpansioncoefficient", "");
    model.component("comp1").material("mat1").propertyGroup("def").set("molarmass", "");
    model.component("comp1").material("mat1").propertyGroup("def").set("bulkviscosity", "");
    model.component("comp1").material("mat1").propertyGroup("def")
         .set("thermalexpansioncoefficient", new String[]{"alpha_p(pA,T)", "0", "0", "0", "alpha_p(pA,T)", "0", "0", "0", "alpha_p(pA,T)"});
    model.component("comp1").material("mat1").propertyGroup("def").set("molarmass", "0.02897[kg/mol]");
    model.component("comp1").material("mat1").propertyGroup("def").set("bulkviscosity", "muB(T)");
    model.component("comp1").material("mat1").propertyGroup("def")
         .set("relpermeability", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat1").propertyGroup("def")
         .set("relpermittivity", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat1").propertyGroup("def").set("dynamicviscosity", "eta(T)");
    model.component("comp1").material("mat1").propertyGroup("def").set("ratioofspecificheat", "1.4");
    model.component("comp1").material("mat1").propertyGroup("def")
         .set("electricconductivity", new String[]{"0[S/m]", "0", "0", "0", "0[S/m]", "0", "0", "0", "0[S/m]"});
    model.component("comp1").material("mat1").propertyGroup("def").set("heatcapacity", "Cp(T)");
    model.component("comp1").material("mat1").propertyGroup("def").set("density", "rho(pA,T)");
    model.component("comp1").material("mat1").propertyGroup("def")
         .set("thermalconductivity", new String[]{"k(T)", "0", "0", "0", "k(T)", "0", "0", "0", "k(T)"});
    model.component("comp1").material("mat1").propertyGroup("def").set("soundspeed", "cs(T)");
    model.component("comp1").material("mat1").propertyGroup("def").addInput("temperature");
    model.component("comp1").material("mat1").propertyGroup("def").addInput("pressure");
    model.component("comp1").material("mat1").propertyGroup("RefractiveIndex")
         .set("n", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat1").propertyGroup("NonlinearModel").set("BA", "def.gamma-1");
    model.component("comp1").material("mat1").propertyGroup("idealGas").func("Cp").label("Piecewise 2");
    model.component("comp1").material("mat1").propertyGroup("idealGas").func("Cp").set("arg", "T");
    model.component("comp1").material("mat1").propertyGroup("idealGas").func("Cp")
         .set("pieces", new String[][]{{"200.0", "1600.0", "1047.63657-0.372589265*T^1+9.45304214E-4*T^2-6.02409443E-7*T^3+1.2858961E-10*T^4"}});
    model.component("comp1").material("mat1").propertyGroup("idealGas").func("Cp").set("argunit", "K");
    model.component("comp1").material("mat1").propertyGroup("idealGas").func("Cp").set("fununit", "J/(kg*K)");
    model.component("comp1").material("mat1").propertyGroup("idealGas").set("Rs", "R_const/Mn");
    model.component("comp1").material("mat1").propertyGroup("idealGas").set("heatcapacity", "Cp(T)");
    model.component("comp1").material("mat1").propertyGroup("idealGas").set("ratioofspecificheat", "1.4");
    model.component("comp1").material("mat1").propertyGroup("idealGas").set("molarmass", "0.02897[kg/mol]");
    model.component("comp1").material("mat1").propertyGroup("idealGas").addInput("temperature");
    model.component("comp1").material("mat1").propertyGroup("idealGas").addInput("pressure");
    model.component("comp1").material("mat1").materialType("nonSolid");

//    In the tree, select AC/DC > Soft Iron (Without Losses).
//    Click Add to Component in the window toolbar.

    model.component("comp1").material().create("mat2", "Common");
    model.component("comp1").material("mat2").propertyGroup().create("BHCurve", "BHCurve", "B-H Curve");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func().create("BH", "Interpolation");
    model.component("comp1").material("mat2").propertyGroup()
         .create("EffectiveBHCurve", "EffectiveBHCurve", "Effective B-H Curve");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func()
         .create("BHeff", "Interpolation");
    model.component("comp1").material("mat2").label("Soft Iron (Without Losses)");
    model.component("comp1").material("mat2").set("family", "iron");
    model.component("comp1").material("mat2").propertyGroup("def")
         .set("electricconductivity", new String[]{"0[S/m]", "0", "0", "0", "0[S/m]", "0", "0", "0", "0[S/m]"});
    model.component("comp1").material("mat2").propertyGroup("def")
         .set("relpermittivity", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat2").propertyGroup("BHCurve").label("B-H Curve");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").label("Interpolation 1");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH")
         .set("table", new String[][]{{"0", "0"}, 
         {"663.146", "1"}, 
         {"1067.5", "1.1"}, 
         {"1705.23", "1.2"}, 
         {"2463.11", "1.3"}, 
         {"3841.67", "1.4"}, 
         {"5425.74", "1.5"}, 
         {"7957.75", "1.6"}, 
         {"12298.3", "1.7"}, 
         {"20462.8", "1.8"}, 
         {"32169.6", "1.9"}, 
         {"61213.4", "2"}, 
         {"111408", "2.1"}, 
         {"188487.757", "2.2"}, 
         {"267930.364", "2.3"}, 
         {"347507.836", "2.4"}});
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").set("extrap", "linear");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").set("fununit", new String[]{"T"});
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH")
         .set("argunit", new String[]{"A/m"});
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").set("plotleftextrap", false);
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").set("defineinv", true);
    model.component("comp1").material("mat2").propertyGroup("BHCurve").func("BH").set("defineprimfun", true);
    model.component("comp1").material("mat2").propertyGroup("BHCurve").set("normB", "BH(normHin)");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").set("normH", "BH_inv(normBin)");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").set("Wpm", "BH_prim(normHin)");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").descr("normHin", "Magnetic field norm");
    model.component("comp1").material("mat2").propertyGroup("BHCurve")
         .descr("normBin", "Magnetic flux density norm");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").addInput("magneticfield");
    model.component("comp1").material("mat2").propertyGroup("BHCurve").addInput("magneticfluxdensity");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").label("Effective B-H Curve");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .label("Interpolation 1");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("table", new String[][]{{"0", "0"}, 
         {"663.146", "1.000000051691021"}, 
         {"1067.5", "1.4936495124126294"}, 
         {"1705.23", "1.9415328461315795"}, 
         {"2463.11", "2.257765669366018"}, 
         {"3841.67", "2.609980642431287"}, 
         {"5425.74", "2.8664452090837504"}, 
         {"7957.75", "3.1441438097176118"}, 
         {"12298.3", "3.448538051654125"}, 
         {"20462.8", "3.7816711973679054"}, 
         {"32169.6", "4.058345590113038"}, 
         {"61213.4", "4.420646552950275"}, 
         {"111408", "4.721274089545955"}, 
         {"188487.757", "4.972148140718701"}, 
         {"267930.364", "5.145510860855953"}, 
         {"347507.836", "5.245510861426532"}});
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("extrap", "linear");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("fununit", new String[]{"T"});
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("argunit", new String[]{"A/m"});
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("plotleftextrap", false);
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff").set("defineinv", true);
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").func("BHeff")
         .set("defineprimfun", true);
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").set("normBeff", "BHeff(normHeffin)");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve")
         .set("normHeff", "BHeff_inv(normBeffin)");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve")
         .set("Wpmeff", "BHeff_prim(normHeffin)");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve")
         .descr("normHeffin", "Effective magnetic field norm");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve")
         .descr("normBeffin", "Effective magnetic flux density norm");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").addInput("magneticfield");
    model.component("comp1").material("mat2").propertyGroup("EffectiveBHCurve").addInput("magneticfluxdensity");

//    In the tree, select AC/DC > Copper.
//    Click Add to Component in the window toolbar.

    model.component("comp1").material().create("mat3", "Common");
    model.component("comp1").material("mat3").propertyGroup()
         .create("Enu", "Enu", "Young's modulus and Poisson's ratio");
    model.component("comp1").material("mat3").propertyGroup().create("linzRes", "linzRes", "Linearized resistivity");
    model.component("comp1").material("mat3").label("Copper");
    model.component("comp1").material("mat3").set("family", "copper");
    model.component("comp1").material("mat3").propertyGroup("def")
         .set("relpermeability", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat3").propertyGroup("def")
         .set("electricconductivity", new String[]{"5.998e7[S/m]", "0", "0", "0", "5.998e7[S/m]", "0", "0", "0", "5.998e7[S/m]"});
    model.component("comp1").material("mat3").propertyGroup("def").set("heatcapacity", "385[J/(kg*K)]");
    model.component("comp1").material("mat3").propertyGroup("def")
         .set("relpermittivity", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat3").propertyGroup("def").set("emissivity", "0.5");
    model.component("comp1").material("mat3").propertyGroup("def").set("density", "8940[kg/m^3]");
    model.component("comp1").material("mat3").propertyGroup("def")
         .set("thermalconductivity", new String[]{"400[W/(m*K)]", "0", "0", "0", "400[W/(m*K)]", "0", "0", "0", "400[W/(m*K)]"});
    model.component("comp1").material("mat3").propertyGroup("Enu").set("E", "126e9[Pa]");
    model.component("comp1").material("mat3").propertyGroup("Enu").set("nu", "0.34");
    model.component("comp1").material("mat3").propertyGroup("linzRes").set("rho0", "1.667e-8[ohm*m]");
    model.component("comp1").material("mat3").propertyGroup("linzRes").set("alpha", "3.862e-3[1/K]");
    model.component("comp1").material("mat3").propertyGroup("linzRes").set("Tref", "293.15[K]");
    model.component("comp1").material("mat3").propertyGroup("linzRes").addInput("temperature");

//    In the tree, select AC/DC > Hard Magnetic Materials > Sintered NdFeB Grades (Chinese Standard) > N54 (Sintered NdFeB).
//    Click Add to Component in the window toolbar.

    model.component("comp1").material().create("mat4", "Common");
    model.component("comp1").material("mat4").propertyGroup()
         .create("RemanentFluxDensity", "RemanentFluxDensity", "Remanent flux density");
    model.component("comp1").material("mat4").label("N54 (Sintered NdFeB)");
    model.component("comp1").material("mat4").set("family", "chrome");
    model.component("comp1").material("mat4").propertyGroup("def")
         .set("electricconductivity", new String[]{"1/1.4[uohm*m]", "0", "0", "0", "1/1.4[uohm*m]", "0", "0", "0", "1/1.4[uohm*m]"});
    model.component("comp1").material("mat4").propertyGroup("def")
         .set("relpermittivity", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat4").propertyGroup("RemanentFluxDensity")
         .set("murec", new String[]{"1.05", "0", "0", "0", "1.05", "0", "0", "0", "1.05"});
    model.component("comp1").material("mat4").propertyGroup("RemanentFluxDensity").set("normBr", "1.47[T]");

//    In the tree, select Built-in > Iron.
//    Click Add to Component in the window toolbar.

    model.component("comp1").material().create("mat5", "Common");
    model.component("comp1").material("mat5").propertyGroup()
         .create("Enu", "Enu", "Young's modulus and Poisson's ratio");
    model.component("comp1").material("mat5").label("Iron");
    model.component("comp1").material("mat5").set("family", "iron");
    model.component("comp1").material("mat5").propertyGroup("def")
         .set("relpermeability", new String[]{"4000", "0", "0", "0", "4000", "0", "0", "0", "4000"});
    model.component("comp1").material("mat5").propertyGroup("def")
         .set("electricconductivity", new String[]{"1.12e7[S/m]", "0", "0", "0", "1.12e7[S/m]", "0", "0", "0", "1.12e7[S/m]"});
    model.component("comp1").material("mat5").propertyGroup("def")
         .set("thermalexpansioncoefficient", new String[]{"12.2e-6[1/K]", "0", "0", "0", "12.2e-6[1/K]", "0", "0", "0", "12.2e-6[1/K]"});
    model.component("comp1").material("mat5").propertyGroup("def").set("heatcapacity", "440[J/(kg*K)]");
    model.component("comp1").material("mat5").propertyGroup("def")
         .set("relpermittivity", new String[]{"1", "0", "0", "0", "1", "0", "0", "0", "1"});
    model.component("comp1").material("mat5").propertyGroup("def").set("density", "7870[kg/m^3]");
    model.component("comp1").material("mat5").propertyGroup("def")
         .set("thermalconductivity", new String[]{"76.2[W/(m*K)]", "0", "0", "0", "76.2[W/(m*K)]", "0", "0", "0", "76.2[W/(m*K)]"});
    model.component("comp1").material("mat5").propertyGroup("Enu").set("E", "200[GPa]");
    model.component("comp1").material("mat5").propertyGroup("Enu").set("nu", "0.29");

//    In the Materials toolbar, click Add Material to close the Add Material window.
//    In the Settings window for Material, locate the Geometric Entity Selection section.
//    From the Selection list, select Iron.

    model.component("comp1").material("mat2").selection().named("uni1");

//    In the Model Builder window, click Iron (mat5).
//    In the Settings window for Material, locate the Geometric Entity Selection section.
//    From the Selection list, select Shaft (Internal Rotor – Surface Mounted Magnets 1).

    model.component("comp1").material("mat5").selection().named("geom1_pi1_shaft_dom");

//    Locate the Material Contents section.
//    In the table, enter the following settings:

    model.component("comp1").material("mat5").propertyGroup("def").set("electricconductivity", new String[]{"0"});
    model.component("comp1").material("mat5").propertyGroup("Enu").set("E", new String[]{"200e9[Pa]"});

//    In the Model Builder window, click Copper (mat3).
//    In the Settings window for Material, locate the Geometric Entity Selection section.
//    From the Selection list, select Stator slots (External Stator – Slotted 1).

    model.component("comp1").material("mat3").selection().named("geom1_pi2_stator_slots");

//    In the Model Builder window, click N54 (Sintered NdFeB) (mat4).
//    In the Settings window for Material, locate the Geometric Entity Selection section.
//    From the Selection list, select Rotor Magnets (Internal Rotor – Surface Mounted Magnets 1).

    model.component("comp1").material("mat4").selection().named("geom1_pi1_rotor_magnets");

//    In the Physics toolbar, click Moving Mesh and choose Rotating Domain.

    model.component("comp1").common().create("rot1", "RotatingDomain");
    model.component("comp1").common("rot1").selection().all();

//    In the Settings window for Rotating Domain, locate the Domain Selection section.
//    From the Selection list, select All domains (Internal Rotor – Surface Mounted Magnets 1).

    model.component("comp1").common("rot1").selection().named("geom1_pi1_all_dom");

//    Locate the Rotation section.
//    From the Rotation type list, select Specified rotational velocity.

    model.component("comp1").common("rot1").set("rotationType", "rotationalVelocity");

//    In the \[\omega\] text field, type w_rot*2*pi.

    model.component("comp1").common("rot1").set("angularVelocity", "w_rot*2*pi");

//    In the Model Builder window, under Component 1 (comp1), click Rotating Machinery, Magnetic (rmm).
//    In the Settings window for Rotating Machinery, Magnetic, locate the Thickness section.
//    In the \[d\] text field, type L.

    model.component("comp1").physics("rmm").prop("d").set("d", "L");

//    In the Physics toolbar, click Domains and choose Laminated Core, Ampère's Law.

    model.component("comp1").physics("rmm").create("lcvf1", "LaminatedCoreVectorFormulation", 2);

//    In the Settings window for Laminated Core, Ampère's Law, locate the Domain Selection section.
//    From the Selection list, select Iron.

    model.component("comp1").physics("rmm").feature("lcvf1").selection().named("uni1");

//    Locate the Lamination Model section.
//    From the Lamination model list, select Out-of-plane lamination.

    model.component("comp1").physics("rmm").feature("lcvf1").set("LaminationModel", "OutOfPlane");

//    In the Physics toolbar, click Domains and choose Conducting Magnet.

    model.component("comp1").physics("rmm").create("cmag1", "ConductingMagnet", 2);

    return model;
  }

  public static Model run2(Model model) {

//    In the Settings window for Conducting Magnet, locate the Domain Selection section.
//    From the Selection list, select Rotor Magnets (Internal Rotor – Surface Mounted Magnets 1).

    model.component("comp1").physics("rmm").feature("cmag1").selection().named("geom1_pi1_rotor_magnets");

//    Locate the Magnet section.
//    From the Pattern type list, select Circular pattern.

    model.component("comp1").physics("rmm").feature("cmag1").set("PatternType", "CircularPattern");

//    From the Type of periodicity list, select Alternating.

    model.component("comp1").physics("rmm").feature("cmag1").set("PeriodicType", "Alternating");

//    In the Physics toolbar, click Attributes and choose Loss Calculation.

    model.component("comp1").physics("rmm").feature("cmag1").create("loss1", "LossCalculation", 2);

//    In the Model Builder window, click North 1.
//    Select Boundary 268.

    model.component("comp1").physics("rmm").feature("cmag1").feature("north1").selection().set(268);

//    In the Model Builder window, click South 1.
//    Select Boundary 265.

    model.component("comp1").physics("rmm").feature("cmag1").feature("south1").selection().set(265);

//    The Multiphase Winding feature simplifies excitation of stator coils of electrical machines. For three-phase systems an automatic ordering of coil domains into a balanced stator winding is supported, provided that the electrical machine topology in terms of number of poles and slots can accommodate it. In the following steps, use a Multiphase Winding feature to automatically populate the selections of three subnodes with coil domains representing each phase.
//    In the Physics toolbar, click Domains and choose Multiphase Winding.

    model.component("comp1").physics("rmm").create("wnd1", "MultiphaseWinding", 2);

//    In the Settings window for Multiphase Winding, locate the Domain Selection section.
//    From the Selection list, select Stator slots (External Stator – Slotted 1).

    model.component("comp1").physics("rmm").feature("wnd1").selection().named("geom1_pi2_stator_slots");

//    Locate the Multiphase Winding section.
//    In the \[I_\mathrm{pk}\] text field, type I0.

    model.component("comp1").physics("rmm").feature("wnd1").set("Ipk", "I0");

//    In the \[\alpha_\textrm{i}\] text field, type init_ang.

    model.component("comp1").physics("rmm").feature("wnd1").set("alpha_i", "init_ang");

//    In the \[f_\textrm{t}\] text field, type f_el.

    model.component("comp1").physics("rmm").feature("wnd1").set("freq_t", "f_el");

//    Locate the Homogenized Conductor section.
//    In the \[N\] text field, type Nturn.

    model.component("comp1").physics("rmm").feature("wnd1").set("N", "Nturn");

//    In the \[f\] text field, type ff_slot.

    model.component("comp1").physics("rmm").feature("wnd1").set("FillingFactor", "ff_slot");

//    Locate the Multiphase Winding section.
//    From the Winding layout configuration list, select Automatic three phase.

    model.component("comp1").physics("rmm").feature("wnd1").set("WindingLayout", "automatic");

//    In the \[n_{\textrm{poles}}\] text field, type Np.

    model.component("comp1").physics("rmm").feature("wnd1").set("NoPoles", "Np");

//    In the \[n_{\textrm{slots}}\] text field, type Ns.

    model.component("comp1").physics("rmm").feature("wnd1").set("NoSlots", "Ns");

//    In the Number of coils per slot text field, type 2.

    model.component("comp1").physics("rmm").feature("wnd1").set("NoCoilsPerSlot", 2);

//    Click Add Phases.

    model.component("comp1").physics("rmm").feature("wnd1").runCommand("addPhases");

//    Selection of the generated phases can be inspected.
//    In the Model Builder window, click Automatic Phase 1.
//    In the Model Builder window, expand the Automatic Phase 1 node, then click Reversed Current Direction 1.
//    In the Model Builder window, under Component 1 (comp1) > Rotating Machinery, Magnetic (rmm), click Multiphase Winding 1.
//    In the Physics toolbar, click Attributes and choose Loss Calculation.

    model.component("comp1").physics("rmm").feature("wnd1").create("loss1", "LossCalculation", 2);

//    Next, implement the Arkkio Torque Calculation feature for calculating the torque on the rotor. The node is automatically applied to the air gap. The Arkkio force integrand is multiplied with a support function which is nonzero in the correct radial extent, between the rotor magnets and stator iron.
//    In the Physics toolbar, click Domains and choose Arkkio Torque Calculation.

    model.component("comp1").physics("rmm").create("ark1", "ArkkioTorqueCalculation", 2);

//    Set up a probe for the motor torque.
//    In the Definitions toolbar, click Probes and choose Global Variable Probe.

    model.component("comp1").probe().create("var1", "GlobalVariable");

//    In the Settings window for Global Variable Probe, type Torque in the Label text field.

    model.component("comp1").probe("var1").label("Torque");

//    Click Replace Expression in the upper-right corner of the Expression section.
//    From the menu, choose Component 1 (comp1) > Rotating Machinery, Magnetic > Mechanical > rmm.Tark_1 - Axial torque - N·m.

    model.component("comp1").probe("var1").set("expr", "rmm.Tark_1");
    model.component("comp1").probe("var1").set("descr", "Axial torque");

//    Adjust the default mesh to ensure sufficient resolution of magnetic field in the airgap and in stator core.
//    In the Model Builder window, click Identity Boundary Pair 1 (ap1).
//    In the Settings window for Pair, locate the Source Boundaries section.
//    Click Create Selection.
//    In the Create Selection dialog, type source in the Selection name text field.
//    Click OK.

    model.component("comp1").selection().create("sel1", "Explicit");
    model.component("comp1").selection("sel1").geom(1);
    model.component("comp1").selection("sel1").label("source");
    model.component("comp1").selection("sel1").set(89, 90, 101, 102, 121, 122, 142, 143, 165, 166, 185, 186);

//    In the Settings window for Pair, locate the Destination Boundaries section.
//    Click Create Selection.
//    In the Create Selection dialog, type dest in the Selection name text field.
//    Click OK.

    model.component("comp1").selection().create("sel2", "Explicit");
    model.component("comp1").selection("sel2").geom(1);
    model.component("comp1").selection("sel2").label("dest");
    model.component("comp1").selection("sel2").set(237, 238, 247, 248, 259, 260, 279, 280, 291, 292);

//    In the Definitions toolbar, click Union.

    model.component("comp1").selection().create("uni2", "Union");

//    In the Settings window for Union, type Airgap Boundaries in the Label text field.

    model.component("comp1").selection("uni2").label("Airgap Boundaries");

//    Locate the Geometric Entity Level section.
//    From the Level list, select Boundary.

    model.component("comp1").selection("uni2").set("entitydim", 1);

//    Locate the Input Entities section.
//    Under Selections to add, click Add.
//    In the Add dialog, select source, dest in the Selections to add list.
//    Click OK.

    model.component("comp1").selection("uni2").set("input", new String[]{"sel1", "sel2"});

//    In the Model Builder window, right-click Component 1 (comp1) > Mesh 1 and choose Edit Physics-Induced Sequence.

    model.component("comp1").mesh("mesh1").automatic(false);

//    In the Model Builder window, right-click Mesh 1 and choose Size.

    model.component("comp1").mesh("mesh1").create("size1", "Size");

//    Right-click Mesh 1 and choose Size.

    model.component("comp1").mesh("mesh1").create("size2", "Size");

//    Right-click and choose Move Up.

    model.component("comp1").mesh("mesh1").feature().move("size1", 1);
    model.component("comp1").mesh("mesh1").feature().move("size2", 2);

//    In the Model Builder window, click Size 1.
//    In the Settings window for Size, locate the Geometric Entity Selection section.
//    From the Geometric entity level list, select Boundary.

    model.component("comp1").mesh("mesh1").feature("size1").selection().geom("geom1", 1);

//    From the Selection list, select Airgap Boundaries.

    model.component("comp1").mesh("mesh1").feature("size1").selection().named("uni2");

//    Locate the Element Size section.
//    Click the Custom button.

    model.component("comp1").mesh("mesh1").feature("size1").set("custom", true);

//    Locate the Element Size Parameters section.
//    Select the Maximum element size checkbox.

    model.component("comp1").mesh("mesh1").feature("size1").set("hmaxactive", true);

//    In the associated text field, type 0.5[mm]/3.

    model.component("comp1").mesh("mesh1").feature("size1").set("hmax", "0.5[mm]/3");

//    In the Model Builder window, click Size 2.
//    In the Settings window for Size, locate the Geometric Entity Selection section.
//    From the Geometric entity level list, select Domain.

    model.component("comp1").mesh("mesh1").feature("size2").selection().geom("geom1", 2);

//    From the Selection list, select Stator iron (External Stator – Slotted 1).

    model.component("comp1").mesh("mesh1").feature("size2").selection().named("geom1_pi2_stator_iron_dom");

//    Locate the Element Size section.
//    Click the Custom button.

    model.component("comp1").mesh("mesh1").feature("size2").set("custom", true);

//    Locate the Element Size Parameters section.
//    Select the Maximum element size checkbox.

    model.component("comp1").mesh("mesh1").feature("size2").set("hmaxactive", true);

//    In the associated text field, type 1[mm].

    model.component("comp1").mesh("mesh1").feature("size2").set("hmax", "1[mm]");

//    Click Build All.

    model.component("comp1").mesh("mesh1").run();

//    Configure a stationary study to find the electrical angle providing maximum motoring torque.
//    In the Model Builder window, click Study 1.
//    In the Settings window for Study, type Study 1: Initial Electrical Angle Sweep in the Label text field.

    model.study("std1").label("Study 1: Initial Electrical Angle Sweep");

//    In the Model Builder window, under Study 1: Initial Electrical Angle Sweep, click Step 1: Stationary.
//    In the Settings window for Stationary, click to expand the Study Extensions section.
//    Select the Auxiliary sweep checkbox.

    model.study("std1").feature("stat").set("useparam", true);

//    Click Add.

    model.study("std1").feature("stat").setIndex("pname", "L", 0);
    model.study("std1").feature("stat").setIndex("plistarr", "", 0);
    model.study("std1").feature("stat").setIndex("punit", "m", 0);
    model.study("std1").feature("stat").setIndex("pname", "L", 0);
    model.study("std1").feature("stat").setIndex("plistarr", "", 0);
    model.study("std1").feature("stat").setIndex("punit", "m", 0);

//    In the table, enter the following settings:

    model.study("std1").feature("stat").setIndex("pname", "init_ang", 0);
    model.study("std1").feature("stat").setIndex("plistarr", "range(0,10[deg],360[deg])", 0);
    model.study("std1").feature("stat").setIndex("punit", "deg", 0);

//    In the Model Builder window, collapse the Study 1: Initial Electrical Angle Sweep node.
//    Monitor the torque while solving by clicking the <l>Probe Plot 1</l> next to the <l>Graphics</l> window after pushing the <l>Compute</l>-button.
//    In the Study toolbar, click Compute.

    model.study("std1").createAutoSequences("all");

    model.component("comp1").probe("var1").genResult("none");

    model.sol("sol1").runAll();

    model.result().create("pg2", "PlotGroup2D");
    model.result("pg2").label("Magnetic Flux Density (rmm)");
    model.result("pg2").set("frametype", "spatial");
    model.result("pg2").set("showlegendsmaxmin", true);
    model.result("pg2").feature().create("surf1", "Surface");
    model.result("pg2").feature("surf1").set("solutionparams", "parent");
    model.result("pg2").feature("surf1").set("colortable", "Prism");
    model.result("pg2").feature("surf1").set("colortabletrans", "nonlinear");
    model.result("pg2").feature("surf1").set("colorcalibration", -0.8);
    model.result("pg2").feature("surf1").set("evaluationsettings", "parent");
    model.result("pg2").feature("surf1").set("data", "parent");
    model.result("pg2").feature().create("str1", "Streamline");
    model.result("pg2").feature("str1").set("solutionparams", "parent");
    model.result("pg2").feature("str1").set("titletype", "none");
    model.result("pg2").feature("str1").set("posmethod", "uniform");
    model.result("pg2").feature("str1").set("udensity", 2);
    model.result("pg2").feature("str1").set("color", "custom");
    model.result("pg2").feature("str1")
         .set("customcolor", new double[]{0.3764705955982208, 0.3764705955982208, 0.3764705955982208});
    model.result("pg2").feature("str1").set("evaluationsettings", "parent");
    model.result("pg2").feature("str1").set("maxlen", 0.4);
    model.result("pg2").feature("str1").set("maxtime", Double.POSITIVE_INFINITY);
    model.result("pg2").feature("str1").set("inheritcolor", false);
    model.result("pg2").feature("str1").set("maxtime", Double.POSITIVE_INFINITY);
    model.result("pg2").feature("str1").set("data", "parent");
    model.result("pg2").feature("str1").selection().geom("geom1", 1);
    model.result("pg2").feature("str1").selection()
         .set(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207, 208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252, 253, 254, 255, 256, 257, 258, 259, 260, 261, 262, 263, 264, 265, 266, 267, 268, 269, 270, 271, 272, 273, 274, 275, 276, 277, 278, 279, 280, 281, 282, 283, 284, 285, 286, 287, 288, 289, 290, 291, 292, 293, 294, 295, 296);
    model.result("pg2").feature("str1").set("inheritplot", "surf1");
    model.result("pg2").feature("str1").feature().create("filt1", "Filter");
    model.result("pg2").feature("str1").feature("filt1").set("expr", "!isScalingSystemDomain");
    model.result("pg2").feature().create("con1", "Contour");
    model.result("pg2").feature("con1").set("solutionparams", "parent");
    model.result("pg2").feature("con1").set("expr", "rmm.Az");
    model.result("pg2").feature("con1").set("titletype", "none");
    model.result("pg2").feature("con1").set("number", 10);
    model.result("pg2").feature("con1").set("levelrounding", false);
    model.result("pg2").feature("con1").set("coloring", "uniform");
    model.result("pg2").feature("con1").set("colorlegend", false);
    model.result("pg2").feature("con1").set("color", "custom");
    model.result("pg2").feature("con1")
         .set("customcolor", new double[]{0.3764705955982208, 0.3764705955982208, 0.3764705955982208});
    model.result("pg2").feature("con1").set("evaluationsettings", "parent");
    model.result("pg2").feature("con1").set("inheritcolor", false);
    model.result("pg2").feature("con1").set("data", "parent");
    model.result("pg2").feature("con1").set("inheritplot", "surf1");
    model.result("pg2").feature("con1").feature().create("filt1", "Filter");
    model.result("pg2").feature("con1").feature("filt1").set("expr", "!isScalingSystemDomain");
    model.result("pg2").run();
    model.result("pg2").run();

//    In the Model Builder window, expand the Magnetic Flux Density (rmm) node.
//    Right-click Streamline 1 and choose Disable.

    model.result("pg2").feature("str1").active(false);
    model.result("pg2").run();

//    In the Model Builder window, click Contour 1.
//    In the Settings window for Contour, locate the Levels section.
//    In the Total levels text field, type 16.

    model.result("pg2").feature("con1").set("number", 16);

//    Locate the Coloring and Style section.
//    From the Color list, select Black.

    model.result("pg2").feature("con1").set("color", "black");

//    In the Magnetic Flux Density (rmm) toolbar, click Plot.

    model.result("pg2").run();
    model.result("pg1").set("window", "window1");
    model.result("pg1").run();

//    In the Model Builder window, under Results, click Probe Plot Group 1.
//    In the Settings window for 1D Plot Group, type Torque in the Label text field.

    model.result("pg1").label("Torque");

//    Locate the Plot Settings section.
//    Select the x-axis label checkbox.

    model.result("pg1").set("xlabelactive", true);

//    In the associated text field, type Angle [deg].

    model.result("pg1").set("xlabel", "Angle [deg]");

//    Select the y-axis label checkbox.

    model.result("pg1").set("ylabelactive", true);

//    In the associated text field, type Torque [N*m].

    model.result("pg1").set("ylabel", "Torque [N*m]");

//    In the Results toolbar, click 1D Plot Group.

    model.result().create("pg3", "PlotGroup1D");
    model.result("pg3").run();

//    In the Settings window for 1D Plot Group, type Torque Initial Electrical Angle Sweep in the Label text field.

    model.result("pg3").label("Torque Initial Electrical Angle Sweep");

//    Locate the Plot Settings section.
//    Select the x-axis label checkbox.

    model.result("pg3").set("xlabelactive", true);

//    In the associated text field, type Angle [deg].

    model.result("pg3").set("xlabel", "Angle [deg]");

//    Select the y-axis label checkbox.

    model.result("pg3").set("ylabelactive", true);

//    In the associated text field, type Torque [N*m].

    model.result("pg3").set("ylabel", "Torque [N*m]");

//    Right-click Torque Initial Electrical Angle Sweep and choose Global.

    model.result("pg3").create("glob1", "Global");
    model.result("pg3").feature("glob1").set("markerpos", "datapoints");
    model.result("pg3").feature("glob1").set("linewidth", "preference");

//    In the Settings window for Global, locate the y-Axis Data section.
//    In the table, enter the following settings:

    model.result("pg3").feature("glob1").setIndex("expr", "rmm.Tark_1", 0);

//    Right-click Global 1 and choose Graph Marker.

    model.result("pg3").feature("glob1").create("gmrk1", "GraphMarker");
    model.result("pg3").feature("glob1").feature("gmrk1").set("linewidth", "preference");
    model.result("pg3").run();

//    In the Settings window for Graph Marker, locate the Text Format section.
//    Select the Show x-coordinate checkbox.

    model.result("pg3").feature("glob1").feature("gmrk1").set("inclxcoord", true);

//    Select the Include unit checkbox.

    model.result("pg3").feature("glob1").feature("gmrk1").set("includeunit", true);

//    In the Precision text field, type 3.

    model.result("pg3").feature("glob1").feature("gmrk1").set("precision", 3);

//    Locate the Display section.
//    From the Display list, select Max.

    model.result("pg3").feature("glob1").feature("gmrk1").set("display", "max");

//    In the Torque Initial Electrical Angle Sweep toolbar, click Plot.

    model.result("pg3").run();

//    The maximum torque is found at an initial electrical angle offset of \[200^\circ \]. Update init_ang with this value to orient the stator field with respect to rotor magnets so as to achieve maximum torque production.
//    In the Model Builder window, under Global Definitions, click Parameters 1.
//    In the Settings window for Parameters, locate the Parameters section.
//    In the table, enter the following settings:

    model.param().set("init_ang", "200[deg]");
    model.param().descr("init_ang", "Initial mechanical angle");

//    In the Home toolbar, click Add Study to open the Add Study window.
//    Find the Studies subsection.
//    In the Select Study tree, select General Studies > Stationary.
//    Click Add Study in the window toolbar.

    model.study().create("std2");
    model.study("std2").create("stat", "Stationary");

//    In the Home toolbar, click Add Study to close the Add Study window.
//    In the Settings window for Study, type Study 2: Synchronous Rotation in the Label text field.

    model.study("std2").label("Study 2: Synchronous Rotation");

//    In the Study toolbar, click Time Dependent.

    model.study("std2").create("time", "Transient");

//    In the Settings window for Time Dependent, locate the Study Settings section.
//    In the Output times text field, type range(0,1/12/6,1.1)/f_el.

    model.study("std2").feature("time").set("tlist", "range(0,1/12/6,1.1)/f_el");

//    In the Study toolbar, click Show Default Solver.

    model.study("std2").showAutoSequences("all");

//    In the Model Builder window, collapse the Study 2: Synchronous Rotation node.
//    Click Compute.

    model.study("std2").createAutoSequences("all");

    model.component("comp1").probe("var1").genResult("none");

    model.sol("sol2").runAll();

    model.result().create("pg4", "PlotGroup2D");
    model.result("pg4").label("Magnetic Flux Density (rmm) 1");
    model.result("pg4").set("data", "dset3");
    model.result("pg4").setIndex("looplevel", 80, 0);
    model.result("pg4").set("frametype", "spatial");
    model.result("pg4").set("showlegendsmaxmin", true);
    model.result("pg4").feature().create("surf1", "Surface");
    model.result("pg4").feature("surf1").set("solutionparams", "parent");
    model.result("pg4").feature("surf1").set("colortable", "Prism");
    model.result("pg4").feature("surf1").set("colortabletrans", "nonlinear");
    model.result("pg4").feature("surf1").set("colorcalibration", -0.8);
    model.result("pg4").feature("surf1").set("evaluationsettings", "parent");
    model.result("pg4").feature("surf1").set("data", "parent");
    model.result("pg4").feature().create("str1", "Streamline");
    model.result("pg4").feature("str1").set("solutionparams", "parent");
    model.result("pg4").feature("str1").set("titletype", "none");
    model.result("pg4").feature("str1").set("posmethod", "uniform");
    model.result("pg4").feature("str1").set("udensity", 2);
    model.result("pg4").feature("str1").set("color", "custom");
    model.result("pg4").feature("str1")
         .set("customcolor", new double[]{0.3764705955982208, 0.3764705955982208, 0.3764705955982208});
    model.result("pg4").feature("str1").set("evaluationsettings", "parent");
    model.result("pg4").feature("str1").set("maxlen", 0.4);
    model.result("pg4").feature("str1").set("maxtime", Double.POSITIVE_INFINITY);
    model.result("pg4").feature("str1").set("inheritcolor", false);
    model.result("pg4").feature("str1").set("maxtime", Double.POSITIVE_INFINITY);
    model.result("pg4").feature("str1").set("data", "parent");
    model.result("pg4").feature("str1").selection().geom("geom1", 1);
    model.result("pg4").feature("str1").selection()
         .set(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 159, 160, 161, 162, 163, 164, 165, 166, 167, 168, 169, 170, 171, 172, 173, 174, 175, 176, 177, 178, 179, 180, 181, 182, 183, 184, 185, 186, 187, 188, 189, 190, 191, 192, 193, 194, 195, 196, 197, 198, 199, 200, 201, 202, 203, 204, 205, 206, 207, 208, 209, 210, 211, 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 240, 241, 242, 243, 244, 245, 246, 247, 248, 249, 250, 251, 252, 253, 254, 255, 256, 257, 258, 259, 260, 261, 262, 263, 264, 265, 266, 267, 268, 269, 270, 271, 272, 273, 274, 275, 276, 277, 278, 279, 280, 281, 282, 283, 284, 285, 286, 287, 288, 289, 290, 291, 292, 293, 294, 295, 296);
    model.result("pg4").feature("str1").set("inheritplot", "surf1");
    model.result("pg4").feature("str1").feature().create("filt1", "Filter");
    model.result("pg4").feature("str1").feature("filt1").set("expr", "!isScalingSystemDomain");
    model.result("pg4").feature().create("con1", "Contour");
    model.result("pg4").feature("con1").set("solutionparams", "parent");
    model.result("pg4").feature("con1").set("expr", "rmm.Az");
    model.result("pg4").feature("con1").set("titletype", "none");
    model.result("pg4").feature("con1").set("number", 10);
    model.result("pg4").feature("con1").set("levelrounding", false);
    model.result("pg4").feature("con1").set("coloring", "uniform");
    model.result("pg4").feature("con1").set("colorlegend", false);
    model.result("pg4").feature("con1").set("color", "custom");
    model.result("pg4").feature("con1")
         .set("customcolor", new double[]{0.3764705955982208, 0.3764705955982208, 0.3764705955982208});
    model.result("pg4").feature("con1").set("evaluationsettings", "parent");
    model.result("pg4").feature("con1").set("inheritcolor", false);
    model.result("pg4").feature("con1").set("data", "parent");
    model.result("pg4").feature("con1").set("inheritplot", "surf1");
    model.result("pg4").feature("con1").feature().create("filt1", "Filter");
    model.result("pg4").feature("con1").feature("filt1").set("expr", "!isScalingSystemDomain");
    model.result("pg4").run();
    model.result("pg1").set("window", "window1");
    model.result("pg1").run();

//    In the Model Builder window, under Results, click Torque.
//    In the Settings window for 1D Plot Group, type Torque Ripple in the Label text field.

    model.result("pg1").label("Torque Ripple");

//    Locate the Plot Settings section.
//    In the x-axis label text field, type Time [s].

    model.result("pg1").set("xlabel", "Time [s]");

//    Locate the Axis section.
//    Select the Manual axis limits checkbox.

    model.result("pg1").set("axislimits", true);

//    In the x minimum text field, type 0.

    model.result("pg1").set("xmin", 0);

//    In the x maximum text field, type 0.02.

    model.result("pg1").set("xmax", 0.02);

//    In the y minimum text field, type 0.

    model.result("pg1").set("ymin", 0);

//    In the y maximum text field, type 4.

    model.result("pg1").set("ymax", 4);

//    Locate the Legend section.
//    From the Position list, select Middle right.

    model.result("pg1").set("legendpos", "middleright");

//    In the Torque Ripple toolbar, click Plot.

    model.result("pg1").set("window", "window1");
    model.result("pg1").run();
    model.result("pg1").set("axislimits", false);

//    Now plot the radial component of the magnetic flux density in the air gap. To do that, define a suitable boundary within the air gap, and plot the quantity along its arc length.
//    In the Results toolbar, click 1D Plot Group.

    model.result().create("pg5", "PlotGroup1D");
    model.result("pg5").run();

//    In the Settings window for 1D Plot Group, type Air Gap Radial Magnetic Flux Density in the Label text field.

    model.result("pg5").label("Air Gap Radial Magnetic Flux Density");

//    Locate the Data section.
//    From the Dataset list, select Study 2: Synchronous Rotation/Solution 2 (sol2).

    model.result("pg5").set("data", "dset3");

//    From the Time selection list, select First.

    model.result("pg5").setIndex("looplevelinput", "first", 0);

//    Right-click Air Gap Radial Magnetic Flux Density and choose Line Graph.

    model.result("pg5").create("lngr1", "LineGraph");
    model.result("pg5").feature("lngr1").set("markerpos", "datapoints");
    model.result("pg5").feature("lngr1").set("linewidth", "preference");
    model.result("pg5").feature("lngr1").set("evaluationsettings", "parent");

//    In the Settings window for Line Graph, locate the Selection section.
//    From the Selection list, select Exterior (Internal Rotor – Surface Mounted Magnets 1).

    model.result("pg5").feature("lngr1").selection().named("geom1_pi1_exterior");

//    Locate the y-Axis Data section.
//    In the Expression text field, type rmm.ark1.Brad.

    model.result("pg5").feature("lngr1").set("expr", "rmm.ark1.Brad");

//    In the Air Gap Radial Magnetic Flux Density toolbar, click Plot.

    model.result("pg5").run();

//    In the Home toolbar, click Add Study to open the Add Study window.
//    Find the Studies subsection.
//    In the Select Study tree, select Preset Studies for Selected Physics Interfaces > Time-to-Frequency Losses.
//    Click Add Study in the window toolbar.

    model.study().create("std3");
    model.study("std3").create("emloss", "TimeToFrequencyLosses");
    model.study("std3").feature("emloss").set("fftinputstudy", "current");
    model.study("std3").feature("emloss").set("lossstarttime", "0");
    model.study("std3").feature("emloss").set("notsolnum", "auto");
    model.study("std3").feature("emloss").set("outputmap", new String[]{});

//    In the Home toolbar, click Add Study to close the Add Study window.
//    In the Settings window for Study, type Study 3: Time Average Loss Calculation in the Label text field.

    model.study("std3").label("Study 3: Time Average Loss Calculation");

//    In the Model Builder window, under Study 3: Time Average Loss Calculation, click Step 1: Time-to-Frequency Losses.
//    In the Settings window for Time-to-Frequency Losses, locate the Study Settings section.
//    From the Input study list, select Study 2: Synchronous Rotation, Time Dependent.

    model.study("std3").feature("emloss").set("fftinputstudy", "std2");

//    In the Electrical period text field, type 1/f_el.

    model.study("std3").feature("emloss").set("emT0", "1/f_el");

//    In the Study toolbar, click Compute.

    model.study("std3").createAutoSequences("all");

    model.sol("sol4").runAll();

    model.result().create("pg6", "PlotGroup2D");
    model.result("pg6").label("Cycle Averaged Losses (rmm)");
    model.result("pg6").set("data", "dset5");
    model.result("pg6").setIndex("looplevel", 1, 0);
    model.result("pg6").set("frametype", "spatial");
    model.result("pg6").set("showlegendsmaxmin", true);
    model.result("pg6").feature().create("surf1", "Surface");
    model.result("pg6").feature("surf1").set("solutionparams", "parent");
    model.result("pg6").feature("surf1").set("expr", "rmm.Qh");
    model.result("pg6").feature("surf1").set("colortable", "GrayBody");
    model.result("pg6").feature("surf1").set("evaluationsettings", "parent");
    model.result("pg6").feature("surf1").set("data", "parent");
    model.result("pg6").feature("surf1").feature().create("filt1", "Filter");

    return model;
  }

  public static Model run3(Model model) {
    model.result("pg6").feature("surf1").feature("filt1").set("expr", "rmm.isLossCalculationDomain");
    model.result("pg6").run();

//    In the Cycle Averaged Losses (rmm) toolbar, click Plot.

    model.result("pg6").run();

//    In the Model Builder window, collapse the Component 1 (comp1) node.
//    In the Results toolbar, click Evaluation Group.

    model.result().evaluationGroup().create("eg1", "EvaluationGroup");

//    In the Settings window for Evaluation Group, locate the Data section.
//    From the Dataset list, select Study 2: Synchronous Rotation/Solution 2 (sol2).

    model.result().evaluationGroup("eg1").set("data", "dset3");

//    In the Label text field, type Torque over One Electrical Period.

    model.result().evaluationGroup("eg1").label("Torque over One Electrical Period");

//    Right-click Torque over One Electrical Period and choose Global Evaluation.

    model.result().evaluationGroup("eg1").create("gev1", "EvalGlobal");

//    In the Settings window for Global Evaluation, locate the Expressions section.
//    In the table, enter the following settings:

    model.result().evaluationGroup("eg1").feature("gev1").setIndex("expr", "rmm.Tark_1", 0);

//    In the Model Builder window, click Torque over One Electrical Period.
//    In the Settings window for Evaluation Group, locate the Data section.
//    From the Time selection list, select Interpolated.

    model.result().evaluationGroup("eg1").setIndex("looplevelinput", "interp", 0);

//    In the Times (s) text field, type range(0.1,1/12/6,1.1)/f_el.

    model.result().evaluationGroup("eg1").setIndex("interp", "range(0.1,1/12/6,1.1)/f_el", 0);

//    In the Torque over One Electrical Period toolbar, click Evaluate.

    model.result().evaluationGroup("eg1").run();

//    In the Results toolbar, click 1D Plot Group.

    model.result().create("pg7", "PlotGroup1D");
    model.result("pg7").run();

//    In the Settings window for 1D Plot Group, type Torque Harmonics in the Label text field.

    model.result("pg7").label("Torque Harmonics");

//    Click to expand the Title section.
//    From the Title type list, select Manual.

    model.result("pg7").set("titletype", "manual");

//    In the Title text area, type Torque Harmonics.

    model.result("pg7").set("title", "Torque Harmonics");

//    Locate the Plot Settings section.
//    Select the x-axis label checkbox.

    model.result("pg7").set("xlabelactive", true);

//    In the associated text field, type Harmonic Order.

    model.result("pg7").set("xlabel", "Harmonic Order");

//    Right-click Torque Harmonics and choose Table Graph.

    model.result("pg7").create("tblp1", "Table");
    model.result("pg7").feature("tblp1").set("markerpos", "datapoints");
    model.result("pg7").feature("tblp1").set("linewidth", "preference");

//    In the Settings window for Table Graph, locate the Data section.
//    From the Source list, select Evaluation group.

    model.result("pg7").feature("tblp1").set("source", "evaluationgroup");

//    From the Transformation list, select Discrete Fourier transform.

    model.result("pg7").feature("tblp1").set("transform", "fourier");

//    From the Show list, select Frequency spectrum.

    model.result("pg7").feature("tblp1").set("fouriershow", "spectrum");

//    From the Scale list, select Multiply by sampling period.

    model.result("pg7").feature("tblp1").set("scale", "multiplyperiod");

//    Click to expand the Preprocessing section.
//    Find the x-axis column subsection.
//    From the Transformation list, select Linear.

    model.result("pg7").feature("tblp1").set("preprocx", "linear");

//    In the Scaling text field, type f_el.

    model.result("pg7").feature("tblp1").set("scalingx", "f_el");

//    Locate the Coloring and Style section.
//    From the Width list, select 2.

    model.result("pg7").feature("tblp1").set("linewidth", 2);

//    In the Torque Harmonics toolbar, click Plot.

    model.result("pg7").run();
    model.result("pg4").run();

    model.title("Permanent Magnet Motor in 2D");

    model
         .description("In this tutorial, a PM motor with 10\u00a0rotor poles and 12\u00a0stator slots is modeled in 2D, to capture the torque ripple over an electrical period and map the volumetric loss density in the rotor and stator iron.");

    return model;
  }

  public static void main(String[] args) {
    Model model = run();
    model = run2(model);
    run3(model);
  }

}
