Nevrona Designs' Rave Reports is a Report Engine for use by Embarcadero's Delphi IDE.
This is what I call the Rave Endless Loop bug. In Rave Reports
version 6.5.0 (VCL10) that comes bundled with Delphi 2006, there is a
nortorious bug that plagues many Rave report developers. If you have a
non-empty dataset, and the data rows for this dataset fit exactly into a
page (that is to say there are zero widow rows), then upon PrintPreview,
Rave will get stuck in an infinite loop generating pages.
This problem has been previously reported in this newsgroup under the
following headings:
"error: generating infinite pages"; Hugo Hiram 20/9/2006 8:44PM
"Rave loop bug. Please help"; Tomas Lazar 11/07/2006 7:35PM
"Loop on full page of data?"; Tony Chistiansen 23/12/2004 3:41PM
reply to (3) by another complainant; Oliver Piche
"Endless lopp print bug"; Richso 9/11/2004 4:44PM
In each of these postings, there was no response from Nevrona, and no
solution was reported.
Possibly, the problem has also been reported on an allied newsgroup
(nevrona.public.rave.reports.general), to wit:
6. "Continuously generating report"; Jobard 20/11/2005
Although it is not clear to me if (6) is the Rave Endless loop bug or
another problem. This posting did get a reply from Nevrona, but it was
more in relation to multiple regions ("There is a problem when using
multiple regions that go over a page-break.") than the problem of zero
widows.
This is more of a work-around than a true solution. I first posted this work-around on the Nevrona newsgroup (Group=nevrona.public.rave.developer.delphi.rave; Subject="Are you suffering from the Rave Endless Loop bug?: Work-around announced."; Date=13/11/2006 7:06 PM)
So here is my solution. It is more of a work-around than a good
long-term solution, and I hope that Nevrona will give this issue some
serious attention in the near future.
Given your particular report layout, count the maximum number of rows
per page. Let us say that this is 40.
Set up a counter to count the rows within the page (as opposed to rows within the whole report). You could do this either by event script or by a CalcTotal component.
Define an OnBeforePrint scripted event handler for the main data band.
In this event handler set the FinishNewPage property of the main data band to be True when the row-per-page count is one or two below the max (in our example, this would be 38). And set it to False in all other cases. The effect of this is to give every page a non-zero number of widows (in this case 1..38), thus avoiding the condition that gives rise to the Rave Endless loop problem.
Thanks so much for this Sean - unfortunately this wouldn't work for me but I came up with another solution...
You see I have a memo at the top of the region that might expand or contract depending on how many notes the user has left in the database. This means that the number of rows that can fit on a page varies.
However. there is another solution - you use the MaxHeightLeft property of a databand.
All you do is measure the height of your databand, multiply it by 2, and put this in your MaxHeightLeft property. This will force 1 or 2 records onto the next page if it fills up that much.
thank's a lot, this thread helps me out from my problem with endless printing loop in Nevrona Rave...., I set MinHeightLeft to 0,500, this setting is work but i'm not sure that it will work for anothers result set of my query report.
Master,
The solution is MinHeightLeft to 0,500 , i use property wastefit area in true and generated the loop in the second print, but when changed the property MinHeightLeft to 0,500 the error disapear.
Thanks !
Atte
Fabiola Herrera.
Fabi_ucv#hotmail.com
Related
I have a problem that I can't seem to get rid of.
When a customer of mine prints a specific QRP, he gets a "WARNING. This report may extend beyond the printer page margins. Text may be clipped, depending on the printer in use. Do you wish to continue?"
While of course in no way critical, it's a problem due to the sheer number of prints per day this customer has, having to confirm this dialog every time.
I've had this issue before and seemed to be able to fix it by setting the report format to "Custom", but I've recently updated the QRP and the problem is back despite being still set to "Custom". I have also tried A4 (which is the printer's standard page format) and A5, to no avail.
Is there maybe a way to suppress this error in code?
The report itself is way smaller than A4 (it's an A5 format packaging label) so there is no way it would lead to any problems with the print margins, and the prints do come out perfectly fine.
You can use the constant RPT_PrintNoWarn along with SalReportPrint function. The constant is used for suppressing warnings about margin overflow and tiled pages.
It can be combained with constant RPT_PrintNoErrors using pipe symbol.
SalReportPrint ( hWndFrm, strTemplate, strVariables, strInputs, nCopies, RPT_PrintNoWarn|RPT_PrintNoErrors, nFirstPage, nLastPage, nErr )
I am trying to construct a window of object from type TickVo.
I managed to do so using:
TickVO.win:time_batch(1 min)
but my first tick starts for example from 44 miliseconds after midnight, meaning 00:00:00.44.
my question is:
how can i make the window start from 0 miliseconds and end in such.
for example: 00:00:00.44 will be added to the window of 00:00:01
but 00:00:01.15 tick will be added to the window of 00:00:02.
because what happens now is that both 00:00:00.44 and 00:00:01.15 are added to the first tick, since ( as i saw) it is relevant to the starting point.
update: after further investigation, i found out that my solution should rely on
win:ext_timed
but i still haven't figured out the filter i should use as timestamp_expression
The time-batch can take a reference point as a parameter in the form "TickVO#time_batch(1 min, 0L)". The zero tells the runtime to align to 0 millis.
There are a few related approaches on the solution patterns page.
You may find detailed description of how batch windows behave useful.
Session windows are generally done using overlapping or non-overlapping contexts.
I have been struggling with parallel and async constructs in F# for the last couple days and not sure where to go at this point. I have been programming with F# for about 4 months - certainly no expert - and I currently have a series of calculations that are implemented in F# (asp.net 4.5) and are working correctly when executed sequentially. I am running the calculations on a multi-core server and since there are millions of inputs to perform the same calculation on, I am hoping to take advantage of parallelism to speed it up.
The calculations are extremely data parallel - basically the exact calculation on different input data. I have tried a number of different avenues and I continually run into the same issue - it seems as if the parallel looping never gets to the end of the input data set. I have tried TPL, ConcurrentQueues, Parallel.Array.map/iter and all the same result: the program starts out fine and then somewhere in the middle (indeterminate) it just hangs and never completes. For simplicity I actually removed the calculation from the program and I am just calling a print method, and Here is where the code is currently at:
let runParallel =
let ids = query {for c in db.CustTable do select c.id} |> Seq.take(5)
let customerInputArray= getAllObservations ids
Array.Parallel.iter(fun c -> testParallel c) customerInputArray
let key = System.Console.ReadKey()
0
A few points...
I limited the results above to only 5 just for debugging. The actual program does not apply the Take(5).
The testParallel method is just a printfn "test".
The customerInputArray is a complex data type. It is a tuple of lists that contain records. So I am pretty sure my problem must be there...but I added exception handling and no exception is getting raised, so have no idea how to go about finding the problem.
Any help is appreciated. Thanks in advance.
EDIT: Thanks for the advice...I think it is definitely deadlock. When I remove all of the printfn, sprintfn, and string concat operations, it completes. (of course, I need those things in there.)
Is printfn, sprintfn, and string ops not thread-safe?
Another EDIT: Iteration always stops on the last item..So if my input array has 15 items, the processing stops on item 14, or seems to never get to item 15. Then everything just hangs. Does not matter what the size of the input array is..Any ideas what can be causing this? I even switched over to Parallel.ForEach (instead of Array.Parallel) and same behavior.
Update on the situation and how I resolved this issue.
I was unable to upload code from my example due to my company's firewall policy, so in the end my question did not have enough details. I failed to mention that I was using a type provider which was important information in this situation. But here is what I figured out.
I am using the F# type provider for SQL Server and was passing around its Service Types which I suspect are not thread-safe. When I replaced the ServiceTypes with plain old F# Records, the code worked fine - no more deadlocks and everything completed without error.
I've tried every possible fields but can not find the number of times functions are called.
Besides, I don't get Self and # Self. What do these two numbers mean?
There are several other ways to accomplish this. One is obviously to create a static hit counter and an NSLog that emits and increments a counter. This is intrusive though and I found a way to do this with lldb.
Set a breakpoint
Execute the program until you hit the breakpoint the first time and note the breakpoint number on the right hand side of the line you hit (e.g. "Thread 1: breakpoint 7.1", note the 7.1)
Context click on the breakpoint and choose "Edit Breakpoint"
Leave condition blank and choose "Add Action"
Choose "Debugger Command"
In the command box, enter "breakpoint list 7.1" (using the breakpoint number for your breakpoint from step 2). I believe you can use "info break " if you are using gdb.
Check Options "Automatically Continue after evaluating"
Continue
Now, instead of stopping, llvm will emit info about the breakpoint including the number of times it has been passed.
As for the discussion between Glenn and Mike on the previous answer, I'll describe a performance problem where function execution count was useful: I had a particular action in my app where performance degraded considerably with each execution of the action. The Instruments time profiler showed that each time the action was executed, a particular function was taking twice as long as the time before until quickly the app would hang if the action was performed repeatedly. With the count, I was able to determine that with each execution, the function was called twice as many times as it was during the previous execution. It was then pretty easy to look for the reason, which turned out to be that someone was re-registering for a notification in NotificationCenter on each event execution. This had the effect of doubling the number of response handler calls on each execution and thus doubling the "cost" of the function each time. Knowing that it was doubling because it was called twice as many times and not because the performance was just getting worse caused me to look at the calling sequence rather than for reasons the function itself could be degrading over time.
While it's interesting, knowing the number of times called doesn't have anything to do with how much time is spent in them. Which is what Time Profiler is all about. In fact, since it does sampling, it cannot answer how many times.
It seems you cannot use Time Profiler for counting function calls. This question seems to address potential methods for counting.
W/ respect to self and #self:
Self is "The number of times the symbol calls itself." according to the Apple Docs on the Time Profiler.
From the way the numbers look though, it seems self is the summed duration of samples that had this symbol at the bottom of its stack trace. That would make:
# self: the number of samples where this symbol was at the bottom of the stack trace
% self: the percent of self samples relative to total samples of currently displayed call tree
(eg - #self / total samples).
So this wouldn't tell you how many times a method was called. But it would give you an idea how much time is spent in a method or lower in the call tree.
NOTE: I too am unsure about the various 'self' meanings though. Would love to see someone answer this authoritatively. Arrived here searching for that...
IF your objective is to find out what you need to fix to make the program as fast as possible,
Number of calls and self time may be interesting but are irrelevant.
Look at my answer to this question, in particular points 6 and 8.
EDIT: To clarify the point further, suppose the following is the timeline of execution of the program. Some of that time (in this case about 50%) is spent in an activity that can be removed, if you know what it is, such as needless buried I/O, excessive calls to new, runaway notifications, or "insignificant" data validation. If a random-time sample is taken, it has a 50% chance of occurring in that activity, and an examination of the call stack and/or program variables shows that it is doing something that can be removed. Then, if 10 such samples are taken, the activity will be seen on roughly 5 of them, regardless of whether the activity occurs in a few large chunks of time, or many small ones. The activity may be a few lines of code in a function doing something unnecessary, or it may be something much more generalized. Regardless, you recognize it, fix it, and get roughly a factor of 2 speedup. Call counts and self time contribute nothing to this process.
Using ReportBuilder 7.X
Question
Is it possible to Control Print to File.
I need to change the Length of a field at print time
Example:
label2
In the setup - I set its length to 800 which is the max possible this field should ever be.
However, in many cases the record is less than that and i need to set it to the calculated size before printing to file.
Is this possible?
Is it possible to control any portions of this Print to file...at print time (before Print, after print)?
Are the objects avaiable?
We are registered users of the 10.x and above i believe, but have still not gotten around to recompiling are application in Delphi 2009 and the new ReportBuilder....so, that is not an option at this point.
Thanks
Shane
You can try to use the OnDataChange event of the tDataSource that you are using to link your data to your report. This event fires when the current record in the associated dataset changes. In that event, adjust your label to the size for the current record.
i solved this! Each control has a saveLength property. I can just use a global variable that can change at any time (controlling length of entire record). Then just before i print he label, i can set its saveLength property
thanks to all who responded though