GVSetNamedInt with window/chart ID info

Questions about MultiCharts and user contributed studies.
kernel
Posts: 91
Joined: 19 Feb 2013
Has thanked: 21 times
Been thanked: 4 times

GVSetNamedInt with window/chart ID info

Postby kernel » 28 Dec 2015

Hi,

When using GVSetNamedInt to communicate, is there any way that you also explicitly include the window/chart ID of the sender? With that info attached, the receiver may be able to tell who the sender is even if you have multiple windows/charts that contain the same instrument and time frame.

Thanks,

-kernel

janus
Posts: 770
Joined: 25 May 2009
Has thanked: 45 times
Been thanked: 91 times

Re: GVSetNamedInt with window/chart ID info

Postby janus » 28 Dec 2015

Not sure. I use another approach by setting an input variable for each indicator to a unique number and constructing a named integer that incorporates that number. That way the "receiver" can check each broadcasted value. I also use another named integer to inform the "receiver" when there's a new update, and the "receiver" acknowledges it by setting it to another value so that the 'sender" can do some cleaning up.

kernel
Posts: 91
Joined: 19 Feb 2013
Has thanked: 21 times
Been thanked: 4 times

Re: GVSetNamedInt with window/chart ID info

Postby kernel » 29 Dec 2015

Janus,

Thank you for your reply. That's exactly what I did. By incorporating symbol name and time frame into the broadcast message. How ever, if I have two charts/windows with the same instrument and TF, I need to incorporate more info to be able to tell them apart. This piece of info needs to be unique to the particular chart/window, and also needs to be aware of by both the sender and receiver in the chart. Intuitively what I can think of is the chart identifier, the question is, how do I get hold of it, is there any function to call?

One thing I didn't get from your description is, with GVSetNamedInt/GVGetNamedInt, why do you need another integer to "inform the receiver when there's a new update"? and how? My understanding is communication via GVSetNamedInt/GVGetNamedInt is performed in a timely manner (asychronous pooling?). ...however, if you can prevent the receiver from pooling and put it to sleep, and later on nudge him to wake up when new updates available, a lot of resources can be saved on frequent passive pooling.
Last edited by kernel on 30 Dec 2015, edited 1 time in total.

janus
Posts: 770
Joined: 25 May 2009
Has thanked: 45 times
Been thanked: 91 times

Re: GVSetNamedInt with window/chart ID info

Postby janus » 29 Dec 2015

This is the way I would do it. I would be set the reference input value for one chart indicator to 1 and the reference input value for the other chart indicator to 2. Let's call this input variable "id". That way the "receiver" can determine which of the two sent the message by checking the corresponding named variable. The named variable would be constructed from the id value. The indicator on both charts would use text("xxx_",id:0:0) as the named variable. I use a second "acknowledgment" variable to know whether the variable has been updated or not. So the process is a follows:

Indicator on chart 1 with input variable id = 1
1. Indicator "broadcasts" a new value for named variable xxx_1
2. Indicator "broadcasts" a value of 1 for named variable update_1

Indicator on chart 2 with input variable id = 2
1. Indicator "broadcasts" a new value for named variable xxx_2
2. Indicator "broadcasts" a value of 1 for named variable update_2

Indicator on "receiver" chart
1. Indicator checks if variable update_1 = 1
2. If = 1 then get the new value for xxx_1 and set update_1 = 0
3. Indicator checks if variable update_2 = 1
4. If = 1 then get the new value for xxx_2 and set update_2 = 0
5. Use any new values for the purposes required (you can also use timers to check if any expected updates failed to come through and warn appropriately; eg, one of the "send" indicators stopped working).
6. .....

If you do not need to have such syncing then you can skip the update_? parts. You can sync the other way to inform the "sender" when the updated value was retrieved for whatever purpose. In that case the "receiver" would set the update variable not to 0 but to 2 and the "sender" would check for that, clear it and do whatever is required as a consequence.

Of course there could be a situation where xxx_? is updated multiple times before the "receiver" gets a chance to read it. This depends on the time frames used. One way to minimize this is to set the "receiver" indicator to update on every tick and check for any update regardless of the barstatus value. You can go one step more and use RecalcLastBarAfter(1) to force the indicator to check even when there is no update tick. What you then do depends on your requirements. For example, you may not use any updated value straight away but delay until barstatus = 2. You can modify the procedure above to pass extra information to fine tune the way the "receiver" processes the new information. For example, you can pass on the corresponding barstatus information if they are sending on every tick. It all depends on what your requirements are. As you can tell it can get messy so it might need some careful design before implementing the solution.

There is another more sophisticated way to buffer the values in array with time stamps but it would involve a multi-threaded DLL with a "master" thread to co-ordinate and feedback the appropriate values one at a time. I doubt this is necessary for your circumstance but I don't know enough of your requirements to make a definitive statement.

Hope this helps.

User avatar
JoshM
Posts: 2099
Joined: 20 May 2011
Location: The Netherlands
Has thanked: 1526 times
Been thanked: 1504 times
Contact:

Re: GVSetNamedInt with window/chart ID info

Postby JoshM » 30 Dec 2015

