NAME
    MooseX::Prototype - prototype-based programming for Moose

SYNOPSIS
    From Wikipedia: *"Prototype-based programming is a style of
    object-oriented programming in which classes are not present, and
    behaviour reuse (known as inheritance in class-based languages) is
    performed via a process of cloning existing objects that serve as
    prototypes."*

       use MooseX::Prototype;
   
       my $Person = object {
          name       => undef,
       };
   
       my $Employee = $Person->new->extend({
          job        => undef,
          employer   => undef,
       });
   
       my $CivilServant = $Employee->new(
          employer   => 'Government',
       );
   
       $CivilServant->extend({
          department => undef,
       });
   
       my $bob = $CivilServant->new(
          name       => 'Robert',
          department => 'HMRC',
          job        => 'Tax Inspector',
       );
   
       print $bob->dump;
   
       # $VAR1 = bless( {
       #    name       => 'Robert',
       #    job        => 'Tax Inspector',
       #    department => 'HMRC',
       #    employer   => 'Government'
       # }, 'MooseX::Prototype::__ANON__::0006' );

DESCRIPTION
    Due to familiarity with class-based languages such as Java, many
    programmers assume that object-oriented programming is synonymous with
    class-based programming. However, class-based programming is just one kind
    of object-oriented programming style, and other varieties exist such as
    role-oriented, aspect-oriented and prototype-based programming.

    A prominent example of a prototype-based programming language is
    ECMAScript (a.k.a. Javascript/JScript/ActionScript). ECMAScript does
    provide a thin class-like layer over the top of its prototype-based OO
    system, which some (even experienced) ECMAScript developers rarely see
    beyond.

    This module implements a thin prototype-like layer on top of Moose's
    class/role-based toolkit.

  Ex-Nihilo Object Creation
    In prototype-based languages, objects are created by cloning other
    objects. But it's often useful to be able to magic up an object out of
    nowhere. MooseX::Prototype provides a convenience function to do this:

    `object \%attrs`
        Creates a new object with the given attributes. The hash is treated as
        attribute-name, attribute-value pairs, but any names beginning with
        "&" are installed as methods. For example:

           my $person = object {
              "name"         => "Robert",
              "&changeName"  => sub {
                 my ($self, $newname) = @_;
                 $self->name($newname);
              },
           };

        Objects created this way inherit from Moose::Object and perform the
        `MooseX::Prototype::Trait::Object` role.

  Creating Objects from a Prototype
    A prototype is just an object. When you create a new object from it, the
    prototype will be cloned and the new object will inherit all its
    attributes and methods.

    `$prototype->new(%attrs)`
        Creates a new object which inherits its methods and attributes from
        $prototype. The %attrs hash can override attribute values from the
        prototype, but cannot add new attributes or methods.

        This method is provided by the `MooseX::Prototype::Trait::Object`
        role, so $prototype must perform that role.

    `$prototype->create_class`
        Rather than creating a new object from a prototype, this creates a
        whole new Moose class which can be used to instantiate objects. If you
        need to create a whole bunch of objects from a prototype, it is
        probably more efficient to create a class and use that, rather than
        just calling `new` a bunch of times.

        The class can be given a name, a la:

           $prototype->create_class("Foo::Bar");

        Otherwise an arbitary name will be generated and returned.

        This method is provided by the `MooseX::Prototype::Trait::Object`
        role, so $prototype must perform that role.

    `create_class_from_prototype($prototype)`
        A convenience function allowing you to use arbitary Moose objects
        (which lack the `create_class` method) as prototypes.

        Also note:

           my $obj = create_class_from_prototype($proto)->new(%attrs);

        This function is not exported by default, but can be exported using:

           use MooseX::Prototype -all;

  Extending Existing Objects
    A key feature of Javascript is that new attributes and methods can be
    given to an object using simple assignment;

       my_object.some_attribute = 123;
       my_object.some_method = function () { return 456 };

    In MooseX::Prototype, there is an explicit syntax for adding new
    attributes and methods to an object.

    `$object->extend(\%attrs)`
        As per ex-nihilo object creation, the attribute hashref can define
        attribute name-value pairs, or new methods with a leading "&".

HISTORY
    Version 0.001 of MooseX::Prototype consisted of just a single function,
    `use_as_prototype` which was much the same as
    `create_class_from_prototype`.

    Version 0.002 is an almost complete rewrite.

BUGS
    Please report any bugs to
    <http://rt.cpan.org/Dist/Display.html?Queue=MooseX-Prototype>.

SEE ALSO
    Object::Prototype, Class::Prototyped, JE::Object.

AUTHOR
    Toby Inkster <tobyink@cpan.org>.

COPYRIGHT AND LICENCE
    This software is copyright (c) 2012 by Toby Inkster.

    This is free software; you can redistribute it and/or modify it under the
    same terms as the Perl 5 programming language system itself.

DISCLAIMER OF WARRANTIES
    THIS PACKAGE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
    WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
    MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.

