XlEventRegister to catch event xlCalculationEnded - xll

I am trying to implement the xlCalculationEnded event using xll sdk. Used XlEventRegister to register the same in my xll addin which is compiled as .xll file. Checked Steve Dalton's book on xll sdk and msdn , don't see any example or documentation on how to implement this event.
Tried googling , no luck.
Please provide an example if there is one.
Note: I have implemented udf which gives me selected range of data, but if there are Excel builtin or any other add-in related functions in the same range, I am not getting calculated values, rather it call udf before excel completes the calculation. That is the reason why I am trying to register the above call back which can give me info on Excel calculation.

I have just tested this code and it works , the event is fired at every calculation. I have just added an Event function and modifiy a bit :
1- Modify in xlAutoOpen(void)
Excel12f(xlEventRegister, 0, 2, (LPXLOPER12)TempStr12(rgFuncs[i][0]), TempInt12(xleventCalculationEnded));
to
Excel12f(xlEventRegister, 0, 2, (LPXLOPER12)TempStr12(L"EventOnCalc"), TempInt12(xleventCalculationEnded));
2- create the event function :
__declspec(dllexport) void WINAPI EventOnCalc()
{
Excel12f(xlcAlert, 0, 1, TempStr12(L"On Calc event !"));
}
I tested and the EventOnCalc() event is fired.

Related

how to limit edit events on dynamic form changes

I'm working on a form building app, and I use an event of type edit, each time updating the form in the DB.
But the problem is that my form builder auto saves each change which causes a lot of edit events to occur.
Is there a way to limit the edit events creation, like only consider the last change in the form as an edit event?
You want some underscore power.
var saveFunction = function(dataToSave) { ... },
debouncedSaved = _.debounce(saveFunction, 700);
In this example, debouncedSaved will only be eventually called if left idle for 700 milliseconds.
It should be easily adapted to your code, you can use debounced functions as event handlers since they're still classic functions.

Data initialize is called before Report Start in Active Reports (Data dynamics)

Per Active reports documentation, the Report start is called first and Data initialize. Any reference to Data source inside Report start will invoke Data Initialize event. I am modifying an existing report; and to my surprise the order is reversed. I have an existing logic to get the count of nodes (my datasource is xml) in data initialize event; just because the event firing sequence is reversed, I am getting 0 as count always.
I am using Active reports for .NET 2.0 ( I think the version is 4.*). As I dont have support for the designer, I have the designer xml and code behind.
Please suggest what could force the event sequence to correct order.
There is probably not enough information for us to help you here. We'd need to see the report code at least, but better if you can do some debugging to find out more detail about what specific code you have that is causing the trouble.
I'm actually not sure about event order in this specific case, but to troubleshoot you could try with a new blank report to verify the event order in that case and move over one piece of code at a time to find out which line of code causes the event order to change.

Flex's FileReference.save() can only be called in a user event handler -- how can I get around this?

