Minimize object - javascript

I have a code like this:
var methods = {
collapse: function(element) {
modify(element);
},
other_method: function() {
// ...
}
};
function modify(element)
{
console.log('collapse method');
}
Is it possible to minify collapse method to one line? So it should always call modify function.

Try this:
var methods = {
collapse: modify,
other_method: function() {
// ...
}
};
function modify(element) {
console.log('collapse method');
}
Because we have function declaration (not expression), modify is visible when you declare the object methods. The thing which is done here is just setting collapse to be equal to modify's reference.
This is the same as:
var modify = function (element) {
console.log('collapse method');
}
var methods = {
other_method: function() {
// ...
}
};
methods.collapse = modify;

Related

Overriding a function on a javascript object's property

How would you override a function on a javascript object when the function is on another object within the parent object.
Example:
function TestingABC() {
this.events = { finish: function() { console.log("FINISHED"); } };
}
function TestingXYZ() {
TestingABC.call(this);
}
TestingXYZ.prototype = Object.create(TestingABC.prototype);
How would I override the events.finish function on TestingXYZ to run the parent (TestingABC) code along with some new code that I need to write?
Because the events object is property of the instance, not on the prototype, you could employ a technique similar to monkey patching, where you store a reference to the current function, then override the current function with one that can call the old one in addition to doing other stuff.
e.g.
function TestingABC() {
this.events = { finish: function() { console.log("FINISHED"); } };
}
function TestingXYZ() {
TestingABC.call(this);
var superEvents = this.events;
this.events = {
finish: function () {
superEvents.finish();
doMyStuff();
}
};
}
TestingXYZ.prototype = Object.create(TestingABC.prototype);
.events is an instantiated property of the TestingABC() constructor - so you can amend the value once you have an instantiation of it.
Perhaps something like this is what you're after?...
function TestingABC() {
this.events = {
finish: function() {
console.log('ABC FINISHED');
},
other: function() {
console.log('ABC OTHER');
}
};
}
function TestingXYZ() {
TestingABC.call(this);
}
TestingXYZ.prototype = Object.create(TestingABC.prototype);
TestingXYZ.prototype.callEvents = function() {
this.events.finish();
this.events.other();
}
var test1 = new TestingABC();
var test2 = new TestingXYZ();
test2.events.finish = function() {
console.log('XYZ FINISHED');
};
test1.events.finish();
test1.events.other();
//-> ABC FINISHED
//-> ABC OTHER
test2.callEvents();
//-> XYZ FINISHED
//-> ABC OTHER

Check if a private function exists inside an object in JavaScript

How can I check if a private function exist inside an object?
var myObj = function(){
var myFunc = function(){};
var init = function(){
//has myFunc been defined?
}
}
I know that I can do this:
if (typeof myFunc == 'function') {
//myFunc exist
}
But this is checking the global scope.
How can I limit this to my objects scope?
Here is the most simplified case that i need:
var myComponent = function () {
var exportExcel = function () {
};
this.export = function (type) {
if('export'+type is a private function in this scope){
window["export"+type]()//but in local scope;
}
}
};
And here is my work around for now :
var myComponent = function () {
var Exports = {
Excel: function () {
}
};
this.export = function (type) {
if (Exports.hasOwnProperty(type)) {
Exports[type]();
} else {
alert('This Export type has not been implemented Yet ! or it never will ... how knows? well i don\'t ...');
}
}
};
As you probably noticed:
function myFunc () {};
function myObj () {
function init () {
if (myFunc) // passes
};
}
You could cheat a bit :-|
function myObj () {
var isdef = { myFunc: true };
function myFunc () {};
function init () {
if (isdef.myFunc) // do something
};
}
I wonder why one would do that though.
Bases on the extra information given, the most practical pattern is what you're calling the "temporary workaround": keeping your functions in a private object, keyed by type.
var myComponent = function () {
var exporters = Object.create(null, {
"Excel": function () {
// do magic export here
}
});
this.export = function (type) {
if (type in exporters) {
// defined locally
return exporters[type].call(this); // binding is optional
} else {
// no export for you!
}
}
};
This prevents two things:
Referencing the function via string composition,
Querying the global scope (or, actually, any scope in between your component and the global scope).
This may not be your design principle, you could further extend this code to allow for adding / removing exporters.

Call parent method in JavaScript class but stll have access to prototype methods inside object instance?

Is it possible to call parent method in JavaScript class but to still have access to prototype methods from parent and child class. Here is code example:
var Base = function() {
this.baseMethod = function(){
return 'baseMethod';
};
this.baseInitMethod = function() {
return 'baseInitMethod';
}
}
Base.prototype.basePrototypeMethod = function() {
return "basePrototypeMethod";
};
var Specific = function() {
Base.call(this);
this.baseInitMethod = function() {
// call baseInitMethod from Base class
}
this.specificMethod = function(){
return 'specificMethod';
}
this.specificInitMethod = function() {
return this.basePrototypeMethod();
}
}
Specific.prototype.specificPrototypeMethod = function() {
return 'specificPrototypeMethod' + '-' + this.baseInitMethod();
}
for(var p in Base.prototype) {
Specific.prototype[p] = Base.prototype[p]
}
var s = new Specific();
console.log(s.baseMethod());
console.log(s.baseInitMethod());
console.log(s.basePrototypeMethod());
console.log(s.specificMethod());
console.log(s.specificInitMethod());
console.log(s.specificPrototypeMethod());
I want to call baseInitMethod in Base class from baseInitMethod method inside Specific class but so that all function calls from above still works. Is that possible?
Your Specific.prototype object should inherit from the Base.prototype object. Currently you're copying over all its properties to the object with this code:
for(var p in Base.prototype) {
Specific.prototype[p] = Base.prototype[p]
}
But you should actually use Object.create to establish a real prototype chain:
Specific.prototype = Object.create(Base.prototype);
Specific.prototype.specificPrototypeMethod = function() {
return 'specificPrototypeMethod' + '-' + this.baseInitMethod();
}
I want to call baseInitMethod in Base class from baseInitMethod method inside Specific class
Yes. In your Specific constructor, you first need get Base's baseInitMethod instance method, before you overwrite the property of the instance:
function Specific() {
Base.call(this);
var parentInitMethod = this.baseInitMethod;
this.baseInitMethod = function() {
// call baseInitMethod from Base class:
parentInitMethod.call(this /*, arguments…*/);
}
…
}
so that all function calls from above still works.
I'm not sure what you mean by that exactly. The specificPrototypeMethod will always call the baseInitMethod of the current instance, which would be Specific's overwritten one not the original that was defined in Base.
Here is what you need to do:
var Base = function () {
};
Base.prototype.baseMethod = function () {
return 'baseMethod';
};
Base.prototype.baseInitMethod = function () {
return 'baseInitMethod';
};
Base.prototype.basePrototypeMethod = function () {
return "basePrototypeMethod";
};
var Specific = function () {
Base.apply(this, arguments);
};
Specific.prototype.baseInitMethod = function () {
Base.prototype.baseInitMethod.apply(this,arguments);
};
Specific.prototype.specificMethod = function () {
return 'specificMethod';
};
Specific.prototype.specificInitMethod = function () {
var basePrototypeMethodCallResult = Base.prototype.basePrototypeMethod.apply(this,arguments);
};
You're overwriting the baseInitMethod of Base inside Specific, with Specific's definition, so why would you ever want to call the Base version? If you simply remove the overwrite of the function you should call the Base definition:
var Base = function() {
this.baseMethod = function(){
return 'baseMethod';
};
this.baseInitMethod = function() {
return 'baseInitMethod';
}
}
Base.prototype.basePrototypeMethod = function() {
return "basePrototypeMethod";
};
var Specific = function() {
Base.call(this);
this.baseInitMethod(); // calls the Base definition only
this.specificMethod = function(){
return 'specificMethod';
}
this.specificInitMethod = function() {
return this.basePrototypeMethod();
}
}
One might argue "Why always trying to mimic 'classical' behaviour and fuss with call and apply instead of embracing the prototype delegation pattern instead?"
Here is what I would code :
var Base = {
baseVariable1: "baseValue1",
baseVariable2: "baseValue2",
baseMethod: function () {
return 'baseMethod';
},
baseInitMethod: function () {
return 'baseInitMethod';
}
}
var Specific = Object.create(Base);
Specific.variable1 = "value1";
Specific.variable2 = "value2";
Specific.specificInitMethod = function () {
return 'specificInitMethod' + '-' + this.baseInitMethod();
}
Specific.specificMethod = function () {
return 'specificMethod' + '-' + this.baseInitMethod();
}
var s = Object.create(Specific);
console.log(s.baseInitMethod());
console.log(s.baseVariable1);
console.log(s.baseVariable2);
console.log(s.variable1);
console.log(s.variable2);
console.log(s.baseMethod());
console.log(s.specificInitMethod());
console.log(s.specificMethod());
class Parentable {
get parent() {
return this.__proto__.__proto__;
}
}
class A extends Parentable {
say() {
console.log('Hello from A');
}
}
class B extends A {
say() {
console.log('Im not A, I am B! But A send you a message:');
this.parent.say();
}
}
(new B()).say();

Object as jQuery.fn prototype?

If I define prototype like this
jQuery.fn.myFunc = function() {
console.log(this);
}
and call it like this:
$('div').myFunc();
this inside of myFunc will refer to jQuery object selection.
Now if I don't want to pollute .fn with multiple attached functions, can I do something like
jQuery.fn.myPlugin = {
myFunc1: function() {
},
myFunc2: function() {
}
}
If I call it $('div').myPlugin.myFunc1(); - how do I get reference to selected objects inside of myFunc1? Or is there a different, better approach?
Nope. can't do it that way. Instead, define it as a function, then add properties to that function.
jQuery.fn.myPlugin = function() {
console.log(this);
};
jQuery.fn.myPlugin.myFunc1 = function() {
};
jQuery.fn.myPlugin.myFunc2 = function() {
};
note that myFunc1 and myFunc2 still wont' have access to the selected element, therefore it's relatively useless to define them this way other than the fact that they can be easily overridden by other developers (which is a good thing)
The normal way of having additional methods within your plugin is to have your plugin method accept a parameter that can eitehr be an object to init the plugin, or a string to execute a target method on the element. for example, $("somediv").myPlugin("myFunc1")
The jQuery plugin tutorial suggests this:
(function( $ ) {
$.fn.popup = function( action ) {
if ( action === "open") {
// Open popup code.
}
if ( action === "close" ) {
// Close popup code.
}
};
}( jQuery ));
I suppose this would be another alternative:
(function($) {
$.fn.myPlugin = function (action) {
var functions = {
open: function () {
console.log('open: ', this);
},
close: function () {
console.log('close:', this);
}
}
if (action && functions[action]) {
functions[action].call(this)
} else {
console.log('no function', this);
}
return this;
};
}(jQuery));
$('#theDiv')
.myPlugin()
.myPlugin('open')
.myPlugin('close');
http://jsfiddle.net/faJAk/
work if you create a object before.
Like this:
<script>
jQuery.fn.myPlugin = {};
jQuery.fn.myPlugin = {
myFunc1: function() {
console.log(this);
},
myFunc2: function() {
alert(this);
}
};
$(document).ready(function(){
$('div').myPlugin.myFunc1();
$('div').myPlugin.myFunc2();
});
</script>
Another possible approach is to use defineProperty:
(function($) {
var myPlugin = {
foo: function() {
console.log(this)
}
}
Object.defineProperty($.fn, "myPlugin", {
get : function() { return $.extend({}, this, myPlugin) }
});
})(jQuery);
Now $(...).myPlugin.foo should resolve this correctly:
$(function() {
$("body").myPlugin.foo(); // logs "body"
})

Efficient way for Javascript inheritance

I have two javascript classes as
class1 = function(opt) {
function abc () {
}
function def () {
}
function xyz () {
}
};
class2 = function(opt) {
function abc () {
}
function def () {
}
function lmn () {
}
};
These two classes contain some common methods like (abc, def) and some specific methods like (lmn, xyz). Can anybody suggest me how to apply inheritance to this situation effectively, so that I can have common methods in one file and specific methods in respective files. I tried prototype method, but this is not working. So is there any other way to this.
Thanks.
Depending on whether these classes just share behavior (interface) or are actually subclasses of a common class, you should use either a mixin or prototypal inheritance respectively.
An example for prototypes:
function BaseClass () {
}
BaseClass.prototype = {
abc: function () {
},
def: function () {
}
};
function class1 () {
}
class1.prototype = new BaseClass();
class1.prototype.xyz = function () {
};
function class2 () {
}
class2.prototype = new BaseClass();
class2.prototype.lmn = function () {
};
And an example of mixins:
function BaseMixin (object) {
object.abc = BaseMixin.prototype.abc;
object.def = BaseMixin.prototype.def;
}
BaseMixin.prototype = {
abc: function () {
},
def: function () {
}
};
function class1 () {
BaseMixin(this);
}
class1.prototype = {
xyz: function () {
}
};
function class2 () {
BaseMixin(this);
}
class2.prototype = {
lmn: function () {
}
};
Javascript dont have classes
But you can systemise your code.Javascript inheritance is totally different from that of othe oop languages.
Here,We use prototypes and constructors.
**prototype==>**In simple words,I am used for extension purpose
**constructors==>**I am used for creating multiple instances.Any function can be used as a constructor by using the new keyword.
Just sample codes for understanding.
SAMPLE 1:BY USING OBJECT LITERAL
var Myobject = {
Function_one: function()
{
//some code
Myobject.function_three();
},
Function_two: function()
{
//some code
Myobject.function_three();//lets say i want to execute a functin in my object ,i do it this way...
},
Function_three: function()
{
//some code
}
};
window.onload = Myobject.Function_one //this is how you call a function which is in an object
SAMPLE 2:BY USING PROTOTYPE
function function_declareVariable()
{
this.a= 10; //i declare all my variable inside this function
this.b= 20;
}
function_declareVariable.prototype.Function_one = function()
{
//some code
Myobject.Function_three();
};
function_declareVariable.prototype.Function_two = function()
{
Myobject.Function_three();
};
function_declareVariable.prototype.Function_three = function()
{
alert(Myobject.a or Myobject.b)
//some code
};
var Myobject = new function_declareVariable();//this is how i instantiate
REFER 1:what are constructors ,prototypes
REFER 2:prototypal inheritance

Categories

Resources