I am designing a set of custom components for fluid system modelling. As there will only be one medium throughout the model, I want to be able to define that medium in one place. The system
component we need for most Modelica.Fluid systems anyway seems like a good place.
I have tried the following MWE, but I'm running into problems with class lookup that I don't know how to avoid.
Using current OpenModelica, when checking the CommonMediaClosedVolume
, I'm getting an error
Class name 'system.CommonMedium' was found via a component (only component and function call names may be accessed in this way).
I noticed that there is a Fluid.System.Medium
defined which I thought could serve a similar purpose, but it's not visible for changing in the parameter dialog in OMEdit (Although it has a choicesAllMatching
annotation -- an OM bug?), and it does not seem to get used anywhere else. In any case, it shows the same lookup error message.
Question:
PartialMedium
) in TweakedSystem
so that I can extend my models to pick that up by default, and so that I can select the desired medium in a TweakedSystem
instance system
?package CommonMediaDefinition
model TweakedSystem "Extended system featuring a common media definition"
extends Modelica.Fluid.System(Medium = CommonMedium);
replaceable package CommonMedium = Modelica.Media.Air.DryAirNasa constrainedby Modelica.Media.Interfaces.PartialMedium annotation(
choicesAllMatching = true);
annotation(
defaultComponentName = "system",
defaultComponentPrefixes = "inner");
end TweakedSystem;
model CommonMediaClosedVolume "ClosedVolume with a default Medium defined in system"
extends Modelica.Fluid.Vessels.ClosedVolume;
// Want to define a Medium default choice that is defined in system (a TweakedSystem instance)
redeclare replaceable package Medium = system.CommonMedium;
// Errors with Class name 'system.CommonMedium' was found via a component (only component and function call names may be accessed in this way).
end CommonMediaClosedVolume;
model SimulationModel
inner TweakedSystem system
annotation(
Placement(visible = true, transformation(origin = {-60, -56}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
CommonMediaClosedVolume commonMediaClosedVolume(V = 1)
annotation(
Placement(visible = true, transformation(origin = {0, -20}, extent = {{-10, -10}, {10, 10}}, rotation = 0)));
end SimulationModel;
end CommonMediaDefinition;
Edit: It seems that this way I envisioned propagating a class is not allowed in Modelica: https://stackoverflow.com/a/24209596/599884
I was not able to add the medium to the system. Maybe someone else knows how to do so.
But you could achieve a global media definition by defining an inner package
for your single medium at top of your simulation model. The modified components have an outer package
defined.
At the end the usage is quite similar to your approach. Instead of adding just a modified System, you have to use the original System and additionally extend a base model which provides the inner Medium package.
Unfortunately this method makes some troubles. In Dymola 2022x it works fine (unless you activate pedantic mode, which gives an error due to problems in the medium Modelica.Media.Air.DryAirNasa...). But in OpenModelica 1.18.1 you have to switch to the "Old Frontend", as translation fails otherwise. And you have to define a non-partial medium in the components. I am not sure if this will make troubles later...
package CommonMediaDefinition
partial model CommonMediumSelector "Extend to inherit CommonMedium parameter"
inner replaceable package CommonMedium = Modelica.Media.Air.DryAirNasa
constrainedby Modelica.Media.Interfaces.PartialMedium
annotation (choicesAllMatching = true);
end CommonMediumSelector;
model CommonMediaClosedVolume "ClosedVolume with Medium defined via outer CommonMedium"
// I would use this in Dymola, to ensure that a proper medium is selected, but it does not
// work in OpenModelica...
// outer replaceable package CommonMedium = Modelica.Media.Interfaces.PartialMedium;
// ... hence we have to use this:
outer replaceable package CommonMedium = Modelica.Media.Air.DryAirNasa;
extends Modelica.Fluid.Vessels.ClosedVolume(redeclare final package Medium=CommonMedium);
end CommonMediaClosedVolume;
model SimulationModel
inner Modelica.Fluid.System system annotation (Placement(transformation(extent={{-90,70},{-70,90}})));
extends CommonMediumSelector(redeclare package CommonMedium = Modelica.Media.Air.DryAirNasa);
CommonMediaClosedVolume commonMediaClosedVolume(V=1)
annotation (Placement(visible=true, transformation(origin={0,-20}, extent={{-10,-10},{10,10}}, rotation=0)));
end SimulationModel;
annotation (uses(Modelica(version="4.0.0")));
end CommonMediaDefinition;