Can't add selector for all matching choices in Dymola - modelica

I was following the tutorial from Claytex at https://www.claytex.com/blog/dymola-basics-8-dymola-model-inheritance/ on partial and extended models. I'm able to create an inherited (extended) model from a parent (partial) model, and it allows me to change between sibling classes. However, I want to add the box selector for all sibling classes as shown in the tutorial
Here's my code
Model 'a'
partial model a
Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_a port_a annotation (
Placement(transformation(rotation=0, extent={{-110,-10},{-90,10}})));
Modelica.Thermal.HeatTransfer.Interfaces.HeatPort_b port_b annotation (
Placement(transformation(rotation=0, extent={{90,-10},{110,10}})));
annotation (uses(Modelica(version="3.2.3")), Icon(graphics={Text(
extent={{-100,102},{98,-98}},
lineColor={28,108,200},
textString="A")}));
end a;
Model 'b'
model b
extends a;
Modelica.Thermal.HeatTransfer.Components.ThermalResistor thermalResistor(R=3)
annotation (Placement(transformation(extent={{-10,-10},{10,10}})));
equation
connect(port_a, thermalResistor.port_a)
annotation (Line(points={{-100,0},{-10,0}}, color={191,0,0}));
connect(port_b, thermalResistor.port_b)
annotation (Line(points={{100,0},{10,0}}, color={191,0,0}));
annotation (Icon(graphics={Text(
extent={{26,96},{98,12}},
lineColor={28,108,200},
textString="B")}));
end b;
Model 'assembly'
model assembly
Modelica.Thermal.HeatTransfer.Sources.FixedTemperature fixedTemperature(T=274.15)
annotation (Placement(transformation(extent={{-60,40},{-40,60}})));
Modelica.Thermal.HeatTransfer.Sources.FixedTemperature fixedTemperature1(T=275.15)
annotation (Placement(transformation(extent={{40,40},{20,60}})));
replaceable b a1 constrainedby a annotation (choicesAllMatching=true, Placement(transformation(extent={
{-20,40},{0,60}})));
equation
connect(fixedTemperature.port, a1.port_a)
annotation (Line(points={{-40,50},{-20,50}}, color={191,0,0}));
connect(a1.port_b, fixedTemperature1.port)
annotation (Line(points={{0,50},{20,50}}, color={191,0,0}));
annotation (uses(Modelica(version="3.2.3")));
end assembly;
I'd appreciate if someone can point out where my implementation is different from the tutorial. Thanks in advance.

That should work in itself (assuming all classes are public) in Dymola, but to get the box selector you either need to click in the background of assembly diagram or create a TopModel using it as in the Tutorial and then bring up the parameter dialog for assembly1
model TopModel
assembly assembly1
annotation (Placement(transformation(extent={{-40,20},{-20,40}})));
annotation (Icon(coordinateSystem(preserveAspectRatio=false)), Diagram(
coordinateSystem(preserveAspectRatio=false)));
end TopModel;
Additionally partial classes are filtered out from the selector so you only get b in it unless you also add:
model c
extends a;
Modelica.Thermal.HeatTransfer.Components.ThermalResistor thermalResistor(R=3)
annotation (Placement(transformation(extent={{-10,-10},{10,10}})));
equation
connect(port_a, thermalResistor.port_a)
annotation (Line(points={{-100,0},{-10,0}}, color={191,0,0}));
connect(port_b, thermalResistor.port_b)
annotation (Line(points={{100,0},{10,0}}, color={191,0,0}));
annotation (Icon(graphics={Text(
extent={{26,96},{98,12}},
lineColor={28,108,200},
textString="C")}));
end c;
I had all of these classes within one package P. Note that the selector may take a few second to open the first time.

Your code works fine for me (Dymola 2023x)
I can right click a1, select Change Class --> All Matching Choices and select model b (or c which is just a copy of b).
I can open the Parameters dialog for assembly (right click the modelling canvas and click Parameters) and select b or c in the dropdown menu next to a1.

Related

How to inherit a standard Fluid component and override and replace some equations of the base model?

