bf_user_post = function() {
	this.ajax = new BF_Request();
	this.categories = {'7':'Food',
        '2':'Movie',
        '3':'Music',
        '4':'Tech',
        '5':'Style',
        '6':'Celebrity',
        '9':'TV',
        '10':'Politics',
        '11':'Sports',
        '12':'Culture',
        '13':'Business',
        '15':'Science'
	};
	this.__auto_complete = {};
	this.__auto_complete_elements = [];
	this.__auto_complete_idx = 0;
	// methods for preprocessing
	this.CLEANUP = {
		'prepend_http' : function(str) {
			if ( str == '' ) return '';
			else if (!str.match(/^https?:\/\//)) return 'http://'+str;
			else return str;
		},
		'trim' : function(str) {
			return str.strip();
		},
				
		'url_entities' : function(s) {
			if(s) {
				var newtext = '';
				var chars = s.split("");
				for(i = 0; i < chars.length; i++) {
					var chr = chars[i].charCodeAt(0);
					if( chr > 127 ) { 
						newtext += encodeURIComponent(chars[i]);
					} else { 
						newtext += chars[i];
					}
				}
				return newtext;
			}
		}
	};
	
	// methods for validation
	this.VALIDATE = {
		'required' : function(str) {
			return str.length>0;
		}
	};
	
	// Map button IDs to buzz type
	this.ID_TO_TYPE_MAP = {
		'quickpost-create-link':'link',	
		'quickpost-create-video':'video',	
		'quickpost-create-image':'image',
		'quickpost-create-enhanced':'enhanced',
		'quickpost-create-list':'enhanced',	
		'quickpost-create-quiz':'enhanced',
		'quickpost-create-embed':'embed'	
	};

	// Map button IDs to buzz type
	this.ID_TO_ENHANCED_MAP = {
 		'quickpost-create-list':'TopList',	
		'quickpost-create-quiz':'ClassifyQuiz'	
	};
	
	// Define values for FB that differe by type
	this.FACEBOOK = {
		form_string : {
			text : '',	
			quote : ' a quote ',
			link : ' a link ',
			image : ' an image ',
			video : ' a video ' 
		}	
	};
	
	// Define unique qualities of different buzz types.
	// List forms to show for data entry, template to use for preview, and map form field to data object.
	// Mapping specifies:
	//  - name in object
	//  - optional label (for error display),
	//  - optional list of preprocess methods to run,
	//  - optional list of validation methods to run
	this.STRUCTURE = {
		'embed': {
			data_entry_form_ids : ['user-edit-quickpost','edit-quickpost-form','quickpost-embed'],
			//template : 'quickpost_embed',
			template : 'quickpost_embed preview_buzz',
			form_to_obj_map : {
				'quickpost-title' : {
					name: 'title',
					label: 'Title',
					field: 'name',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-embed-code': {
					name : 'embed',
					label : 'Embed Code',
					field : 'code',
					preprocess : [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-description': {
					name : 'text',
					label : 'Description',
					field : 'blurb',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-embed-image-file': {
					name : 'thumb',
					label : 'Thumbnail',
					field : 'image',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-tags': {
					name : 'tags',
					field: 'tags'
				},
				'quickpost-categorization': {
					name : 'categorization',
					field: 'category_id'
				},
				'quickpost-tame': {
					name : 'tame',
					field: 'nsfw'
				},
				'buzz-type': { name : 'type' },
				'buzz-type': { name : 'buzz_type' },
				'username': { name : 'display_name' }
			}
		},
		'link': {
			data_entry_form_ids : ['user-edit-quickpost','edit-quickpost-form','quickpost-link'],
			//template : 'quickpost_link',
			template : 'quickpost_link preview_buzz',
			form_to_obj_map : {
				'quickpost-title' : {
					name: 'title',
					label: 'Title',
					field: 'name',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-link-url': {
					name : 'link',
					label : 'Link URL',
					field : 'link_buzz',
					preprocess : [this.CLEANUP.trim,this.CLEANUP.prepend_http,this.CLEANUP.url_entities],
					validation: [this.VALIDATE.required]
				},
				'quickpost-description': {
					name : 'text',
					label : 'Description',
					field : 'blurb',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-link-image-file': {
					name : 'thumb',
					label : 'Thumbnail',
					field : 'image',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-tags': {
					name : 'tags',
					field : 'tags'
				},
				'quickpost-categorization': {
					name : 'categorization',
					field : 'category_id'
				},
				'quickpost-tame': {
					name : 'tame',
					field : 'nsfw'
				},
				'buzz-type': { name : 'type' },
				'buzz-type': { name : 'buzz_type' },
				'username': { name : 'display_name' }
			}
		},
		'image': {
			data_entry_form_ids : ['user-edit-quickpost','edit-quickpost-form','quickpost-image'],
			//template: 'quickpost_image',
			template: 'quickpost_image preview_buzz',
			form_to_obj_map: {
				'quickpost-title': {
					name: 'title',
					label: 'Title',
					field: 'name',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-image-link-url' : {
					name: 'credit_url',
					label: 'Link Image To',
					field : 'credit_url',
					preprocess : [this.CLEANUP.trim,this.CLEANUP.prepend_http,this.CLEANUP.url_entities]
				},
				'quickpost-description' : {
					name : 'caption',
					label: 'Description',
					field : 'blurb',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-image-image-file' : {
					name : 'image',
					label : 'Image',
					field : 'image_buzz',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-tags': {
					name : 'tags',
					field : 'tags'
				},
				'quickpost-categorization': {
					name : 'categorization',
					field : 'category_id'
				},
				'quickpost-tame': {
					name : 'tame',
					field : 'nsfw'
				},
				'quickpost-image-image-width': { name: 'image_width', field:'image_buzz_width' },
				'quickpost-image-image-height': { name: 'image_height', field:'image_buzz_height' },
				'quickpost-image-image-thumb' : { name: 'thumb', field:'image_small' },
				'buzz-type': { name : 'type' },
				'buzz-type': { name : 'buzz_type' },
				'username': { name : 'display_name' }
			}
		},
		'video': {
			data_entry_form_ids : ['user-edit-quickpost','edit-quickpost-form','quickpost-video'],
			//template: 'quickpost_video',
			template: 'quickpost_video preview_buzz',
			form_to_obj_map: {
				'quickpost-title' : {
					name:'title',
					label:'Title',
					field:'name',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-video-url' : {
					name:'video_url',
					label: 'Video URL',
					field: 'video_url',
					preprocess : [this.CLEANUP.trim,this.CLEANUP.prepend_http,this.CLEANUP.url_entities],
					validation: [this.VALIDATE.required]
				},
				'quickpost-description' : {
					name:'caption',
					label:'Description',
					field:'blurb',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-video-image-file' : {
					name: 'thumb',
					label:'Thumbnail',
					field: 'image',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-video-ok' : {
					name:'video_ok',
					label:'Supported Video Source'
				},
				'quickpost-tags': {
					name : 'tags',
					field: 'tags'
				},
				'quickpost-categorization': {
					name : 'categorization',
					field: 'category_id'
				},
				'quickpost-tame': {
					name : 'tame',
					field: 'nsfw'
				},
				'buzz-type': { name : 'type' },
				'buzz-type': { name : 'buzz_type' },
				'username': { name : 'display_name' }
			}
		},
		'enhanced': {
			data_entry_form_ids : ['user-edit-quickpost','edit-quickpost-form','quickpost-enhanced'],
			template: 'quickpost_enhanced preview_buzz',
			form_to_obj_map: {
				'quickpost-title' : {
					name:'title',
					label:'Title',
					field:'name',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-description' : {
					name:'text',
					label:'Description',
					field:'blurb',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-enhanced-image-file': {
					name : 'thumb',
					label : 'Thumbnail',
					field : 'image',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-enhanced-data': {
					name : 'enhanced-data',
					label : 'enhanced',
					field : 'description',
					preprocess: [this.CLEANUP.trim],
					validation: [this.VALIDATE.required]
				},
				'quickpost-tags': {
					name : 'tags',
					field: 'tags'
				},
				'quickpost-categorization': {
					name : 'categorization',
					field: 'category_id'
				},
				'quickpost-tame': {
					name : 'tame',
					field: 'nsfw'
				},
				'buzz-type': { name : 'type' },
				'buzz-type': { name : 'buzz_type' },
				'username': { name : 'display_name' }
			},
			init: function( type ) {

				stub_id = user_post.ID_TO_ENHANCED_MAP[user_post.trigger_element];
				
				new Ajax.Request( "/static/js/enhanced/stubs/" + stub_id + "-stub.js?v=" + BF_STATIC.version,{
						method: 'get',
						onSuccess: function(o) {
							var stub = o.responseText.evalJSON();
							window[stub.id] = { stub: stub, set_field: {} };
							user_post.enhanced_js = window[stub.id];
							if (typeof stub.edit_css != "undefined")
							{
								$$('head').first().insert(new Element('link', {
									href: BF_STATIC.static_root + stub.edit_css + "?v=" + BF_STATIC.version,
									type: "text/css",
									rel: 'stylesheet'
								}));
							}
							
							$('quickpost-enhanced-form').show();
							new Ajax.Updater('quickpost-enhanced-form', '/buzzfeed/_enhanced', {
								parameters: {
									template: stub.edit_template,
									stash: Object.toJSON(window[stub.id])
								},
								onComplete: function(el) { BF_XSS.swift_injection( BF_STATIC.static_root + stub.edit_js + "?v=" + BF_STATIC.version ) }
							});
						}
					});
				$$('.classify-enhanced-class-image').each( function (el) { el.observe('click', user_post.image_handler) } );
				
			},
			preprocess: function() {
				$('quickpost-enhanced-data').value = user_post.enhanced_js.as_string();
			},
			postprocess: function() {
				user_post.enhanced_js.cleanup();				
			}
			
		}
	};
	
	// initialize the object; this happens once per page load
	this.init = function() {
		var user_info = (new BF_User()).getUserInfo();
		if (user_info && typeof user_info.p_disable_quickpost != 'undefined' 
			&& user_info.p_disable_quickpost == 'true')
		{
			$('select-quickpost-box').style.display = 'none';
			return true;
		}
		if ($('get-drafts')) {
			var draft_count = eval('('+$('draft-count').getAttribute('rel:data')+')');
			if ( draft_count.draft_count > 0 ) $('get-drafts').show();
		}
		
		this.set_handlers();
		if ( $('video-supported-text') ) $('video-supported-text').update(BF_VIDEO_TYPES_STRING);
		if ( $('quickpost-video-label') ) $('quickpost-video-label').update('Video URL <span class="note">(' + BF_VIDEO_TYPES_STRING + ')</span>');
		Facebook.observe('user_logged_in', function(){ Facebook.showContributionCheckbox();}, {retroactive:true} );
		Facebook.observe('user_not_logged_in', function(){ Facebook.hideContributionCheckbox()} );
		if ( typeof bf_chicklet != 'undefined' ) bf_chicklet.addLink( function(e) {
			user_post.show_user_post_form( 'link' );
		});
		if (! Prototype.Browser.FF2 && ! Prototype.Browser.IE6 ) {
			var temp = $('quickpost-create-embed');
			if ( temp ) temp.show()
			var temp = $('quickpost-create-enhanced') ;
			if ( temp ) temp.show()
			temp = $('quickpost-create-list') ;
			if ( temp ) temp.show()
			temp = $('quickpost-create-quiz') ;
			if ( temp ) temp.show()
		}
		if ( Prototype.Browser.FF2 || Prototype.Browser.IE6 ) {
			if ($('unsupported-types')) $('unsupported-types').show();
		}
		user_post.initialized = true;
	}
	
	// set buzz type in form, clear all values from the form, then display appropriate form parts for this type
	this.show_user_post_form = function( type ) {
		if( $('bookmarklet-loading-div') ) $('bookmarklet-loading-div').hide();
		this.reset_post_form();
		$('buzz-type').value = type;
		var post_structure = user_post.STRUCTURE[type];
		var forms = post_structure.data_entry_form_ids;
		for( var i = 0; i < forms.length; i++ ) {
			var f = $(forms[i]);
			if ( f.id == 'edit-quickpost-form') f.showOnScreen();
			else f.show();
		}
		if (typeof post_structure.init != 'undefined') post_structure.init(type);
		if ( $('quickpost-save-as-draft') ) $('quickpost-save-as-draft').show();
		if ( $('quickpost-save-as-draft-button') && !window.location.href.match(/\/submit\//) && typeof contest_manager=='undefined') $('quickpost-save-as-draft-button').show();
	}
	
	// Clear out all data and validation-related classes from user post form
	this.reset_post_form = function() {
		this.message('quickpost-error-msg',{hide:true, message:''});
		var hide_ids = ['quickpost-enhanced-form','quickpost-enhanced','quickpost-embed','quickpost-link','quickpost-image','quickpost-video','quickpost-video-thumb-msg','link-thumbnail','enhanced-thumbnail','video-link-thumbnail','image-preview','image-preview-div'];
		var clear_values = ['quickpost-embed-image-file','quickpost-link-image-file','quickpost-video-image-file','quickpost-image-image-thumb','quickpost-image-image-file'];
		var clear_src = ['link-thumbnail','enhanced-thumbnail','video-link-thumbnail','image-preview'];
		for ( var i = 0; i < hide_ids.length; i++ ) {
			var target = $(hide_ids[i]);
			if (target) target.hide();
		}
		for ( var i = 0; i < clear_values.length; i++ ) {
			var target = $(clear_values[i]);
			if (target) target.value = '';
		}
		for ( var i = 0; i < clear_src.length; i++ ) {
			var target = $(clear_src[i]);
			if (target) target.src = '';
		}
		$('quickpost-video-ok').value='true';
		$('quickpost-video-thumb-msg').update('');
		$('embed-preview').update('');
		this.clear_form_of_errors();
		$('edit-quickpost-form').reset();
	}
		
	// Clear out all validation-related classes from user post form
	this.clear_form_of_errors = function() {	
		var form = $('edit-quickpost-form');
		var divs = form.getElementsByTagName('DIV');
		var missing_regex = new RegExp('missing', 'i');
		var error_regex = new RegExp('error', 'i');
		for ( var i = 0; i < divs.length; i++ ) {
			this.remove_class( divs[i], missing_regex );
		}
		for ( var i = 0; i < form.elements.length; i++ ) {
			this.remove_class( form.elements[i], error_regex );
		}
	}
	
	// request preview of data
	// for enhanced types, we must call save_panel, which will call the _preview_from_server method after it is done;
	// for other types, just call _preview_from_server directly.
	this.preview_from_server = function( obj, fn ) {
		if ( obj.buzz_type=='enhanced') {
			user_post.save_panel(user_post.enhanced_js.as_string(), obj, fn);
		}
		else {
			this._preview_from_server( obj, fn );
		}
	}
	
	// this is the real logic for preview. 
	this._preview_from_server = function( obj, fn ) {	
		if ($('quickpost-spinner')) $('quickpost-spinner').show();
		var user = new BF_User();
		var userInfo = user.getUserInfo();
		obj.display_name = (userInfo.display_name=='' || typeof userInfo.display_name == 'undefined') ? userInfo.username : userInfo.display_name;		
		obj.username = userInfo.username;
		if(userInfo.image && userInfo.image != null && userInfo.image != 'null') {
			obj.user_image = userInfo.image;			
		} else {
			obj.user_image = '/static/images/public/defaults/user_large.jpg';
		}
		obj.action = 'process';
		obj.preview = 'true';
		obj.since_minutes = '1';
		obj.static_root = parent ? parent.BF_STATIC.static_root : BF_STATIC.static_root;
		obj.web_root = parent ? parent.BF_STATIC.web_root : BF_STATIC.web_root;
		obj.image_root = parent ? parent.BF_STATIC.image_root : BF_STATIC.image_root;
		obj.big_image_root = parent ? parent.BF_STATIC.image_root : BF_STATIC.image_root;
		// terminal-preview variables
		var user = new BF_User();
		var user_info = user.getUserInfo();
		obj.page='Buzz';
		obj.buzz = {
			badges:[],
			blurb:obj.caption?obj.caption:(obj.text?obj.text:obj.blurb),
			call_to_action:'',
			campaignid:obj.campaignid?obj.campaignid:0,
			category_name:user_post.categories[obj.categorization+''] ? user_post.categories[obj.categorization+''] : '',
			click:'',
			contribution:{
				link:1,
				video:1,
				image:1,
				quote:1,
				text:1
			},
			clientid:1,
			commentary_raw_html:obj.commentary_raw_html ? obj.commentary_raw_html : 0,
			credit_url:obj.credit_url,
			display_name:user_info.display_name,
			fedcount:'',
			form:obj.buzz_type,
			image:obj.thumb,
			image_buzz:obj.image,
			image_buzz_height:obj.image_height,
			image_buzz_width:obj.image_width,
			impressions:'',
			link_buzz:obj.link,
			links:[],
			name:obj.title,
			origin:'quickpost',
			parent:0,
			short_description:obj.short_description,
			since_minutes:1,
			tag_list:obj.tags?obj.tags.split(','):'',
			title_is_excerpt:'',
			unix_time:'1234567890',
			uri:obj.uri?obj.uri:'',
			user_id:0,
			user_image:'',
			username:user_info.username,
			video_url:obj.video_url,
			code:obj.embed,
			preview_mode:true
		};
		if ( obj.buzz.code ) {
			var width = 200;
			var height = 200;
			if ( obj.buzz.code.match(/width\s*=\s*'?"?(\d+)/i) ) width = RegExp.$1;
			if ( obj.buzz.code.match(/height\s*=\s*'?"?(\d+)/i)) height = RegExp.$1;
			obj.buzz.embed_data = {
				width:width,
				height:height,
				embed_domain:'/'
			}
		}
		if ( obj.buzz.form == 'image' ) obj.buzz.image='';
		user_post.posted_buzz = obj.buzz;
		//obj.buzz.code = escape(obj.buzz.code);
		obj.buzz = Object.toJSON(obj.buzz);
		if ( !user_post.save_as_draft ) {
			user_post.ajax.request('/buzzfeed/_template', {
				method:'post',
				parameters:obj,
				onSuccess: fn,
				onFailure: function(resp){alert('Error contacting server');$('quickpost-spinner').hide()},
				bf_auth: true 
			});
		}
		else {
			fn({responseText:Object.toJSON({
				success : true
			})},obj);
		}
	}
	
	this.save_panel = function ( app_json, obj, fn ) {
		json = eval('('+app_json+')');
		var ajax = new BF_Request();
		ajax.request( '/buzzfeed/_enhanced',{
			parameters: {
				template: json.stub.public_template,
				stash: '{ "enhanced":' + app_json + '}'
			},
			onSuccess: function(o){
				obj.short_description = user_post._cleanup_wide_chars( o.responseText.replace(/\n/g,'') );
				obj.commentary_raw_html=1;
				user_post._preview_from_server( obj, fn );
			}
		});
	};
	
	this._cleanup_wide_chars = function( str ) {
		var value;
		try{
		var cleanup_div = document.createElement('div');
		var cleanup_input = document.createElement('input');
		cleanup_div.setAttribute('style', 'display:none');
		cleanup_input.setAttribute('style', 'display:none');
		document.getElementsByTagName('BODY')[0].appendChild(cleanup_div);
		document.getElementsByTagName('BODY')[0].appendChild(cleanup_input);
		cleanup_div.update( str );
		cleanup_input.value = cleanup_div.innerHTML;
		value = cleanup_input.value;
		cleanup_div.parentNode.removeChild( cleanup_div );
		cleanup_input.parentNode.removeChild( cleanup_input );
		} catch(e){}
		return value || str;
	}
	
	// show preview on screen
	this.preview_from_server_ok = function( r ) {
		if ($('quickpost-spinner')) $('quickpost-spinner').hide();
		var obj = eval( '('+ r.responseText +')' );
		if ( obj.success ) {
			if (obj.preview_buzz) {
				obj.preview_buzz = obj.preview_buzz.replace(/<object.*\/object>/i, '');
				// show iframe (user_post_preview)
				BF_UI.showDialog('user_post_preview', 'Preview');
				// populate div in iframe with obj.snippet
				//var el = window.frames[1].document.getElementById('preview_div');
				var el = window.frames['user_post_preview_iframe'].document.getElementById('preview_div');
				el.innerHTML = obj.preview_buzz;
				
				if (typeof user_post.enhanced_js != 'undefined')
				{

					try {
						if (user_post.enhanced_js.stub.public_js)
						{
							var our_frame = window.frames['user_post_preview_iframe'];

							var script_el = new our_frame.Element('script', {src: BF_STATIC.static_root + user_post.enhanced_js.stub.public_js + "?v=" + user_post.enhanced_js.stub.version });

							our_frame.document.getElementsByTagName('head')[0].appendChild(script_el);
						}
					} catch (e) { console.error(e); }
				}
				
				// special logic for embeds
				//var ifrm = window.frames[1].document.getElementById('embed');
				var ifrm = window.frames['user_post_preview_iframe'].document.getElementById('embed');
				if ( ifrm ) {
					ifrm = (ifrm.contentWindow) ? ifrm.contentWindow : (ifrm.contentDocument.document) ? ifrm.contentDocument.document : ifrm.contentDocument;
					var code = unescape(user_post.posted_buzz.code);
					ifrm.document.open();
					ifrm.document.write( code );
					ifrm.document.close();
				}
				// special logic for video
				if ( user_post.posted_buzz.form == 'video' ) {
					if ( top.frames['user_post_edit_iframe'] && top.frames['user_post_edit_iframe'].frames['user_post_preview_iframe'] )
					top.frames['user_post_edit_iframe'].frames['user_post_preview_iframe'].load_video(user_post.posted_buzz.video_url);
					else if ( top.frames['user_post_preview_iframe'] ) {
						top.frames['user_post_preview_iframe'].load_video(user_post.posted_buzz.video_url);
					}
				}
			}
			if ( obj.snippet ) {
				var html = obj.snippet;
				html = "<div id='list-of-buzz-preview'><ul class='flow'>" + html + "</ul></div>";
				if ($('contribute-preview-content')) {
					$('contribute-preview-content').update( html );
					if (!obj.preview_buzz) $('contribute-preview').show();
					else $('contribute-preview').hide();
				}
			}
		}
		else {
			var error_msg = '';
			for( var key in obj.errors ) {
				if ( error_msg != '' ) error_msg += ', ';
				error_msg += obj.errors[ key ];
			}
			user_post.error('quickpost-error-msg',{show:true,message:error_msg});
			$('contribute-preview').hide();
		}
	}
	
	// show preview on screen, then save user post
	this.preview_from_server_and_save = function( r, data ) {
		user_post.preview_from_server_ok(r);
		user_post.fire_event('save:preparing', data);
		$('quickpost-spinner').show();
		var obj = eval('('+r.responseText+')');
		$('user_post_preview').hide();
		data.not_promoted = 1;
		if ($('quickpost-publish') && $('quickpost-publish').checked) delete data.not_promoted ;
		if (user_post.save_as_draft) data.draft = 1;
		if ( obj.success ) {
			user_post.ajax.request('/buzzfeed/_contribute', {
				method:'post',
				parameters:data,
				onSuccess: function(resp){
					user_post.save_ok(resp, data)
				},
				onFailure: function(resp){
					user_post.save_failed(resp);
				}, bf_auth: true
			});
		}
	}
	
	// upon successful save, send to FB (if desired), clear form, update page with new user post
	this.save_ok = function( r, data ) {
		var json = eval( '('+r.responseText+')' );
		if ( json.updated ) {
			BFW_Util.updateInfoCookie({last_active:json.last_active});
			user_post.buzz = json;
			if ( $('embed-preview') ) $('embed-preview').hide();
			var fb_post = $('facebook_post_contribution_checkbox');
			fb_post = fb_post && fb_post.checked;
			if ( fb_post ) {
				data.form_string = user_post.FACEBOOK.form_string[data.buzz_type];
				data.uri = json.uri;
				if (! data.text && data.caption ) data.text = data.caption;
				if (! data.blurb && data.text ) data.blurb = data.text;
				data.image_src = json.thumb;
				Facebook.postToWall( 'quickpost', data );
			}
			if ( !json.draft ) {
				user_post.copy_preview_to_list(json);
			}
			else {
				user_post.saved_as_draft_notice(json);
			}
			user_post.reset_post_form();
			$('user-edit-quickpost').hide();
			$('quickpost-spinner').hide();
			$('contribute-preview').hide();
			$('select-quickpost-box').show();
			user_post.fire_event('save:success', {data:data,json:json});
		}
		else {
			user_post.save_failed(json);
		}
	}
	
	this.update_element = function( id, content ) {
		var parent = $(id).parentNode;
		var span = document.createElement('span');
		span.innerHTML = content ;
		span.id = id;
		parent.replaceChild( span, $(id) );
	}
	
	// upon unsuccessful save, notify user
	this.save_failed = function( obj ) {
		$('quickpost-spinner').hide();
		if(obj.error == 'duplicate name') {
			user_post.message('quickpost-error-msg',{
				show:true,
				message: "You've already posted a buzz with that name. Please rename your buzz."
			});
		} else {
			user_post.message('quickpost-error-msg',{
				show:true,
				message:'An error occurred whle trying to save your post.'
			});			
		}
		user_post.fire_event('save:failed', {json:obj});
	}
	
	// clone preview and add it to list of user posts
	this.copy_preview_to_list = function(json) {
		var buzz_type = $('edit-quickpost-form').elements['buzz-type'].value ;
		var obj = user_post.build_post_object(buzz_type);
		if ( user_post.buzz.id ) obj.campaignid = user_post.buzz.id;
		if ( user_post.buzz.uri ) obj.uri = user_post.buzz.uri ;
		user_post.preview_from_server(obj, function(r){
			var rObj = eval( '('+r.responseText+')' );
			var html = rObj.snippet;
			html = "<div id='list-of-buzz-preview'><ul class='flow'>" + html + "</ul></div>";
			if ($('contribute-preview-content')) {
				$('contribute-preview-content').update( html );
			}
			user_post._copy_preview_to_list(json)
		});
	}	
	
	this._copy_preview_to_list = function(json) {
		try {
			if ( !$('list-of-buzz') ) return;
			var user = new BF_User();
			var user_info = user.getUserInfo();
			var first_buzz;
			var list_of_buzz = $('list-of-buzz').getElementsByTagName('UL')[1];
			if ( list_of_buzz ) {
				first_buzz = list_of_buzz.firstChild;
			}
			if ( !list_of_buzz ) {
				list_of_buzz = $('list-of-buzz').getElementsByTagName('P')[0];
				list_of_buzz.innerHTML='';
				list_of_buzz.appendChild(document.createElement('div'));
				first_buzz = list_of_buzz.firstChild;
			}
			var quickpostView = $('preview-quickpost').cloneNode(true);
			quickpostView.id = (new Date()).getTime();
			// update url
			var hrefs = quickpostView.getElementsByTagName('A');
			for( var i = 0; i < hrefs.length; i++ ) {
				if ( hrefs[ i ].href.match(/\/#quickpost/) ) {					
					hrefs[ i ].href = BF_STATIC.web_root + '/'+user_info.username+'/'+json.uri;
				}
			}
			// update image
			var images = quickpostView.getElementsByTagName('img');
			for( var i = 0; i < images.length; i++ ) {
				if ( images[ i ].src.match(/\/static\/tmp\//) ) {					
					images[ i ].src = BF_STATIC.image_root + json.thumb;
				}
			}
			list_of_buzz.insertBefore(quickpostView, first_buzz);
			bf_editor.init();
		} catch(e) {
			console.error(e);
		}
	}
	
	this.saved_as_draft_notice = function(json){
		var first_buzz;
		if ( !$('list-of-buzz') ) return;
		var list_of_buzz = $('list-of-buzz').getElementsByTagName('UL')[1];
		if ( list_of_buzz ) {
			first_buzz = list_of_buzz.firstChild;
		}
		if ( !list_of_buzz ) {
			list_of_buzz = $('list-of-buzz').getElementsByTagName('P')[0];
			list_of_buzz.innerHTML='';
			list_of_buzz.appendChild(document.createElement('div'));
			first_buzz = list_of_buzz.firstChild;
		}
		var user_info = (new BF_User()).getUserInfo();
		
		var quickpostView = document.createElement('li');
		var h3 = document.createElement('h3');
		h3.appendChild( document.createTextNode('Your Draft Has Been Saved') );
		var p = document.createElement('p');
		var a = document.createElement('a');
		a.setAttribute('href',BF_STATIC.web_root + '/drafts/' + user_info.username);
		a.appendChild( document.createTextNode( 'your drafts page' ) );
		p.appendChild( document.createTextNode('You can view, edit, and publish draft posts anytime from ') );
		p.appendChild(a);
		p.appendChild( document.createTextNode('.') );
		
		quickpostView.appendChild( h3 );
		quickpostView.appendChild( p );
		/*
		var terminalLink = document.createElement('a');
		terminalLink.setAttribute('href', BF_STATIC.terminal_root_url+'?action=buzz_edit&bid='+json.id);
		terminalLink.appendChild( document.createTextNode('Terminal') );
		quickpostView.appendChild( document.createTextNode('Go to the ') );
		quickpostView.appendChild( terminalLink );
		quickpostView.appendChild( document.createTextNode(' to make further edits or publish it.') );
		*/
		var draft_count_el = $('draft-count');
		if ( draft_count_el ) {
			var draft_count = draft_count_el.getAttribute('rel:data');
			draft_count = eval('('+draft_count+')');
			draft_count.draft_count++;
			draft_count_el.setAttribute('rel:data', Object.toJSON(draft_count));
			draft_count_el.update(draft_count.draft_count);
			$('get-drafts').show();
		}
		quickpostView.id = (new Date()).getTime();
		quickpostView.className = 'post2 media-buzz link-buzz track saved_as_draft_notice';
		list_of_buzz.insertBefore(quickpostView, first_buzz);
	}
	
	// Validate form data for specified type
	this.validate = function( type, options ) {
		if (!options) options = {} ;
		var post_structure = user_post.STRUCTURE[type];
		if  (typeof post_structure['preprocess'] != 'undefined' )
		{
			post_structure.preprocess();
		}
		var mapping = post_structure.form_to_obj_map;
		var errors = new Array();
		for ( var each in mapping ) {
			if (options.draft && each != 'quickpost-title') continue;
			var value = $(each).value;
			if ( mapping[each].validation ) {
				for( var i = 0; i < mapping[each].validation.length; i++ ) {
					if ( !mapping[each].validation[i](value)) {
						errors.push({
							name : mapping[each].name,
							label: mapping[each].label,
							element_id: each
						});
						break;
					}
				}
			}
		}
		if ( type == 'embed' && !options.draft ) {
			var embed = $('quickpost-embed-code').value;
			var width = embed.match(/<(embed|object)\s[^>]*width\s*=\s*'?"?(\d+)/i);
			if (! width ) errors.push({name:'embed',label:'Embed Tag width attribute',element_id:'quickpost-embed-code'});
			if (! embed.match(/<(embed|object)\s[^>]*height\s*=\s*'?"?(\d+)/i)) errors.push({name:'embed',label:'Embed Tag height attribute',element_id:'quickpost-embed-code'});
			if ( width && width[2] && parseInt(width[2]) > 950 ) errors.push( { name:'embed',label:'Embed width cannot exceed 950', element_id:'quickpost-embed-code'} );
		}

		return errors;
	}
	
	// Display validation errors on screen
	this.show_validation_errors = function( type, options ) {
		if (!options) options = {} ;
		var displayed_something = true;
		var validation_errors = user_post.validate( type, options );
		if ( validation_errors.length ) {
			var msg_labels = new Array();
			for( var i = 0; i < validation_errors.length; i++ ) {
				msg_labels.push(validation_errors[i].label)
				$($(validation_errors[i].element_id).parentNode).addClassName('missing');
			}
			user_post.message('quickpost-error-msg',{
				show:true,
				message:"Looks like you're missing: " + msg_labels.join(', ')
			});
		}
		else {
			user_post.message('quickpost-error-msg',{hide:true});
			displayed_something = false;
		}
		return displayed_something;
	}	
	
	// Create data object of specified type from form 
	this.build_post_object = function(type) {
		var post_structure = user_post.STRUCTURE[type];
		var obj = {};
		var mapping = post_structure.form_to_obj_map;
		for ( var each in mapping ) {
			if ( $(each).type == 'select' ){
				value = $(each).options[$(each).selectedIndex].value;
			}
			else if ( $(each).type == 'checkbox' ) {
				value = $(each).checked;
			}
			else {
				value = $(each).value;
			}
			if ( mapping[each].preprocess ) {
				for ( var i = 0; i < mapping[each].preprocess.length; i++ ) { 
					value = mapping[each].preprocess[i](value);
				}
			}
			obj[mapping[each].name] = value;
		}
		if ( type == 'embed' ) {
			if ( obj.embed.match(/width\s*=\s*'?"?(\d+)/i) ) obj.embed_width = RegExp.$1;
			if ( obj.embed.match(/height\s*=\s*'?"?(\d+)/i)) obj.embed_height = RegExp.$1;
		}
		obj.post_type = 'quickpost';
		obj.uri = '#quickpost';
		obj.type = type;
		obj.template = post_structure.template;
		obj.image_root = BF_STATIC.image_root;
		obj.static_root = BF_STATIC.static_root;
		if ($('quickpost-titlecase') && $('quickpost-titlecase').checked) {
			obj.title = TT_Filters.titleCase(obj.title);
			if ($('quickpost-title')) $('quickpost-title').value = obj.title;
		}
		return obj;
	}
	
	// Handle user post-specific stuff when saving an image
	this.save_quickpost_image = function( type, image ) {
		// This is called after save_image()
		$('user-image-edit').hide();
		switch( type ) {
			case 'link':
			case 'enhanced':
				break;
			case 'image':
				$('quickpost-image-image-width').value = image.width;
				$('quickpost-image-image-height').value = image.height;
				$('img-form-preview').src = BF_STATIC.image_root+image.image_path
				$('img-form-preview').show();
				$('image-form-preview').show();
				break;
			case 'video':
				break;
		}
	}
	
	// assign event handlers
	this.set_handlers = function() {
		var create_user_post_buttons = $$('.post-button');
		for ( var i = 0; i < create_user_post_buttons.length; i++ ) {
			create_user_post_buttons[i].observe('click', this.create_user_post);
		}
		if ($('quickpost-preview-button')) $('quickpost-preview-button').observe('click', this.preview_quickpost );
		if ($('quickpost-post-button')) $('quickpost-post-button').observe('click', this.save_quickpost );
		if ($('quickpost-save-as-draft-button')) $('quickpost-save-as-draft-button').observe('click', this.save_quickpost_as_draft );
		if ($('quickpost-cancel-button')) $('quickpost-cancel-button').observe('click', this.cancel_quickpost );
		if ($('quickpost-video-url')) $('quickpost-video-url').observe('blur',this.upload_video );
		if ($('image-button')) $('image-button').observe('click', this.image_handler);
		if ($('embed-image-button')) $('embed-image-button').observe('click', this.image_handler);
		//if ($('quickpost-embed-code')) $('quickpost-embed-code').observe('blur',this.preview_embed );
		if ($('link-image-button')) $('link-image-button').observe('click', this.image_handler);
		if ($('enhanced-image-button')) $('enhanced-image-button').observe('click', this.image_handler);
		if ($('video-image-button')) $('video-image-button').observe('click', this.image_handler);
		if ($('quickpost-tags')) {
			$('quickpost-tags').observe('keydown',this.auto_complete_special);
			$('quickpost-tags').observe('keyup',this.auto_complete);
			$('quickpost-tags').observe('focus',function(){$('tag_suggestions').show()});
			$('quickpost-tags').observe('blur',function(){window.setTimeout(function(){$('tag_suggestions').hide()},200)});
		}
		if ($('close-image')) $('close-image').observe( 'click', function(){
			BF_UI.closeDialog('user-image-edit');
		} );
	}
	
	this.preview_embed = function( e ) {
		var embed_string = e.target.value;
		$('embed-preview').update(embed_string);
		$('embed-preview').show();
	}
	
	/* Event handlers */
	// get tag suggestions unless query term already is cached
	this._auto_complete_term = function(value) {
		var terms = value.split(',');
		query = terms.pop();
		query = query.replace(/^\s*/,'');
		query = query.replace(/\s*$/,'');
		return query;
	}
	
	this._find_element = function( idx ) {
		if ( idx < 0 || idx > user_post.__auto_complete_elements.length ) return null;
		var el = null;
		for( var i = 0; i < user_post.__auto_complete_elements.length; i++ ) {
			if( user_post.__auto_complete_elements[i].getAttribute('rel:idx') == idx ) {
				el = user_post.__auto_complete_elements[i];
				break;
			}
		}
		return el;
	}

	this._handle_special_keys = function( key_code ) {
		// enter key (Event.KEY_RETURN): add highlighted suggested keyword to keywords
		// escape key (27) : hide suggested keywords
		// arrow up (Event.KEY_UP): highlight higher keyword
		// arrow down (Event.KEY_DOWN): highlight lower keyword
		this.select_it = function(){
			var el = user_post._find_element( user_post.__auto_complete_idx );
			if ( el ) user_post.auto_complete_select({stop:function(){},target:el});
			$('tag_suggestions').hide();
		}
		if ( key_code == Event.KEY_RETURN ) {
			this.select_it();
		}
		else if ( key_code == Event.KEY_UP ) {
			var el = user_post._find_element( parseInt( user_post.__auto_complete_idx ) - 1 );
			if ( el ) user_post.auto_complete_hover({stop:function(){},target:el});
		}
		else if ( key_code == Event.KEY_DOWN ) {
			var el = user_post._find_element( parseInt( user_post.__auto_complete_idx ) + 1 );
			if ( el ) user_post.auto_complete_hover({stop:function(){},target:el});
		}
		else if ( key_code == 27 ) {
			$('tag_suggestions').hide();
		}
		else if ( key_code == 9 ) {
			this.select_it();
		}
	}
	
	this.auto_complete_special = function(e) {
		var keyCode = e.keyCode;
		if ( keyCode == 9 || keyCode == Event.KEY_RETURN || keyCode == Event.KEY_UP || keyCode == Event.KEY_DOWN || keyCode == 27 ) {
			e.stop();
			user_post._handle_special_keys( keyCode );
		}
	}
	
	this.auto_complete = function(e) {
		var keyCode = e.keyCode;
		if ( keyCode == 9 || keyCode == Event.KEY_RETURN || keyCode == Event.KEY_UP || keyCode == Event.KEY_DOWN || keyCode == 27 ) {
			e.stop();
		}
		else {
			$('tag_suggestions-spinner').show();
			$('tag_suggestions').update('');
			$('tag_suggestions').show();
			var query = user_post._auto_complete_term(e.target.value);
			if ( query.length > 0 ) {
				if ( typeof user_post.__auto_complete[query] == 'undefined' ) {
					var ajax = new BF_Request();
					ajax.request('/buzzfeed/_public_tag_autocomplete', {
						method:'get',
						parameters:{query:query},
						onSuccess: user_post._auto_complete_success,
						onFailure: function(resp){alert('Error contacting server');},
						bf_auth: true 
					});
				}
			}
			else {
				$('tag_suggestions-spinner').hide();
			}
			// poll tag completion cache periodically until update is available
			user_post._auto_complete_update();
		}
	}
	
	// add results to tag completion cache
	this._auto_complete_success = function(r) {
		if ( r.status == 200 ) {
			user_post.__auto_complete[r.request.options.parameters.query] = r.responseText;
		}
		else {
			$('tag_suggestions-spinner').hide();
		}
	}
	
	// update field with value from cache; recheck periodically if value is not available
	this._auto_complete_update = function() {
		var query = user_post._auto_complete_term($('quickpost-tags').value);
		if ( query.length > 0 ) {
			if ( typeof user_post.__auto_complete[query] != 'undefined' ) {
				$('tag_suggestions-spinner').hide();
				$('tag_suggestions').update( user_post.__auto_complete[query] );
				user_post.__auto_complete_elements = [];
				var terms = $('tag_suggestions').getElementsByTagName('LI');
				for( var i = 0; i < terms.length; i++ ) {
					$(terms[i]).setAttribute( 'rel:idx', i );
					$(terms[i]).observe('mouseover',user_post.auto_complete_hover);
					$(terms[i]).observe('mouseout',user_post.auto_complete_unhover);
					$(terms[i]).observe('click',user_post.auto_complete_select);
					user_post.__auto_complete_elements.push( $(terms[i]) );
				}
				user_post.__auto_complete_idx = 0;
				var el = user_post._find_element( parseInt( user_post.__auto_complete_idx ) );
				if ( el ) user_post.auto_complete_hover({stop:function(){},target:el});
			}
			else {
				window.setTimeout(user_post._auto_complete_update,200);
			}
		}
	}
	
	this.auto_complete_unhover = function( e ) {
		e.stop();
		e.target.removeClassName( 'selected' );
	}
	
	this.auto_complete_hover = function( e ) {
		e.stop();
		var el = user_post._find_element( parseInt( user_post.__auto_complete_idx ) );
		if ( el ) user_post.auto_complete_unhover({stop:function(){},target:el});
		user_post.__auto_complete_idx = e.target.getAttribute( 'rel:idx' );
		e.target.addClassName( 'selected' );
	}
	
	this.auto_complete_select = function( e ) {
		e.stop();
		var value = e.target.innerHTML;
		var field_value = $('quickpost-tags').value;
		var terms = field_value.split(',');
		var existing_terms = {};
		terms.pop();
		for( var i = 0; i < terms.length; i++ ) {
			terms[i] = terms[i].replace(/^\s*/,'');
			terms[i] = terms[i].replace(/\s*$/,'');
			existing_terms[ terms[i] ] = true;
		}
		value = value.replace( /^\s*/,'' );
		value = value.replace( /\s*$/,'' );
		if ( typeof existing_terms[ value ] == 'undefined' ) terms.push(value);
		$('quickpost-tags').value = terms.join(', ') ;
		$('quickpost-tags').focus();
	}
	
	this.image_handler = function(e) {
		e.stop();
		window.default_image_handler = 'user_setting';
		user_post.image_element_clicked = e.target;
		$('user-image-edit-iframe').src="/static/images/public/spinners/big_on_eee.gif";
		$('image-preview-div').show();
		if ($('user-loading')) $('user-loading').show();
		BF_UI.showDialog('user-image-edit');
		$('image-preview').hide();
		// if(Prototype.Browser.IE && parseInt(navigator.userAgent.substring(navigator.userAgent.indexOf("MSIE")+5))==6) {
		// 	var offsets = document.viewport.getScrollOffsets();
		// 	var vheight = document.viewport.getHeight();
		// 	var top = vheight / 2 + offsets.top;
		// 	$('user-image-edit').setStyle({top: top});
		// }
		$('user-image-edit-iframe').src="/buzzfeed/_edit_user_contribution_image?action=imageform&template=public/user/quickpost_imageform.tt";
		var buzz_type = 'link';
		if ( e.target.id == 'image-button' ) buzz_type = 'image';
		else if ( e.target.id == 'video-image-button' ) buzz_type = 'video';
		$('user-image-edit-iframe').observe('load',	function(ev){
			if (typeof ev.target.contentWindow.user_image != 'undefined')
				ev.target.contentWindow.user_image.setBuzzType(buzz_type);
		});
		if ($('video-form-preview')) $('video-form-preview').hide();
	};
	
	this.upload_video = function( e ) {
		e.stop();
		var thumbnail_display='block';
		var video = new bf2_terminal_Video();
		video.detect_type( e.target.value.toString() );
		if ( video.type ) {
			$('quickpost-video-ok').value='true';
			if( e.target.value.toString().length == 0 ) thumbnail_display = 'none';
			$('quickpost-video-thumb').style.display=thumbnail_display;
			var so = BF_initSwfObject(video.src_link,{width:250,height:202});
			so.write("video-form-preview");
			user_post.message('quickpost-video-thumb-msg',{hide:true});
			$('video-form-preview').show();
			e.target.value = video.src_link;
		}
		else {
			$('quickpost-video-ok').value='false';
			$('video-form-preview').hide();
			user_post.message('quickpost-video-thumb-msg',{
				show:true,
				message:'Sorry, that doesn\'t seem to be a supported video type'
			});
		}
	}
	
	this.preview_quickpost = function(e) {
		e.stop();
		user_post.clear_form_of_errors();
		var buzz_type = e.target.form.elements['buzz-type'].value ;
		if ( !user_post.show_validation_errors( buzz_type ) ) {
			var obj = user_post.build_post_object(buzz_type);
			user_post.preview_from_server(obj, user_post.preview_from_server_ok);
		}
	}	
	
	this.delete_quickpost = function(e) {
		e.stop();
		var id = e.target.getAttribute('rel:id');
		if ( id ) user_post._delete_quickpost(id);
	}	
	
	this._delete_quickpost = function(id) {
		var data = {
			action:'delete',
			id:id
		}
		var ajax = new BF_Request();
		ajax.request('/buzzfeed/_public_admin', {
			method:'post',
			parameters:data,
			onSuccess: function(resp){
				//edit_post.save_ok(resp, data)
			},
			onFailure: function(resp){
				user_post.save_failed(resp);
			}, bf_auth: true
		});
	}
	
	this.save_quickpost_as_draft = function(e) {
		e.stop();
		var type = $F('buzz-type');
		var post_structure = user_post.STRUCTURE[type];
		if  (typeof post_structure['preprocess'] != 'undefined' )
		{
			post_structure.preprocess();
		}
		if ( typeof user_post.enhanced_js != 'undefined' ) {
			$('quickpost-enhanced-data').value = user_post.enhanced_js.as_string();
		}
		user_post.save_quickpost(e, {save_as_draft:true});
	}	
	
	this.save_quickpost = function(e, params) {
		e.stop();
		if ( typeof params == 'undefined' ) params = {};
		user_post.save_as_draft = params.save_as_draft ? params.save_as_draft : false;
		var buzz_type = e.target.form.elements['buzz-type'].value ;
		if ( !user_post.show_validation_errors( buzz_type, {draft:user_post.save_as_draft} ) ) {
			var obj = user_post.build_post_object(buzz_type);
			var user = new BF_User();
			if (user.getUserInfo().terminal_user!='true') {
				delete obj.categorization ;
				delete obj.tags ;
				delete obj.tame ;
			}
			user_post.preview_from_server(obj, function(r){
				user_post.preview_from_server_and_save(r,obj)
			});
		}
	}	
	
	this.cancel_quickpost = function(e) {
		e.stop();
		$('contribute-preview').hide();
		$('user-edit-quickpost').hide();
		$('select-quickpost-box').show();
		user_post.reset_post_form();
		user_post.show_video_preview = false;
		user_post.fire_event('cancel', {});
	}
	
	this.create_user_post = function(e) {
		e.stop();
		if ($('user_post_preview_iframe')) {
			$('close-preview').observe('click',function(e){$('user_post_preview').hide()});
			$('user_post_preview_iframe').src='/static/html/quickpost_preview.html?cb='+(new Date()).getTime();
		}
		var buzz_type = user_post.ID_TO_TYPE_MAP[e.target.id];
		var post_structure = user_post.STRUCTURE[buzz_type];
		user_post.trigger_element = e.target.id;

		$('select-quickpost-box').hide();
		user_post.show_user_post_form( buzz_type );
		user_post.fire_event('create:opening_form', {buzz_type:buzz_type,post_structure:post_structure});
	}
	
	/* Utility methods */
	this.remove_class = function( obj, regex ) {
		var c_name = obj.className;
		c_name = c_name.replace(regex,'');
		obj.className = c_name;
	}
	
	this.message = function( target_id, args ) {
		var target = $(target_id);
		if ( !target ) return;
		if ( args.show == true || args.hide == false ) {
			target.show();
		}
		else if ( args.show == false || args.hide == true ) {
			target.hide();
		}
		if ( args.message ) target.update( args.message );
	}

	this.fire_event = function( ev, data ) {
		if ( typeof data == 'undefined' ) data = {};
		if ( this.__EVENTS[ev] ) {
			var listeners = this.__EVENTS[ev].listeners;
			for ( var i = 0; i < listeners.length; i++ ) {
				listeners[i](data);
			}
		}
	}
	
	this.observe = function( ev, fn ) {
		if ( !this.__EVENTS[ev] ) return;
		this.__EVENTS[ev].listeners.push( fn );
	}
	
	this.__EVENTS = {
		'create:opening_form': {listeners:[]},
		'save:preparing': {listeners:[]},
		'save:success': {listeners:[]},
		'save:fail': {listeners:[]},
		'cancel': {listeners:[]}
	};
}

var user_post = new bf_user_post();
user_post.init()
//BuzzLoader.register(function(){user_post.init()},1);	
