programming to patterns
DESCRIPTION
Aaron Newton's slides from SF JS #4 on Pattern Programming and MooTools.TRANSCRIPT
![Page 1: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/1.jpg)
Programming To Patterns
![Page 2: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/2.jpg)
How I used to write
![Page 3: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/3.jpg)
How I used to write
ClassesDatePicker
FormValidatorFx
RequestSlideshow
etc...
![Page 4: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/4.jpg)
How I used to writevar myApp = { init: function(){ myApp.apples() myApp.orange() myApp.lemons() }, apples: function(){ $$(‘div.apple’).each(function(apple) { var form = apple.getElement(‘form’); form.addEvent(‘submit’, funciton(event){ ....}); }); }, orange: function(){ $(‘orange’).getElements(‘li’).each... },
etc...
ClassesDatePicker
FormValidatorFx
RequestSlideshow
etc...
![Page 5: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/5.jpg)
How I used to writevar myApp = { init: function(){ myApp.apples() myApp.orange() myApp.lemons() }, apples: function(){ $$(‘div.apple’).each(function(apple) { var form = apple.getElement(‘form’); form.addEvent(‘submit’, funciton(event){ ....}); }); }, orange: function(){ $(‘orange’).getElements(‘li’).each... },
etc...
ClassesDatePicker
FormValidatorFx
RequestSlideshow
etc...
This tends to get out of hand
![Page 6: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/6.jpg)
Banging it out...<script>
window.addEvent(‘domready’, function(){
$(‘myForm’).addEvent(‘submit’, function(evt){
evt.preventDefault();
this.send({
onComplete: function(result){ ... },
update: $(‘myContainer’)
});
});
});
</script>
This is very tempting.
![Page 7: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/7.jpg)
Pros•Writing the logic for a specific app is fast
and furious
•The test environment is the app
![Page 8: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/8.jpg)
Pros•Writing the logic for a specific app is fast
and furious
•The test environment is the app
& Cons•It’s much harder to maintain
•A high percentage of code you write for the app isn’t reusable
![Page 9: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/9.jpg)
Using Classes
![Page 10: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/10.jpg)
Using Classes
var Human = new Class({isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
Human
This is how MooTools does it
![Page 11: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/11.jpg)
Using Classes
var Human = new Class({isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
Human
bob
var bob = new Human();//bob.energy === 1
bob.eat();//bob.energy === 2
This is how MooTools does it
![Page 12: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/12.jpg)
Extending Classes
![Page 13: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/13.jpg)
Extending Classesvar Human = new Class({
initialize: function(name, age){this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
![Page 14: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/14.jpg)
Extending Classesvar Human = new Class({
initialize: function(name, age){this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Ninja = new Class({Extends: Human,initialize: function(side, name, age){
this.side = side;this.parent(name, age);
},energy: 100,attack: function(target){
this.energy = this.energy - 5;target.isAlive = false;
}});
![Page 15: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/15.jpg)
Extending Classesvar Human = new Class({
initialize: function(name, age){this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Ninja = new Class({Extends: Human,initialize: function(side, name, age){
this.side = side;this.parent(name, age);
},energy: 100,attack: function(target){
this.energy = this.energy - 5;target.isAlive = false;
}});
![Page 16: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/16.jpg)
Extending Classes
var bob = new Human('Bob', 25);
var Human = new Class({initialize: function(name, age){
this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Ninja = new Class({Extends: Human,initialize: function(side, name, age){
this.side = side;this.parent(name, age);
},energy: 100,attack: function(target){
this.energy = this.energy - 5;target.isAlive = false;
}});
![Page 17: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/17.jpg)
Extending Classes
var bob = new Human('Bob', 25);
var Human = new Class({initialize: function(name, age){
this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Ninja = new Class({Extends: Human,initialize: function(side, name, age){
this.side = side;this.parent(name, age);
},energy: 100,attack: function(target){
this.energy = this.energy - 5;target.isAlive = false;
}});
var blackNinja = new Ninja('evil', 'Nin Tendo', 'unknown');//blackNinja.isAlive = true//blackNinja.name = 'Nin Tendo'
blackNinja.attack(bob);//bob never had a chance
![Page 18: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/18.jpg)
Implementing Classes
![Page 19: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/19.jpg)
Implementing Classesvar Human = new Class({
initialize: function(name, age){this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
![Page 20: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/20.jpg)
Implementing Classesvar Human = new Class({
initialize: function(name, age){this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Warrior = new Class({energy: 100,kills: 0,attack: function(target){
if (target.energy < this.energy) {target.isAlive = false;this.kills++;
}this.energy = this.energy - 5;
}});
![Page 21: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/21.jpg)
Implementing Classesvar Ninja = new Class({
Extends: Human,Implements: [Warrior],initialize: function(side, name, age){
this.side = side;this.parent(name, age);
}});
var Human = new Class({initialize: function(name, age){
this.name = name;this.age = age;
},isAlive: true,energy: 1,eat: function(){
this.energy++;}
});
var Warrior = new Class({energy: 100,kills: 0,attack: function(target){
if (target.energy < this.energy) {target.isAlive = false;this.kills++;
}this.energy = this.energy - 5;
}});
var Samurai = new Class({Extends: Human,Implements: [Warrior],side: 'good',energy: 1000
});
![Page 22: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/22.jpg)
When to write a class...
![Page 23: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/23.jpg)
When to write a class...
![Page 24: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/24.jpg)
When to write a class...
![Page 25: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/25.jpg)
When to write a class...
![Page 26: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/26.jpg)
When to write a class...
![Page 27: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/27.jpg)
Key Aspects of JS Classes
![Page 28: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/28.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
![Page 29: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/29.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
•Break up logic into small methods.
![Page 30: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/30.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
•Break up logic into small methods.
•Break up functionality into small classes.
![Page 31: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/31.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
•Break up logic into small methods.
•Break up functionality into small classes.
•Build ‘controller’ classes for grouped functionality.
![Page 32: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/32.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
•Break up logic into small methods.
•Break up functionality into small classes.
•Build ‘controller’ classes for grouped functionality.
•Use options and events liberally.
![Page 33: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/33.jpg)
Key Aspects of JS Classes
•Shallow inheritance works best.
•Break up logic into small methods.
•Break up functionality into small classes.
•Build ‘controller’ classes for grouped functionality.
•Use options and events liberally.
•Don’t be afraid to refactor, but avoid breaking the interface.
![Page 34: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/34.jpg)
Let’s look at that earlier example again
...
<script>
$(‘myForm’).addEvent(‘submit’, function(evt){
evt.preventDefault();
this.send({
onComplete: function(result){ ... },
update: $(‘myContainer’)
});
});
</script>
![Page 35: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/35.jpg)
Program a Patternvar FormUpdater = new Class({
initialize: function(form, container, options) {this.form = $(form);this.container = $(container);this.request = new Request(options);this.attach();
},attach: function(){
this.form.addEvent(‘submit’,this.send.bind(this));
},send: function(evt){
if (evt) evt.preventDefault();this.request.send({
url: this.form.get(‘action’),onComplete: this.onComplete.bind(this)
});},onComplete: function(responseTxt){
this.container.set(‘html’, responseTxt);}
});new FormUpdater($(‘myForm’), $(‘myContainer’));
![Page 36: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/36.jpg)
...and then extend itvar FormUpdater.Append = new Class({
Extends: FormUpdater,onComplete: function(responseTxt){
this.container.adopt(new Element(‘div’, {html: responseTxt})
);}
});new FormUpdater.Append($(‘myForm’), $(‘myTarget’));
![Page 37: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/37.jpg)
How I write now
![Page 38: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/38.jpg)
How I write nowvar myApp = { init: function(){ myApp.apples() myApp.orange() myApp.lemons() }, apples: function(){ new AppleGroup($$(‘div.apple’)); }, orange: function(){ new Orange($(‘orange’) },
etc...
ClassesDatePicker
FormValidatorFx
RequestSlideshow
AppleAppleGroup
Orangeetc...
![Page 39: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/39.jpg)
How I write nowvar myApp = { init: function(){ myApp.apples() myApp.orange() myApp.lemons() }, apples: function(){ new AppleGroup($$(‘div.apple’)); }, orange: function(){ new Orange($(‘orange’) },
etc...
ClassesDatePicker
FormValidatorFx
RequestSlideshow
AppleAppleGroup
Orangeetc...
I write as little of this as possible
![Page 40: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/40.jpg)
Pros• Small, reusable, readable, generic classes
• Only the variables are managed in a specific application
• The footprint between a specific app and your generic codebase is as small as possible - only instantiation calls
![Page 41: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/41.jpg)
Pros• Small, reusable, readable, generic classes
• Only the variables are managed in a specific application
• The footprint between a specific app and your generic codebase is as small as possible - only instantiation calls
• Requires a bit more skill.
• Can often mean more bytes of code in the short term.
• Test driven development is a must.
& Cons
![Page 42: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/42.jpg)
I use MooTools
![Page 43: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/43.jpg)
I use MooTools•MooTools makes JavaScript easier (as do
all frameworks).
![Page 44: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/44.jpg)
I use MooTools•MooTools makes JavaScript easier (as do
all frameworks).
•It encourages you to reuse your work, and to write your code to be flexible for future use.
![Page 45: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/45.jpg)
I use MooTools•MooTools makes JavaScript easier (as do
all frameworks).
•It encourages you to reuse your work, and to write your code to be flexible for future use.
•It is designed to be extended.
![Page 46: Programming To Patterns](https://reader038.vdocument.in/reader038/viewer/2022102922/54b72e414a7959193b8b4574/html5/thumbnails/46.jpg)
I use MooTools•MooTools makes JavaScript easier (as do
all frameworks).
•It encourages you to reuse your work, and to write your code to be flexible for future use.
•It is designed to be extended.
•These are qualities of JavaScript really; MooTools just makes the interface more accessible.