I want to customize a standard Fluid Library component in Modelica using OpenModelica. 
I want to create a customized version of a new Pump where several equations will be changed.
I inherited Fluid.Machines.BaseClasses.PartialPump as a base model by "extends" keyword. When I tried to change and redefine an equation, it gave an overdetermined system error. 
I put redeclare or redifine in front of the equation, and it still gives an error.
What is the best way to create a customised component model without copying everything into a new model? 
Thanks
Unfortunately, you cannot change existing code* — you can only add new code.
In your case, you will have to make a copy of Fluid.Machines.BaseClasses.PartialPump and modify the equation in question. However, you don't necessarily need to copy its base class (Modelica.Fluid.Interfaces.PartialTwoPort).
The PartialPump model is quite versatile. If you need different pump curves (pressure, efficiency or power) you can write additional functions based on the base classes in Fluid.Machines.BaseClasses.PumpCharacteristics.
*) One exception to my initial statement is the inheritance of graphical annotations: if you extend a model and add the annotation primitivesVisible=false the graphical annotations (icon) will not be inherited, for example:
model myModel
extends baseModel annotation(IconMap(primitivesVisible=false));
<new icon annotations>
end myModel;
The usage of extends suggests one wants to inherit all the behaviours of the extended class. You can change those behaviours unless they are redeclarable. The best is to create a new class by duplicating the base model and then change the behaviours as you want. Hope this works!

Modelica: how to use replaceable components?

I am trying to build a model that can use two different components (taken from an existing library) for the same scope: in particular a system with an heat exchanger; this heat exchanger can be based on different technologies, e.g. pipes or plates.
I want then define a model with a default replaceable exchanger and say which other technologies may be used.
This is a vey simple exemple of what I tried:
package Test
// Component 1 original definition in the library
model COMP1
parameter Real p1=1 "";
Real v "";
equation
v=p1*time;
end COMP1;
// Component 2 original definition in the library
model COMP2
parameter Real p2=1 "";
Real v "";
equation
v=p2*time;
end COMP2;
// Main module (system)
model MAIN
parameter Real pm=100 "";
Real vm "";
// Redefinition of the component modifing the default values
model call1 = COMP1(p1=10);
model call2 = COMP2(p2=20);
replaceable call1 OBJ
annotation(choices(
choice(redeclare call1 OBJ "Default"),
choice(redeclare call2 OBJ "Variant")));
equation
vm = OBJ.v+pm;
end MAIN;
// Application model, using the main model
model APP
MAIN mAIN;
end APP;
end Test;
The model APP run successfully. However, if I open the parameters of APP.mAIN and change OBJ (either selecting "Default" or "Variant"), which results in modifing the APP model as follows:
model APP
MAIN mAIN(redeclare call1 OBJ "Default");
end APP;
I get the following error:
Component type specifier call1 not found
I do not understand what I did wrong, please help.
The problem related to the error occurs, because you did not use the correct class path in the choices annotations.
If you select "Default" in APP, you get the following code:
model APP
MAIN mAIN(redeclare call1 OBJ "Default");
end APP;
Here we see that the class path call1 is not valid. APP can access call1 only by using the relative class path MAIN.call1 or the absolute class path Test.MAIN.call1.
So you can fix this problem by using the following annotation:
replaceable call1 OBJ
annotation(choices(
choice(redeclare MAIN.call1 OBJ "Default"),
choice(redeclare MAIN.call2 OBJ "Variant")));
However, in Dymola the model still does not check, apparently due to the local class definitions in MAIN, under Redefinition of the component modifying the default values.
Here you create the new classes call1 and call2. This could be a Dymola bug, as it works in OpenModelica - but the new classes are not necessary. Instead, you can use the original classes and set the parameters with modifier equations in the redeclare statement as follows:
model MAIN
parameter Real pm=100 "";
Real vm "";
replaceable COMP1 OBJ
annotation(choices(
choice(redeclare Test.COMP1 OBJ(p1=10) "Default"),
choice(redeclare Test.COMP2 OBJ(p2=10) "Variant")));
equation
vm = OBJ.v+pm;
end MAIN;
Now the model works for no selection and "Default", but when "Variant" is selected, Dymola complains that the redeclared class does not contain the same variables as the original one.
This is one of the restrictions you have when you work with replaceable classes (again, OpenModelica has no problem with it, but Dymola warns you that this is not conform to the Modelica language specification)
Alternative approach: MSL-Style with interfaces
I suggest to create an interface model like the Modelica library usually does (e.g. with Modelica.Electrical.Analog.Interfaces.OnePort):
You create a partial base model, which contains everything that is common for all variants, called the interface
The variants extend the interface and one of the models of the the existing library
The class using the variants instantiates one of the variants and constrains the redeclaration to the interface using constrainedby
Instead of creating the choices annotations manually you can now create it automatically with the annotation choicesAllMatching
This is how your example could look like. The third-party-components COMP1 and COMP2 are moved to the package ReadOnlyLibrary.
package Test
// Original definition of Component 1 and 2 in the external library
package ReadOnlyLibrary
model COMP1
parameter Real p1=1 "";
Real v "";
equation
v=p1*time;
end COMP1;
model COMP2
parameter Real p2=1 "";
Real v "";
equation
v=p2*time;
end COMP2;
end ReadOnlyLibrary;
// Interface and variants with modified default values
partial model Call_Interface
Real v "";
end Call_Interface;
model Call1 "Default"
extends Call_Interface;
extends ReadOnlyLibrary.COMP1(p1=10);
end Call1;
model Call2 "Variant"
extends Call_Interface;
extends ReadOnlyLibrary.COMP2(p2=20);
end Call2;
// Main module (system)
model Main
parameter Real pm=100 "";
Real vm "";
replaceable Test.Call1 OBJ constrainedby Test.Call_Interface annotation (choicesAllMatching);
equation
vm = OBJ.v+pm;
end Main;
// Application model, using the main model
model App
Main main annotation (Placement(transformation(extent={{-12,10},{8,30}})));
end App;
end Test;

