Skip to main content
Member
August 6, 2026
Question

Variance Explanations by Company Thresholds

  • August 6, 2026
  • 3 replies
  • 34 views

We complete variance explanations each quarter, and each business unit has different thresholds that require explanation. Is there a way to apply different thresholds within the report based on the selected business unit using the conditional formatting? I would like to flag it red only but I can’t figure out how to do by business unit using the same report.

Users are prompted to select their business unit when they run the variance report.

This is what I currently have, but it applies the same threshold to all companies:

If (CellAmount > 50000) Then

    ExcelTextColor = Red, ReportTextColor = Red, TextColor = Red

Else If (CellAmount < -50000) Then

    ExcelTextColor = Red, ReportTextColor = Red, TextColor = Red

End If

3 replies

Member
August 6, 2026

Have you tried writing an XFBR Rule and passing in the Entity as a parameter to the XFBR call?  You can write various Select Case statements for the entities and put in the conditional formatting.

KWOLFAuthor
Member
August 7, 2026

I have not. Do you have an example by chance on how to write it?

Member
August 7, 2026

I have had to do something very similar for a project I have been working on. 

Our logic for when a variance explanation is required became a bit complicated, but I have tried to quickly re-write it to fit your explanation above. 

It uses the current cube view POV as the default value for any dimensions not provided as parameters.  Where the threshold is held in a dimension different to the CV POV, they need to be specified. 

In the case of using it in the cell format of a row member filter containing entities, I expect something along these lines:

XFBR(XFBR_ThresholdAmount, GetThresholdAmount, Entity=[|MFEntity|], Account=[**VarianceThresholdAccount**])

Imports System
Imports System.Collections.Generic
Imports System.Data
Imports System.Data.Common
Imports System.Globalization
Imports System.IO
Imports System.Linq
Imports Microsoft.VisualBasic
Imports OneStream.Finance.Database
Imports OneStream.Finance.Engine
Imports OneStream.Shared.Common
Imports OneStream.Shared.Database
Imports OneStream.Shared.Engine
Imports OneStream.Shared.Wcf
Imports OneStream.Stage.Database
Imports OneStream.Stage.Engine

Namespace OneStream.BusinessRule.DashboardStringFunction.XFBR_ThresholdAmount
Public Class MainClass
Public Function Main(
ByVal si As SessionInfo,
ByVal globals As BRGlobals,
ByVal api As Object,
ByVal args As DashboardStringFunctionArgs
) As Object
Try
If args.FunctionName.XFEqualsIgnoreCase("GetThresholdAmount") Then
' Assign default values as cube view POV if XFBR String called from a cube view.
Dim currentCubeView As CubeView = args.SubstVarSourceInfo.CubeViewOrNull

Dim defaultCubeName As String = String.Empty
Dim defaultEntityName As String = String.Empty
Dim defaultParentName As String = String.Empty
Dim defaultScenarioName As String = String.Empty
Dim defaultAccountName As String = String.Empty
Dim defaultTimeName As String = String.Empty
Dim defaultConsName As String = String.Empty
Dim defaultIcName As String = String.Empty
Dim defaultViewName As String = String.Empty
Dim defaultOriginName As String = String.Empty
Dim defaultFlowName As String = String.Empty
Dim defaultUD1Name As String = String.Empty
Dim defaultUD2Name As String = String.Empty
Dim defaultUD3Name As String = String.Empty
Dim defaultUD4Name As String = String.Empty
Dim defaultUD5Name As String = String.Empty
Dim defaultUD6Name As String = String.Empty
Dim defaultUD7Name As String = String.Empty
Dim defaultUD8Name As String = String.Empty

If currentCubeView IsNot Nothing Then
defaultCubeName = currentCubeView.CubeViewCube.Name
defaultEntityName = currentCubeView.CubeViewPovMembers.Entity.Name
defaultParentName = currentCubeView.CubeViewPovMembers.Parent.Name
defaultScenarioName = currentCubeView.CubeViewPovMembers.Scenario.Name
defaultAccountName = currentCubeView.CubeViewPovMembers.Account.Name
defaultTimeName = currentCubeView.CubeViewPovMembers.Time.Name
defaultConsName = currentCubeView.CubeViewPovMembers.Consolidation.Name
defaultIcName = currentCubeView.CubeViewPovMembers.IC.Name
defaultViewName = currentCubeView.CubeViewPovMembers.View.Name
defaultOriginName = currentCubeView.CubeViewPovMembers.Origin.Name
defaultFlowName = currentCubeView.CubeViewPovMembers.Flow.Name
defaultUD1Name = currentCubeView.CubeViewPovMembers.UD1.Name
defaultUD2Name = currentCubeView.CubeViewPovMembers.UD2.Name
defaultUD3Name = currentCubeView.CubeViewPovMembers.UD3.Name
defaultUD4Name = currentCubeView.CubeViewPovMembers.UD4.Name
defaultUD5Name = currentCubeView.CubeViewPovMembers.UD5.Name
defaultUD6Name = currentCubeView.CubeViewPovMembers.UD6.Name
defaultUD7Name = currentCubeView.CubeViewPovMembers.UD7.Name
defaultUD8Name = currentCubeView.CubeViewPovMembers.UD8.Name
End If

