What happened to the Messenger Plus! forums on msghelp.net?
Shoutbox » MsgHelp Archive » Messenger Plus! for Live Messenger » Scripting » [IDEA] plusQuery

Pages: (2): « First [ 1 ] 2 » Last »
[IDEA] plusQuery
Author: Message:
Amec
Junior Member
**


Posts: 19
32 / Male / Flag
Joined: Sep 2008
O.P. [IDEA] plusQuery
Hello. I was wondering if anyone had thought of making a jQuery-esque library for Messenger Plus! Live. I believe this would make it much easier and quicker to develop scripts, much like jQuery is for web dev.

For example, something like the following could be used as a simple googling script: (minus some parsing)
code:
$("ChatWnd").receiveMessage(
    function() {
        if(this.message.substr(0, 7) === "!google") {
            var wnd = this;
            $.get(
                "http://www.google.com?q=" + this.message.substr(9, this.message.length - 9),
                function(data) {
                    //parse data here
                    wnd.send(data);
                }
            );
        }
    }
);

I was thinking we could store everything in like an xml data structure, and access it via $(). Like, $("ChatWnd") would select all the ChatWnds, $("ScriptMenu") would select the menu, etc... Or we could do it like $.chatWnd and $.scriptMenu or something... I really don't know atm.

Would anyone be interested in working on this with me? ;)

Edit: Let me clarify on "we could store everything in like an xml data structure".

An example with a LOT of stuff missing:
code:
<Root>
    <ChatWnds>
        <ChatWnd>
            <Handle>{ json rep for HWND object, etc. }</Handle>
            <Contacts>
                <Contact>
                    <Blocked>false</Blocked>
                    <Email>lol@u.com</Email>
                    <Name>Amec</Name>
                    <PersonalMessage>Yo.</PersonalMessage>
                </Contact>
                <Contact>
                    <Blocked>false</Blocked>
                    <Email>lol@me.com</Email>
                    <Name>Yep</Name>
                    <PersonalMessage>Bro.</PersonalMessage>
                </Contact>
            </Contacts>
        </ChatWnd>
    </ChatWnds>
</Root>

One could do $("Contact") to get a Contacts object, or $("Contact > Email:contains('lol')") to get a list of Contacts whose email has 'lol' in it. And this shouldn't just apply to ChatWnds, every data structure (Debug, Messenger, MsgPlus, Emoticons, PlusWnd, Interop, ScriptCommands, ScriptMenu, etc.) should be accessible in this structure, which is updated at run time when data changes...

This post was edited on 07-13-2010 at 05:09 AM by Amec.
07-13-2010 04:43 AM
Profile E-Mail PM Find Quote Report
Spunky
Former Super Mod
*****

Avatar

Posts: 3658
Reputation: 61
36 / Male / Flag
Joined: Aug 2006
RE: [IDEA] plusQuery
I like the idea, but it'd be hard to implement I think. Then you either have to ship the file with every script that uses it giving you multiple copies on the same user's PC, or find a way to download it from an online source and execute it into the current script.


This post was edited on 07-13-2010 at 06:29 AM by Spunky.
<Eljay> "Problems encountered: shit blew up" :zippy:
07-13-2010 06:29 AM
Profile PM Find Quote Report
Matti
Elite Member
*****

Avatar
Script Developer and Helper

Posts: 1646
Reputation: 39
32 / Male / Flag
Joined: Apr 2004
RE: [IDEA] plusQuery
I've had a similar idea once, mainly because I would love to assign and remove event handlers like in jQuery (with bind() and unbind()).

However, if you would want to actually make such framework for Plus! scripts, you're going to need to find a way to create regular OnEvent_* functions in your script and mirror these to your framework. After some testing, I found that it was possible to create these in run-time by manually creating an extra script file and loading that with MsgPlus.LoadScriptFile. The problem is that you can't assign window event handlers without knowing their IDs to create OnWindowIdEvent_* handlers. To get these IDs, you'd need to ask the user of your framework to name all used windows in your script at initialization and whenever the user adds an extra window, he/she must remember to add it into the list.