I need to call FileReference.save() after a web service call has completed, but this method has a restriction: "In Flash Player, you can only call this method successfully in response to a user event (for example, in an event handler for a mouse click or keypress event). Otherwise, calling this method results in Flash Player throwing an Error exception." (from the documentation here)
This restriction is a bit vague. Does it mean that I can only call the FileReference.save() method from within an event handler function that is registered as a listener for certain types of user events? If so then exactly which user events are valid? (Perhaps there's an event that will never be dispatched by user interaction with my application and I could register an event handler function for that event type and make the save() call from within that function?)
My difficulty is that I can't safely call the FileReference.save() method until my web service returns with the data that will be used as the argument of the FileReference.save() method call, so the event that triggers the FileReference.save() call is actually a ResultEvent rather than a user event, and I'm leery of dispatching a new (faux) user event type in order to be able to trigger the FileReference.save() call unless it's definitely a user event that would never be dispatched as a result of actual user interaction with my application.
In a nutshell what I'm doing now is this: I have a function that is registered as a handler for a button click. In this function I make my web service call to fetch data from the server. I also have a result handler function which gets invoked when the web service call completes, and it's in here that I want to call the FileReference.save() method since it's at this point that I know that the data is ready to be saved to a file. But the aforementioned restriction is blocking me from doing this -- I get an error:
Error #2176: Certain actions, such as those that display a pop-up window,
may only be invoked upon user interaction, for example by a mouse click
or button press.
I've tried many things to get around this such as creating a second mouse click event handler function with the FileReference.save() call within and calling it after a timeout interval (to give the web service time to complete), but I keep running into the same error -- maybe that approach doesn't work since the second function isn't registered as an event listener for the event type used as its argument.
I'm new to Flex development so perhaps I'm just not thinking about this in the right way. If anyone can suggest another approach I'd really appreciate it. Thanks in advance for your comments or suggestions.
--James
Adobe does this as a sort of security measure to ensure users are the ones messing with files rather than potentially harmful code. My understanding is that they enforce this by only allowing handlers of (click?) events that originate from UI components to execute the FileReference methods, so generating your own events programmatically will not work, although I have not tried to verify this. Unfortunately the best resolution I've found is to re-work the UI a bit to conform to this constraint. In your particular situation, you could make this a two click process with a button that says something like "Prepare Download", which changes to "Download File" after the web service is complete. This is less than ideal from a user perspective, but I don't think there's much else that can be done unless you can somehow complete your web service call prior to displaying the button that triggers the FileReference.save() call.
After struggling for that for well, a couple hours I found a workaround: you can use both mouseDown AND mouseUp events instead of just click.
For instance:
s:Button
mouseDown="prepare_PDF()"
mouseUp="save_PDF()"
Works fine for me!
Happy coding!
--Thomas
As a workaround I used the ExternalInterface class. I created a javascript function with this code
function downloadFile (url) {
window.open(url);
}
An in AS3 I call
var url = 'www.example.com/downloadfile.php?file_id=xxx';
ExternalInterface.call('downloadAttachmentFile', url);
So with that I transfer the file handling to JS/HTML.
This is a comment on Thomas' answer (I don't have enough XP to comment yet): The mousedown and mouseup workaround works nicely. Just a note that if you make any changes in prepare_PDF() that need 'undoing' in save_PDF(), then its a good idea to call that code on the mouseout event as well, since there might be a case that the user mousedown's on the button, but then moves the mouse away from the button.
This was particularly relevant for my case, in which we increase the size of a watermark on an image when the user clicks the download button (that triggers the .save() call). I reduce the size of the watermark down to normal on the mousedown and mouseout events.
I had this same issue, I chose to use flash.net methods. Call flash.net.navigateToURL(url); from an actionscript or navigateToURL(url); from mxml.
What i do to solve this is to show an alert message with an anonymous function so i don't have to create a button.
Alert.show("Do you wish to download the file?", "Confirm", Alert.OK | Alert.CANCEL, this, function (eventObj:CloseEvent):void {
if (eventObj.detail == Alert.OK) {
fileReference.save(zipOut.byteArray, dateFormater_titulo.format(new Date ()) + ".zip");
}//if
}/*function*/, null, Alert.OK);

Event Capture in classic ASP (vbscript) - is this possible?

We have just purchased some software that provides an API into our phone system allowing us to dial, hangup etc.. The API was designed to be used client side (internet explorer / activex). We want to use this server side and execute the dial commands via an ajax call to a classic ASP script.
The basic VBScript for initialising the component is as follows:
<%
set objPhone = server.createobject("XariosPhoneManager.PhoneManager")
objPhone.RemoteHost = "192.168.0.17"
objPhone.RemotePort = "2001"
objPhone.OAIPassword = ""
objPhone.Extension = "1000"
objPhone.Initialise()
set objPhone = nothing
%>
but I can't call the dial command
objPhone.MakeCall("1001")
until the "initialised" event has happened. Is there a way in classic ASP to wait for an event to fire before executing some code?
Not the most graceful of solutions but you could catch errors then loop and re-try the call if it fails then you try again - you could put a pause in the loop to give the process chance to finish. You could also put a limit on the number of tries so that it does eventually give up and not end up in an infinate loop. Something like (not complete or tested):
numTries = 0
processComplete = False
Do Until processComplete or numTries>=10
On Error Resume Next
'## YOUR CODE TO CALL THE PROCESS HERE
On Error Goto 0
numTries=CDbl(numTries)+1
Loop
I don't know anything about this component so the following involves some guesswork.
1) If the component has a property to track when it is initialised, you can check that and once it is initialised, call the MakeCall method.
2) I am guessing that the component has a OnInitializedComplete event(or something like that), if so, write your server side code in JScript and assign a function to the event.
turns out it simply isn't possible in ASP. There's no property exposed that says the component is initialised, just the initialised event that fires. Unfortunately ASP cannot detect events. The developer has suggested wrapping their component in a new DLL that takes care of the event management, but I don't have the resources to do that. They have promised true serverside capability in a future version of the software

How to determine currently processed event in ActionScript?

When one call Clipboard.generalClipboard.getData() in ActionScript outside of Event.PASTE processing function it fails with following message
The Clipboard.generalClipboard object may only be read while processing a flash.events.Event.PASTE event.
Even if I dispatch Event.PASTE event and call this function within event handler it still fails.
How does it determine which event is currently being processed?
you need to lister for the real paste Event from the stage and not simulate it. This is a security issue so flash apps do not read your global clipboard data, only on user paste action.

Resources