' Get POV for threshold amount using parameters, defaulting to cube view POV if available
Dim cubeName As String = args.NameValuePairs.XFGetValue(
"Cube",
defaultCubeName
)
Dim entityName As String = args.NameValuePairs.XFGetValue(
"Entity",
defaultEntityName
)
Dim parentName As String = args.NameValuePairs.XFGetValue(
"Parent",
defaultParentName
)
Dim scenarioName As String = args.NameValuePairs.XFGetValue(
"Scenario",
defaultScenarioName
)
Dim accountName As String = args.NameValuePairs.XFGetValue(
"Account",
defaultAccountName
)
Dim timeName As String = args.NameValuePairs.XFGetValue(
"Time",
defaultTimeName
)
Dim consName As String = args.NameValuePairs.XFGetValue(
"Consolidation",
defaultConsName
)
Dim icName As String = args.NameValuePairs.XFGetValue(
"IC",
defaultIcName
)
Dim viewName As String = args.NameValuePairs.XFGetValue(
"View",
defaultViewName
)
Dim originName As String = args.NameValuePairs.XFGetValue(
"Origin",
defaultOriginName
)
Dim flowName As String = args.NameValuePairs.XFGetValue(
"Flow",
defaultFlowName
)
Dim ud1Name As String = args.NameValuePairs.XFGetValue(
"UD1",
defaultUD1Name
)
Dim ud2Name As String = args.NameValuePairs.XFGetValue(
"UD2",
defaultUD2Name
)
Dim ud3Name As String = args.NameValuePairs.XFGetValue(
"UD3",
defaultUD3Name
)
Dim ud4Name As String = args.NameValuePairs.XFGetValue(
"UD4",
defaultUD4Name
)
Dim ud5Name As String = args.NameValuePairs.XFGetValue(
"UD5",
defaultUD5Name
)
Dim ud6Name As String = args.NameValuePairs.XFGetValue(
"UD6",
defaultUD6Name
)
Dim ud7Name As String = args.NameValuePairs.XFGetValue(
"UD7",
defaultUD7Name
)
Dim ud8Name As String = args.NameValuePairs.XFGetValue(
"UD8",
defaultUD8Name
)

' Config for if you want to format the threshold value to display.
Dim numberFormat As String = args.NameValuePairs.XFGetValue(
"NumberFormat",
"0.00"
)
Dim numberSuffix As String = args.NameValuePairs.XFGetValue(
"NumberSuffix",
String.Empty
)
Dim includeCurrency As Boolean = ConvertHelper.ToBoolean(
args.NameValuePairs.XFGetValue(
"IncludeCurrency",
"False"
)
)

' Get threshold amount
Dim thresholdMbr As New MemberScriptBuilder(
cubeName,
entityName,
parentName,
consName,
scenarioName,
timeName,
viewName,
accountName,
flowName,
originName,
icName,
ud1Name,
ud2Name,
ud3Name,
ud4Name,
ud5Name,
ud6Name,
ud7Name,
ud8Name
)
Dim thresholdAmount As Decimal = BRApi.Finance.Data.GetDataCellUsingMemberScript(
si,
cubeName,
thresholdMbr.GetMemberScript()
).DataCellEx.DataCell.CellAmount

'Optional Formatting
Dim currencySymbol As String = String.Empty
Dim resultText As String = $"{thresholdAmount.ToString(numberFormat)}{numberSuffix}"
If includeCurrency Then
Dim currencyName As String = consName
Dim currencyObject As New Currency()
If currencyName = "Local" OrElse currencyName = String.Empty Then
currencyObject = BRApi.Finance.Entity.GetLocalCurrency(
si,
BRAPI.Finance.Members.GetMemberId(si, DimTypeId.Entity, entityName)
)
Else
currencyObject = BRApi.Finance.Cons.GetCurrency(si, currencyName)
End If
currencySymbol = currencyObject.Symbol


If currencySymbol = String.Empty Then
resultText = $"{thresholdAmount.ToString(numberFormat)}{numberSuffix} {currencyObject.Name}"
Else
resultText = $"{currencySymbol}{thresholdAmount.ToString(numberFormat)}{numberSuffix}"
End If

End If

Return resultText
End If

Return Nothing
Catch ex As Exception
Throw ErrorHandler.LogWrite(si, New XFException(si, ex))
End Try
End Function
End Class
End Namespace

Hope it helps!

Stuart