One solution could be to ask for the paths to the interface XML files and collect all window IDs at initialization. The result of this scanning process could then be cached inside ScriptInfo.xml. The created script file with all mirrored events could be cached in a similar fashion. However these are all nasty workarounds, it is tough to do it right on top of the current scripting environment.

As for selecting objects with CSS-like queries, I don't think scripts would benefit from it that much. In the HTML DOM, it's good to have a selector engine since the current JavaScript functions aren't sufficient for modern scripts and there are many browser inconsistencies to overcome when crawling through the DOM. It's also a very logical way to select elements with CSS-like queries, since we're used to do that in CSS and thus we know exactly what we should expect.

I doubt this query language would make sense in Plus! scripting. Surely, you could have object types as tag names, attribute selectors and descendants, but why would you need all that? I think it's good to be able to plusQuerify an object and dynamically bind events on it, but why do you need to be able to select these objects like that? Most of the time, Plus! already gives you the object you need as event parameter, so just $(ChatWnd) should be enough.

quote:
Originally posted by Spunky
I like the idea, but it'd be hard to implement I think. Then you either have to ship the file with every script that uses it giving you multiple copies on the same user's PC, or find a way to download it from an online source and execute it into the current script.
I think such a library shouldn't get much larger than 10 to 15 kB when properly minified. Besides, if it's a good library which really makes scripting easier, the file size doesn't matter that much anyway.
Plus! Script Developer | Plus! Beta Tester | Creator of Countdown Live | Co-developer of Screenshot Sender 5

Found my post useful? Rate me!
07-13-2010 07:55 AM
Profile E-Mail PM Web Find Quote Report
CookieRevised
Elite Member
*****

Avatar

Posts: 15517
Reputation: 173
– / Male / Flag
Joined: Jul 2003
Status: Away
RE: [IDEA] plusQuery
quote:
Originally posted by Matti
...which really makes scripting easier
... bigger, slower, more prone to errors, very hard to debug, beginning scripters don't even know what they actually are doing (and thus asking more questions as to why something doesn't work), etc....

This post was edited on 07-13-2010 at 11:48 PM by CookieRevised.
.-= A 'frrrrrrrituurrr' for Wacky =-.
07-13-2010 11:47 PM
Profile PM Find Quote Report
Matti
Elite Member
*****

Avatar
Script Developer and Helper

Posts: 1646
Reputation: 39
32 / Male / Flag
Joined: Apr 2004
RE: [IDEA] plusQuery
quote:
Originally posted by CookieRevised
... bigger, slower, more prone to errors, very hard to debug, beginning scripters don't even know what they actually are doing (and thus asking more questions as to why something doesn't work), etc....
That's what you could say about any abstraction layer: jQuery, .NET,... :P

The extra file weight shouldn't be so much of a problem for modern computers and Internet connections, nor should the difference in performance be very noticeable if the library creator knows what he's doing.

I agree that the use of a framework can make debugging tougher, it adds an extra abstraction layer between developer and machine so the chance that you're doing something wrong may increase. However I think the chance of doing something wrong is bigger when the developer has to write a whole function by himself then when he calls a library function which is already thoroughly tested.

You're probably right that beginning developers will tend to jump straight onto a library without learning the underlying language. I didn't learn C++ before C# either so I'm also in that same boat, but I started with JavaScript so I already knew about the basics of programming. I've seen people jump straight into jQuery who don't know anything about the basic structures of JavaScript. This also applies to Plus! scripting on top of JScript: newcomers try to do two things when a message is send, so they define two OnEvent_ChatWndSendMessage functions... Perhaps a library could help here.

I understand your worries about using frameworks. Perhaps a better solution would be that the Plus! scripting environment itself gets updated to comply with our needs (I really want better event handling!), so we don't need libraries to give us what the scripting environment can't do. And if that doesn't happen, I could just make a small private framework for my own scripts without releasing it separately. If there's something wrong with the library, then I can still just update my own scripts and don't need to worry about other developers using my library.

Note to self: write shorter posts!
Plus! Script Developer | Plus! Beta Tester | Creator of Countdown Live | Co-developer of Screenshot Sender 5

