<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[995] sites/trunk/wordcamp.org/public_html/wp-content/plugins: WordCamp Payments: Initial commit.</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta" style="font-size: 105%">
<dt style="float: left; width: 6em; font-weight: bold">Revision</dt> <dd><a style="font-weight: bold" href="http://meta.trac.wordpress.org/changeset/995">995</a><script type="application/ld+json">{"@context":"http://schema.org","@type":"EmailMessage","description":"Review this Commit","action":{"@type":"ViewAction","url":"http://meta.trac.wordpress.org/changeset/995","name":"Review Commit"}}</script></dd>
<dt style="float: left; width: 6em; font-weight: bold">Author</dt> <dd>iandunn</dd>
<dt style="float: left; width: 6em; font-weight: bold">Date</dt> <dd>2014-11-19 19:12:57 +0000 (Wed, 19 Nov 2014)</dd>
</dl>

<pre style='padding-left: 1em; margin: 2em 0; border-left: 2px solid #ccc; line-height: 1.25; font-size: 105%; font-family: sans-serif'>WordCamp Payments: Initial commit.</pre>

<h3>Added Paths</h3>
<ul>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/</li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsbootstrapphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/bootstrap.php</a></li>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/</li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsclassespaymentrequestphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/payment-request.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsclasseswordcamppaymentsphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/wordcamp-payments.php</a></li>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/css/</li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentscsswordcamppaymentscss">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/css/wordcamp-payments.css</a></li>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/</li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsjavascriptattachedfilesjs">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/attached-files.js</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsjavascriptwordcamppaymentsjs">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/wordcamp-payments.js</a></li>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/</li>
<li>sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/</li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputcheckboxphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-checkbox.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputfilesphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-files.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputradiophp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-radio.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputselectphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-select.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputtextphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-text.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputtextareaphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-textarea.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxfilesphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-files.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxgeneralphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-general.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxpaymentphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-payment.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxstatusphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-status.php</a></li>
<li><a href="#sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxvendorphp">sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-vendor.php</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsbootstrapphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/bootstrap.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/bootstrap.php                           (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/bootstrap.php     2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,20 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+/*
+Plugin Name: WordCamp Payments
+Plugin URI:  http://wordcamp.org/
+Description: Provides tools for collecting and processing payment requests from WordCamp organizers.
+Author:      tellyworth, iandunn
+Version:     0.1
+*/
+
+if ( ! defined( 'ABSPATH' ) ) {
+       die( 'Access denied.' );
+}
+
+if ( is_admin() ) {
+       require_once( __DIR__ . '/classes/wordcamp-payments.php' );
+       require_once( __DIR__ . '/classes/payment-request.php' );
+
+       $GLOBALS['wordcamp_payments']   = new WordCamp_Payments();
+       $GLOBALS['wcp_payment_request'] = new WCP_Payment_Request();
+}
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsclassespaymentrequestphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/payment-request.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/payment-request.php                             (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/payment-request.php       2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,869 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+
+/*
+ * Create the Payment Request post type and associated functionality
+ */
+class WCP_Payment_Request {
+       const POST_TYPE = 'wcp_payment_request';
+
+       public function __construct() {
+               // Initialization
+               add_action( 'init',                   array( $this, 'register_post_type' ));
+               add_action( 'init',                   array( $this, 'register_post_statuses' ) );
+               add_action( 'add_meta_boxes',         array( $this, 'init_meta_boxes' ) );
+
+               // Miscellaneous
+               add_filter( 'display_post_states',    array( $this, 'display_post_states' ) );
+
+               // Saving posts
+               add_filter( 'wp_insert_post_data',    array( $this, 'update_request_status' ), 10, 2 );
+               add_action( 'save_post',              array( $this, 'save_payment' ), 10, 2 );
+               add_action( 'transition_post_status', array( $this, 'notify_central_of_new_requests' ), 10, 3 );
+               add_filter( 'map_meta_cap',           array( $this, 'modify_capabilities' ), 10, 4 );
+
+               // Columns
+               add_filter( 'manage_'.      self::POST_TYPE .'_posts_columns',       array( $this, 'get_columns' ) );
+               add_filter( 'manage_edit-'. self::POST_TYPE .'_sortable_columns',    array( $this, 'get_sortable_columns' ) );
+               add_action( 'manage_'.      self::POST_TYPE .'_posts_custom_column', array( $this, 'render_columns' ), 10, 2 );
+               add_action( 'pre_get_posts',                                         array( $this, 'sort_columns' ) );
+       }
+
+       /**
+        * Register the custom post type
+        *
+        * @return object | WP_Error
+        */
+       public function register_post_type() {
+               $labels = array(
+                       'name'               => _x( 'Payment Requests', 'post type general name', 'wordcamporg' ),
+                       'singular_name'      => _x( 'Payment Request', 'post type singular name', 'wordcamporg' ),
+                       'menu_name'          => _x( 'Payment Requests', 'admin menu', 'wordcamporg' ),
+                       'name_admin_bar'     => _x( 'Payment Request', 'add new on admin bar', 'wordcamporg' ),
+                       'add_new'            => _x( 'Add New', 'payment', 'wordcamporg' ),
+                       'add_new_item'       => __( 'Add New Payment Request', 'wordcamporg' ),
+                       'new_item'           => __( 'New Payment Request', 'wordcamporg' ),
+                       'edit_item'          => __( 'Edit Payment Request', 'wordcamporg' ),
+                       'view_item'          => __( 'View Payment Request', 'wordcamporg' ),
+                       'all_items'          => __( 'All Payment Requests', 'wordcamporg' ),
+                       'search_items'       => __( 'Search Payment Requests', 'wordcamporg' ),
+                       'parent_item_colon'  => __( 'Parent Payment Requests:', 'wordcamporg' ),
+                       'not_found'          => __( 'No payment requests found.', 'wordcamporg' ),
+                       'not_found_in_trash' => __( 'No payment requests found in Trash.', 'wordcamporg' )
+               );
+
+               $args = array(
+                       'labels'            => $labels,
+                       'description'       => 'WordCamp Payment Requests',
+                       'public'            => false,
+                       'show_ui'           => true,
+                       'show_in_nav_menus' => true,
+                       'menu_position'     => 25,
+                       'supports'          => array( 'title' ),
+                       'has_archive'       => true,
+               );
+
+               return register_post_type( self::POST_TYPE, $args );
+       }
+
+       /**
+        * Register our custom post statuses
+        */
+       public function register_post_statuses() {
+               register_post_status(
+                       'paid',
+                       array(
+                               'label'              => _x( 'Paid', 'post', 'wordcamporg' ),
+                               'label_count'        => _nx_noop( 'Paid <span class="count">(%s)</span>', 'Paid <span class="count">(%s)</span>', 'wordcamporg' ),
+                               'public'             => true,
+                               'publicly_queryable' => false,
+                       )
+               );
+
+               register_post_status(
+                       'unpaid',
+                       array(
+                               'label'              => _x( 'Unpaid', 'post', 'wordcamporg' ),
+                               'label_count'        => _nx_noop( 'Unpaid <span class="count">(%s)</span>', 'Unpaid <span class="count">(%s)</span>', 'wordcamporg' ),
+                               'public'             => true,
+                               'publicly_queryable' => false,
+                       )
+               );
+       }
+
+       public function init_meta_boxes() {
+               // We're build our own Publish box, thankyouverymuch
+               remove_meta_box( 'submitdiv', self::POST_TYPE, 'side' );
+
+               add_meta_box(
+                       'submitdiv',
+                       __( 'Status', 'wordcamporg' ),
+                       array( $this, 'render_status_metabox' ),
+                       self::POST_TYPE,
+                       'side',
+                       'high'
+               );
+
+               add_meta_box(
+                       'wcp_general_info',
+                       __( 'General Information', 'wordcamporg' ),
+                       array( $this, 'render_general_metabox' ),
+                       self::POST_TYPE,
+                       'normal',
+                       'high'
+               );
+
+               add_meta_box(
+                       'wcp_payment_details',
+                       __( 'Payment Details', 'wordcamporg' ),
+                       array( $this, 'render_payment_metabox' ),
+                       self::POST_TYPE,
+                       'normal',
+                       'high'
+               );
+
+               add_meta_box(
+                       'wcp_vendor_details',
+                       __( 'Vendor Details', 'wordcamporg' ),
+                       array( $this, 'render_vendor_metabox' ),
+                       self::POST_TYPE,
+                       'normal',
+                       'high'
+               );
+
+               add_meta_box(
+                       'wcp_files',
+                       __( 'Attach Supporting Documentation', 'wordcamporg' ),
+                       array( $this, 'render_files_metabox' ),
+                       self::POST_TYPE,
+                       'normal',
+                       'high'
+               );
+       }
+
+       /**
+        * Render the Status metabox
+        *
+        * @param WP_Post $post
+        */
+       public function render_status_metabox( $post ) {
+               wp_nonce_field( 'status', 'status_nonce' );
+
+               $delete_text                   = EMPTY_TRASH_DAYS ? __( 'Move to Trash' ) : __( 'Delete Permanently' );
+               $submit_text                   = 'auto-draft' == $post->post_status ? __( 'Submit Request', 'wordcamporg' ) : __( 'Update Request', 'wordcamporg' );
+               $current_user_can_edit_request = in_array( $post->post_status, array( 'auto-draft', 'unpaid' ) ) || current_user_can( 'manage_network' );
+
+               require_once( dirname( __DIR__ ) . '/views/payment-request/metabox-status.php' );
+       }
+
+       /**
+        * Render the General Information metabox
+        *
+        * @param WP_Post $post
+        */
+       public function render_general_metabox( $post ) {
+               wp_nonce_field( 'general_info', 'general_info_nonce' );
+
+               $categories        = self::get_payment_categories();
+               $assigned_category = get_post_meta( $post->ID, '_camppayments_payment_category', true );
+
+               $date_vendor_paid = get_post_meta( $post->ID, '_camppayments_date_vendor_paid', true );
+               if ( current_user_can( 'manage_network' ) ) {
+                       $date_vendor_paid_readonly = false;
+               } else {
+                       $date_vendor_paid_readonly = true;
+               }
+
+               require_once( dirname( __DIR__ ) . '/views/payment-request/metabox-general.php' );
+
+               // todo If they select other but don't fill in the explanation, set to draft and display error msg, similar to require_complete_meta_to_publish_wordcamp()
+       }
+
+       /**
+        * Render the Vendor Details metabox
+        *
+        * @param WP_Post $post
+        */
+       public function render_vendor_metabox( $post ) {
+               wp_nonce_field( 'vendor_details', 'vendor_details_nonce' );
+
+               require_once( dirname( __DIR__ ) . '/views/payment-request/metabox-vendor.php' );
+       }
+
+       /**
+        * Render the Payment Details
+        *
+        * @param $post
+        */
+       public function render_payment_metabox( $post ) {
+               wp_nonce_field( 'payment_details', 'payment_details_nonce' );
+               $selected_payment_method = get_post_meta( $post->ID, '_camppayments_payment_method', true );
+
+               require_once( dirname( __DIR__ ) . '/views/payment-request/metabox-payment.php' );
+       }
+
+       /**
+        * Render the Vendor Details metabox
+        *
+        * @param WP_Post $post
+        */
+       public function render_files_metabox( $post ) {
+               wp_nonce_field( 'wcp_files', 'wcp_files_nonce' );
+
+               require_once( dirname( __DIR__ ) . '/views/payment-request/metabox-files.php' );
+       }
+
+       /**
+        * Render a <textarea> field with the given attributes.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        * @param string $description
+        */
+       protected function render_textarea_input( $post, $label, $name, $description = '' ) {
+               $date = get_post_meta( $post->ID, '_camppayments_' . $name, true );
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-textarea.php' );
+       }
+
+       /**
+        * Render a <select> field with the given attributes.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        */
+       protected function render_select_input( $post, $label, $name ) {
+               $selected = get_post_meta( $post->ID, '_camppayments_' . $name, true );
+               $options  = $this->get_field_value( $name, $post );
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-select.php' );
+       }
+
+       /**
+        * Render a <input type="radio"> field with the given attributes.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        */
+       protected function render_radio_input( $post, $label, $name ) {
+               $selected = get_post_meta( $post->ID, '_camppayments_' . $name, true );
+               $options  = $this->get_field_value( $name, $post );
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-radio.php' );
+       }
+
+       /**
+        * Render a <input type="checkbox"> field with the given attributes.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        */
+       protected function render_checkbox_input( $post, $label, $name, $description = '' ) {
+               $value = $this->get_field_value( $name, $post );
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-checkbox.php' );
+       }
+
+       /**
+        * Render a <input type="text"> field with the given attributes.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        */
+       protected function render_text_input( $post, $label, $name, $description = '', $variant = 'text', $row_classes = array(), $readonly = false ) {
+               $value = $this->get_field_value( $name, $post );
+               array_walk( $row_classes, 'sanitize_html_class' );
+               $row_classes = implode( ' ', $row_classes );
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-text.php' );
+       }
+
+       /**
+        * Render an upload button and list of uploaded files.
+        *
+        * @param WP_Post $post
+        * @param string $label
+        * @param string $name
+        * @param string $description
+        */
+       protected function render_files_input( $post, $label, $name, $description = '' ) {
+               $files = get_posts( array(
+                       'post_parent'    => $post->ID,
+                       'post_type'      => 'attachment',
+                       'posts_per_page' => -1,
+                       'orderby'        => 'title',
+                       'order'          => 'ASC',
+               ) );
+
+               foreach ( $files as &$file ) {
+                       $file->filename = wp_basename( $file->guid );
+                       $file->url      = wp_get_attachment_url( $file->ID );
+               }
+
+               require( dirname( __DIR__ ) . '/views/payment-request/input-files.php' );
+       }
+
+       /**
+        * Get the value of a given field.
+        *
+        * @param string $name
+        * @param WP_Post $post
+        *
+        * @return mixed
+        */
+       protected function get_field_value( $name, $post ) {
+               switch( $name ) {
+                       case 'request_id':
+                               $value = $post->ID;
+                               break;
+
+                       case 'requester':
+                               $requester = get_user_by( 'id', $post->post_author );
+                               if ( is_a( $requester, 'WP_User' ) ) {
+                                       $value = sprintf( '%s <%s>', $requester->get( 'display_name' ), $requester->get( 'user_email' ) );
+                               } else {
+                                       $value = '';
+                               }
+                               break;
+
+                       case 'date_vendor_paid':
+                       case 'due_by':
+                               if ( $value = get_post_meta( $post->ID, '_camppayments_' . $name, true ) ) {
+                                       $value = date( 'Y-m-d', $value );
+                               }
+                               break;
+
+                       case 'currency':
+                               $value = $this->get_currencies();
+                               break;
+
+                       case 'payment_method':
+                               $value = array( 'Check', 'Credit Card', 'Wire' );
+                               break;
+
+                       default:
+                               $value = get_post_meta( $post->ID, '_camppayments_' . $name, true );
+                               break;
+               }
+
+               return $value;
+       }
+
+       /**
+        * Get a list of all world currencies, with the most frequently used at the top.
+        *
+        * @return array
+        */
+       protected function get_currencies() {
+               $currencies = array (
+                       'null-most-frequently-used' => 'Most Frequently Used:',
+                       'USD' => 'United States Dollar',
+                       'EUR' => 'Euro Member Countries',
+
+                       'null-separator2' => '',
+
+                       'null-all' => 'All:',
+                       'ALL' => 'Albania Lek',
+                       'AFN' => 'Afghanistan Afghani',
+                       'ARS' => 'Argentina Peso',
+                       'AWG' => 'Aruba Guilder',
+                       'AUD' => 'Australia Dollar',
+                       'AZN' => 'Azerbaijan New Manat',
+                       'BSD' => 'Bahamas Dollar',
+                       'BBD' => 'Barbados Dollar',
+                       'BDT' => 'Bangladeshi taka',
+                       'BYR' => 'Belarus Ruble',
+                       'BZD' => 'Belize Dollar',
+                       'BMD' => 'Bermuda Dollar',
+                       'BOB' => 'Bolivia Boliviano',
+                       'BAM' => 'Bosnia and Herzegovina Convertible Marka',
+                       'BWP' => 'Botswana Pula',
+                       'BGN' => 'Bulgaria Lev',
+                       'BRL' => 'Brazil Real',
+                       'BND' => 'Brunei Darussalam Dollar',
+                       'KHR' => 'Cambodia Riel',
+                       'CAD' => 'Canada Dollar',
+                       'KYD' => 'Cayman Islands Dollar',
+                       'CLP' => 'Chile Peso',
+                       'CNY' => 'China Yuan Renminbi',
+                       'COP' => 'Colombia Peso',
+                       'CRC' => 'Costa Rica Colon',
+                       'HRK' => 'Croatia Kuna',
+                       'CUP' => 'Cuba Peso',
+                       'CZK' => 'Czech Republic Koruna',
+                       'DKK' => 'Denmark Krone',
+                       'DOP' => 'Dominican Republic Peso',
+                       'XCD' => 'East Caribbean Dollar',
+                       'EGP' => 'Egypt Pound',
+                       'SVC' => 'El Salvador Colon',
+                       'EEK' => 'Estonia Kroon',
+                       'FKP' => 'Falkland Islands (Malvinas) Pound',
+                       'FJD' => 'Fiji Dollar',
+                       'GHC' => 'Ghana Cedis',
+                       'GIP' => 'Gibraltar Pound',
+                       'GTQ' => 'Guatemala Quetzal',
+                       'GGP' => 'Guernsey Pound',
+                       'GYD' => 'Guyana Dollar',
+                       'HNL' => 'Honduras Lempira',
+                       'HKD' => 'Hong Kong Dollar',
+                       'HUF' => 'Hungary Forint',
+                       'ISK' => 'Iceland Krona',
+                       'INR' => 'India Rupee',
+                       'IDR' => 'Indonesia Rupiah',
+                       'IRR' => 'Iran Rial',
+                       'IMP' => 'Isle of Man Pound',
+                       'ILS' => 'Israel Shekel',
+                       'JMD' => 'Jamaica Dollar',
+                       'JPY' => 'Japan Yen',
+                       'JEP' => 'Jersey Pound',
+                       'KZT' => 'Kazakhstan Tenge',
+                       'KPW' => 'Korea (North) Won',
+                       'KRW' => 'Korea (South) Won',
+                       'KGS' => 'Kyrgyzstan Som',
+                       'LAK' => 'Laos Kip',
+                       'LVL' => 'Latvia Lat',
+                       'LBP' => 'Lebanon Pound',
+                       'LRD' => 'Liberia Dollar',
+                       'LTL' => 'Lithuania Litas',
+                       'MKD' => 'Macedonia Denar',
+                       'MYR' => 'Malaysia Ringgit',
+                       'MUR' => 'Mauritius Rupee',
+                       'MXN' => 'Mexico Peso',
+                       'MNT' => 'Mongolia Tughrik',
+                       'MZN' => 'Mozambique Metical',
+                       'NAD' => 'Namibia Dollar',
+                       'NPR' => 'Nepal Rupee',
+                       'ANG' => 'Netherlands Antilles Guilder',
+                       'NZD' => 'New Zealand Dollar',
+                       'NIO' => 'Nicaragua Cordoba',
+                       'NGN' => 'Nigeria Naira',
+                       'NOK' => 'Norway Krone',
+                       'OMR' => 'Oman Rial',
+                       'PKR' => 'Pakistan Rupee',
+                       'PAB' => 'Panama Balboa',
+                       'PYG' => 'Paraguay Guarani',
+                       'PEN' => 'Peru Nuevo Sol',
+                       'PHP' => 'Philippines Peso',
+                       'PLN' => 'Poland Zloty',
+                       'QAR' => 'Qatar Riyal',
+                       'RON' => 'Romania New Leu',
+                       'RUB' => 'Russia Ruble',
+                       'SHP' => 'Saint Helena Pound',
+                       'SAR' => 'Saudi Arabia Riyal',
+                       'RSD' => 'Serbia Dinar',
+                       'SCR' => 'Seychelles Rupee',
+                       'SGD' => 'Singapore Dollar',
+                       'SBD' => 'Solomon Islands Dollar',
+                       'SOS' => 'Somalia Shilling',
+                       'ZAR' => 'South Africa Rand',
+                       'LKR' => 'Sri Lanka Rupee',
+                       'SEK' => 'Sweden Krona',
+                       'CHF' => 'Switzerland Franc',
+                       'SRD' => 'Suriname Dollar',
+                       'SYP' => 'Syria Pound',
+                       'TWD' => 'Taiwan New Dollar',
+                       'THB' => 'Thailand Baht',
+                       'TTD' => 'Trinidad and Tobago Dollar',
+                       'TRY' => 'Turkey Lira',
+                       'TRL' => 'Turkey Lira',
+                       'TVD' => 'Tuvalu Dollar',
+                       'UAH' => 'Ukraine Hryvna',
+                       'GBP' => 'United Kingdom Pound',
+                       'UYU' => 'Uruguay Peso',
+                       'UZS' => 'Uzbekistan Som',
+                       'VEF' => 'Venezuela Bolivar',
+                       'VND' => 'Viet Nam Dong',
+                       'YER' => 'Yemen Rial',
+                       'ZWD' => 'Zimbabwe Dollar'
+               );
+
+               return $currencies;
+       }
+
+       /**
+        * Define the payment categories
+        *
+        * The slugs are explicitly registered in English so they will match across sites that use different locales,
+        * which facilitates aggregating the data into reports.
+        *
+        * This is public so that WordCamp Payments Network Dashboard can access it, in order to aggregate posts by their slug.
+        *
+        * @return array
+        */
+       public static function get_payment_categories() {
+               return array(
+                       'after-party'     => __( 'After Party',                    'wordcamporg' ),
+                       'audio-visual'    => __( 'Audio Visual',                   'wordcamporg' ),
+                       'food-beverages'  => __( 'Food & Beverage',                'wordcamporg' ),
+                       'office-supplies' => __( 'Office Supplies',                'wordcamporg' ),
+                       'signage-badges'  => __( 'Signage & Badges',               'wordcamporg' ),
+                       'speaker-event'   => __( 'Speaker Event',                  'wordcamporg' ),
+                       'swag'            => __( 'Swag (t-shirts, stickers, etc)', 'wordcamporg' ),
+                       'venue'           => __( 'Venue',                          'wordcamporg' ),
+                       'other'           => __( 'Other',                          'wordcamporg' ), // This one is intentionally last, regardless of alphabetical order
+               );
+       }
+
+       /**
+        * Display the status of a post after its title on the Payment Requests page
+        *
+        * @param array $states
+        *
+        * @return array
+        */
+       function display_post_states( $states ) {
+               global $post;
+
+               if ( 'paid' == $post->post_status && 'paid' != get_query_var( 'post_status' ) ) {
+                       $states['paid'] = __( 'Paid', 'camptix' );
+               }
+
+               if ( 'unpaid' == $post->post_status && 'unpaid' != get_query_var( 'post_status' ) ) {
+                       $states['unpaid'] = __( 'Unpaid', 'camptix' );
+               }
+
+               return $states;
+       }
+
+       /**
+        * Determines whether we want to perform actions on the given post based on the current context.
+        *
+        * Examples of actions we might perform are saving the meta fields during the `save_post` hook, or send out an
+        * e-mail notification during the `transition_post_status` hook.
+        *
+        * This function is called by several other functions, each of which may require additional checks that are
+        * specific to their circumstances. This function only covers checks that are common to all of its callers.
+        *
+        * @param WP_Post | array $post
+        *
+        * @return bool
+        */
+       protected function post_edit_is_actionable( $post ) {
+               if ( is_array( $post ) ) {
+                       $post = (object) $post;
+               }
+
+               $is_actionable   = true;
+               $ignored_actions = array( 'trash', 'untrash', 'restore', 'bulk_edit' ); // todo ignore bulk deletion too
+
+               // Don't take action on other post types
+               if ( ! $post || $post->post_type != self::POST_TYPE ) {
+                       $is_actionable = false;
+               }
+
+               // Don't take action if the user isn't allowed. The ID will be missing from new posts during `wp_insert_post_data`, though, so skip it then.
+               if ( $is_actionable && isset( $post->ID ) && ! current_user_can( 'edit_post', $post->ID ) ) {
+                       $is_actionable = false;
+               }
+
+               // Don't take action while trashing the post, etc
+               if ( $is_actionable && isset( $_GET['action'] ) && in_array( $_GET['action'], $ignored_actions ) ) {
+                       $is_actionable = false;
+               }
+
+               // Don't take action during autosaves
+               if ( $is_actionable && ( ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) || $post->post_status == 'auto-draft' ) ) {
+                       $is_actionable = false;
+               }
+
+               return $is_actionable;
+       }
+
+       /**
+        * Set the request's status based on whether the vendor has been paid.
+        *
+        * @param array $post_data
+        * @param array $post_data_raw
+        * @return array
+        */
+       public function update_request_status( $post_data, $post_data_raw ) {
+               if ( $this->post_edit_is_actionable( $post_data ) ) {
+                       $post_data['post_status'] = strtotime( sanitize_text_field( $_POST['date_vendor_paid'] ) ) ? 'paid' : 'unpaid';
+               }
+
+               return $post_data;
+       }
+
+       /**
+        * Save the post's data
+        *
+        * @param int     $post_id
+        * @param WP_Post $post
+        */
+       public function save_payment( $post_id, $post ) {
+               if ( ! $this->post_edit_is_actionable( $post ) ) {
+                       return;
+               }
+
+               // Verify nonces
+               $nonces = array( 'status_nonce', 'general_info_nonce', 'payment_details_nonce', 'vendor_details_nonce' );    // todo add prefix to all of these
+
+               foreach ( $nonces as $nonce ) {
+                       if ( ! isset( $_POST[ $nonce ] ) || ! wp_verify_nonce( $_POST[ $nonce ], str_replace( '_nonce', '', $nonce ) ) ) {
+                               return;
+                       }
+               }
+
+               // Sanitize and save the field values
+               $this->sanitize_save_normal_fields( $post_id );
+               $this->sanitize_save_misc_fields(   $post_id );
+       }
+
+       /**
+        * Sanitize and save values for all normal fields
+        *
+        * @param int $post_id
+        */
+       protected function sanitize_save_normal_fields( $post_id ) {
+               foreach ( $_POST as $key => $unsafe_value ) {
+                       switch ( $key ) {
+                               case 'description':
+                               case 'general_notes':
+                               case 'file_notes':
+                                       $safe_value = wp_kses( $unsafe_value, wp_kses_allowed_html( 'strip' ) );
+                                       break;
+
+                               case 'payment_amount':
+                               case 'currency':
+                               case 'payment_category':
+                               case 'vendor_name':
+                               case 'vendor_phone_number':
+                               case 'vendor_email_address':
+                               case 'vendor_street_address':
+                               case 'vendor_city':
+                               case 'vendor_state':
+                               case 'vendor_zip_code':
+                               case 'vendor_country':
+                               case 'bank_name':
+                               case 'bank_street_address':
+                               case 'bank_city':
+                               case 'bank_state':
+                               case 'bank_zip_code':
+                               case 'bank_country':
+                               case 'bank_bic':
+                               case 'beneficiary_account_number':
+                               case 'beneficiary_name':
+                               case 'beneficiary_street_address':
+                               case 'beneficiary_city':
+                               case 'beneficiary_state':
+                               case 'beneficiary_zip_code':
+                               case 'beneficiary_country':
+                               case 'payable_to':
+                               case 'vendor_contact_person':
+                               case 'other_category_explanation':
+                                       $safe_value = sanitize_text_field( $unsafe_value );
+                                       break;
+
+                               case 'payment_method':
+                                       if ( in_array( $unsafe_value, $this->get_field_value( 'payment_method', null ) ) ) {
+                                               $safe_value = $unsafe_value;
+                                       } else {
+                                               $safe_value = false;
+                                       }
+                                       break;
+
+                               case 'due_by':
+                                       if ( empty( $_POST[ $key ] ) ) {
+                                               $safe_value = '';
+                                       } else {
+                                               $safe_value = strtotime( sanitize_text_field( $unsafe_value ) );
+                                       }
+                                       break;
+
+                               default:
+                                       $safe_value = null;
+                                       break;
+                       }
+
+                       if ( ! is_null( $safe_value ) ) {
+                               update_post_meta( $post_id, '_camppayments_' . $key, $safe_value );
+                       }
+               }
+       }
+
+       /**
+        * Sanitize and save values for all checkbox fields
+        *
+        * @param int $post_id
+        */
+       protected function sanitize_save_misc_fields( $post_id ) {
+               // Status
+               if ( current_user_can( 'manage_network' ) ) {
+                       $safe_value = strtotime( sanitize_text_field( $_POST['date_vendor_paid'] ) );
+                       update_post_meta( $post_id, '_camppayments_date_vendor_paid', $safe_value );
+               }
+
+               // Checkboxes
+               $checkbox_fields = array( 'requesting_reimbursement' );
+               foreach( $checkbox_fields as $field ) {
+                       if ( isset( $_POST[ $field ] ) ) {
+                               update_post_meta( $post_id, '_camppayments_' . $field, $_POST[ $field ] );
+                       } else {
+                               delete_post_meta( $post_id, '_camppayments_' . $field );
+                       }
+               }
+       }
+
+       /**
+        * Notify WordCamp Central that a new request has been made.
+        *
+        * @param string $new_status
+        * @param string $old_status
+        * @param WP_Post $post
+        */
+       public function notify_central_of_new_requests( $new_status, $old_status, $post ) {
+               /** @var WP_User $requester */
+
+               if ( ! $this->post_edit_is_actionable( $post ) ) {
+                       return;
+               }
+
+               if ( 'unpaid' != $new_status || 'unpaid' == $old_status ) {
+                       return;
+               }
+
+               $requester = get_user_by( 'id', $post->post_author );
+
+               $message = sprintf(
+                       "A new payment request has been made.
+
+                       WordCamp: %s
+                       Item: %s
+                       Due Date: %s
+                       Requester: %s
+
+                       View details: %s",
+
+                       get_bloginfo( 'name' ),
+                       $post->post_title,
+                       $_POST['due_by'],
+                       $requester->get( 'display_name' ),
+                       admin_url( 'post.php?post='. $post->ID .'&action=edit' )
+               );
+               $message = str_replace( "\t", '', $message );
+
+               $headers = array(
+                       'Reply-To: ' . $requester->get( 'user_email' ),
+               );
+
+               wp_mail( 'support@wordcamp.org', 'New Payment Request: ' . $post->post_title, $message, $headers );
+       }
+
+       /**
+        * Define columns for the Payment Requests screen.
+        *
+        * @param array $_columns
+        * @return array
+        */
+       public function get_columns( $_columns ) {
+               $columns = array(
+                       'cb'             => $_columns['cb'],
+                       'author'         => __( 'Author' ),
+                       'title'          => $_columns['title'],
+                       'date'           => $_columns['date'],
+                       'due_by'         => __( 'Due by', 'wordcamporg' ),
+                       'vendor_name'    => __( 'Vendor', 'wordcamporg' ),
+                       'payment_amount' => __( 'Amount', 'wordcamporg' ),
+               );
+
+               return $columns;
+       }
+
+       /**
+        * Register our sortable columns.
+        *
+        * @param array $columns
+        * @return array
+        */
+       public function get_sortable_columns( $columns ) {
+               $columns['due_by']   = '_camppayments_due_by';
+
+               return $columns;
+       }
+
+       /**
+        * Render custom columns on the Payment Requests screen.
+        *
+        * @param string $column
+        * @param int $post_id
+        */
+       public function render_columns( $column, $post_id ) {
+               switch ( $column ) {
+                       case 'payment_amount':
+                               $currency = get_post_meta( $post_id, '_camppayments_currency', true );
+                               if ( false === strpos( $currency, 'null' ) ) {
+                                       echo esc_html( $currency ) . ' ';
+                               }
+
+                               echo esc_html( get_post_meta( $post_id, '_camppayments_payment_amount', true ) );
+                               break;
+
+                       case 'due_by':
+                               if ( $date = get_post_meta( $post_id, '_camppayments_due_by', true ) ) {
+                                       echo date( 'F jS, Y', $date );
+                               }
+                               break;
+
+                       default:
+                               echo esc_html( get_post_meta( $post_id, '_camppayments_' . $column, true ) );
+                               break;
+               }
+       }
+
+       /**
+        * Sort our custom columns.
+        *
+        * @param WP_Query $query
+        */
+       public function sort_columns( $query ) {
+               if ( self::POST_TYPE != $query->get( 'post_type' ) ) {
+                       return;
+               }
+
+               $orderby = $query->get( 'orderby' );
+
+               switch( $orderby ) {
+                       case '_camppayments_due_by':
+                               $query->set( 'meta_key', '_camppayments_due_by' );
+                               $query->set( 'orderby', 'meta_value_num' );
+                               break;
+
+                       default:
+                               break;
+               }
+       }
+
+       /**
+        * Modify the default capabilities
+        *
+        * @param array  $required_capabilities The primitive capabilities that are required to perform the requested meta capability
+        * @param string $requested_capability  The requested meta capability
+        * @param int    $user_id               The user ID.
+        * @param array  $args                  Adds the context to the cap. Typically the object ID.
+        */
+       public function modify_capabilities( $required_capabilities, $requested_capability, $user_id, $args ) {
+               global $post;
+
+               if ( is_a( $post, 'WP_Post' ) && self::POST_TYPE == $post->post_type ) {
+                       /*
+                        * Only network admins can edit requests once they've been paid.
+                        *
+                        * They can still open the request (in order to view the status and details), but won't be allowed to make any changes to it.
+                        */
+                       if ( 'edit_post' == $requested_capability && 'paid' == $post->post_status && isset( $_REQUEST['action'] ) && 'edit' != $_REQUEST['action'] ) {
+                               $required_capabilities[] = 'manage_network';
+                       }
+
+                       // Only network admins can delete requests
+                       if ( 'delete_post' == $requested_capability ) {
+                               $required_capabilities[] = 'manage_network';
+                       }
+               }
+
+               return $required_capabilities;
+       }
+}
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsclasseswordcamppaymentsphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/wordcamp-payments.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/wordcamp-payments.php                           (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/classes/wordcamp-payments.php     2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,70 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<?php
+
+/*
+ * Main class to provide functionality common to all other classes
+ */
+class WordCamp_Payments {
+       const VERSION = '0.1.0';
+
+       /**
+        * Constructor
+        */
+       public function __construct() {
+               add_action( 'admin_enqueue_scripts',  array( $this, 'enqueue_assets' ) );
+       }
+
+       /**
+        * Enqueue scripts and stylesheets
+        */
+       public function enqueue_assets( $hook ) {
+               global $post;
+
+               // todo setup grunt to concat/minify js and css?
+
+               // Register our assets
+               wp_register_script(
+                       'wordcamp-payments',
+                       plugins_url( 'javascript/wordcamp-payments.js', __DIR__ ),
+                       array( 'jquery', 'jquery-ui-datepicker', 'media-upload', 'media-views' ),
+                       self::VERSION,
+                       true
+               );
+
+               wp_register_script(
+                       'wcp-attached-files',
+                       plugins_url( 'javascript/attached-files.js', __DIR__ ),
+                       array( 'wordcamp-payments', 'backbone', 'wp-util' ),
+                       self::VERSION,
+                       true
+               );
+
+               wp_register_style(
+                       'wordcamp-payments',
+                       plugins_url( 'css/wordcamp-payments.css', __DIR__ ),
+                       array( 'jquery-ui', 'wp-datepicker-skins' ),
+                       self::VERSION
+               );
+
+               // Enqueue our assets if they're needed on the current screen
+               $current_screen = get_current_screen();
+
+               if ( in_array( $current_screen->id, array( 'edit-wcp_payment_request', 'wcp_payment_request' ) ) ) {
+                       wp_enqueue_script( 'wordcamp-payments' );
+                       wp_enqueue_style( 'wordcamp-payments' );
+
+                       if ( in_array( $current_screen->id, array( 'wcp_payment_request' ) ) && isset( $post->ID ) ) {
+                               wp_enqueue_media( array( 'post' => $post->ID ) );
+                               wp_enqueue_script( 'wcp-attached-files' );
+                       }
+
+                       wp_localize_script(
+                               'wordcamp-payments',
+                               'wcpLocalizedStrings',          // todo merge into wordcampPayments var
+                               array(
+                                       'uploadModalTitle'  => __( 'Attach Supporting Documentation', 'wordcamporg' ),
+                                       'uploadModalButton' => __( 'Attach Files', 'wordcamporg' ),
+                               )
+                       );
+               }
+       }
+}
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentscsswordcamppaymentscss"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/css/wordcamp-payments.css</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/css/wordcamp-payments.css                               (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/css/wordcamp-payments.css 2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,28 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+/*
+ * Payment Methods
+ */
+.payment_method_fields.active,
+.wcp_no_files_uploaded.active {
+       display: block;
+}
+
+tr#row-payment-method label {
+       margin-right: 20px;
+}
+
+
+/*
+ * Files
+ */
+#wcp_files .description {
+       margin-bottom: 1em;
+}
+
+.wcp_files_list li {
+       list-style-type: disc;
+       margin-left: 15px;
+}
+
+.form-table td p.wcp_no_files_uploaded {
+       margin-bottom: 1em;
+}
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsjavascriptattachedfilesjs"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/attached-files.js</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/attached-files.js                            (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/attached-files.js      2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,73 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+jQuery( document ).ready( function( $ ) {
+
+       /*
+        * Model for an attached file
+        */
+       $.wordcampPayments.AttachedFile = Backbone.Model.extend( {
+               defaults: {
+                       'ID':       0,
+                       'filename': '',
+                       'url':      ''
+               }
+       } );
+
+       /*
+        * Collection of attached files
+        */
+       $.wordcampPayments.AttachedFiles = Backbone.Collection.extend( {
+               model: $.wordcampPayments.AttachedFile
+       } );
+
+       /*
+        * View for a single attached file
+        */
+       $.wordcampPayments.AttachedFileView = Backbone.View.extend( {
+               tagName: 'li',
+               template: wp.template( 'wcp-attached-file' ),
+
+               initialize: function() {
+                       _.bindAll( this, 'render' );
+               },
+
+               render: function() {
+                       $( this.el ).html( this.template( this.model.toJSON() ) );
+                       return this;
+               }
+       } );
+
+       /*
+        * View for a collection of attached files
+        */
+       $.wordcampPayments.AttachedFilesView = Backbone.View.extend( {
+               el: $( '#wcp_files' ),
+
+               initialize: function() {
+                       _.bindAll( this, 'render', 'appendFile' );
+
+                       this.collection = new $.wordcampPayments.AttachedFiles( wcpAttachedFiles );
+                       this.collection.bind( 'add', this.appendFile );
+
+                       this.render();
+               },
+
+               render: function() {
+                       var self = this;
+
+                       _( this.collection.models ).each( function( file ) {
+                               self.appendFile( file );
+                       } );
+               },
+
+               appendFile: function( file ) {
+                       var noFilesUploaded  = $( '.wcp_no_files_uploaded' );
+                       var attachedFileView = new $.wordcampPayments.AttachedFileView( { model: file } );
+
+                       $( '.wcp_files_list' ).append( attachedFileView.render().el );
+                       noFilesUploaded.removeClass( 'active' );
+                       noFilesUploaded.addClass( 'hidden' );
+               }
+       } )
+
+       $.wordcampPayments.attachedFilesView = new $.wordcampPayments.AttachedFilesView();
+
+} );
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsjavascriptwordcamppaymentsjs"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/wordcamp-payments.js</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/wordcamp-payments.js                         (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/javascript/wordcamp-payments.js   2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,115 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+jQuery( document ).ready( function( $ ) {
+
+       $.wordcampPayments = {
+
+               /**
+                * Main entry point
+                */
+               init: function () {
+                       $.wordcampPayments.registerEventHandlers();
+                       $.wordcampPayments.setupDatePicker();
+               },
+
+               /**
+                * Registers event handlers
+                */
+               registerEventHandlers : function() {
+                       $( '#wcp_payment_details' ).find( 'input[name=payment_method]' ).change( $.wordcampPayments.togglePaymentMethodFields );
+                       $( '#payment_category' ).change( $.wordcampPayments.toggleOtherCategoryDescription );
+                       $( '#wcp_files' ).find( 'a.wcp-insert-media' ).click( $.wordcampPayments.showUploadModal );
+               },
+
+               /**
+                * Toggle the payment method fields based on which method is selected
+                *
+                * @param {object} event
+                */
+               togglePaymentMethodFields : function( event ) {
+                       var active_fields_container = '#' + $( this ).attr( 'id' ) + '_fields';
+                       var payment_method_fields   = '.payment_method_fields';
+
+                       $( payment_method_fields   ).removeClass( 'active' );
+                       $( payment_method_fields   ).addClass( 'hidden' );
+                       $( active_fields_container ).removeClass( 'hidden' );
+                       $( active_fields_container ).addClass( 'active' );
+
+                       // todo make the transition smoother
+               },
+
+               /**
+                * Example event handler
+                *
+                * @param {object} event
+                */
+               toggleOtherCategoryDescription : function( event ) {
+                       var otherCategoryDescription = $( '#row-other-category-explanation' );
+
+                       if ( 'other' == $( this ).find( 'option:selected' ).val() ) {
+                               $( otherCategoryDescription ).removeClass( 'hidden' );
+                       } else {
+                               $( otherCategoryDescription ).addClass( 'hidden' );
+                       }
+
+                       // todo make the transition smoother
+               },
+
+               /**
+                * Initialize Core's Media Picker
+                *
+                * @param {object} event
+                */
+               showUploadModal : function( event ) {
+                       if ( 'undefined' == typeof $.wordcampPayments.fileUploadFrame ) {
+                               // Create the frame
+                               $.wordcampPayments.fileUploadFrame = wp.media( {
+                                       title: wcpLocalizedStrings.uploadModalTitle,
+                                       multiple: true,
+                                       button: {
+                                               text: wcpLocalizedStrings.uploadModalButton
+                                       }
+                               } );
+
+                               // Add models to the collection for each selected attachment
+                               $.wordcampPayments.fileUploadFrame.on( 'select', $.wordcampPayments.addSelectedFilesToCollection );
+                       }
+
+                       $.wordcampPayments.fileUploadFrame.open();
+                       return false;
+               },
+
+               /**
+                * Add files selected from the Media Picker to the current collection of files
+                */
+               addSelectedFilesToCollection : function() {
+                       var attachments = $.wordcampPayments.fileUploadFrame.state().get( 'selection' ).toJSON();
+
+                       $.each( attachments, function( index, attachment ) {                                                                                            // todo if selected an existing file, it isn't attached, so after post is saved it wont be in the list
+                               var newFile = new $.wordcampPayments.AttachedFile( {
+                                       'ID':       attachment.id,
+                                       'filename': attachment.filename,
+                                       'url':      attachment.url
+                               } );
+
+                               $.wordcampPayments.attachedFilesView.collection.add( newFile );
+                       } );
+               },
+
+               /**
+                * Fallback to the jQueryUI datepicker if the browser doesn't support <input type="date">
+                */
+               setupDatePicker : function() {
+                       var browserTest = document.createElement( 'input' );
+                       browserTest.setAttribute( 'type', 'date' );
+
+                       if ( 'text' === browserTest.type ) {
+                               $( '#wcp_general_info' ).find( 'input[type=date]' ).not( '[readonly="readonly"]' ).datepicker( {
+                                       dateFormat : 'yy-mm-dd',
+                                       changeMonth: true,
+                                       changeYear : true
+                               } );
+                       }
+               }
+       };
+
+       $.wordcampPayments.init();
+} );
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputcheckboxphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-checkbox.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-checkbox.php                                (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-checkbox.php  2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,23 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>">
+       <th>
+               <label for="<?php echo esc_attr( $name ); ?>">
+                       <?php echo esc_html( $label ); ?>:
+               </label>
+       </th>
+
+       <td>
+               <input
+                       type="checkbox"
+                       id="<?php echo esc_attr( $name ); ?>"
+                       name="<?php echo esc_attr( $name ); ?>"
+                       value="<?php echo esc_attr( $name ); ?>"
+                       <?php checked( $value, $name ); ?>
+                       />
+
+               <?php if ( ! empty( $description ) ) : ?>
+                       <label for="<?php echo esc_attr( $name ); ?>">
+                               <span class="description"><?php echo esc_html( $description ); ?></span>
+                       </label>
+               <?php endif; ?>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputfilesphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-files.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-files.php                           (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-files.php     2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,31 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>">
+       <th><?php echo esc_html( $label ); ?>:</th>
+
+       <td>
+               <?php if ( ! empty( $description ) ) : ?>
+                       <p class="description">
+                               <?php echo esc_html( $description ); ?>
+                       </p>
+               <?php endif; ?>
+
+               <p>
+                       <a class="button wcp-insert-media" role="button">
+                               <?php _e( 'Add files', 'wordcamporg' ); ?>
+                       </a>
+               </p>
+
+               <h4><?php _e( 'Attached files:', 'wordcamporg' ); ?></h4>
+
+               <ul class="wcp_files_list"></ul>
+
+               <p class="wcp_no_files_uploaded <?php echo $files ? 'hidden' : 'active'; ?>">
+                       <?php _e( "You haven't uploaded any files yet.", 'wordcamporg' ); ?>
+               </p>
+
+               <script type="text/html" id="tmpl-wcp-attached-file">
+                       <a href="{{ data.url }}">{{ data.filename }}</a>
+               </script>
+
+               <?php wp_localize_script( 'wcp-attached-files', 'wcpAttachedFiles', $files ); // todo merge into wordcampPayments var ?>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputradiophp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-radio.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-radio.php                           (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-radio.php     2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,23 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>">
+       <th>
+               <?php echo esc_html( $label ); ?>:
+       </th>
+
+       <td>
+               <?php foreach ( $options as $option ) : ?>
+                       <?php $option_name = $name . '_' . sanitize_title_with_dashes( str_replace( ' ', '_', $option ) ); ?>
+
+                       <input
+                               type="radio"
+                               id="<?php echo esc_attr( $option_name ); ?>"
+                               name="<?php echo esc_attr( $name ); ?>"
+                               value="<?php echo esc_attr( $option ); ?>"
+                               <?php checked( $option, $selected ); ?>
+                               />
+
+                       <label for="<?php echo esc_attr( $option_name ); ?>">
+                               <?php echo esc_html( $option ); ?>:
+                       </label>
+               <?php endforeach; ?>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputselectphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-select.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-select.php                          (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-select.php    2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,22 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>">
+       <th>
+               <label for="<?php echo esc_attr( $name ); ?>">
+                       <?php echo esc_html( $label ); ?>:
+               </label>
+       </th>
+
+       <td>
+               <select id="<?php echo esc_attr( $name ); ?>" name="<?php echo esc_attr( $name ); ?>">
+                       <option value="null-select-one">
+                               <?php printf( __( '-- Select a %s --', 'wordcamporg' ), $label ); ?>
+                       </option>
+                       <option value="null-separator1"></option>
+
+                       <?php foreach ( $options as $value => $option_label ) : ?>
+                               <option value="<?php echo esc_attr( $value ); ?>" <?php selected( $value, $selected ); ?>>
+                                       <?php echo esc_html( $option_label ); ?>
+                               </option>
+                       <?php endforeach; ?>
+               </select>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputtextphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-text.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-text.php                            (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-text.php      2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,24 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>" class="<?php echo esc_attr( $row_classes ); ?>">
+       <th>
+               <label for="<?php echo esc_attr( $name ); ?>">
+                       <?php echo esc_html( $label ); ?>:
+               </label>
+       </th>
+
+       <td>
+               <input
+                       type="<?php echo esc_attr( $variant ); ?>"
+                       id="<?php echo esc_attr( $name ); ?>"
+                       name="<?php echo esc_attr( $name ); ?>"
+                       value="<?php echo esc_attr( $value ); ?>"
+                       <?php if ( $readonly ) { echo 'readonly="readonly"'; } ?>
+                       class="regular-text"
+                       />
+
+               <?php if ( ! empty( $description ) ) : ?>
+                       <label for="<?php echo esc_attr( $name ); ?>">
+                               <span class="description"><?php echo esc_html( $description ); ?></span>
+                       </label>
+               <?php endif; ?>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestinputtextareaphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-textarea.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-textarea.php                                (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/input-textarea.php  2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,17 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<tr id="row-<?php echo esc_attr( str_replace( '_', '-', $name ) ); ?>">
+       <th>
+               <label for="<?php echo esc_attr( $name ); ?>">
+                       <?php echo esc_html( $label ); ?>:
+               </label>
+       </th>
+
+       <td>
+               <textarea id="<?php echo esc_attr( $name ); ?>" name="<?php echo esc_attr( $name ); ?>" class="large-text"><?php echo esc_html( $date ); ?></textarea>
+
+               <?php if ( ! empty( $description ) ) : ?>
+                       <label for="<?php echo esc_attr( $name ); ?>">
+                               <p class="description"><?php echo esc_html( $description ); ?></p>
+                       </label>
+               <?php endif; ?>
+       </td>
+</tr>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxfilesphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-files.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-files.php                         (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-files.php   2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,4 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<table class="form-table">
+       <?php $this->render_files_input( $post, 'Files', 'files', __( 'Attach supporting documentation including invoices, contracts, or other vendor correspondence. If no supporting documentation is available, please indicate the reason in the notes below.', 'wordcamporg' ) ); ?>
+       <?php $this->render_textarea_input( $post, 'Notes', 'file_notes' ); ?>
+</table>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxgeneralphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-general.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-general.php                               (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-general.php 2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,36 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<table class="form-table">
+       <?php
+               $this->render_text_input( $post, 'Request ID', 'request_id', '', 'text', array(), true );
+               $this->render_text_input( $post, 'Requester', 'requester', '', 'text', array(), true );
+               $this->render_text_input( $post, 'Date Vendor was Paid', 'date_vendor_paid', '', 'date', array(), $date_vendor_paid_readonly );
+               $this->render_textarea_input( $post, 'Description', 'description' );
+               $this->render_text_input( $post, 'Requested date for payment/due by', 'due_by', '', 'date' );
+               $this->render_text_input( $post, 'Amount', 'payment_amount' );
+               $this->render_select_input( $post, 'Currency', 'currency' );
+               $this->render_textarea_input( $post, 'Notes', 'general_notes', 'Any other details you want to share.' );
+       ?>
+
+       <tr>
+               <th><label for="payment_category">Category</label></th>
+               <td>
+                       <select name="payment_category" id="payment_category" class="postform">
+                               <option value="null">-- Select a Category --</option>
+
+                               <?php foreach( $categories as $key => $name ) : ?>
+                                       <option value="<?php echo esc_attr( $key ); ?>" <?php selected( $assigned_category, $key ); ?>><?php echo esc_html( $name ); ?></option>
+                               <?php endforeach; ?>
+                       </select>
+               </td>
+       </tr>
+
+       <?php
+               $this->render_text_input(
+                       $post,
+                       'Other Category',
+                       'other_category_explanation',
+                       __( 'Please describe what category this request fits under.', 'wordcamporg' ),
+                       'text',
+                       isset( $assigned_category->name ) && 'Other' == $assigned_category->name ? array() : array( 'hidden')    // todo i18n, see notes in insert_default_terms()
+               );
+       ?>
+</table>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxpaymentphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-payment.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-payment.php                               (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-payment.php 2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,34 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<table class="form-table">
+       <?php $this->render_radio_input( $post, 'Payment Method', 'payment_method' ); ?>
+       <?php $this->render_checkbox_input( $post, 'Reimbursing Personal Expense', 'requesting_reimbursement', 'Check this box if you paid for this expense out of pocket. Please attach the original payment support below with the vendor attached (if any), and proof of disbursed funds.' ); ?>
+</table>
+
+<table id="payment_method_check_fields" class="form-table payment_method_fields <?php echo 'Check' == $selected_payment_method ? 'active' : 'hidden'; ?>">
+       <?php $this->render_text_input( $post, 'Payable To', 'payable_to' ); ?>
+</table>
+
+<p id="payment_method_credit_card_fields" class="description payment_method_fields <?php echo 'Credit Card' == $selected_payment_method ? 'active' : 'hidden'; ?>">
+       <?php _e( 'Please make sure that you upload an authorization form below, if one is required by the vendor.', 'wordcamporg' ); ?>
+</p>
+
+<div id="payment_method_wire_fields" class="form-table payment_method_fields <?php echo 'Wire' == $selected_payment_method ? 'active' : 'hidden'; ?>">
+       <table>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank Name',              'bank_name' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank Street Address',    'bank_street_address' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank City',              'bank_city' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank State / Province',  'bank_state' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank ZIP / Postal Code', 'bank_zip_code' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank Country',           'bank_country' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Bank SWIFT BIC',         'bank_bic' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Account Number or IBAN', 'beneficiary_account_number' ); ?>
+       </table>
+
+       <table>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Name',              'beneficiary_name' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Street Address',    'beneficiary_street_address' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s City',              'beneficiary_city' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s State / Province',  'beneficiary_state' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s ZIP / Postal Code', 'beneficiary_zip_code' ); ?>
+               <?php $this->render_text_input( $post, 'Beneficiary’s Country',           'beneficiary_country' ); ?>
+       </table>
+</div>
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxstatusphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-status.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-status.php                                (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-status.php  2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,48 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<div id="submitpost" class="submitbox">
+       <div id="minor-publishing">
+               <div id="misc-publishing-actions">
+                       <div class="misc-pub-section misc-pub-post-status">
+                               <label for="post_status"><?php _e( 'Status:' ) ?></label>
+
+                               <span id="post-status-display">
+                                       <?php if ( 'paid' == $post->post_status ) : ?>
+                                               <?php _e( 'Paid' ); ?>
+                                       <?php else : ?>
+                                               <?php _e( 'Not Paid' ); ?>
+                                       <?php endif; ?>
+                               </span>
+                       </div> <!-- .misc-pub-section -->
+
+                       <div class="clear"></div>
+               </div> <!-- #misc-publishing-actions -->
+
+               <div class="clear"></div>
+       </div> <!-- #minor-publishing -->
+
+
+       <div id="major-publishing-actions">
+               <?php if ( $current_user_can_edit_request ) : ?>
+
+                       <div id="delete-action">
+                               <?php if ( current_user_can( 'delete_post', $post->ID ) ) : ?>
+                                       <a class="submitdelete deletion" href="<?php echo get_delete_post_link( $post->ID ); ?>">
+                                               <?php echo $delete_text; ?>
+                                       </a>
+                               <?php endif; ?>
+                       </div>
+
+                       <div id="publishing-action">
+                               <input name="original_publish" type="hidden" id="original_publish" value="<?php esc_attr( $submit_text ) ?>" />
+                               <?php submit_button( $submit_text, 'primary button-large', 'save', false, array( 'accesskey' => 'p' ) ); ?>
+                       </div>
+
+                       <div class="clear"></div>
+
+               <?php else : ?>
+
+                       <p><?php _e( 'Paid requests are closed and cannot be edited.', 'wordcamporg' ); ?></p>
+
+               <?php endif; ?>
+       </div> <!-- #major-publishing-actions -->
+
+</div> <!-- .submitbox -->
</ins></span></pre></div>
<a id="sitestrunkwordcamporgpublic_htmlwpcontentpluginswordcamppaymentsviewspaymentrequestmetaboxvendorphp"></a>
<div class="addfile"><h4 style="background-color: #eee; color: inherit; margin: 1em 0; padding: 1.3em; font-size: 115%">Added: sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-vendor.php</h4>
<pre class="diff"><span>
<span class="info" style="display: block; padding: 0 10px; color: #888">--- sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-vendor.php                                (rev 0)
+++ sites/trunk/wordcamp.org/public_html/wp-content/plugins/wordcamp-payments/views/payment-request/metabox-vendor.php  2014-11-19 19:12:57 UTC (rev 995)
</span><span class="lines" style="display: block; padding: 0 10px; color: #888">@@ -0,0 +1,13 @@
</span><ins style="background-color: #dfd; text-decoration:none; display:block; padding: 0 10px">+<table class="form-table">
+       <?php
+               $this->render_text_input( $post, 'Vendor Name', 'vendor_name' );
+               $this->render_text_input( $post, 'Contact Person', 'vendor_contact_person' );
+               $this->render_text_input( $post, 'Phone Number', 'vendor_phone_number', '', 'tel' );
+               $this->render_text_input( $post, 'Email Address', 'vendor_email_address', '', 'email' );
+               $this->render_text_input( $post, 'Street Address', 'vendor_street_address' );
+               $this->render_text_input( $post, 'City', 'vendor_city' );
+               $this->render_text_input( $post, 'State / Province', 'vendor_state' );
+               $this->render_text_input( $post, 'ZIP / Postal Code', 'vendor_zip_code' );
+               $this->render_text_input( $post, 'Country', 'vendor_country' );
+       ?>
+</table>
</ins></span></pre>
</div>
</div>

</body>
</html>