Adds missing transient simulation settings
Adds maximum step size setting used by transient analysis solver, and 'use initial conditions (uic)' setting. Enabling uic disables DC operating point analysis and may introduce singularities. It requires a careful selection of initial conditions of circuit elements. Fixes https://gitlab.com/kicad/code/kicad/issues/2515
This commit is contained in:
parent
b2bf3229e6
commit
82e8198fee
|
@ -85,6 +85,7 @@ DIALOG_SIM_COMMAND::DIALOG_SIM_COMMAND( wxWindow* aParent,
|
||||||
m_transStep->SetValidator( m_spiceValidator );
|
m_transStep->SetValidator( m_spiceValidator );
|
||||||
m_transFinal->SetValidator( m_spiceValidator );
|
m_transFinal->SetValidator( m_spiceValidator );
|
||||||
m_transInitial->SetValidator( m_spiceEmptyValidator );
|
m_transInitial->SetValidator( m_spiceEmptyValidator );
|
||||||
|
m_transMaxStep->SetValidator( m_spiceEmptyValidator );
|
||||||
|
|
||||||
refreshUIControls();
|
refreshUIControls();
|
||||||
|
|
||||||
|
@ -261,15 +262,38 @@ bool DIALOG_SIM_COMMAND::TransferDataFromWindow()
|
||||||
if( !m_pgTransient->Validate() )
|
if( !m_pgTransient->Validate() )
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
wxString initial;
|
const SPICE_VALUE timeStep( m_transStep->GetValue() );
|
||||||
|
const SPICE_VALUE finalTime( m_transFinal->GetValue() );
|
||||||
|
|
||||||
|
SPICE_VALUE startTime;
|
||||||
|
|
||||||
if( !empty( m_transInitial ) )
|
if( !empty( m_transInitial ) )
|
||||||
initial = SPICE_VALUE( m_transInitial->GetValue() ).ToSpiceString();
|
startTime = SPICE_VALUE( m_transInitial->GetValue() );
|
||||||
|
|
||||||
m_simCommand.Printf( ".tran %s %s %s",
|
wxString optionals;
|
||||||
SPICE_VALUE( m_transStep->GetValue() ).ToSpiceString(),
|
|
||||||
SPICE_VALUE( m_transFinal->GetValue() ).ToSpiceString(),
|
if( m_useInitialConditions->GetValue() )
|
||||||
initial );
|
optionals = "uic";
|
||||||
|
|
||||||
|
if( !empty( m_transMaxStep ) )
|
||||||
|
optionals = SPICE_VALUE( m_transMaxStep->GetValue() ).ToSpiceString() + " " + optionals;
|
||||||
|
else if( !optionals.IsEmpty() )
|
||||||
|
{
|
||||||
|
SPICE_VALUE maxStep = ( finalTime - startTime ) / 50.0;
|
||||||
|
|
||||||
|
if( maxStep > timeStep )
|
||||||
|
maxStep = timeStep;
|
||||||
|
|
||||||
|
optionals = maxStep.ToSpiceString() + " " + optionals;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( !empty( m_transInitial ) )
|
||||||
|
optionals = startTime.ToSpiceString() + " " + optionals;
|
||||||
|
else if( !optionals.IsEmpty() )
|
||||||
|
optionals = "0 " + optionals;
|
||||||
|
|
||||||
|
m_simCommand.Printf( ".tran %s %s %s", timeStep.ToSpiceString(), finalTime.ToSpiceString(),
|
||||||
|
optionals );
|
||||||
}
|
}
|
||||||
else if( page == m_pgCustom ) // Custom directives
|
else if( page == m_pgCustom ) // Custom directives
|
||||||
{
|
{
|
||||||
|
@ -510,6 +534,18 @@ bool DIALOG_SIM_COMMAND::parseCommand( const wxString& aCommand )
|
||||||
|
|
||||||
if( !tkn.IsEmpty() )
|
if( !tkn.IsEmpty() )
|
||||||
m_transInitial->SetValue( SPICE_VALUE( tkn ).ToSpiceString() );
|
m_transInitial->SetValue( SPICE_VALUE( tkn ).ToSpiceString() );
|
||||||
|
|
||||||
|
// Max step is an optional field
|
||||||
|
tkn = tokenizer.GetNextToken();
|
||||||
|
|
||||||
|
if( !tkn.IsEmpty() )
|
||||||
|
m_transMaxStep->SetValue( SPICE_VALUE( tkn ).ToSpiceString() );
|
||||||
|
|
||||||
|
// uic is an optional field
|
||||||
|
tkn = tokenizer.GetNextToken();
|
||||||
|
|
||||||
|
if( tkn == "uic" )
|
||||||
|
m_useInitialConditions->SetValue( true );
|
||||||
}
|
}
|
||||||
else if( tkn == ".op" )
|
else if( tkn == ".op" )
|
||||||
{
|
{
|
||||||
|
|
|
@ -394,6 +394,36 @@ DIALOG_SIM_COMMAND_BASE::DIALOG_SIM_COMMAND_BASE( wxWindow* parent, wxWindowID i
|
||||||
fgSizer6->Add( m_staticText24, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
|
fgSizer6->Add( m_staticText24, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
|
||||||
|
|
||||||
|
|
||||||
|
m_maxTimeLabel = new wxStaticText( m_pgTransient, wxID_ANY, _("Max. time step:"), wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
m_maxTimeLabel->Wrap( -1 );
|
||||||
|
fgSizer6->Add( m_maxTimeLabel, 0, wxALIGN_CENTER_VERTICAL|wxLEFT, 5 );
|
||||||
|
|
||||||
|
m_transMaxStep = new wxTextCtrl( m_pgTransient, wxID_ANY, wxEmptyString, wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
fgSizer6->Add( m_transMaxStep, 0, wxALIGN_CENTER_VERTICAL|wxRIGHT|wxLEFT|wxEXPAND, 5 );
|
||||||
|
|
||||||
|
m_transMaxStepUnits = new wxStaticText( m_pgTransient, wxID_ANY, _("seconds"), wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
m_transMaxStepUnits->Wrap( -1 );
|
||||||
|
fgSizer6->Add( m_transMaxStepUnits, 0, wxALIGN_CENTER_VERTICAL|wxALIGN_LEFT|wxRIGHT, 5 );
|
||||||
|
|
||||||
|
m_staticText25 = new wxStaticText( m_pgTransient, wxID_ANY, _("(optional; default min{tstep, (tstop-tstart)/50})"), wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
m_staticText25->Wrap( -1 );
|
||||||
|
fgSizer6->Add( m_staticText25, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
|
||||||
|
|
||||||
|
|
||||||
|
m_useInitialConditionsLabel = new wxStaticText( m_pgTransient, wxID_ANY, _("Use initial conditions:"), wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
m_useInitialConditionsLabel->Wrap( -1 );
|
||||||
|
fgSizer6->Add( m_useInitialConditionsLabel, 0, wxALIGN_CENTER_VERTICAL|wxLEFT, 5 );
|
||||||
|
|
||||||
|
m_useInitialConditions = new wxCheckBox( m_pgTransient, wxID_ANY, wxEmptyString, wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
fgSizer6->Add( m_useInitialConditions, 0, wxALIGN_CENTER_VERTICAL|wxRIGHT|wxLEFT|wxEXPAND, 5 );
|
||||||
|
|
||||||
|
fgSizer6->Add( 0, 0, 0, wxEXPAND, 5 );
|
||||||
|
|
||||||
|
m_staticText26 = new wxStaticText( m_pgTransient, wxID_ANY, _("(optional; default off)"), wxDefaultPosition, wxDefaultSize, 0 );
|
||||||
|
m_staticText26->Wrap( -1 );
|
||||||
|
fgSizer6->Add( m_staticText26, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
|
||||||
|
|
||||||
|
|
||||||
bSizer81->Add( fgSizer6, 0, wxALL|wxEXPAND, 5 );
|
bSizer81->Add( fgSizer6, 0, wxALL|wxEXPAND, 5 );
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -112,6 +112,13 @@ class DIALOG_SIM_COMMAND_BASE : public DIALOG_SHIM
|
||||||
wxTextCtrl* m_transInitial;
|
wxTextCtrl* m_transInitial;
|
||||||
wxStaticText* m_transInitialUnits;
|
wxStaticText* m_transInitialUnits;
|
||||||
wxStaticText* m_staticText24;
|
wxStaticText* m_staticText24;
|
||||||
|
wxStaticText* m_maxTimeLabel;
|
||||||
|
wxTextCtrl* m_transMaxStep;
|
||||||
|
wxStaticText* m_transMaxStepUnits;
|
||||||
|
wxStaticText* m_staticText25;
|
||||||
|
wxStaticText* m_useInitialConditionsLabel;
|
||||||
|
wxCheckBox* m_useInitialConditions;
|
||||||
|
wxStaticText* m_staticText26;
|
||||||
wxPanel* m_pgCustom;
|
wxPanel* m_pgCustom;
|
||||||
wxStaticText* m_staticText18;
|
wxStaticText* m_staticText18;
|
||||||
wxTextCtrl* m_customTxt;
|
wxTextCtrl* m_customTxt;
|
||||||
|
|
Loading…
Reference in New Issue