Index: wp-admin/admin-ajax.php
===================================================================
--- wp-admin/admin-ajax.php	(revision 22966)
+++ wp-admin/admin-ajax.php	(working copy)
@@ -56,7 +56,7 @@
 	'save-widget', 'set-post-thumbnail', 'date_format', 'time_format', 'wp-fullscreen-save-post',
 	'wp-remove-post-lock', 'dismiss-wp-pointer', 'upload-attachment', 'get-attachment',
 	'query-attachments', 'save-attachment', 'save-attachment-compat', 'send-link-to-editor',
-	'send-attachment-to-editor',
+	'send-attachment-to-editor', 'save-attachment-order',
 );
 
 // Register core Ajax calls.
Index: wp-admin/includes/ajax-actions.php
===================================================================
--- wp-admin/includes/ajax-actions.php	(revision 22966)
+++ wp-admin/includes/ajax-actions.php	(working copy)
@@ -1927,6 +1927,39 @@
 	wp_send_json_success( $attachment );
 }
 
+function wp_ajax_save_attachment_order() {
+	if ( ! isset( $_REQUEST['post_id'] ) )
+		wp_send_json_error();
+
+	if ( ! $post_id = absint( $_REQUEST['post_id'] ) )
+		wp_send_json_error();
+
+	if ( empty( $_REQUEST['attachments'] ) )
+		wp_send_json_error();
+
+	check_ajax_referer( 'update-post_' . $post_id, 'nonce' );
+
+	$attachments = $_REQUEST['attachments'];
+
+	if ( ! current_user_can( 'edit_post', $post_id ) )
+		wp_send_json_error();
+
+	$post = get_post( $post_id, ARRAY_A );
+
+	foreach ( $attachments as $attachment_id => $menu_order ) {
+		if ( ! current_user_can( 'edit_post', $attachment_id ) )
+			continue;
+		if ( ! $attachment = get_post( $attachment_id ) )
+			continue;
+		if ( 'attachment' != $attachment->post_type )
+			continue;
+
+		wp_update_post( array( 'ID' => $attachment_id, 'menu_order' => $menu_order ) );
+	}
+
+	wp_send_json_success();
+}
+
 /**
  * Generates the HTML to send an attachment to the editor.
  * Backwards compatible with the media_send_to_editor filter and the chain
Index: wp-includes/js/media-models.js
===================================================================
--- wp-includes/js/media-models.js	(revision 22966)
+++ wp-includes/js/media-models.js	(working copy)
@@ -523,6 +523,34 @@
 		_requery: function() {
 			if ( this.props.get('query') )
 				this.mirror( Query.get( this.props.toJSON() ) );
+		},
+
+		// If this collection is sorted by `menuOrder`, recalculates and saves
+		// the menu order to the database.
+		saveMenuOrder: function() {
+			if ( 'menuOrder' !== this.props.get('orderby') )
+				return;
+
+			// Removes any uploading attachments, updates each attachment's
+			// menu order, and returns an object with an { id: menuOrder }
+			// mapping to pass to the request.
+			var attachments = this.chain().filter( function( attachment ) {
+				return ! _.isUndefined( attachment.id );
+			}).map( function( attachment, index ) {
+				// Indices start at 1.
+				index = index + 1;
+				attachment.set( 'menuOrder', index );
+				return [ attachment.id, index ];
+			}).object().value();
+
+			if ( _.isEmpty( attachments ) )
+				return;
+
+			return media.post( 'save-attachment-order', {
+				nonce:       media.model.settings.updatePostNonce,
+				post_id:     media.model.settings.postId,
+				attachments: attachments
+			});
 		}
 	}, {
 		comparator: function( a, b, options ) {
Index: wp-includes/js/media-views.js
===================================================================
--- wp-includes/js/media-views.js	(revision 22966)
+++ wp-includes/js/media-views.js	(working copy)
@@ -14,6 +14,7 @@
 
 	// Copy the `postId` setting over to the model settings.
 	media.model.settings.postId = media.view.settings.postId;
+	media.model.settings.updatePostNonce = media.view.settings.nonce.updatePost;
 
 	// Check if the browser supports CSS 3.0 transitions
 	$.support.transition = (function(){
@@ -267,7 +268,8 @@
 			content:    'browse',
 			searchable: true,
 			filterable: false,
-			uploads:    true
+			uploads:    true,
+			sortable:   true
 		},
 
 		initialize: function() {
@@ -2768,6 +2770,10 @@
 						at:     ui.item.index(),
 						silent: true
 					});
+
+					// If the collection is sorted by menu order,
+					// update the menu order.
+					collection.saveMenuOrder();
 				}
 			});
 
@@ -2783,7 +2789,11 @@
 				return;
 
 			// If the `collection` has a `comparator`, disable sorting.
-			this.$el.sortable( 'option', 'disabled', !! this.collection.comparator );
+			var collection = this.collection,
+				orderby = collection.props.get('orderby'),
+				enabled = 'menuOrder' === orderby || ! collection.comparator;
+
+			this.$el.sortable( 'option', 'disabled', ! enabled );
 		},
 
 		createAttachmentView: function( attachment ) {
@@ -3049,7 +3059,7 @@
 				}).render() );
 			}
 
-			if ( this.options.sortable ) {
+			if ( this.options.sortable && ! this.options.filters ) {
 				this.toolbar.set( 'dragInfo', new media.View({
 					el: $( '<div class="instructions">' + l10n.dragInfo + '</div>' )[0],
 					priority: -40
Index: wp-includes/media.php
===================================================================
--- wp-includes/media.php	(revision 22966)
+++ wp-includes/media.php	(working copy)
@@ -1433,6 +1433,7 @@
 	if ( isset( $args['post'] ) ) {
 		$post = get_post( $args['post'] );
 		$settings['postId'] = $post->ID;
+		$settings['nonce']['updatePost'] = wp_create_nonce( 'update-post_' . $post->ID );
 	}
 
 	$hier = $post && is_post_type_hierarchical( $post->post_type );
