Formula won't display when certain fields are null - crystal-reports

Similar to my first question. I want to show my address in a text box containing the fields as follows
{Company}
{AddLine1}
{AddLine2}
{ZIP}{State}{City}
{Country}
The line that concerns me (and hopefully some of you guys) is {ZIP} {City} {State}. What I want to produce is a consistent addressing format, so that there will be no blank space or indentation even if a ZIP, City or State field has been left blank in the DB. This line should still line up with the rest of the rows and not be indented. I also wish to insert commas between zip, state, city where they are relevant and leave them out where not. For this I have written a formula. Below:
If isnull({BILL_TO.ZIP}) or trim({BILL_TO.ZIP})= "" Then "" else {BILL_TO.ZIP}
+
(If isnull({BILL_TO.State}) or trim({BILL_TO.State})= "" Then ""
else(If not isnull({BILL_TO.ZIP}) and length(trim({BILL_TO.ZIP})) <> 0 Then ", " else "") + {BILL_TO.State})
+
(If isnull({BILL_TO.CITY}) or length(trim({BILL_TO.CITY})) = 0 Then ""
else(
If (not isnull({BILL_TO.State}) and length(trim({BILL_TO.State})) <> 0)
or
(not isnull({BILL_TO.Zip}) and length(trim({BILL_TO.Zip})) <> 0)
Then ", " else "")+ {BILL_TO.CITY}))
The problem is that when there is only a city (no state or zip entered) the formula itself will not display. It does however display when the others are present.
Can anyone see a bug in this code??? Its killing me
Thanks for the help.
Look forward to hearing from you guys!

There are a whole lot of if-then-elses going on in that formula so it's hard to tell, but if it's not displaying anything that probably means that you're using a field somewhere without handling its null condition first. Something simpler might be your best bet:
local stringvar output;
if not(isnull({Customer.Postal Code})) then output:=trim({Customer.Postal Code}) + ', ';
if not(isnull({Customer.Region})) then output:=output + trim({Customer.Region}) + ', ';
if not(isnull({Customer.City})) then output:=output + trim({Customer.City}) + ', ';
left(output,length(output)-2)

Create a formula field for each database field. For example:
// {#CITY}
If Isnull({BILL_TO.CITY}) Then
""
Else
Trim({BILL_TO.CITY})
// {#STATE}
If Isnull({BILL_TO.STATE}) Then
Space(2)
Else
Trim({BILL_TO.STATE})
// {#ZIP}
If Isnull({BILL_TO.ZIP}) Then
Space(5) //adjust to meet your needs
Else
Trim({BILL_TO.ZIP})
Embed each formula field in a text object.
Format text object and its fields to meet your need.
** edit **
I you have data-quality issues, address them in the STATE and ZIP formulas (because they will be a constant length). I would add the commas and spacing the text object.

Related

Is there a way to prevent square brackets being inserted into my string?

I seem to be getting some square brackets being inserted into my string that I am using for a dynamic SOQL query. I'm trying to check if the status of an order is one of the options chosen by the user. Usually I would be able to just throw a list after the IN clause, but because this is a string I'm not able to do so. Instead, I have a loop that iterates through the list of selected statuses and adds to the query string as needed.
I've used the exact same syntax in another org with no issues, so I'm curious as to why this would happen in another one. I've posted the version that is having the issue. Hopefully this isn't too tough to remove.
if(orderStatuses.size() > 0){
query += ' AND ccrz__OrderStatus__c IN (\''+orderStatuses[0]+'\'';
for(Integer i = 1; i < orderStatuses.size(); i++){
query += ', \''+orderStatuses[i]+'\'';
}
query += ')';
}
What I want to have is a string that looks something like
'AND ccrz__OrderStatus__c IN ('Completed', 'Order Submitted')'
But instead I get
'AND ccrz__OrderStatus__c IN ('[Completed', ' Order Submitted]')'
I've also tried using the 'replaceAll()' method to forcibly remove them before the query is run, but they still appear anyways.
query.replaceAll('[\\[\\]]','');
When only selecting one option, it formats perfectly fine without any brackets, but once more than one is picked, this happens.
Any and all help would be greatly appreciated on this one. As I mentioned above, this same exact code (granted with different objects, etc.) was giving me the correct results when run in a different org, so I'm stumped. Thanks in advance!
I was able to reproduce your issue by adding the '[' and ']' to your array "orderStatuses". If I was you, I'd look at those square brackets for your error. It is likely that the square brackets you see are literally part of the strings you're passing. There is also an extra space in the orderStatuses[1] that is further telling me you have something being added to the array you don't want earlier in the code/SQL.
var orderStatuses = [];
orderStatuses.push("[Completed");
orderStatuses.push(" Order Submitted]");
var query = ' AND ccrz__OrderStatus__c IN (\'' + orderStatuses[0] + '\'';
for (var i = 1; i < orderStatuses.length; i++) {
query += ', \'' + orderStatuses[i] + '\'';
}
query += ')';
alert(query)

