Help - Search - Members - Calendar
Full Version: Measuring the angle of a perodic signal
Modelica Forum > Modelica > Modelica
RungeZipperer
I have a question concerning my Modelica-Model "TEST_PhaseControl".
I will try to keep the explanations as simple as possible but as detailed as necessary.
I started to model a phase angle control which I tested in a simple electrical circuit.
At every timestep of the simulation I need the angle (only between 0 and 180 degrees) of the feeding voltage source.
Therefore I introduced a new block called "angle". This is the only block I developed myself, all other components are taken from the library (2.2).
The circuit works fine if the voltage source is connected directly to the phase angle control (IdealPhaseControl.mo). If it is connected in series with a resistor (resistor1) I get an error during the translation:

"Error: The current version of Dymola cannot generate code for algebraic loops involving when equations or algorithms with when parts.
You may be able to cut the loop
by putting 'pre' around some of the references to unknown continuous time variables in when parts.".

If I leave the resistor resistor1 this error doesnīt occur. This is really confusing me.

Iīve read through the code over and over again but I couldnīt find any mistake. So it seems that I do not understand a very basic characteristic of Modelica!?

This is the code of the block "angle". Maybe the mistake is so obvious that it is not necessary to look at the complete "TEST_PhasControl"-system.

CODE
block angle "Measuring the angle of a periodic signal"
  annotation (
    uses(Modelica(version="2.2")),
    Diagram,
    Icon(Text(
        extent=[-40,36; 42,-40],
        style(color=3, rgbcolor={0,0,255}),
        string="angle")));
  extends Modelica.Blocks.Interfaces.SISO; protected
  Boolean u_pos(start=false);
  Real period_duration(start=0.0);
  Real eventtime;
algorithm
  u_pos := u >= 0;
  //Setting the output
  y := if period_duration > 0.0001 then 180*(time - eventtime)/period_duration else
          0.0;
  //Event at zero crossing
  when change(u_pos) == true then
    period_duration := time - eventtime;
    eventtime := time;
  end when;
end angle;



Maybe you can help me.


Itīs a bit difficult to explain the whole system here so I start posting only the block I developed an I attach a picture of the phase angle control Click to view attachment and of the complete system Click to view attachment.


Thanks a lot.
wagner
Hello RungeZipperer,

you are modelling a control loop. By adding the resistor, you close the feedback loop. If you are only using continous models this is not a problem for Modelica / Dymola. The problem is the algorithm section in your angle model. Since you are using an algorithm section to determine its behaviour you specify a certain evaluation order in your overall model. But in a feedback loop, you don't know what is first, the output or the input. That's where your model crashes. If in your algorithm section in the when part an event occurs, Modelica needs to calculate the output by means of the input. But since the input depends on the output (feedback) the output needs to evaluated first. This behaviour is called an algebraic loop.

The compiler proposes to add a pre() around change(...) in the when part of your algorithm. But the pre() command only accepts plain variables as parameters. Hence, this is not the solution.

An easy workaround for your problem would be to interrupt the algebraic loop by delaying the evaluation of your sensor input for a short period of time. This can be done with the Model Modelica.Blocks.Discrete.ZeroOrderHold. Attached to this posting you find a package that demonstrates how to use the ZeroOrderHold model in your application.

The disadvantage of this approach is that a lot of unnecessary events appear which slow down your simulation if you choose the sample time to be to small.


I hope this can help you.

Greetings
RungeZipperer
Hello,


QUOTE

[...] The problem is the algorithm section in your angle model. Since you are using an algorithm section to determine its behaviour you specify a certain evaluation order in your overall model. But in a feedback loop, you don't know what is first, the output or the input. That's where your model crashes.


Using an equation instead leads to the same error.

CODE

block angle "Measuring the angle of a periodic signal"  
  annotation (
    uses(Modelica(version="2.2")),
    Diagram,
    Icon(Text(
        extent=[-40,36; 42,-40],
        style(color=3, rgbcolor={0,0,255}),
        string="angle")));
  extends Modelica.Blocks.Interfaces.SISO;
protected
  Boolean u_pos(start=false);
  Real period_duration(start=0.0);
  Real eventtime;
equation
  u_pos = u >= 0;
  //Setting the output
  y = if period_duration > 0.0001 then 180*(time - eventtime)/period_duration else
          0.0;
  
  //Event at zero crossing
  when change(u_pos) == true then
    period_duration = time - pre(eventtime);
    eventtime = time;
  end when;
end angle;



QUOTE
The disadvantage of this approach is that a lot of unnecessary events appear which slow down your simulation if you choose the sample time to be to small.


When I compare my old model with the resistor and the new one with the ZeroOrderHold there is a difference in the drawing of the resulting graphs. The results of the old model show very clear and thin lines, when using the new model the lines become thicker. Thatīs another effect of the ZeroOrderHold.


QUOTE

I hope this can help you.