Found my post useful? Rate me!
07-14-2010 10:28 AM
Profile E-Mail PM Web Find Quote Report
Amec
Junior Member
**


Posts: 19
32 / Male / Flag
Joined: Sep 2008
O.P. RE: [IDEA] plusQuery
lol really old post. So uhh... Since no one seemed interested, I decided to do this myself! Although, I did change it a lot from my original suggestion as I became a better ECMAScript "programmer"...

Source: https://github.com/tyscorp/plusquery/

Suggestions/additions/criticisms are welcome. ;)

Edit: I guess I should have included more information...

Wrapper objects
It includes a set of "wrapper objects", which allow the interfaces to be extended. For example, you can overload ChatWnd.SendMessage to do other stuff...

Event Handling
It includes functions for binding/unbinding event listeners, to any plusQuery object. If it is bound to the main plusQuery object, it is always executed when the event is called. If it is bound to a plusQuery( * ) object, it is executed whenever the objects match.
So, if you bind "ChatWndSendMessage" to plusQuery, the function you specify will get called each time you send a message. If you bind it to a plusQuery(ChatWnd) object, the function is only called when you send a message from that ChatWnd object. (binding to instances is buggy atm. >_>)

Timers
It has setTimeout/setInterval/clearTimeout/clearInterval. Based on a mixture of mine and Matti's ideas.

Is also extends Object and Array a lot currently; I will be moving this to the plusQuery object. (except for the delicious Function.prototype.bind ;D)

The latest build is attached.

.zip File Attachment: _plusquery.0.0.2.zip (8.63 KB)
This file has been downloaded 141 time(s).

This post was edited on 04-06-2011 at 05:00 AM by Amec.
04-06-2011 04:34 AM
Profile E-Mail PM Find Quote Report
Matti
Elite Member
*****

Avatar
Script Developer and Helper

Posts: 1646
Reputation: 39
32 / Male / Flag
Joined: Apr 2004
RE: [IDEA] plusQuery
That is truly amazing! :O

Here's a suggestion: use combined getter/setter methods for the properties in the wrapper classes. Instead of storing this.original.Size in this.Size, make a method Size which can be called as a getter with Size() or as a setter with Size(newSize). Right now every wrapped property is read-only, although some properties should be read/write such as DataBloc.Size or Messenger.MyStatus.

Example:
js code:
$.wrappers.DataBloc.prototype = {
    Size: function (newSize) {
        if( typeof newSize !== "undefined" ) {
            this.original.Size = newSize;
        }
        return this.original.Size;
    }
}
Another thing I noticed is that you're extending Object.prototype. While this may work just fine in your library when using your version of Object.prototype.forEach, this surely will break a lot of scripts which iterate over plain objects using a standard for...in loop without the Object.prototype.hasOwnProperty check. I think it's better to simply drop the prototype extensions and only extend the static Object. This is not so much of an issue with the Array and String prototypes, as those should never be iterated over with for...in anyway.

The thing I miss is (of course) event binding on PlusWnd objects. If this were possible, we could write classes to work with window controls which can bind the necessary handlers to the used window events. Now, I understand that this is very tough to implement and would probably require a lot of hackish constructions. I found a way to inject function in the global object in run-time, but it's very, very ugly. :P Hopefully the event architecture gets fixed/improved in some future version of Plus!...

This deserves its own thread though... :P
Plus! Script Developer | Plus! Beta Tester | Creator of Countdown Live | Co-developer of Screenshot Sender 5

Found my post useful? Rate me!
04-06-2011 09:43 AM
Profile E-Mail PM Web Find Quote Report
Amec
Junior Member
**


Posts: 19
32 / Male / Flag
Joined: Sep 2008
O.P. RE: RE: [IDEA] plusQuery
quote:
Originally posted by Matti
That is truly amazing! :O
Thanks. :D

