Skip to content

New cmod_csp_tower_particle_IPH.cpp - #1414

Open
marianabraun wants to merge 14 commits into
NatLabRockies:particle_gen3_cspfrom
marianabraun:IPH
Open

New cmod_csp_tower_particle_IPH.cpp#1414
marianabraun wants to merge 14 commits into
NatLabRockies:particle_gen3_cspfrom
marianabraun:IPH

Conversation

@marianabraun

Copy link
Copy Markdown

Adds a new compute module, csp_tower_particle_iph, for falling-particle tower systems delivering industrial process heat (IPH). It combines the heat/heat-sink workflow from cmod_mspt_iph (thermal design point driven by q_pb_design, no power block) with the particle-receiver field and receiver physics from cmod_csp_tower_particle, supporting multi-receiver layouts. Also exposes eta_cosine_field, the field-average cosine efficiency, read directly from SolarPILOT.

@qualand
qualand requested review from Copilot and qualand July 7, 2026 20:15

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Note

Copilot couldn't run its full agentic review because no GitHub Actions runner was available. Make sure your repository has a runner available to run Copilot's review, or add a copilot-setup-steps.yml file specifying one with the runs-on attribute. See the docs for more details.

Adds a new SSC compute module (csp_tower_particle_iph) for falling-particle tower systems delivering industrial process heat (IPH), combining particle-tower receiver/field modeling with a heat-sink workflow and exposing field-average cosine efficiency from SolarPILOT.

Changes:

  • Registers the new csp_tower_particle_iph module with SSC and build system.
  • Extends SolarPILOT invocation utilities to expose field-average cosine efficiency.
  • Implements a new compute module cmod_csp_tower_particle_IPH.cpp with multi-receiver support and heat-sink outputs.

Reviewed changes

Copilot reviewed 5 out of 6 changed files in this pull request and generated 11 comments.

Show a summary per file
File Description
ssc/sscapi.cpp Registers the new compute module entry so SSC can discover it.
ssc/csp_common.h / ssc/csp_common.cpp Adds getFieldAverageCosine() to pull cosine efficiency directly from SolarPILOT.
solarpilot/AutoPilot_API.h Exposes SolarField* from AutoPilot to enable cosine averaging.
ssc/CMakeLists.txt Adds the new module file to the SSC build.
ssc/cmod_csp_tower_particle_IPH.cpp New IPH compute module combining particle tower + heat-sink workflow and outputs.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread ssc/CMakeLists.txt
Comment on lines 30 to +34
cmod_csp_tower_particle.cpp
cmod_csp_heatsink.cpp
cmod_csp_subcomponent.cpp
cmod_csp_tower_particle.cpp
cmod_csp_tower_particle_IPH.cpp

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is correct.

Comment on lines +2225 to +2226
// If electricity pricing data is not available, then dispatch to a uniform schedule
elec_pricing_schedule = C_timeseries_schedule_inputs(1.0, std::numeric
}
else { // if no dispatch optimization, don't need an input pricing schedule
// If electricity pricing data is not available, then dispatch to a uniform schedule
elec_pricing_schedule = C_timeseries_schedule_inputs(1.0, std::numeric

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

p_gen is hardcoded to 0 for all timesteps since this module has no electric output

Comment thread ssc/cmod_csp_tower_particle_IPH.cpp Outdated
}
else { // if no dispatch optimization, don't need an input pricing schedule
// If electricity pricing data is not available, then dispatch to a uniform schedule
elec_pricing_schedule = C_timeseries_schedule_inputs(1.0, std::numeric

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

p_gen is hardcoded to 0 for all timesteps since this module has no electric output

Comment thread ssc/cmod_csp_tower_particle_IPH.cpp Outdated
}
else { // if no dispatch optimization, don't need an input pricing schedule
// If electricity pricing data is not available, then dispatch to a uniform schedule
elec_pricing_schedule = C_timeseries_schedule_inputs(1.0, std::numeric

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

p_gen is hardcoded to 0 for all timesteps since this module has no electric output

Comment on lines +817 to +818
for (size_t i = 0; i < num_recs; i++) { // loop through receivers
input_idx = duplicate_recs ? 0 : i; // Use the first element if duplicate receivers

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This block is unchanged from cmod_csp_tower_particle.cpp

Comment on lines +828 to +829
q_dot_des_per_rec.at(i) = q_dot_rec_des * (power_fraction[input_idx] / power_fraction_sum); // Receiver design point power
rec_orientation = rec_azimuth[i];

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This block is unchanged from cmod_csp_tower_particle.cpp

{ SSC_INPUT, SSC_NUMBER, "transport_deltaT_cold", "Temperature loss for cold particle transport", "K", "", "Tower and Receiver", "*", "", ""},

// Falling particle receiver inputs for SolarPILOT that should *not* be reset during call to this cmod
{ SSC_INPUT, SSC_MATRIX, "rec_tower_offset", "Distance from tower optical height to receiver aperture center, format [[x1,y1],[x2,y2],...] or [[x1,y1,z1],[x2,y2,z2],...]", "m", "", "Tower and Receiver", "?", "", ""},

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Identical to cmod_csp_tower_particle.cpp

}
else { // if no dispatch optimization, don't need an input pricing schedule
// If electricity pricing data is not available, then dispatch to a uniform schedule
elec_pricing_schedule = C_timeseries_schedule_inputs(1.0, std::numeric

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Identical to cmod_csp_tower_particle.cpp

{ SSC_INPUT, SSC_NUMBER, "is_parallel_htr", "Does plant include a HTF heater parallel to solar field?", "", "", "System Control", "?=0", "", ""},
{ SSC_INPUT, SSC_NUMBER, "T_htf_cold_des", "Cold HTF inlet temperature at design conditions", "C", "", "System Design", "*", "", ""},
{ SSC_INPUT, SSC_NUMBER, "T_htf_hot_des", "Hot HTF outlet temperature at design conditions", "C", "", "System Design", "*", "", ""},
{ SSC_INPUT, SSC_NUMBER, "q_pb_design", "Design heat input to power block", "MWt", "", "System Design", "*", "", ""},

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Labeled identical to the molten-salt IPH

capacity_factor_highest_1000_ppas / _2000_ppas summed p_gen, which is
always 0 in this heat-only module, so the outputs were structurally
zero. Removed the two SSC outputs and their calculation block.
Addresses PR NatLabRockies#1414 review comment.
Adds rec_fixed_cost input (default 0) charged once per receiver in the receiver cost loop, alongside the existing area-scaled power law. Defaults reproduce prior behavior exactly.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants