Skip to content

Commit

Permalink
Cleanup of the revisions screen, both on the PHP API side, and the JS.
Browse files Browse the repository at this point in the history
* Much simpler PHP API
* Cleaner and more Backbone-y JS API
* Consequently, does batch queries; this now scales up to hundreds of revisions

Currently missing, but much easier considering the cleaned up base:

* Compare two mode
* RTL

props koopersmith, nacin, adamsilverstein, ocean90. see #24425

git-svn-id: http://core.svn.wordpress.org/trunk@24520 1a063a9b-81f0-0310-95a4-ce76da25c4cd
  • Loading branch information
markjaquith committed Jun 26, 2013
1 parent b14622b commit 77abb9f
Show file tree
Hide file tree
Showing 7 changed files with 609 additions and 1,025 deletions.
4 changes: 2 additions & 2 deletions wp-admin/admin-ajax.php
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@

$core_actions_get = array(
'fetch-list', 'ajax-tag-search', 'wp-compression-test', 'imgedit-preview', 'oembed-cache',
'autocomplete-user', 'dashboard-widgets', 'logged-in', 'revisions-data'
'autocomplete-user', 'dashboard-widgets', 'logged-in',
);

$core_actions_post = array(
Expand All @@ -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', 'save-attachment-order', 'heartbeat',
'send-attachment-to-editor', 'save-attachment-order', 'heartbeat', 'get-revision-diffs',
);

// Register core Ajax calls.
Expand Down
70 changes: 44 additions & 26 deletions wp-admin/css/wp-admin.css
Original file line number Diff line number Diff line change
Expand Up @@ -3481,6 +3481,48 @@ td.plugin-title p {
/*------------------------------------------------------------------------------
11.2 - Post Revisions
------------------------------------------------------------------------------*/
.revisions .spinner {
float: none;
margin: 100px auto;
}

.revisions.loading .spinner {
display: block;
}

.revisions-control-frame,
.revisions-diff-frame {
position: relative;
}

.revisions-controls {
height: 60px;
padding: 40px 0 20px;
border-bottom: 1px solid #dfdfdf;
margin-bottom: 10px;
}

.revisions-meta {
margin-top: 15px;
}
.revision-toggle-compare-mode {
position: absolute;
top: 0;
right: 0;
}

.revisions-previous {
float: left;
}

.revisions-next {
float: right;
}

.wp-slider {
width: 70%;
margin: 6px auto 0;
}

/* Revision meta box */
.post-revisions li img,
Expand Down Expand Up @@ -3527,13 +3569,6 @@ table.diff .diff-addedline ins {
position: relative;
}

#toggle-revision-compare-mode {
position: absolute;
top: 0;
right: 0;
padding: 9px 9px 0 0;
}

#loading-status {
display: none;
position: absolute;
Expand All @@ -3551,24 +3586,6 @@ table.diff .diff-addedline ins {
padding: 20px 0;
}

#diff-next-revision,
#diff-previous-revision {
margin-top: -.4em; /* Same line as the slider (height: .8em) */
}

#diff-next-revision {
float: right;
}

#diff-previous-revision {
float: left;
}

#diff-slider {
width: 70%;
margin: 0 auto;
}

.comparetwo #diff-slider {
width: 95%;
}
Expand All @@ -3588,7 +3605,7 @@ table.diff .diff-addedline ins {
}

#diff-title-to strong {
display: none;
display: inline;
}

.comparing-two-revisions #diff-title-to strong {
Expand All @@ -3605,6 +3622,7 @@ table.diff .diff-addedline ins {
-webkit-border-radius: 3px;
border-radius: 3px;
padding: 5px 200px 5px 5px;
clear: both;
}

