 Thanks guys, my name is Shane Riley. I'm the front-end developer for hash rocket. We are a Ruby on rails consultancy primarily. We're just now getting into Objective C development for iphone ipad, etc. I Wanted to go through A bit about how we have started developing our jQuery plugins a Lot of times when we need to solve a specific problem The plugins we come across They tend to have Far too many options for for what we're looking for we want something that's As slim as can be does exactly what we need and is also something that that we're comfortable with Digging into and modifying on a case-by-case basis So I wanted to kind of share that process we we've started doing With our plug-in development So plug-ins I imagine nearly everyone here has used them how many people have used a plug-in on a project and Figured every hand would be up So plug-ins they're not just for slideshows and autocompletes although I'm sure you've used them most often for those They abstract repetitive code for reuse which is nice You're not copying and pasting Like the dynamic drive days if anyone remembers that Allows you to customize by passing in an options hash so The usual plug-in pattern rather than having 12 arguments and passing in null for a foam you have an options hash where you just Add the options that you need to override You've got portability between projects It's very easy to encapsulate Plug-in code and move it from one file to it or one project to another Simply by including that file and It's easier to test as as we've already seen So I'm not gonna go too far into that but Let's go into The anatomy of a plug-in. This is a very basic Example skeleton of how you would write a plug-in. This is taken right from the jQuery docs website Which I've been told by yarn is Severely out of date. Hopefully that'll be fixed soon Okay, so what we got here As you've seen in in Ben's Talk here, we've got an immediately called function where we pass in the jQuery object That's already been explained yet, and then we attach a method to the buck dot fn object the usual Behavior you you get an options object You extend that options object with the defaults as you see on line six through nine So we've got the extend method being called we're storing that extended object in the settings And then we do whatever plug-in Code we need in the each loop and make sure to return the jQuery collection maintain maintain chain ability So if you got an edge to scratch There's always a plug-in for that in fact, there's probably 20 plugins for that So why would you go through and develop your own plug-in? For us primarily, it's the learning experience. I I think figuring out how How you develop a plug-in to to serve that need Allows you to identify a number of Pitfalls and issues that you normally wouldn't come across and that ends up making you a better developer as a result So let's take a contrived example of an accordion plug-in And put that to use so we've got The same sort of Pattern that we saw in the example. We've got an options object. We're extending I We're going to iterate over the collection make sure to return the collection for chain chain ability I And then internally we're going to cash each instance of the collection Just to make it a little bit easier to read So let's put the plug-in to use we're going to call it with all the defaults So we're just going to call Dot accordion on it But then the the client says hey, you know, it'd be great If we click on this link in the footer and they take action on this particular thing We want the last Instance of this accordion to behave differently. We want it to animate in a different way You gotta be kidding me We handpicked this this plug-in because it's it serves exactly the purpose that we need, you know It doesn't have this functionality built-in. What do we do? Do we go out and search for another plug-in? Do we modify the existing one? If we modify the existing one water, what are the problems that will counter along the way throughout the rest of the development of the application? First thing you want to do is Rebind your plug-in. This is kind of the quick and dirty way of Achieving what the what the client wants So rather than modify the plug-in and and have the possibility of the plug-in being overwritten When a new version comes out and another developer not knowing you've overwritten it We're gonna unbind the click event Re-initialize the plug-in with the new option The problem is you need to add the option to the plug-in. So we're back to the issue of not being able to to update the plug-in without shoe-horning this back in So let's continue down this path modify the plug-in We're gonna create a new anim animation method object or property rather on the options object And then just use the array notation to call the method based on what's on the options So by default we'll call slide toggle For what the client needs we just want to call toggle with a particular speed and callback So what happens if you do update the plug-in if it needs to be updated the changes have to be retrofitted So a pull request could be submitted to the the plug-in author If they're using git, but it's not guaranteed it'll be introduced into master So you may still have to continue shoe-horning this in with each release of the plug-in So another option is changing the options after the fact But it's difficult to change the options in in this case once the Options are passed in and the plug-ins initialized We don't have that exposed anywhere on the object So we don't have any way internally or externally to modify that without unbinding and rebinding it So you may need to unbind and rebind events in this instance, which is Really messy You may also need to keep track of all the elements with the plug-in called on them for this purpose Because as as we saw and as I'll go over a little bit later There's no namespacing of that event. So you don't know which event you're unbinding When you call unbind click you may be unbinding some other plug-in code and now that's that functionality is no longer be there And it may also be difficult or impossible to unbind only those elements as I just mentioned, but Let's start improving on this this plug-in pattern So what we're gonna do is read the plug-in name from a plug-in object to start with So this is gonna be used for namespacing your events and provide a single point of editing when naming conflicts arise So if you have similar plug-ins Throughout the site and they're they're being Included on the same page you can change the namespace of this one plug-in It's something more specific so that they're not stepping on each other's toes So we're gonna provide a plug-in name is object property. We're gonna read the plug-in name from the object use it for the namespacing and Provide a single point to modify that in the future We're gonna go through a namespace the event bindings Have an option to live bind an event or bind it to a context both with the the new on method So where do we start with this refactor? Well, if you look further down in the documentation on plug-in development There's an example that's close to what we what we're shooting for And I'm just gonna break this apart into a couple pieces here First we've got an Object that's going to store all of our methods. They're gonna be called either internally or externally related to this plug-in So we've got an initialized method that's gonna do the event binding and whatnot the event binding as you see is going to Trigger the reposition method also on the same object So it's nice neat encapsulated. You know where everything is And then we have an option to call the method externally If we pass in a string instead of an object we can call any one of these individual methods from outside of the plug-in Which is a tremendous benefit the more you get into customizing plug-ins And then of course we initialize the plug-in by attaching the event So let's start rewriting with this sort of pattern So we create our plug-in object Name an accordion appropriately and as you see here, we've got a name property of accordion That's gonna be used again for namespacing and for attaching to the buck fn object We've got the same after callback as before and then we've taken the Click event and abstracted that into a method called toggle And it what you'll see in the initializer are we're going to bind accordion toggle to the click event And then we're going to add the namespace To that click event so it's easier to identify and unbind that with the teardown method Now why are we calling the method? in here I from what I found It's a little bit easier to understand What's going on when you override the method externally? What we're going to do is Store an instance of this object this accordion object and outside of the plug-in You'll be able to modify that method because it's publicly exposed However, since that was already bound there's a pointer to the original or the original method So your modified methods not going to get called in this instance The modified version is always going to be called because it's always going to look it up and get the most recent version of it So let's initialize the plug-in. We're using the accordion name property to make sure that we're using the same namespace It's much easier to change the plug-in name this way if conflicts arise, of course I and the first condition provides the ability to call methods by name on the collection The second condition Will run the initialization so if we pass in an object instead of a string we know to initialize There's a separate copy of the plug-in created as a plug-in instance That we're later going to use To attach as a data object so we can access it externally on a per element basis per collection basis whatever you're going to do to to override And then we can override the toggle method somewhat similar as before it's still a bit Disgusting how we how we're doing this so we want to try and clean this up a bit more Because this gets a little spaghetti like We also have lost our new option for the animation method, so we need to get that added back in So we're going to put a new option for animation method again call the method with the array notation And now we can just change the method name rather than rewrite the callback So when the user clicks on the link in the footer at the last post needs to have a different Animation method we just change that Much cleaner. So let's talk about some other optimizations. We want to create a tear down method So in this example This will unbind all the namespace methods and remove any data stored on the objects So those separate instances of the the plug-in object those will be removed along with the events Much easier to do now that we've got it namespaced We're going to add live binding in context. So If the context is set the events bound to the context rather than each element individually Otherwise the events live bound. This makes a big deal particularly when when dealing with tabular data and having some sort of events on the table cells or Really large pages in in general where you're listing a tremendous amount of content and you want the same event called on Each individual element rather than binding that to each one You bind on the context a lot of plugins. I've seen don't don't really do that. They just bind it to whatever the collection is They're going to bind the event to the parent element that these are our options that we've created in order to do that So we've got the element that it's Going to trigger the click event on within the context of the details container So let's bring this all back together. We've got a new development pattern We're recreating an internal plug-in object to contain defaults and methods It makes it much cleaner to To find the method that you're you're needing to work on that you need to modify Gives you the ability to call methods directly from outside of the plug-in. So for example the destroy method rather than than that being internal and you having to Somehow call that externally we've already got a way to call that externally along with the Animation methods things like that. So if you need to call it on its own rather than trigger the click event you can You can create and store standalone plug-in instances. So as we saw we were writing each instance of the plug-in object on the element So you can override it on a per element basis The plug-ins names based makes it a lot easier to determine which Events we need to remove and we've got the teardown method to facilitate that So the benefits of this method you can write your own overrides to suit your individual needs You don't have to go hunting for a different plug-in when the requirements change You also rarely have to crack open the code in order to modify the plug-in You can upgrade to a new plug-in version without much concern that your your overrides are going to be lost Since you're not modifying the plug-in code itself at this point You can just upgrade to a new version as long as the plug-in author is using the same sort of methods and whatnot Everything will still work. You'll still override what needs to be overridden And again overriding makes or overriding this stuff is much easier as a result So I got a bit of recommended reading and a disclaimer when I started putting this talk together and submitted it I thought I had come across some amazing new way to To develop plug-ins and it turns out as a lot of people have pointed out on the on the jQuery team This already exists in jQuery UI as buck.widget Scott Gonzalez has a blog post on it. There's also some documentation that's forthcoming That does what we've covered in then some so check that out That's the the second link here at the first link is James penalty's link on How jQuery plugins are broken the the initial example I showed you that's he's going into that same sort of Explanation and If you want your mind blown and and you want to see 40 different ways to write a plug-in adi Osmani's got a GitHub repo With a tremendous number of different approaches at the third link there And this will all of course be in the slides on the events website So that's it I I'm Shane Riley. Thanks for listening