var generic = generic || {};
generic.flash = {
    abort: false,
    swfObject : swfobject,
    defaults : {
        defaultAlt : { 
            href: "http://www.adobe.com/go/getflashplayer"
        },
        attributes : { 
            playerversion: "9.0.28",
            width: "100%",
            height: "100%", 
                    hspace: 0,
                    vspace: 0,
                    align: "top"
        },
        params : {
            wmode: "transparent", 
                    quality: "high",
                menu: "true",
                    swliveconnect: "true",
                    allowscriptaccess: "always", 
                    scale: "noScale",
                    allowfullscreen: "true"
                } 
        },
    
    embed: function (attributes, params, placeholderId) { 
        if (generic.flash.abort) return;
     
        if (!$(placeholderId)) { 
            console.log("generic.flash.embed: Element doesnt exist"); 
            return; 
        }    
        
        /**
        //BUG: if two swfs are embedded at the same time (with no delay) & there is a "this" reference,
        //the second one is embedded twice.
                attributes = generic.mixin(generic.flash.defaults.attributes,attributes);
                params = generic.mixin(generic.flash.defaults.params,params);
                **/     
                   var defaults = {
        defaultAlt : { 
            href: "http://www.adobe.com/go/getflashplayer"
        },
        attributes : { 
            playerversion: "9.0.28",
            width: "100%",
            height: "100%", 
                    hspace: 0,
                    vspace: 0,
                    align: "top"
        },
        params : {
            wmode: "transparent", 
                    quality: "high",
                menu: "true",
                    swliveconnect: "true",
                    allowscriptaccess: "always", 
                    scale: "noScale",
                    allowfullscreen: "true"
                } 
                 };
                 
                attributes = Object.extend(defaults.attributes, attributes);
                params = Object.extend(defaults.params, params);
                 
            if (typeof params.flashvars != "string") { 
                params.flashvars = Object.toQueryString(params.flashvars); 
            }  
     
        // version check
        if (generic.flash.swfObject.hasFlashPlayerVersion(attributes.playerversion)) {   
            generic.flash.swfObject.addDomLoadEvent(function() { 
                generic.flash.swfObject.createSWF(attributes,params,placeholderId); 
            }); 
            return;
        }
         
        //content if flash doesn't embed
        var altid = attributes.altcontentid; 
        if (altid && $(altid)) {
            altid.style.visibility = "visible";
                    altid.style.display = "block";
        } else { 
            var defaultalt = $(placeholderId).select(".noflash")[0]; 
            if (!defaultalt) return; 
            if (!defaultalt.getAttribute("href")) {
                     defaultalt.observe("click", function() {
                window.open(defaults.defaultAlt.href);
               });
            }
            defaultalt.style.visibility = "visible";
                    defaultalt.style.display = "block";
          
        }     
    },

    /**
     * @namespace favorites contains favorites-related methods that are called by Action Script.
     * @memberOf generic.flash
     */
    favorites: {
        /* Used by Action Script to add items to a collection. Response data
         * is returned via a callback function.
         * @param args {object}
         * @param args.movieName {String} the value of the embed/object tag's name attribute
         * @param args.callback {String} the name that the container (the browser) uses to access the callback Function
         * @param args.skuBaseId {String} the value of the SKU_BASE_ID field for the SKU that is to be added
         * @methodOf generic.flash.favorites
         */
        add: function (args) {
            var options = Object.extend( {
                movieName : "",
                callback: "",
                skuBaseId: ""
            }, args);

            if ( options.skuBaseId.length < 1 ) {
                return null;
            }
            if ( !generic || !generic.checkout || !generic.checkout.cart ) {
                return null;
            }
            var cartObj = generic.checkout.cart;            
            var callbackFn = function(options, responseObj) {
                // console.log(responseObj.getMessages());
                if ( options.movieName.length > 1 &&
                    document[options.movieName] &&
                    document[options.movieName][options.callback] &&
                    typeof document[options.movieName][options.callback] === "function" ) {
                    if (responseObj.getMessages() || responseObj.getError()) {
                        document[options.movieName][options.callback](responseObj.getMessages());                        
                    }
                }
            }.curry(options);
            cartObj.updateCart({
                params: {
                    skus: [options.skuBaseId],           
                    itemType: "favorites",
                    action: "add"
                },
                onSuccess: callbackFn,
                onFailure: callbackFn
            });        
        }
    },

    /**
     * @namespace cart contains cart-related methods that are called by Action Script.
     * @memberOf generic.flash
     */
    cart: {
        /* Used by Action Script to add items to user's shopping cart. Response data
         * is returned via a callback function.
         * @param args {object}
         * @param args.movieName {String} the value of the embed/object tag's name attribute
         * @param args.callback {String} the name that the container (the browser) uses to access the callback Function
         * @param args.skus {Array} the value of the SKU_BASE_ID field for each SKU that is to be added
         * @param args.quantity: {Number} the quantity of items that will be added to the cart.             
         * @methodOf generic.flash.cart
         */
        add: function (args) {
            var options = Object.extend( {
                movieName : "",
                callback: "",
                skus: [],
                quantity: 1
            }, args);
            if ( options.skus.length < 1 ) {
                return null;
            }
            if ( !generic.checkout || !generic.checkout.cart ) {
                return null;
            }
            var cartObj = generic.checkout.cart;            
            var callbackFn = function(options, responseObj) {
                if ( options.movieName.length > 1 &&
                        document[options.movieName] &&
                        document[options.movieName][options.callback] &&
                        typeof document[options.movieName][options.callback] === "function" ) {
                    if (responseObj.getData()) {
                        document[options.movieName][options.callback](responseObj.getData().ac_results);                        
                    } else if (responseObj.getError()) {
                        document[options.movieName][options.callback](responseObj.getMessages());
                    }
                }
            }.curry(options);
            cartObj.updateCart({
                params: {
                    skus: options.skus,            
                    INCREMENT: 1
                },
                onSuccess: callbackFn,
                onFailure: callbackFn
            });         
        }
    }
};
