Skip to content

Add support for diffuse irradiance components and component-specific IAM to ModelChain - #2847

Open
cbcrespo wants to merge 39 commits into
pvlib:mainfrom
cbcrespo:modelchain-diffuse-iam
Open

Add support for diffuse irradiance components and component-specific IAM to ModelChain#2847
cbcrespo wants to merge 39 commits into
pvlib:mainfrom
cbcrespo:modelchain-diffuse-iam

Conversation

@cbcrespo

@cbcrespo cbcrespo commented Aug 21, 2026

Copy link
Copy Markdown
Contributor

This PR adds support for diffuse irradiance components and component-specific IAM to the ModelChain class, thereby closing the final stage of my GSoC project (#2750) 😄

Note: This PR is currently based on #2845, which has not yet been merged. I expect reviewing will become easier once that PR is merged. Also, I’m very open to revisiting any of the design choices below based on feedback.

This adds a new iam_diffuse_model property to ModelChain, which can be any of the three existing diffuse IAM functions marion_diffuse, martin_ruiz_diffuse, or schlick_diffuse, as well as 'no_loss', which does not apply optical losses to diffuse irradiance. By default, iam_diffuse_model is None, in which case the previous behavior is preserved: ModelChain fetches the FD (fraction diffuse) module parameter for each array and applies it to the overall diffuse irradiance. FD is essentially always 1, meaning this behavior will generally be equivalent to no_loss.

For marion_diffuse specifically, an additional parameter marion_diffuse_model is necessary (corresponding to the model parameter of iam.marion_diffuse). It defaults to None, but can be inferred from the module parameters via the new infer_marion_diffuse_model, which follows a similar logic to the existing infer_aoi_model.

A new iam_diffuse_modifier is added to the ModelChainResult dataclass.

Circumsolar irradiance is treated as direct (i.e., the direct IAM is applied to it). The remaining diffuse components have their respective component-specific IAMs applied.

If a diffuse component is present for which the selected IAM model does not provide an IAM value, no optical losses are applied to that component and a warning is raised. This would happen, for example, with perez and martin_ruiz_diffuse: the perez transposition model provides isotropic, circumsolar, and horizon components, while the martin_ruiz_diffuse diffuse IAM model does not provide a horizon IAM.

If the selected transposition model does not provide individual components for sky diffuse irradiance (as is the case for klucher), optical losses are applied to the ground diffuse component only. The aggregate sky diffuse irradiance is left unmodified (IAM = 1), and a warning is raised to make this behavior explicit.

@ramaroesilva

ramaroesilva commented Aug 21, 2026

Copy link
Copy Markdown
Contributor

If the selected transposition model does not provide individual components for sky diffuse irradiance (as is the case for klucher), optical losses are applied to the ground diffuse component only. The aggregate sky diffuse irradiance is left unmodified (IAM = 1), and a warning is raised to make this behavior explicit.

I understand that this is a clean way to handle things, however I thing it will just make people not use transposition models which don't provide components like klucher (it's bit weird to account for ground but not to sky diffuse).

Would it make sense that users in this case are allowed to use martin_ruiz_diffuse or schlick_diffuse and apply isotropic losses to the total sky diffuse? Personally, I would prefer this than not having any IAM at all for the sky diffuse, even if it meant raising a warning saying that IAM-wise the modelchain will interpret the sky diffuse as isotropic.

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.

Support diffuse irradiance components and component-wise IAM in ModelChain

3 participants