insert and delete text after an Range-position in Word

I have a SET-field in Word 2007. After the set-field there could be everything (text,bookmark, SET field,...). I want to add a text (e.g. "exampletext") in between.
After this I want to delete this inserted text (but I don't want to search through the whole document).
Is there a method?
Trial 1 (it inserts it in the field - and not after the field):
' xStartReturn is a field
Dim myExampletext As WordApp.Range = objDoc.Range(xStartReturn.Code.End, xStartReturn.Code.End )
myExampletext.Text = "exampletext"
Trial 2 (leads to the problem that I don't get the Range-field to delete the exampletext afterwards):
xEndeReturn.insertAfter("exampletext")
Trial 3:
'xStartReturn.Code.End + 1 doesn't work.. but I found out that the "}"-Sign in the setField is +20 after xStartReturn.Code.End. Theoretical this should work - but there could be e.g. also paragraph afterwards.
'-> I can automatically check that there is a paragraph - but why is the exampletext added **after** the paragraph?
Dim example As WordApp.Range = objDoc.Range(xStartReturn.Code.End + 20, xStartReturn.Code.End + 20)
example.Text = "exampletext"
Dim later As WordApp.Range = objBasisvorlage_.Range(objXStartReturn.Code.End + 20, objXStartReturn.Code.End + 20 + "SDFSD".Length) 'this is wrong?!
later.Delete()
The following works for me. Since you didn't give us a minimum code with which to reproduce the problem I don't know how relevant the framework is that I used. But you should be able to follow the steps.
Watch what I do with r_f_Code (field code range). You can ignore/remove r_f_Result as I had that in for reference and debugging purposes.
Collapsing the field code range to its end-point leaves the range just within the field braces. Moving the starting point one character to the right puts it just outside the braces, but before anything else. (Note: I tested with two immediately adjacent SET fields.)
My code then enters some text and bookmarks it. That's the only way you do what you ask if what follows the SET field can be "anything". Although I suppose you could insert a Content Control - that would be uniquely identifiable if you go about it correctly...
Sub PositionAfterFieldCode()
Dim f As word.Field
Dim r_f_Code As word.Range, r_f_Result As word.Range
For Each f In ActiveDocument.Fields
If f.Type = wdFieldSet Then
Set r_f_Code = f.code
Set r_f_Result = f.result
'Debug.Print Len(r_f_Code), r_f_Code.Text, Len(r_f_Result), r_f_Result.Text
r_f_Code.Collapse wdCollapseEnd
r_f_Code.MoveStart wdCharacter, 1
'r_f_Code.Select
r_f_Code.Text = "abc"
r_f_Code.Bookmarks.Add "AfterSet", r_f_Code
Exit For
End If
Next
End Sub

crystal reports trimming strings

I’m new on crystal reports and don’t have much knowledge of programming. I’m looking for a formula that will separate the notes (example: To Syd+We miss you+From Bill&Pat) into 3 different field. Any help would be greatly appreciated.
local stringVar subject := 'To Syd+We miss you+From Bill&Pat';
local numberVar location := instr(subject, '+');
if location > 0 then
left(subject, location)
else
subject;
I have hardcoded the string to be modified, but you can replace it with {table.field}
Also, if there will definitely always be + you can simplify things by removing the if.
a note that Lee's answer will get you the leftmost bit of text only.
instr(subject,"+") returns the location of the leftmost presence of +
left(subject,location) pulls out a chunk of subject of 'location' number of characters
if you then wanted to fish out the second and third bit, you could do this:
local stringvar subject := "string1+string2+string3";
local numberVar location1;
local numberVar location2;
location1 := instr(subject, "+");
location2 := instr(location1+1, subject, "+");
/////this instr only starts to look from location1 for the next leftmost + and I'll show below how you can use
( if location1 > 0
then left(subject, location1-1)
/////use Lee's 'left' command to bring up the first bit, I added the minus1 so that the actual + would not show
else "missing first +" )
+chrw(13)+ //I was displaying this on screen so I added a ENTER, you can get rid of this line
( if location2 > 0
/////error checking is sanity-saving sooner or later
then
(
mid(subject, location1+1, location2-1-location1)
/////pulls a chunk from within subject, starting at location1+1 [to get past the + at location1 itself],
/////going rightward to grab 'location2-1-location1' characters
/////(play a few times with the +1/-1 to get hte idea.
/////try it with a two-character seperator, say "To john12Hello12From jane", helped me get my head straight
+ chrw(13)+ //again, this is just for my proofing
right(subject, length(subject)-location2)
/////pulls a chunk from the right of subject, of size 'length of subject' minus location2,
/////so everything from the end until hit that +
)
else "missing second +" )

Crystal Reports - Help displaying multiple Report Fields with one Formula

I am not a programmer by any means. I am but a curious lowly administrator attempting to modify a report for my needs. I have a Crystal Reports .rpt file that shows Purchase Orders and payments against those purchase orders. My problem is that the payment lines don't reference the purchase order number. Currently, I have to export the report then go through in excel and manually match each AP line to its matching Purchase Order number. I would like the AP line to also show the Purchase Order number.
There is a field in the report called "#Voucher_PO_ID" with the following formula in it:
if {LAGL019Q.RECORD_TYPE} = "3" then
if {LAGL019Q.SOURCE} = "AP" then
{LAGL019Q.TRANS_REF_NUM}
else if {LAGL019Q.SOURCE} = "PO" or {LAGL019Q.SOURCE} = "RQ" then
{LAGL019Q.PO_ID}
else " "
else " "
As I understand it, this formula is saying if the SOURCE is an AP (accounts payable) then for that line show the TRANS_REF_NUM (the check number for the payment), but if the SOURCE is a PO (purchase order) then show PO_ID (the purchase order number).
Again, knowing very little about programming, I was hoping it would be something as simple as modifying the if then statement to:
if {LAGL019Q.SOURCE} = "AP" then
{LAGL019Q.TRANS_REF_NUM} and {LAGL019Q.PO_ID}
But this does not work. I can append some text to the end of {LAGL019Q.TRANS_REF_NUM} by adding {LAGL019Q.TRANS_REF_NUM} + "blah" so I'm not sure why it won't add another field.
It just won't let me change this part of the formula:
" if {LAGL019Q.SOURCE} = "AP" then
{LAGL019Q.TRANS_REF_NUM}"
If I simply try:
if {LAGL019Q.SOURCE} = "AP" then
{LAGL019Q.PO_ID}
It still won't work and I'm not sure why? IF its an accounts payable line, I want it to show the corresponding PO_ID. It just shows a blank field when I do this even though I know the AP line has a corresponding PO.
I'm guessing there is some larger thing I am unaware of regarding how the actual database is setup. Maybe AP lines don't actually reference the PO_ID and I'm just assuming they do.
Most google searches I did brought be back here so I thought I'd post my problem. I've searched similar questions and they are mostly out of my league. Thanks ahead for any suggestions.
I think your only problem is that you're trying to use a logical operator (the AND keyword) instead of a string operator (The + or & characters). Hopefully it's as simple as this:
if {LAGL019Q.RECORD_TYPE} = "3" then
if {LAGL019Q.SOURCE} = "AP" then
"This is the transaction#: " + {LAGL019Q.TRANS_REF_NUM} +
", and this is the PO ID: " + {LAGL019Q.PO_ID}
else if {LAGL019Q.SOURCE} = "PO" or {LAGL019Q.SOURCE} = "RQ" then
{LAGL019Q.PO_ID}
else " "
else " "
If the {LAGL019Q.PO_ID}="AP" then this should result in:
This is the transaction#: <TheActualNumber>, and this is the PO ID: <TheActualPOID>
EDIT1: One other thought: How sure are you that the database actually holds valid PO#s for these records? If you tried to use if {LAGL019Q.SOURCE} = "AP" then {LAGL019Q.PO_ID} and it turned up blank, then that's a pretty good indicator that {LAGL019Q.PO_ID} is actually null for that record.

Format a variable in iReport in a string with multiple fields

I have a text field that has the following expression:
$F{casNo} + " Total " + $P{chosenUom} + ": " + $V{total_COUNT}
casNo is a string, chosenUom is a string. total_COUNT is a sum variable of doubles. The total_COUNT variable displays, but it's got 8 - 10 decimal places (1.34324255234), all I need is something along the lines of 1.34.
Here's what I tried already:
$F{casNo} + " Total " + $P{chosenUom} + ": " + new DecimalFormat("0.00").format($V{total_COUNT}).toString()
Any help would be appreciated
For now I'm just doing basic math, but I'm hoping for a real solution, not a workaround
((int)($V{total_COUNT}*100.0))/100.0
You can format the in lline numbers by using:
new DecimalFormat("###0.00").format(YOUR NUMBER)
You might split the text field into two, one containing everything but the $V{total_COUNT}, and the second containing only $V{total_COUNT}, but with the Pattern property set to something like "#0.00".
You'd have to get a bit creative with layout, though, to prevent unwanted word-wrapping and spacing; for example, first text field could be wide and right-aligned, while text field containing the count could be left-aligned and wide enough to accommodate the formatted number.