When using GVSetNamedInt to communicate, is there any way that you also explicitly include the window/chart ID of the sender?
`GetAppInfo(aiAppId)` returns an unique non-zero integer that identifies the calling application/environment, according to its wiki page. If memory serves me right, I thought it was a window handle (HWND), so not only unique in the MultiCharts program but also separate from other Windows programs running. Anyway, worth looking into I guess.

janus
Posts: 770
Joined: 25 May 2009
Has thanked: 45 times
Been thanked: 91 times

Re: GVSetNamedInt with window/chart ID info

Postby janus » 30 Dec 2015

Yes I also thought of GetAppInfo(aiAppId) but it's not much use to the "receiver". How will it now which chart window it came from? That's why the "sender" indicator using an input variable with a unique predefined number as I illustrated would work. The user can then write code knowing which indicator has updated a global variable and where it came from. When I use DLLs I apply the following to distinguish (within the DLL) who is updating what for which plot in any chart window:

text(getsymbolname,"_",getstrategyname,"_",getappinfo(aiappid):0:0,"_",basedatanumber:0:0,"_",barinterval:0:0,"_",bartype_ex:0:0);

Could be used with simple global variables to determine the same sort of thing but not really necessary. I think my other approach is far simpler and more effective.

kernel
Posts: 91
Joined: 19 Feb 2013
Has thanked: 21 times
Been thanked: 4 times

Re: GVSetNamedInt with window/chart ID info

Postby kernel » 30 Dec 2015

janus,

I put a 0/1 padding to the broadcast message yesterday to differentiate the two instances with the same instrument and TF, just like you said you'd do. That provides a temporary fix for now. For the long haul, if you have more than a dozen of chart windows spreading over different instruments and TFs, manual editing the constructed message may appear to be less pleasing than simply incorporating the chart window handle , which is unique among windows and thus requires no manual editing.

If I understand it correctly, GVSetNamedXXX/GVGetNamedXXX pair utilizes asynchronous passive pooling internally, there's no way that you put one to sleep. That being said, checking variable update_1 before actually updating variable xxx_1 might be unnecessary and thus variable update_1 might be redundant. In my script, one variable serves two purposes, I simply let the receiver compares the new with the old to see if new update arrives. The reason behind is , since you cannot put one into sleep, why bother sending two messengers (one "notifies") when you can have the job done with just one?

kernel
Posts: 91
Joined: 19 Feb 2013
Has thanked: 21 times
Been thanked: 4 times

Re: GVSetNamedInt with window/chart ID info

Postby kernel » 30 Dec 2015

JoshM,

I looked GetAppInfo(aiAppId) the other day, scanned through the available returns to see if I could find something unique to the chart window. My eyes paused for a second or two on the phrase "an unique non-zero integer identifying the calling application"....I guess I wasn't sure what "the calling application" means there perhaps.....kinda overlooked. But thanks for prompting me on that, as you've always been helpful. :-) If it were the handle to the chart window, that'd be exactly the piece of info I've been looking for.

janus
Posts: 770
Joined: 25 May 2009
Has thanked: 45 times
Been thanked: 91 times

Re: GVSetNamedInt with window/chart ID info

Postby janus » 30 Dec 2015

janus,
If I understand it correctly, GVSetNamedXXX/GVGetNamedXXX pair utilizes asynchronous passive pooling internally, there's no way that you put one to sleep. That being said, checking variable update_1 before actually updating variable xxx_1 might be unnecessary and thus variable update_1 might be redundant. In my script, one variable serves two purposes, I simply let the receiver compares the new with the old to see if new update arrives. The reason behind is , since you cannot put one into sleep, why bother sending two messengers (one "notifies") when you can have the job done with just one?
Yes you are right that it's probably redundant but I like to be sure. Also, I might have a situation where the updated value is the same as the previous one but for another bar. It depends on what information I'm "broadcasting". I suppose in that case a time stamp could be employed. That's what I did a long time ago when I used my own version of global variables in DLLs. At the time I needed to buffer them so that the "sender" could broadcast multiple values before the "receiver" even had a chance to read them. I no longer need that procedure so I reverted back to using standard global variables.

arjfca
Posts: 1283
Joined: 23 Nov 2010
Has thanked: 724 times
Been thanked: 222 times

Re: GVSetNamedInt with window/chart ID info

Postby arjfca » 05 Jan 2016

Hi,

When using GVSetNamedInt to communicate, is there any way that you also explicitly include the window/chart ID of the sender? With that info attached, the receiver may be able to tell who the sender is even if you have multiple windows/charts that contain the same instrument and time frame.

Thanks,

-kernel
What I did to resolve that is to put an Input to the indicator that is installed on every charts. For my case, each instruments has 3 charts

Then, I put on a text line, the chart number attached. This way, I always have an idea on which time frame or sub charts I'm working on. I also added on the chart # info, the actual spread of the instrument. A little hint to prevent trading in an un liquid or to liquid time.

Code: Select all

Input:
ShowLastPriceLine (True),
LastPriceColor (darkmagenta),
PipValue (.00015),
LookForGap (False),
TestLastDayHighLow (True),
TestEnglufing (false),
Precision (5),
ChartNum(1);
chart number.png
(81.42 KiB) Downloaded 1084 times


Return to “MultiCharts”