Yes it does biggrin.gif Thank you.
Nevertheless Iīm sure there must be some other and better solution to this problem.

By the way the model contains another mistake...the thyristors do not turn off again. So the phase angle control works fine only for one period. Thatīs the next problem I have to consider.



Greetings.
RungeZipperer
OK, hereīs my next try...and it works smile.gif

The new block "angle" looks like this:

CODE

block angle "Measuring the angle of a periodic signal"
  annotation (
    uses(Modelica(version="2.2")),
    Diagram,
    Icon(Text(
        extent=[-40,36; 42,-40],
        style(color=3, rgbcolor={0,0,255}),
        string="angle")));
  extends Modelica.Blocks.Interfaces.SISO;
protected
  Boolean u_pos(start=false);
  Real period_duration(start=0.0);
  Real eventtime;
equation
  u_pos = u >= 0;
  //Setting the output
  y = if period_duration > 0.0001 then 180*(time - eventtime)/period_duration else
          0.0;
  //Event at zero crossing
  when {pre(u_pos),  not pre(u_pos)} then
    period_duration = time - pre(eventtime);
    eventtime = time;
  end when;
end angle;


The condition for creating the event at a zero crossing had to be changed (Thanks to the Dymola support team)!

The next improvement I had to introduce is that the fire-signal for the thyristors has to be an impulse and not a rectangle function. Therefore I upgraded the boolean section in the model IdealPhaseControl. the condition for firing is no longer

measured_angle>alpha

but

alpha+0.1>measured_angle>alpha.

Iīm not sure if this is a very smart solution but I didnīt find a boolean impulse.

The model TEST_PhaseControl now also works with inductive load.


TEST_PhaseControl Click to view attachment

IdealPhaseControl Click to view attachment
wagner
Hello RungeZipperer,

can you post your models. It's now possible to attach .mo files to a posting.

Thanks

QUOTE(RungeZipperer @ Mar 15 2006, 12:55 PM) *

OK, hereīs my next try...and it works smile.gif

The new block "angle" looks like this:

CODE

block angle "Measuring the angle of a periodic signal"
  annotation (
    uses(Modelica(version="2.2")),
    Diagram,
    Icon(Text(
        extent=[-40,36; 42,-40],
        style(color=3, rgbcolor={0,0,255}),
        string="angle")));
  extends Modelica.Blocks.Interfaces.SISO;
protected
  Boolean u_pos(start=false);
  Real period_duration(start=0.0);
  Real eventtime;
equation
  u_pos = u >= 0;
  //Setting the output
  y = if period_duration > 0.0001 then 180*(time - eventtime)/period_duration else
          0.0;
  //Event at zero crossing
  when {pre(u_pos),  not pre(u_pos)} then
    period_duration = time - pre(eventtime);
    eventtime = time;
  end when;
end angle;


The condition for creating the event at a zero crossing had to be changed (Thanks to the Dymola support team)!

The next improvement I had to introduce is that the fire-signal for the thyristors has to be an impulse and not a rectangle function. Therefore I upgraded the boolean section in the model IdealPhaseControl. the condition for firing is no longer

measured_angle>alpha

but

alpha+0.1>measured_angle>alpha.

Iīm not sure if this is a very smart solution but I didnīt find a boolean impulse.

The model TEST_PhaseControl now also works with inductive load.
TEST_PhaseControl Click to view attachment

IdealPhaseControl Click to view attachment

RungeZipperer
QUOTE(wagner @ Mar 15 2006, 02:11 PM) *

Hello RungeZipperer,

can you post your models. It's now possible to attach .mo files to a posting.

Thanks


OK!


Click to view attachment

Click to view attachment

Click to view attachment
wagner
Hello RungeZipperer,

sorry, it took a little while to post the reply. Attached you'll find a package with your models and and new model that implements an ideal Boolean impulse. Since my power electronic lectures are quite a while back in the past, I can't verify the results. But it seems to me as if it's working.

I updated your angle model a little bit. You have to be careful with the units. Best is not to use the variable type Real but the types defined in Modelica.SIunits. I was a little bit confused with the angle itself. I thought it's defined in rad, but you use in deg.

Greetings
RungeZipperer
QUOTE


I updated your angle model a little bit. You have to be careful with the units. Best is not to use the variable type Real but the types defined in Modelica.SIunits.


OK. Thatīs right. SI units lead to a better understanding an prevents errors.


QUOTE

I was a little bit confused with the angle itself. I thought it's defined in rad, but you use in deg.


Yes Iīve chosen deg. Thatīs more or less fine-tuning. The model is not finished yet.


I do have another big problem after adding another inductor to the model: singularity. I will report about that later.

Thanks for your help.

Greetings
Dietmar Winkler
Hi, some weeks ago I was looking for a phase control and found this thread. I did a bit of clean up of the RungeZipper and like to provide this here as well in case somebody else is looking for something similar.
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Invision Power Board © 2001-2012 Invision Power Services, Inc.