quote:
Originally posted by Matti
Here's a suggestion: use combined getter/setter methods for the properties in the wrapper classes. Instead of storing this.original.Size in this.Size, make a method Size which can be called as a getter with Size() or as a setter with Size(newSize). Right now every wrapped property is read-only, although some properties should be read/write such as DataBloc.Size or Messenger.MyStatus.
Hmm, I just tested this... I guess it's something I overlooked. Oops! I'll change them all to the combined getter/setter functions as you suggested soon.

quote:
Originally posted by Matti
Another thing I noticed is that you're extending Object.prototype. While this may work just fine in your library when using your version of Object.prototype.forEach, this surely will break a lot of scripts which iterate over plain objects using a standard for...in loop without the Object.prototype.hasOwnProperty check. I think it's better to simply drop the prototype extensions and only extend the static Object. This is not so much of an issue with the Array and String prototypes, as those should never be iterated over with for...in anyway.
Yeah, I realised that was terrible after I started to REALLY understand ECMAScript... Haven't had time to move them from Object to plusQuery yet. And people who don't check for hasOwnProperty while iterating are silly. But... I guess I have to take that into account. :P

quote:
Originally posted by Matti
The thing I miss is (of course) event binding on PlusWnd objects. If this were possible, we could write classes to work with window controls which can bind the necessary handlers to the used window events. Now, I understand that this is very tough to implement and would probably require a lot of hackish constructions. I found a way to inject function in the global object in run-time, but it's very, very ugly. :P Hopefully the event architecture gets fixed/improved in some future version of Plus!...
Yeah, I thought about it for a bit, and had no idea. The global variable in JScript seems REALLY screwey. :( Doesn't seem to be a way that I can see which adds properties to it.
js code:
function OnMyWndEvent_Cancel(plusWnd) {
    $.trigger(plusWnd, "MyWndEvent_Cancel", plusQuery.$A(arguments));
}

$.addEventListener("MyWndEvent_Cancel", function (plusWnd) {
    //do stuff here
});

$.addEventListener("MyWndEvent_Cancel", function (plusWnd) {
    //do other stuff here
});
It would be so much easier if you could just add it to the global variable. :( How did you manage to do it?

This post was edited on 04-06-2011 at 11:24 AM by Amec.
04-06-2011 11:12 AM
Profile E-Mail PM Find Quote Report
matty
Scripting Guru
*****


Posts: 8336
Reputation: 109
39 / Male / Flag
Joined: Dec 2002
Status: Away
RE: [IDEA] plusQuery
Simply amazing!
04-06-2011 12:46 PM
Profile E-Mail PM Find Quote Report
Amec
Junior Member
**


Posts: 19
32 / Male / Flag
Joined: Sep 2008
O.P. RE: [IDEA] plusQuery
...oh hey. I just thought of something... It can be done using eval. (feeling kinda sick just by saying that)

js code:
var plusWnd = $(MsgPlus).CreateWnd("interface.xml", "yiew", 0);
//[...]
$.wrappers.MsgPlus.CreateWnd = function (XmlFile, WindowId, Options) {
    var toEval = "var On" + WindowId + "Event_Cancel = function (plusWnd) { $.trigger(plusWnd, '" + WindowId + "Event_Cancel', plusQuery.$A(arguments)); };";
    toEval += "var On" + WindowId + "Event_Destroyed = function (plusWnd, exitCode) { $.trigger(plusWnd, '" + WindowId + "Event_Destroyed', plusQuery.$A(arguments)); };";
    //etc
    (1, eval)(toEval); //indirect call to eval; makes it evaluate in the global scope
    this.original.CreateWnd(XmlFile, WindowId, Options);
}

This would work, no? :)

This post was edited on 04-06-2011 at 02:20 PM by Amec.
04-06-2011 02:07 PM
Profile E-Mail PM Find Quote Report
Pages: (2): « First [ 1 ] 2 » Last »
« Next Oldest Return to Top Next Newest »


Threaded Mode | Linear Mode
View a Printable Version
Send this Thread to a Friend
Subscribe | Add to Favorites
Rate This Thread:

Forum Jump:

Forum Rules:
You cannot post new threads
You cannot post replies
You cannot post attachments
You can edit your posts
HTML is Off
myCode is On
Smilies are On
[img] Code is On