Share the same parameter from model in the toplevel with all components in dymola

i tried to use something like this:
Toplevel with Model1 and the Model with the Parameter in it.
Parametermodel:
Parameter heat_coeffi = 50;
Model1:
outer [Path:Parametermodel] name;
Parameter heat_coeffi = name.heatcoeffi;
The Error message is : "Found non-inner parametermodel for inner model
Failed to find matching inner ....
I tried to use it just like they use System from the original Modelica Lib.
If I understand your question correctly, you instantiate the Parametermodel (similar to the Modelica.Fluid.System) in the top-level model. When you do so you must instantiate it as an inner model. In that way the other instantiated models (model1 etc.) know where to find the global parameters.
In Modelica.Fluid.System there is an annotation defaultComponentPrefixes="inner" that ensures that it is automatically instantiated as an inner model.

EMF Model ecore Diagram eclipse, how to do a two way relation

I'm trying to do my first Model with ecore diagram and I didn't find a way to draw a relationship between two class with any direction on it. In other words, any arrow symbol on the extremity of it.
Is it possible and how to do it?
Create a reference from the first class to the second. Call it ref1, for example. Then create another reference in the opposite direction - from the second class to the first - and set its "opposite" property to ref1.

uml Is it possible for two classes to have relations more than 2?

I make these two calsses and try to express it to UML Class diagram
publc Class A
{
public A(){}
public void Funct1()
{
B b = new B(this);
}
}
public Class B
{
A m_A = null;
public B(A a)
{
m_A = a
}
}
I think class "A" have "Dependency" to B becuase A don't maintain reference to B
And I think class "B" have "one directional Association to A" because class B maintain reference to A.
So, I draw class diagram as follow.
dependency
-------->
[A] [B]
<-
one directioinal association
But, this diagram looks somewhat wrong even to me.
So, I want to know How to express this relation between these classes to class diagram.
No, that seems perfectly valid to me for the reasons you mentioned yourself.
The only thing is that is "somewhat wrong" is the fact that you have a bi-directional dependency between A and B, making the two classes tightly coupled. You should avoid tight coupling whenever possible, but sometimes you don't have much other options.
there is just association needed to define in UML for your example. But, it is not possible to determine what multiplicity is at the B side, multiplicity at A side is 0..1 if there is possible to set null to m_A.
No dependency is necessary to draw in UML in your example. Dependency does not have runt time impact. It is defined between model element definition.
Read UML Superstructure to get precise information about dependency relationship.