.diff-header {
Expand Down
226 changes: 19 additions & 207 deletions wp-admin/includes/ajax-actions.php
Original file line number Diff line number Diff line change
Expand Up @@ -2082,219 +2082,31 @@ function wp_ajax_heartbeat() {
wp_send_json($response);
}

function wp_ajax_revisions_data() {
check_ajax_referer( 'revisions-ajax-nonce', 'nonce' );

$compare_to = ! empty( $_GET['compare_to'] ) ? absint( $_GET['compare_to'] ) : 0;
$show_autosaves = ! empty( $_GET['show_autosaves'] );
$show_split_view = ! empty( $_GET['show_split_view'] );
$post_id = ! empty( $_GET['post_id'] ) ? absint( $_GET['post_id'] ) : 0;
$right_handle_at = ! empty( $_GET['right_handle_at'] ) ? (int) $_GET['right_handle_at'] : 0;
$left_handle_at = ! empty( $_GET['left_handle_at'] ) ? (int) $_GET['left_handle_at'] : 0;
$single_revision_id = ! empty( $_GET['single_revision_id'] ) ? absint( $_GET['single_revision_id'] ) : 0;
$compare_two_mode = (bool) $post_id;

$all_the_revisions = array();
if ( ! $post_id )
$post_id = $compare_to;

if ( ! current_user_can( 'read_post', $post_id ) )
continue;

if ( ! $revisions = wp_get_post_revisions( $post_id ) )
return;

$left_revision = get_post( $compare_to );

// single model fetch mode
// return the diff of a single revision comparison
if ( $single_revision_id ) {
$right_revision = get_post( $single_revision_id );

if ( ! $compare_to )
$left_revision = get_post( $post_id );

// make sure the right revision is the most recent, except on oldest revision
if ( $compare_to && $right_revision->post_date < $left_revision->post_date ) {
$temp = $left_revision;
$left_revision = $right_revision;
$right_revision = $temp;
}

$lines_added = $lines_deleted = 0;
$content = '';
// compare from left to right, passed from application
foreach ( _wp_post_revision_fields() as $field => $field_value ) {
$left_content = apply_filters( "_wp_post_revision_field_$field", $left_revision->$field, $field, $left_revision, 'left' );
$right_content = apply_filters( "_wp_post_revision_field_$field", $right_revision->$field, $field, $right_revision, 'right' );

add_filter( "_wp_post_revision_field_$field", 'htmlspecialchars' );

$args = array();

if ( $show_split_view )
$args = array( 'show_split_view' => true );

// compare_to == 0 means first revision, so compare to a blank field to show whats changed
$diff = wp_text_diff_with_count( ( 0 == $compare_to ) ? '' : $left_content, $right_content, $args );

if ( isset( $diff[ 'html' ] ) ) {
$content .= sprintf( '<div class="diff-label">%s</div>', $field_value );
$content .= $diff[ 'html' ];
}

if ( isset( $diff[ 'lines_added' ] ) )
$lines_added = $lines_added + $diff[ 'lines_added' ];

if ( isset( $diff[ 'lines_deleted' ] ) )
$lines_deleted = $lines_deleted + $diff[ 'lines_deleted' ];
}
$content = '' == $content ? __( 'No difference' ) : $content;

$all_the_revisions = array (
'diff' => $content,
'linesDeleted' => $lines_deleted,
'linesAdded' => $lines_added
);

echo json_encode( $all_the_revisions );
exit();
} // end single model fetch

$count = -1;

// reverse the list to start with oldest revision
$revisions = array_reverse( $revisions );

$previous_revision_id = 0;

/* translators: revision date format, see http://php.net/date */
$datef = _x( 'j F, Y @ G:i:s', 'revision date format');

foreach ( $revisions as $revision ) :
if ( ! $show_autosaves && wp_is_post_autosave( $revision ) )
continue;

$revision_from_date_author = '';
$is_current_revision = false;
$count++;

/**
* return blank data for diffs to the left of the left handle (for right handel model)
* or to the right of the right handle (for left handel model)
* and visa versa in RTL mode
*/
if( ! is_rtl() ) {
if ( ( ( 0 != $left_handle_at && $count < $left_handle_at ) ||
( 0 != $right_handle_at && $count > ( $right_handle_at - 2 ) ) ) ) {
$all_the_revisions[] = array (
'ID' => $revision->ID,
);
continue;
}
} else { // is_rtl
if ( ( 0 != $left_handle_at && $count > ( $left_handle_at - 1 ) ||
( 0 != $left_handle_at && $count < $right_handle_at ) ) ) {
$all_the_revisions[] = array (
'ID' => $revision->ID,
);
continue;
}
}

if ( $compare_two_mode ) {
$compare_to_gravatar = get_avatar( $left_revision->post_author, 24 );
$compare_to_author = get_the_author_meta( 'display_name', $left_revision->post_author );
$compare_to_date = date_i18n( $datef, strtotime( $left_revision->post_modified ) );

$revision_from_date_author = sprintf(
/* translators: post revision title: 1: author avatar, 2: author name, 3: time ago, 4: date */
_x( '%1$s %2$s, %3$s ago (%4$s)', 'post revision title' ),
$compare_to_gravatar,
$compare_to_author,
human_time_diff( strtotime( $left_revision->post_modified ), current_time( 'timestamp' ) ),
$compare_to_date
);
}

$gravatar = get_avatar( $revision->post_author, 24 );
$author = get_the_author_meta( 'display_name', $revision->post_author );
$date = date_i18n( $datef, strtotime( $revision->post_modified ) );
$revision_date_author = sprintf(
/* translators: post revision title: 1: author avatar, 2: author name, 3: time ago, 4: date */
_x( '%1$s %2$s, %3$s ago (%4$s)', 'post revision title' ),
$gravatar,
$author,
human_time_diff( strtotime( $revision->post_modified ), current_time( 'timestamp' ) ),
$date
);
function wp_ajax_get_revision_diffs() {
require ABSPATH . 'wp-admin/includes/revision.php';

/* translators: 1: date */
$autosavef = _x( '%1$s [Autosave]', 'post revision title extra' );
/* translators: 1: date */
$currentf = _x( '%1$s [Current Revision]', 'post revision title extra' );
// check_ajax_referer( 'revisions-ajax-nonce', 'nonce' );

if ( ! $post = get_post( $post_id ) )
continue;
if ( ! $post = get_post( (int) $_REQUEST['post_id'] ) )
wp_send_json_error();

if ( $left_revision->post_modified === $post->post_modified )
$revision_from_date_author = sprintf( $currentf, $revision_from_date_author );
elseif ( wp_is_post_autosave( $left_revision ) )
$revision_from_date_author = sprintf( $autosavef, $revision_from_date_author );
if ( ! current_user_can( 'read_post', $post->ID ) )
wp_send_json_error();

if ( $revision->post_modified === $post->post_modified ) {
$revision_date_author = sprintf( $currentf, $revision_date_author );
$is_current_revision = true;
} elseif ( wp_is_post_autosave( $revision ) ) {
$revision_date_author = sprintf( $autosavef, $revision_date_author );
}
// Really just pre-loading the cache here.
if ( ! $revisions = wp_get_post_revisions( $post->ID ) )
wp_send_json_error();

/* translators: revision date short format, see http://php.net/date */
$date_short_format = _x( 'j M @ G:i', 'revision date short format');
$date_short = date_i18n( $date_short_format, strtotime( $revision->post_modified ) );
$return = array();
@set_time_limit( count( $_REQUEST['compare'] ) );

$revision_date_author_short = sprintf(
'%s <strong>%s</strong><br />%s',
$gravatar,
$author,
$date_short
);
foreach ( $_REQUEST['compare'] as $compare_key ) {
list( $compare_from, $compare_to ) = explode( ':', $compare_key ); // from:to

$restore_link = wp_nonce_url(
add_query_arg(
array( 'revision' => $revision->ID,
'action' => 'restore' ),
admin_url( 'revision.php' )
),
"restore-post_{$revision->ID}"
$return[] = array(
'id' => $compare_key,
'fields' => wp_get_revision_ui_diff( $post, $compare_from, $compare_to ),
);

// if this is a left handled calculation swap data
if ( 0 != $right_handle_at ) {
$tmp = $revision_from_date_author;
$revision_from_date_author = $revision_date_author;
$revision_date_author = $tmp;
}

if ( ( $compare_two_mode || -1 !== $previous_revision_id ) ) {
$all_the_revisions[] = array (
'ID' => $revision->ID,
'titleTo' => $revision_date_author,
'titleFrom' => $revision_from_date_author,
'titleTooltip' => $revision_date_author_short,
'restoreLink' => urldecode( $restore_link ),
'previousID' => $previous_revision_id,
'isCurrent' => $is_current_revision,
);
}
$previous_revision_id = $revision->ID;

endforeach;

// in RTL + single handle mode, reverse the revision direction
if ( is_rtl() && $compare_two_mode )
$all_the_revisions = array_reverse( $all_the_revisions );

echo json_encode( $all_the_revisions );
exit();
}
wp_send_json_success( $return );
}
Loading

0 comments on commit 77abb9f

Please sign in to comment.