Example
We Have built a quote in Quote Entry, with 25 lines.
We have applied a discount (say 10% to 30%) on most of those lines.
We later amend the quote qty per line (from say 10 to 11) and the discount % reverts to 0%.
We have to manually add in the discount %.
Epicor state that this is working as it should.
Our choices are to apply a fixed discount % via pricelist or by customer.
However neither of these work for us.
We tailor our quote to land a big order with a customer and will apply a bespoke discount per line according to the deal we are trying to win.
Is it possible to set a BPM (or similar) so that when the QuoteDtl.ExpectedQty field changes from āanyā to āanotherā - the QuoteDtl.DiscountPercent does not change?
I tried a BPM to instruct the QuoteDtl.DiscountPercent to = QuoteDtl.DiscountPercent when the qty field changed, but it didnāt work, it reverted to 0.
In reality, our quote can be 100+ lines long and so amending the discount % line by line is incredibly tedious for sales so if we can instruct it to remain in place unless over-typed, that would be fantastic!
There is a similar issue when changing the ShipTo. The prices all revert back to $0.00.
Iāve seen a suggestion were you add a UD field to the line, to hold the value you want to keep. Then with a pre-proc BPM, copy the real value in the QuoteDtl to the UD field. Then in a post-proc BPM, copy the UD value back to the QuotDtl field.
Not sure which BO Method(s) youād need to hook into. Use Trace to see which ones fire.
Youāll need to save both the QuoteDtl.DiscountPercent and QuoteDtl.DocDiscount fields. So youāll need 2 UD fields
end edit
The following appears to work:
Two Method Directives as shown below
Method #1 (the Pre-Proc)
Set the UD field to the current DiscPct. Note that I didnāt add a UD field, but just used the field Rpt1Discount. You should add the UD field and use that
I am winning at 75% of this.
pre Processing on: Erp.Quote.ChangeSellingExpQty
set new UD field to store QuoteDtl.Discount, yes this works
set new UD field to store QuoteDtl.DiscountPercent, yes this works
Post Processing on on: Erp.Quote.ChangeSellingExpQty
set QuoteDtl.Discount to equal the new QuoteDtl Discount UD field, No not working, stays wiped at 0.00
set QuoteDtl.DiscountPercent to equal the new QuoteDtl Discount PercentUD field, yes working.
Iām guessing that this is because the quotedtl.discount field is already a calculated field based on several āifā clauses?
field help on quotedtl.discount:
QuoteDtl.DiscountPercent * (QuoteQty * UnitPrice). This field can also be directly updated by the user, However it is refreshed whenever the DiscountPercent, UnitPrice or OrderQty fields are changed?
When I first enter a discount %, the discount amount does not change, see here where the discount% is set to 10 but the actual discount value remains at 0:
This occurs a long way under the āGetUnitPriceInfoā method name, but itās the closes method I can see listed before the 10% discount is displayed:
The actual discount value doesnāt change until much further along the trace log, under the āUpdateā method name:
Erp.Proxy.BO.QuoteImpl
Update
[removed lots of lines inbetweenā¦.]
10.00
3.80
3.80
Long story short, Iāve tried to implement the Quotedtl.discount field to restore back to itās original content (via the new ud field) under the update method instead, but I still get nothing.
Iāve set up an extra new ud field which will take the value of the saved discount amount, so I know I can
a) save the quotedtl.discount value and
b) set another field to take that value
I just canāt get it to work on quotedtl.discount!
It does when I first enter a discount %
The discount amount is 0.00 until I save
If I then change the expected selling qty, the discount % now remains in place (e.g. 10%) but the discount amount reverts to 0.00, and save/refresh does not pull in the correct amount, or any change at all, it stays at 0.00
so I have discount 10%, but discount amount 0.00
We have some similar issues with special rates, which I could only solve by forcing changes to the QuoteQty table, because at some hard-to-define points the QuoteDtl fields seem to re-set to the same as QuoteQty. May be worth exploring?
Hereās the thread where I was wrestling with it.
Iāve got to get out of the office now so anything else will have to wait until tomorrow, Iām afraid. But in general terms, I found that there are some fields in QuoteDtl that, if youāre changing them programmatically, need to be changed in the associated QuoteQty rows(s) as well if you want them to stick. I assume there must be a correct approach that can handle it all in the background as the native UI does, but I havenāt found it. For me, QuoteDtl keeps reverting to QuoteQty and I canāt stop it so I have to make sure both are the same before it happens.
Something I just realizedā¦ You donāt want to save the existing Discount amount, but rather recalculate it based on the qty and Price (which could get tricky if you use price breaks).
Also ā¦ What if you try setting the DiscountPct first (before setting Discount) - since the Disc amount is based on that. Especially since the UI flows that way (you tab to the DiscPct first)
For completeness, hereās the code which is now working for us. Itās from a uBAQ rather than a BPM, but the same BO applies for both.
// Update QuoteQty with changed prices (necessary before setting QuoteDtl price, otherwise QuoteDtl price will reset to this)
// note: if quantity breaks can be used then checks to update only the correct row will be needed
foreach (var ttRow in ttResultsUpdate)
{
int qline = ttRow.QuoteDtl_QuoteLine;
foreach (var qqty in (from row in q.QuoteQty where row.QuoteLine == qline select row))
{
decimal docprice = ttRow.QuoteDtl_DocExpUnitPrice;
if (qqty.DocUnitPrice != docprice || qqty.PricePerCode != ttRow.QuoteDtl_ExpPricePerCode)
{
decimal price = Decimal.Round(docprice / exrate,2);
qqty.UnitPrice = price;
qqty.DocUnitPrice = docprice;
qqty.PricePerCode = ttRow.QuoteDtl_ExpPricePerCode;
qqty.RowMod = "U";
upd = true;
}
}
}
if (upd)
{
svc.Update(ref q);
upd = false;
}
// Update main QuoteDtl with changed prices or discounts
foreach (var ttRow in ttResultsUpdate)
{
int qline = ttRow.QuoteDtl_QuoteLine;
foreach (var qdtl in (from row in q.QuoteDtl where row.QuoteLine == qline select row))
{
decimal docprice = ttRow.QuoteDtl_DocExpUnitPrice;
decimal disc = ttRow.QuoteDtl_DiscountPercent;
if (qdtl.DocDspExpUnitPrice != docprice || qdtl.ExpPricePerCode != ttRow.QuoteDtl_ExpPricePerCode)
{
qdtl.DocDspExpUnitPrice = docprice;
qdtl.ExpPricePerCode = ttRow.QuoteDtl_ExpPricePerCode;
qdtl.RowMod = "U";
svc.GetDtlUnitPriceInfo(true,false,ref q);
svc.GetDtlUnitPriceInfo_User(true,false,false,true,ref q);
qdtl.RowMod = "U";
upd = true;
}
if (qdtl.DiscountPercent != disc)
{
qdtl.DiscountPercent = disc;
qdtl.RowMod = "U";
svc.GetDtlUnitPriceInfo(true,false,ref q);
qdtl.RowMod = "U";
upd = true;
}
}
}
if (upd)
{
svc.Update(ref q);
upd = false;
}
Obviously itās incomplete as itās part of a larger piece of code weāre using, but when we do this the discounts and prices do stay in place. The key is the additional method calls which do the recalculation, I think, and for us (as I said) making sure the QuoteQty doesnāt conflict.
Iām sure this is the approach to take. Iād just add a couple of caveats based on the fact that Iāve been wrestling with Quotes on and off for months now:
Although calculating the fields (as per your Set Argument) mostly works fine, it can cause sporadic problems. Itās more reliable to call the methods in the Quote BO that do it for you, and I think in this case it just needs GetDtlUnitPriceInfo with the right parameters after setting DiscountPercent.
Sometimes you need an extra step to make sure the changes show up in the client. It shouldnāt the way youāve done it, but Iām never surprised when it is needed.
Annoyingly,I can get the discount % to stick but still canāt get the discount amount to recalculate in the QuoteDtl.Discount or QuoteDtl.DocDiscount fields.
Iāve tried setting the variable to generate the new discount amount as :
Iāve also set a new UD field to store this value just so I can run SQL and check it works, and it does. So I can trust the build to a fair extent, but it seems that QuoteDtl.Discount and QuoteDtl.DocDiscount are protected by a force field and I canāt push a value in there.
Iāve tried on
Quote >
ChangeSellingExpQty
GetUnitPriceInfo
Update
I could set the new UD field to be our discount amount but the work then needed to amend every report and other calculation feeding from it would be insane.