Index: src/wp-admin/includes/ajax-actions.php
===================================================================
--- src/wp-admin/includes/ajax-actions.php	(revision 30026)
+++ src/wp-admin/includes/ajax-actions.php	(working copy)
@@ -2300,8 +2300,10 @@
 	wp_update_post( $post );
 
 	foreach ( get_attachment_taxonomies( $post ) as $taxonomy ) {
-		if ( isset( $attachment_data[ $taxonomy ] ) )
-			wp_set_object_terms( $id, array_map( 'trim', preg_split( '/,+/', $attachment_data[ $taxonomy ] ) ), $taxonomy, false );
+		if ( isset( $attachment_data[ $taxonomy ] ) ) {
+			if ( !is_array( $attachment_data[ $taxonomy ] ) ) $attachment_data[ $taxonomy ] = array($attachment_data[ $taxonomy ]);
+			wp_set_object_terms( $id, array_map( 'intval', $attachment_data[ $taxonomy ] ), $taxonomy, false );
+		}
 	}
 
 	if ( ! $attachment = wp_prepare_attachment_for_js( $id ) )
Index: src/wp-admin/includes/media.php
===================================================================
--- src/wp-admin/includes/media.php	(revision 30026)
+++ src/wp-admin/includes/media.php	(working copy)
@@ -1570,17 +1570,27 @@
 			if ( empty($t['args']) )
 				$t['args'] = array();
 
-			$terms = get_object_term_cache($post->ID, $taxonomy);
-			if ( false === $terms )
-				$terms = wp_get_object_terms($post->ID, $taxonomy, $t['args']);
+			$t['taxonomy'] = true;
 
-			$values = array();
+			$inputname = $taxonomy . 'checklist';
+			$t['input'] = $inputname;
 
-			foreach ( $terms as $term )
-				$values[] = $term->slug;
-			$t['value'] = join(', ', $values);
-			$t['taxonomy'] = true;
+			$thtml = '<div class="categorydiv"><ul>';
+			ob_start();
+				wp_terms_checklist($post->ID, array( 'taxonomy' => $taxonomy, 'checked_ontop' => false ) );
+			$thtml .= ob_get_contents();
+			ob_end_clean();
 
+			// right now wp_terms_checklist can only return input elements
+			// with post_category[] as the name
+			//
+			// TODO:  rewrite Walker_Category_Checklist to be more modular
+			// so the input names can be changed
+			$thtml = str_replace('post_category[]', 'attachments[' . $post->ID . '][' . $taxonomy . ']', $thtml);
+			$thtml .= '</ul></div>';
+
+			$t[$inputname] = $thtml;
+
 			$form_fields[$taxonomy] = $t;
 		}
 	}
Index: src/wp-includes/js/media-views.js
===================================================================
--- src/wp-includes/js/media-views.js	(revision 30026)
+++ src/wp-includes/js/media-views.js	(working copy)
@@ -6908,7 +6908,14 @@
 			}
 
 			_.each( this.$el.serializeArray(), function( pair ) {
-				data[ pair.name ] = pair.value;
+				if (data[ pair.name ]) {
+					// this case handles checkbox inputs where multiple can
+					// be selected (like categories on an attachment)
+					if (!_.isArray(data[ pair.name ])) data[ pair.name ] = [data[ pair.name ]];
+					data[ pair.name ].push(pair.value);
+				} else {
+					data[ pair.name ] = pair.value;
+				}
 			});
 
 			this.controller.trigger( 'attachment:compat:waiting', ['waiting'] );
