Prototypes
Prototypes
This is another thing that I've had little luck finding any documentation on (well regarding use with ESTK). What are the advantages/disadvantages of using this? I have come across numerous examples now but as Im not sure of what's actually taking place I've avoided them thus far… If you add a property to some object class how long does this persist? Can it be removed? Can I even check for prototypes?
Prototypes
Here is an old thread about OOP that has some links that might help http://ps-scripts.com/bb/viewtopic.php?f=2&t=902 http://ps-scripts.com/bb/viewtopic.php?f=2&t=400
For what it's worth I never really got my head around the advantages/disadvantages of using prototype.
For what it's worth I never really got my head around the advantages/disadvantages of using prototype.
Prototypes
The way JavaScript (or ExtendScript) works is through so-called prototypal inheritance. When you use the "new" keyword, writing say "myInstance = new MyObject()", an object is created that inherits from "MyObject.prototype", which can be set to anything you like. What happens then is whenever you try to access "myInstance.foo", where "foo" is some property or method, JavaScript will look for "foo" first inside "myInstance" itself, and then if it doesn’t find anything, will go looking in "MyObject.prototype". If it doesn’t find it there, it will look in the prototype’s prototype, and on up the “chain”, until returning "undefined" if it can’t find it there.
If you are just writing simple scripts, it is entirely possible to get away with just passing basic data types around to functions and never defining your own custom objects. But once you start trying to create more complex programs, objects have some advantages in making code organization clear, encapsulating data structures, coordinating program flow, and so forth.
If you are just writing simple scripts, it is entirely possible to get away with just passing basic data types around to functions and never defining your own custom objects. But once you start trying to create more complex programs, objects have some advantages in making code organization clear, encapsulating data structures, coordinating program flow, and so forth.
Prototypes
jacobolus wrote:...But once you start trying to create more complex programs, objects have some advantages in making code organization clear, encapsulating data structures, coordinating program flow, and so forth.
I agree custom objects are very helpful, I have written many scripts where almost the entire script is a custom object. But that can be done without the explicit use of prototype. Code: Select allfunction foo(){
this.bar = true;
this.toString = function(){return 'Custom srript object';}
}
var fooTwo = new foo();// create a new instance of the custom function object.
fooTwo;
What I don't understand is the advantage of the explicit use of prototype.
I agree custom objects are very helpful, I have written many scripts where almost the entire script is a custom object. But that can be done without the explicit use of prototype. Code: Select allfunction foo(){
this.bar = true;
this.toString = function(){return 'Custom srript object';}
}
var fooTwo = new foo();// create a new instance of the custom function object.
fooTwo;
What I don't understand is the advantage of the explicit use of prototype.
Prototypes
One advantage is that in your current code, a different toString() function is created for each foo object you create. This requires a fair amount of memory and processor time. If you instead put the toString function on the prototype, a single copy of it would be shared by every instance. It doesn’t matter too much if you only have a handful of instances floating around, but if you need to create 10,000 foo instances, the overhead is a big waste.
There are other advantages, relating to structuring your code: You can build an inheritance chain. You can test instances against any of their ancestor types using "instanceof", which is great for example in making an exception hierarchy so you can use try/catch as it was meant to be used (the way Python naturally encourages; sadly JavaScript's syntax for dealing w/ exceptions is cluttered and awkward). You can redefine objects' prototypes on the fly, whenever you want, and do some quite sophisticated tricks with that.
There are alternative ways to write the code so that it isn't as cumbersome as writing "foo.prototype.methodname = ..." all the time, but they're a bit beyond the scope of this comment. You can also build a "classical" inheritance system on top of the prototypal one. I like John Resig's version pretty well, http://ejohn.org/blog/simple-javascript-inheritance/ and also recommend his in-progress book Secrets of the JavaScript Ninja if you want to understand these mechanisms in a deeper way.
There are other advantages, relating to structuring your code: You can build an inheritance chain. You can test instances against any of their ancestor types using "instanceof", which is great for example in making an exception hierarchy so you can use try/catch as it was meant to be used (the way Python naturally encourages; sadly JavaScript's syntax for dealing w/ exceptions is cluttered and awkward). You can redefine objects' prototypes on the fly, whenever you want, and do some quite sophisticated tricks with that.
There are alternative ways to write the code so that it isn't as cumbersome as writing "foo.prototype.methodname = ..." all the time, but they're a bit beyond the scope of this comment. You can also build a "classical" inheritance system on top of the prototypal one. I like John Resig's version pretty well, http://ejohn.org/blog/simple-javascript-inheritance/ and also recommend his in-progress book Secrets of the JavaScript Ninja if you want to understand these mechanisms in a deeper way.
Prototypes
Maybe it is because my javascript experience is limited to scripting Adobe apps( mainly Photoshop ), but I have yet to need a custom class with more than one instance. Nor do I recall seeing any Photoshop scripts written by others that make use of multiple instances of a custom class.
Prototypes
Yes, most of the scripting code I've seen, including for instance the example code in Adobe's documentation, is extremely imperative low-level code, with little structure or use of abstraction. This is perfectly reasonable, given that most scripters are not programmers, and most scripting tasks are relatively straight-forward.
In any event, if you only need one instance, you're right that there's not much use in bothering with constructors, prototypes, or the 'new' keyword. Just put functions in the top level, or add them to an object.
One obvious example of a place where it would be a good idea to make several instances of a type is in building nicer APIs wrapping various uses of Photoshop's cryptic ActionReference and ActionDescriptor. For example, a "Layer" type might represent a Photoshop layer, and include class methods for getting a layer by name or selection, and instance methods for deleting the layer, moving it around, showing or hiding it, renaming it, changing its metadata, getting a reference to its mask or its containing layer group, etc. etc. Right now, most of the APIs available to scripts encourage writing code that is impossible to follow and an order of magnitude more verbose than necessary.
In any event, if you only need one instance, you're right that there's not much use in bothering with constructors, prototypes, or the 'new' keyword. Just put functions in the top level, or add them to an object.
One obvious example of a place where it would be a good idea to make several instances of a type is in building nicer APIs wrapping various uses of Photoshop's cryptic ActionReference and ActionDescriptor. For example, a "Layer" type might represent a Photoshop layer, and include class methods for getting a layer by name or selection, and instance methods for deleting the layer, moving it around, showing or hiding it, renaming it, changing its metadata, getting a reference to its mask or its containing layer group, etc. etc. Right now, most of the APIs available to scripts encourage writing code that is impossible to follow and an order of magnitude more verbose than necessary.
Prototypes
I have been thinking about how an AMLayer class would work since your last post. I don't think Action Manager code is hard to follow once you understand the basics of descriptors, references, list, and typeIDs. Nor do I understand why some have an aversion to using an Action Manager function just because they may not be able to follow the code in the function. You can not even access the code inside of a DOM method.
However I do realize that there are a good number of people that don't like Action Manager code and so agree that anything that can make it easier for them to use would be useful.
I see two main problems with creating an AMLayer class( or any class to wrap AM code ). The main one is with AM you are not working with DOM objects but a reference or descriptor for Object. An executeAction or executeActionGet returns a descriptor, not a layer or document object. The only sure way of getting a DOM layer object using action manager is by working with an activeLayer and a mix of AM and DOM code. Another problem is that there are some tasks( aside from making a DOM object reference ) using action manager code that can only be done with an activeLayer. The same is true of some DOM methods but making a layer active gives up one of AM advantages, speed over using the DOM.
But the main drawback for me is I don't know enough about OOP to know how to start creating an AMLayer class.
However I do realize that there are a good number of people that don't like Action Manager code and so agree that anything that can make it easier for them to use would be useful.
I see two main problems with creating an AMLayer class( or any class to wrap AM code ). The main one is with AM you are not working with DOM objects but a reference or descriptor for Object. An executeAction or executeActionGet returns a descriptor, not a layer or document object. The only sure way of getting a DOM layer object using action manager is by working with an activeLayer and a mix of AM and DOM code. Another problem is that there are some tasks( aside from making a DOM object reference ) using action manager code that can only be done with an activeLayer. The same is true of some DOM methods but making a layer active gives up one of AM advantages, speed over using the DOM.
But the main drawback for me is I don't know enough about OOP to know how to start creating an AMLayer class.
Prototypes
Nor do I understand why some have an aversion to using an Action Manager function just because they may not be able to follow the code in the function.
It doesn't even have to be the case that the code is impossible to follow. Every bit of extra boilerplate and every cryptic name in an API makes code written against it harder to write and read, and creates friction which ultimately limits what gets built on top.
As an example, take jQuery over in browser land. It's quite possible to understand code written to manipulate the browser DOM, but the APIs are cumbersome and error prone, and either programs stay relatively rudimentary or code line counts explode and the result is brittle and difficult to change or maintain. Using jQuery radically reduces the friction involved in manipulating web pages, cutting functions that were previously dozens of lines long down to just a few lines. As a result, users can write much more sophisticated behavior with ease, and in a way that can be easily changed in response to changing needs.
It doesn't even have to be the case that the code is impossible to follow. Every bit of extra boilerplate and every cryptic name in an API makes code written against it harder to write and read, and creates friction which ultimately limits what gets built on top.
As an example, take jQuery over in browser land. It's quite possible to understand code written to manipulate the browser DOM, but the APIs are cumbersome and error prone, and either programs stay relatively rudimentary or code line counts explode and the result is brittle and difficult to change or maintain. Using jQuery radically reduces the friction involved in manipulating web pages, cutting functions that were previously dozens of lines long down to just a few lines. As a result, users can write much more sophisticated behavior with ease, and in a way that can be easily changed in response to changing needs.