Implement basic transaction detail blocks
Summary:
Some transactions (like editing configuration values, task descriptions, or Conpherence images) can't be simply explained and need an additional larger element to show them fully (like a text diff).
Support change details like this in ApplicationTransactions. Implements the element in Config, so you can see changes.
Test Plan: {F32974}
Reviewers: chad
Reviewed By: chad
CC: aran
Maniphest Tasks: T2213
Differential Revision: https://secure.phabricator.com/D4984
			
			
This commit is contained in:
		| @@ -57,7 +57,7 @@ $package_spec = array( | |||||||
|     'phabricator-textareautils', |     'phabricator-textareautils', | ||||||
|     'phabricator-file-upload', |     'phabricator-file-upload', | ||||||
|     'javelin-behavior-global-drag-and-drop', |     'javelin-behavior-global-drag-and-drop', | ||||||
|     'javelin-behavior-phabricator-home-reveal-tiles', |     'javelin-behavior-phabricator-reveal-content', | ||||||
|   ), |   ), | ||||||
|   'core.pkg.css' => array( |   'core.pkg.css' => array( | ||||||
|     'phabricator-core-css', |     'phabricator-core-css', | ||||||
|   | |||||||
| @@ -1686,18 +1686,6 @@ celerity_register_resource_map(array( | |||||||
|     ), |     ), | ||||||
|     'disk' => '/rsrc/js/application/core/behavior-file-tree.js', |     'disk' => '/rsrc/js/application/core/behavior-file-tree.js', | ||||||
|   ), |   ), | ||||||
|   'javelin-behavior-phabricator-home-reveal-tiles' => |  | ||||||
|   array( |  | ||||||
|     'uri' => '/res/b3c5cea9/rsrc/js/application/core/behavior-home-reveal-tiles.js', |  | ||||||
|     'type' => 'js', |  | ||||||
|     'requires' => |  | ||||||
|     array( |  | ||||||
|       0 => 'javelin-behavior', |  | ||||||
|       1 => 'javelin-stratcom', |  | ||||||
|       2 => 'javelin-dom', |  | ||||||
|     ), |  | ||||||
|     'disk' => '/rsrc/js/application/core/behavior-home-reveal-tiles.js', |  | ||||||
|   ), |  | ||||||
|   'javelin-behavior-phabricator-keyboard-pager' => |   'javelin-behavior-phabricator-keyboard-pager' => | ||||||
|   array( |   array( | ||||||
|     'uri' => '/res/56d64eff/rsrc/js/application/core/behavior-keyboard-pager.js', |     'uri' => '/res/56d64eff/rsrc/js/application/core/behavior-keyboard-pager.js', | ||||||
| @@ -1789,6 +1777,18 @@ celerity_register_resource_map(array( | |||||||
|     ), |     ), | ||||||
|     'disk' => '/rsrc/js/application/core/behavior-phabricator-remarkup-assist.js', |     'disk' => '/rsrc/js/application/core/behavior-phabricator-remarkup-assist.js', | ||||||
|   ), |   ), | ||||||
|  |   'javelin-behavior-phabricator-reveal-content' => | ||||||
|  |   array( | ||||||
|  |     'uri' => '/res/a4fae14a/rsrc/js/application/core/behavior-reveal-content.js', | ||||||
|  |     'type' => 'js', | ||||||
|  |     'requires' => | ||||||
|  |     array( | ||||||
|  |       0 => 'javelin-behavior', | ||||||
|  |       1 => 'javelin-stratcom', | ||||||
|  |       2 => 'javelin-dom', | ||||||
|  |     ), | ||||||
|  |     'disk' => '/rsrc/js/application/core/behavior-reveal-content.js', | ||||||
|  |   ), | ||||||
|   'javelin-behavior-phabricator-search-typeahead' => |   'javelin-behavior-phabricator-search-typeahead' => | ||||||
|   array( |   array( | ||||||
|     'uri' => '/res/046ab274/rsrc/js/application/core/behavior-search-typeahead.js', |     'uri' => '/res/046ab274/rsrc/js/application/core/behavior-search-typeahead.js', | ||||||
| @@ -3017,7 +3017,7 @@ celerity_register_resource_map(array( | |||||||
|   ), |   ), | ||||||
|   'phabricator-timeline-view-css' => |   'phabricator-timeline-view-css' => | ||||||
|   array( |   array( | ||||||
|     'uri' => '/res/d87e1d60/rsrc/css/layout/phabricator-timeline-view.css', |     'uri' => '/res/5517bf1a/rsrc/css/layout/phabricator-timeline-view.css', | ||||||
|     'type' => 'css', |     'type' => 'css', | ||||||
|     'requires' => |     'requires' => | ||||||
|     array( |     array( | ||||||
| @@ -3471,7 +3471,7 @@ celerity_register_resource_map(array( | |||||||
|       'uri' => '/res/pkg/acc46105/core.pkg.css', |       'uri' => '/res/pkg/acc46105/core.pkg.css', | ||||||
|       'type' => 'css', |       'type' => 'css', | ||||||
|     ), |     ), | ||||||
|     'bc0774e5' => |     'd29c1557' => | ||||||
|     array( |     array( | ||||||
|       'name' => 'core.pkg.js', |       'name' => 'core.pkg.js', | ||||||
|       'symbols' => |       'symbols' => | ||||||
| @@ -3508,9 +3508,9 @@ celerity_register_resource_map(array( | |||||||
|         29 => 'phabricator-textareautils', |         29 => 'phabricator-textareautils', | ||||||
|         30 => 'phabricator-file-upload', |         30 => 'phabricator-file-upload', | ||||||
|         31 => 'javelin-behavior-global-drag-and-drop', |         31 => 'javelin-behavior-global-drag-and-drop', | ||||||
|         32 => 'javelin-behavior-phabricator-home-reveal-tiles', |         32 => 'javelin-behavior-phabricator-reveal-content', | ||||||
|       ), |       ), | ||||||
|       'uri' => '/res/pkg/bc0774e5/core.pkg.js', |       'uri' => '/res/pkg/d29c1557/core.pkg.js', | ||||||
|       'type' => 'js', |       'type' => 'js', | ||||||
|     ), |     ), | ||||||
|     'dca4a03d' => |     'dca4a03d' => | ||||||
| @@ -3682,17 +3682,17 @@ celerity_register_resource_map(array( | |||||||
|     'diffusion-icons-css' => 'c8ce2d88', |     'diffusion-icons-css' => 'c8ce2d88', | ||||||
|     'global-drag-and-drop-css' => 'acc46105', |     'global-drag-and-drop-css' => 'acc46105', | ||||||
|     'inline-comment-summary-css' => '8aaacd1b', |     'inline-comment-summary-css' => '8aaacd1b', | ||||||
|     'javelin-aphlict' => 'bc0774e5', |     'javelin-aphlict' => 'd29c1557', | ||||||
|     'javelin-behavior' => 'a69b9f1f', |     'javelin-behavior' => 'a69b9f1f', | ||||||
|     'javelin-behavior-aphlict-dropdown' => 'bc0774e5', |     'javelin-behavior-aphlict-dropdown' => 'd29c1557', | ||||||
|     'javelin-behavior-aphlict-listen' => 'bc0774e5', |     'javelin-behavior-aphlict-listen' => 'd29c1557', | ||||||
|     'javelin-behavior-aphront-basic-tokenizer' => 'bc0774e5', |     'javelin-behavior-aphront-basic-tokenizer' => 'd29c1557', | ||||||
|     'javelin-behavior-aphront-drag-and-drop' => '95d0d865', |     'javelin-behavior-aphront-drag-and-drop' => '95d0d865', | ||||||
|     'javelin-behavior-aphront-drag-and-drop-textarea' => '95d0d865', |     'javelin-behavior-aphront-drag-and-drop-textarea' => '95d0d865', | ||||||
|     'javelin-behavior-aphront-form-disable-on-submit' => 'bc0774e5', |     'javelin-behavior-aphront-form-disable-on-submit' => 'd29c1557', | ||||||
|     'javelin-behavior-audit-preview' => 'f96657b8', |     'javelin-behavior-audit-preview' => 'f96657b8', | ||||||
|     'javelin-behavior-dark-console' => 'dca4a03d', |     'javelin-behavior-dark-console' => 'dca4a03d', | ||||||
|     'javelin-behavior-device' => 'bc0774e5', |     'javelin-behavior-device' => 'd29c1557', | ||||||
|     'javelin-behavior-differential-accept-with-errors' => '95d0d865', |     'javelin-behavior-differential-accept-with-errors' => '95d0d865', | ||||||
|     'javelin-behavior-differential-add-reviewers-and-ccs' => '95d0d865', |     'javelin-behavior-differential-add-reviewers-and-ccs' => '95d0d865', | ||||||
|     'javelin-behavior-differential-comment-jump' => '95d0d865', |     'javelin-behavior-differential-comment-jump' => '95d0d865', | ||||||
| @@ -3708,29 +3708,29 @@ celerity_register_resource_map(array( | |||||||
|     'javelin-behavior-diffusion-commit-graph' => 'f96657b8', |     'javelin-behavior-diffusion-commit-graph' => 'f96657b8', | ||||||
|     'javelin-behavior-diffusion-pull-lastmodified' => 'f96657b8', |     'javelin-behavior-diffusion-pull-lastmodified' => 'f96657b8', | ||||||
|     'javelin-behavior-error-log' => 'dca4a03d', |     'javelin-behavior-error-log' => 'dca4a03d', | ||||||
|     'javelin-behavior-global-drag-and-drop' => 'bc0774e5', |     'javelin-behavior-global-drag-and-drop' => 'd29c1557', | ||||||
|     'javelin-behavior-konami' => 'bc0774e5', |     'javelin-behavior-konami' => 'd29c1557', | ||||||
|     'javelin-behavior-lightbox-attachments' => 'bc0774e5', |     'javelin-behavior-lightbox-attachments' => 'd29c1557', | ||||||
|     'javelin-behavior-maniphest-batch-selector' => '7707de41', |     'javelin-behavior-maniphest-batch-selector' => '7707de41', | ||||||
|     'javelin-behavior-maniphest-subpriority-editor' => '7707de41', |     'javelin-behavior-maniphest-subpriority-editor' => '7707de41', | ||||||
|     'javelin-behavior-maniphest-transaction-controls' => '7707de41', |     'javelin-behavior-maniphest-transaction-controls' => '7707de41', | ||||||
|     'javelin-behavior-maniphest-transaction-expand' => '7707de41', |     'javelin-behavior-maniphest-transaction-expand' => '7707de41', | ||||||
|     'javelin-behavior-maniphest-transaction-preview' => '7707de41', |     'javelin-behavior-maniphest-transaction-preview' => '7707de41', | ||||||
|     'javelin-behavior-phabricator-active-nav' => 'bc0774e5', |     'javelin-behavior-phabricator-active-nav' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-autofocus' => 'bc0774e5', |     'javelin-behavior-phabricator-autofocus' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-home-reveal-tiles' => 'bc0774e5', |     'javelin-behavior-phabricator-keyboard-shortcuts' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-keyboard-shortcuts' => 'bc0774e5', |     'javelin-behavior-phabricator-nav' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-nav' => 'bc0774e5', |  | ||||||
|     'javelin-behavior-phabricator-object-selector' => '95d0d865', |     'javelin-behavior-phabricator-object-selector' => '95d0d865', | ||||||
|     'javelin-behavior-phabricator-oncopy' => 'bc0774e5', |     'javelin-behavior-phabricator-oncopy' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-remarkup-assist' => 'bc0774e5', |     'javelin-behavior-phabricator-remarkup-assist' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-search-typeahead' => 'bc0774e5', |     'javelin-behavior-phabricator-reveal-content' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-tooltips' => 'bc0774e5', |     'javelin-behavior-phabricator-search-typeahead' => 'd29c1557', | ||||||
|     'javelin-behavior-phabricator-watch-anchor' => 'bc0774e5', |     'javelin-behavior-phabricator-tooltips' => 'd29c1557', | ||||||
|     'javelin-behavior-refresh-csrf' => 'bc0774e5', |     'javelin-behavior-phabricator-watch-anchor' => 'd29c1557', | ||||||
|  |     'javelin-behavior-refresh-csrf' => 'd29c1557', | ||||||
|     'javelin-behavior-repository-crossreference' => '95d0d865', |     'javelin-behavior-repository-crossreference' => '95d0d865', | ||||||
|     'javelin-behavior-toggle-class' => 'bc0774e5', |     'javelin-behavior-toggle-class' => 'd29c1557', | ||||||
|     'javelin-behavior-workflow' => 'bc0774e5', |     'javelin-behavior-workflow' => 'd29c1557', | ||||||
|     'javelin-dom' => 'a69b9f1f', |     'javelin-dom' => 'a69b9f1f', | ||||||
|     'javelin-event' => 'a69b9f1f', |     'javelin-event' => 'a69b9f1f', | ||||||
|     'javelin-install' => 'a69b9f1f', |     'javelin-install' => 'a69b9f1f', | ||||||
| @@ -3752,39 +3752,39 @@ celerity_register_resource_map(array( | |||||||
|     'lightbox-attachment-css' => 'acc46105', |     'lightbox-attachment-css' => 'acc46105', | ||||||
|     'maniphest-task-summary-css' => 'e30a3fa8', |     'maniphest-task-summary-css' => 'e30a3fa8', | ||||||
|     'maniphest-transaction-detail-css' => 'e30a3fa8', |     'maniphest-transaction-detail-css' => 'e30a3fa8', | ||||||
|     'phabricator-busy' => 'bc0774e5', |     'phabricator-busy' => 'd29c1557', | ||||||
|     'phabricator-content-source-view-css' => '8aaacd1b', |     'phabricator-content-source-view-css' => '8aaacd1b', | ||||||
|     'phabricator-core-buttons-css' => 'acc46105', |     'phabricator-core-buttons-css' => 'acc46105', | ||||||
|     'phabricator-core-css' => 'acc46105', |     'phabricator-core-css' => 'acc46105', | ||||||
|     'phabricator-crumbs-view-css' => 'acc46105', |     'phabricator-crumbs-view-css' => 'acc46105', | ||||||
|     'phabricator-directory-css' => 'acc46105', |     'phabricator-directory-css' => 'acc46105', | ||||||
|     'phabricator-drag-and-drop-file-upload' => '95d0d865', |     'phabricator-drag-and-drop-file-upload' => '95d0d865', | ||||||
|     'phabricator-dropdown-menu' => 'bc0774e5', |     'phabricator-dropdown-menu' => 'd29c1557', | ||||||
|     'phabricator-file-upload' => 'bc0774e5', |     'phabricator-file-upload' => 'd29c1557', | ||||||
|     'phabricator-filetree-view-css' => 'acc46105', |     'phabricator-filetree-view-css' => 'acc46105', | ||||||
|     'phabricator-flag-css' => 'acc46105', |     'phabricator-flag-css' => 'acc46105', | ||||||
|     'phabricator-form-view-css' => 'acc46105', |     'phabricator-form-view-css' => 'acc46105', | ||||||
|     'phabricator-header-view-css' => 'acc46105', |     'phabricator-header-view-css' => 'acc46105', | ||||||
|     'phabricator-jump-nav' => 'acc46105', |     'phabricator-jump-nav' => 'acc46105', | ||||||
|     'phabricator-keyboard-shortcut' => 'bc0774e5', |     'phabricator-keyboard-shortcut' => 'd29c1557', | ||||||
|     'phabricator-keyboard-shortcut-manager' => 'bc0774e5', |     'phabricator-keyboard-shortcut-manager' => 'd29c1557', | ||||||
|     'phabricator-main-menu-view' => 'acc46105', |     'phabricator-main-menu-view' => 'acc46105', | ||||||
|     'phabricator-menu-item' => 'bc0774e5', |     'phabricator-menu-item' => 'd29c1557', | ||||||
|     'phabricator-nav-view-css' => 'acc46105', |     'phabricator-nav-view-css' => 'acc46105', | ||||||
|     'phabricator-notification' => 'bc0774e5', |     'phabricator-notification' => 'd29c1557', | ||||||
|     'phabricator-notification-css' => 'acc46105', |     'phabricator-notification-css' => 'acc46105', | ||||||
|     'phabricator-notification-menu-css' => 'acc46105', |     'phabricator-notification-menu-css' => 'acc46105', | ||||||
|     'phabricator-object-item-list-view-css' => 'acc46105', |     'phabricator-object-item-list-view-css' => 'acc46105', | ||||||
|     'phabricator-object-selector-css' => '8aaacd1b', |     'phabricator-object-selector-css' => '8aaacd1b', | ||||||
|     'phabricator-paste-file-upload' => 'bc0774e5', |     'phabricator-paste-file-upload' => 'd29c1557', | ||||||
|     'phabricator-prefab' => 'bc0774e5', |     'phabricator-prefab' => 'd29c1557', | ||||||
|     'phabricator-project-tag-css' => 'e30a3fa8', |     'phabricator-project-tag-css' => 'e30a3fa8', | ||||||
|     'phabricator-remarkup-css' => 'acc46105', |     'phabricator-remarkup-css' => 'acc46105', | ||||||
|     'phabricator-shaped-request' => '95d0d865', |     'phabricator-shaped-request' => '95d0d865', | ||||||
|     'phabricator-side-menu-view-css' => 'acc46105', |     'phabricator-side-menu-view-css' => 'acc46105', | ||||||
|     'phabricator-standard-page-view' => 'acc46105', |     'phabricator-standard-page-view' => 'acc46105', | ||||||
|     'phabricator-textareautils' => 'bc0774e5', |     'phabricator-textareautils' => 'd29c1557', | ||||||
|     'phabricator-tooltip' => 'bc0774e5', |     'phabricator-tooltip' => 'd29c1557', | ||||||
|     'phabricator-transaction-view-css' => 'acc46105', |     'phabricator-transaction-view-css' => 'acc46105', | ||||||
|     'phabricator-zindex-css' => 'acc46105', |     'phabricator-zindex-css' => 'acc46105', | ||||||
|     'sprite-apps-large-css' => 'acc46105', |     'sprite-apps-large-css' => 'acc46105', | ||||||
|   | |||||||
| @@ -684,6 +684,7 @@ phutil_register_library_map(array( | |||||||
|     'PhabricatorApplicationTransactionNoEffectResponse' => 'applications/transactions/response/PhabricatorApplicationTransactionNoEffectResponse.php', |     'PhabricatorApplicationTransactionNoEffectResponse' => 'applications/transactions/response/PhabricatorApplicationTransactionNoEffectResponse.php', | ||||||
|     'PhabricatorApplicationTransactionQuery' => 'applications/transactions/query/PhabricatorApplicationTransactionQuery.php', |     'PhabricatorApplicationTransactionQuery' => 'applications/transactions/query/PhabricatorApplicationTransactionQuery.php', | ||||||
|     'PhabricatorApplicationTransactionResponse' => 'applications/transactions/response/PhabricatorApplicationTransactionResponse.php', |     'PhabricatorApplicationTransactionResponse' => 'applications/transactions/response/PhabricatorApplicationTransactionResponse.php', | ||||||
|  |     'PhabricatorApplicationTransactionTextDiffDetailView' => 'applications/transactions/view/PhabricatorApplicationTransactionTextDiffDetailView.php', | ||||||
|     'PhabricatorApplicationTransactionView' => 'applications/transactions/view/PhabricatorApplicationTransactionView.php', |     'PhabricatorApplicationTransactionView' => 'applications/transactions/view/PhabricatorApplicationTransactionView.php', | ||||||
|     'PhabricatorApplicationTransactions' => 'applications/transactions/application/PhabricatorApplicationTransactions.php', |     'PhabricatorApplicationTransactions' => 'applications/transactions/application/PhabricatorApplicationTransactions.php', | ||||||
|     'PhabricatorApplicationUIExamples' => 'applications/uiexample/application/PhabricatorApplicationUIExamples.php', |     'PhabricatorApplicationUIExamples' => 'applications/uiexample/application/PhabricatorApplicationUIExamples.php', | ||||||
| @@ -2168,6 +2169,7 @@ phutil_register_library_map(array( | |||||||
|     'PhabricatorApplicationTransactionNoEffectResponse' => 'AphrontProxyResponse', |     'PhabricatorApplicationTransactionNoEffectResponse' => 'AphrontProxyResponse', | ||||||
|     'PhabricatorApplicationTransactionQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', |     'PhabricatorApplicationTransactionQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', | ||||||
|     'PhabricatorApplicationTransactionResponse' => 'AphrontProxyResponse', |     'PhabricatorApplicationTransactionResponse' => 'AphrontProxyResponse', | ||||||
|  |     'PhabricatorApplicationTransactionTextDiffDetailView' => 'AphrontView', | ||||||
|     'PhabricatorApplicationTransactionView' => 'AphrontView', |     'PhabricatorApplicationTransactionView' => 'AphrontView', | ||||||
|     'PhabricatorApplicationTransactions' => 'PhabricatorApplication', |     'PhabricatorApplicationTransactions' => 'PhabricatorApplication', | ||||||
|     'PhabricatorApplicationUIExamples' => 'PhabricatorApplication', |     'PhabricatorApplicationUIExamples' => 'PhabricatorApplication', | ||||||
| @@ -2222,7 +2224,7 @@ phutil_register_library_map(array( | |||||||
|     'PhabricatorCalendarHoliday' => 'PhabricatorCalendarDAO', |     'PhabricatorCalendarHoliday' => 'PhabricatorCalendarDAO', | ||||||
|     'PhabricatorCalendarHolidayTestCase' => 'PhabricatorTestCase', |     'PhabricatorCalendarHolidayTestCase' => 'PhabricatorTestCase', | ||||||
|     'PhabricatorCalendarViewStatusController' => 'PhabricatorCalendarController', |     'PhabricatorCalendarViewStatusController' => 'PhabricatorCalendarController', | ||||||
|     'PhabricatorCampfireProtocolAdapter' => 'PhabricatorBaseProtocolAdapter', |     'PhabricatorCampfireProtocolAdapter' => 'PhabricatorBotBaseStreamingProtocolAdapter', | ||||||
|     'PhabricatorChangesetResponse' => 'AphrontProxyResponse', |     'PhabricatorChangesetResponse' => 'AphrontProxyResponse', | ||||||
|     'PhabricatorChatLogChannel' => |     'PhabricatorChatLogChannel' => | ||||||
|     array( |     array( | ||||||
|   | |||||||
| @@ -70,6 +70,39 @@ final class PhabricatorConfigTransaction | |||||||
|     return parent::getIcon(); |     return parent::getIcon(); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|  |   public function hasChangeDetails() { | ||||||
|  |     switch ($this->getTransactionType()) { | ||||||
|  |       case self::TYPE_EDIT: | ||||||
|  |         return true; | ||||||
|  |     } | ||||||
|  |     return parent::hasChangeDetails(); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   public function renderChangeDetails() { | ||||||
|  |     $old = $this->getOldValue(); | ||||||
|  |     $new = $this->getNewValue(); | ||||||
|  |  | ||||||
|  |     if ($old['deleted']) { | ||||||
|  |       $old_text = ''; | ||||||
|  |     } else { | ||||||
|  |       // NOTE: Here and below, we're adding a synthetic "\n" to prevent the | ||||||
|  |       // differ from complaining about missing trailing newlines. | ||||||
|  |       $old_text = PhabricatorConfigJSON::prettyPrintJSON($old['value'])."\n"; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if ($new['deleted']) { | ||||||
|  |       $new_text = ''; | ||||||
|  |     } else { | ||||||
|  |       $new_text = PhabricatorConfigJSON::prettyPrintJSON($new['value'])."\n"; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     $view = id(new PhabricatorApplicationTransactionTextDiffDetailView()) | ||||||
|  |       ->setOldText($old_text) | ||||||
|  |       ->setNewText($new_text); | ||||||
|  |  | ||||||
|  |     return $view->render(); | ||||||
|  |   } | ||||||
|  |  | ||||||
|   public function getColor() { |   public function getColor() { | ||||||
|     $old = $this->getOldValue(); |     $old = $this->getOldValue(); | ||||||
|     $new = $this->getNewValue(); |     $new = $this->getNewValue(); | ||||||
|   | |||||||
| @@ -26,7 +26,7 @@ final class DifferentialParseRenderTestCase extends PhabricatorTestCase { | |||||||
|         $actual = $parser->render(null, null, array()); |         $actual = $parser->render(null, null, array()); | ||||||
|  |  | ||||||
|         $expect = Filesystem::readFile($dir.$file.'.'.$type.'.expect'); |         $expect = Filesystem::readFile($dir.$file.'.'.$type.'.expect'); | ||||||
|         $this->assertEqual($expect, $actual, $file.'.'.$type); |         $this->assertEqual($expect, (string)$actual, $file.'.'.$type); | ||||||
|       } |       } | ||||||
|     } |     } | ||||||
|   } |   } | ||||||
|   | |||||||
| @@ -252,7 +252,7 @@ abstract class DifferentialChangesetRenderer { | |||||||
|     // TODO: Both these steps should happen earlier. |     // TODO: Both these steps should happen earlier. | ||||||
|     $result = str_replace("\t", '  ', $result); |     $result = str_replace("\t", '  ', $result); | ||||||
|  |  | ||||||
|     return $result; |     return phutil_safe_html($result); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|   abstract public function isOneUpRenderer(); |   abstract public function isOneUpRenderer(); | ||||||
|   | |||||||
| @@ -84,7 +84,7 @@ abstract class PhabricatorDirectoryController extends PhabricatorController { | |||||||
|         $show_item = id(new PhabricatorMenuItemView()) |         $show_item = id(new PhabricatorMenuItemView()) | ||||||
|           ->setName(pht('Show More Applications')) |           ->setName(pht('Show More Applications')) | ||||||
|           ->setHref('#') |           ->setHref('#') | ||||||
|           ->addSigil('home-show-applications') |           ->addSigil('reveal-content') | ||||||
|           ->setID($show_item_id); |           ->setID($show_item_id); | ||||||
|  |  | ||||||
|         $hide_item = id(new PhabricatorMenuItemView()) |         $hide_item = id(new PhabricatorMenuItemView()) | ||||||
| @@ -92,7 +92,7 @@ abstract class PhabricatorDirectoryController extends PhabricatorController { | |||||||
|           ->setHref('#') |           ->setHref('#') | ||||||
|           ->setStyle('display: none') |           ->setStyle('display: none') | ||||||
|           ->setID($hide_item_id) |           ->setID($hide_item_id) | ||||||
|           ->addSigil('home-hide-applications'); |           ->addSigil('reveal-content'); | ||||||
|  |  | ||||||
|         $nav->addMenuItem($show_item); |         $nav->addMenuItem($show_item); | ||||||
|         $tile_ids = array($hide_item_id); |         $tile_ids = array($hide_item_id); | ||||||
| @@ -146,9 +146,17 @@ abstract class PhabricatorDirectoryController extends PhabricatorController { | |||||||
|       } |       } | ||||||
|  |  | ||||||
|       if ($is_hide) { |       if ($is_hide) { | ||||||
|         Javelin::initBehavior('phabricator-home-reveal-tiles', array( |         Javelin::initBehavior('phabricator-reveal-content'); | ||||||
|           'tileIDs' => $tile_ids, |  | ||||||
|           'showID' => $show_item_id, |         $show_item->setMetadata( | ||||||
|  |           array( | ||||||
|  |             'showIDs' => $tile_ids, | ||||||
|  |             'hideIDs' => array($show_item_id), | ||||||
|  |           )); | ||||||
|  |         $hide_item->setMetadata( | ||||||
|  |           array( | ||||||
|  |             'showIDs' => array($show_item_id), | ||||||
|  |             'hideIDs' => $tile_ids, | ||||||
|           )); |           )); | ||||||
|         $nav->addMenuItem($hide_item); |         $nav->addMenuItem($hide_item); | ||||||
|       } |       } | ||||||
|   | |||||||
| @@ -321,6 +321,13 @@ abstract class PhabricatorApplicationTransaction | |||||||
|     return array(); |     return array(); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|  |   public function hasChangeDetails() { | ||||||
|  |     return false; | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   public function renderChangeDetails() { | ||||||
|  |     return null; | ||||||
|  |   } | ||||||
|  |  | ||||||
| /* -(  PhabricatorPolicyInterface Implementation  )-------------------------- */ | /* -(  PhabricatorPolicyInterface Implementation  )-------------------------- */ | ||||||
|  |  | ||||||
|   | |||||||
| @@ -0,0 +1,45 @@ | |||||||
|  | <?php | ||||||
|  |  | ||||||
|  | final class PhabricatorApplicationTransactionTextDiffDetailView | ||||||
|  |   extends AphrontView { | ||||||
|  |  | ||||||
|  |   private $oldText; | ||||||
|  |   private $newText; | ||||||
|  |  | ||||||
|  |   public function setNewText($new_text) { | ||||||
|  |     $this->newText = $new_text; | ||||||
|  |     return $this; | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   public function setOldText($old_text) { | ||||||
|  |     $this->oldText = $old_text; | ||||||
|  |     return $this; | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   public function render() { | ||||||
|  |     $old = $this->oldText; | ||||||
|  |     $new = $this->newText; | ||||||
|  |  | ||||||
|  |     // TODO: On mobile, or perhaps by default, we should switch to 1-up once | ||||||
|  |     // that is built. | ||||||
|  |  | ||||||
|  |     // TODO: This should be utf8-aware, but we don't currently have a plain-text | ||||||
|  |     // utf8 hard-wrap function. See T2554. | ||||||
|  |     $old = wordwrap($old, 80); | ||||||
|  |     $new = wordwrap($new, 80); | ||||||
|  |  | ||||||
|  |     $engine = new PhabricatorDifferenceEngine(); | ||||||
|  |     $changeset = $engine->generateChangesetFromFileContent($old, $new); | ||||||
|  |  | ||||||
|  |     $whitespace_mode = DifferentialChangesetParser::WHITESPACE_SHOW_ALL; | ||||||
|  |  | ||||||
|  |     $parser = new DifferentialChangesetParser(); | ||||||
|  |     $parser->setChangeset($changeset); | ||||||
|  |     $parser->setMarkupEngine(new PhabricatorMarkupEngine()); | ||||||
|  |     $parser->setWhitespaceMode($whitespace_mode); | ||||||
|  |  | ||||||
|  |     return $parser->render(0, PHP_INT_MAX, array()); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  | } | ||||||
|  |  | ||||||
| @@ -59,8 +59,17 @@ class PhabricatorApplicationTransactionView extends AphrontView { | |||||||
|         ->setTransactionPHID($xaction->getPHID()) |         ->setTransactionPHID($xaction->getPHID()) | ||||||
|         ->setUserHandle($xaction->getHandle($xaction->getAuthorPHID())) |         ->setUserHandle($xaction->getHandle($xaction->getAuthorPHID())) | ||||||
|         ->setIcon($xaction->getIcon()) |         ->setIcon($xaction->getIcon()) | ||||||
|         ->setColor($xaction->getColor()) |         ->setColor($xaction->getColor()); | ||||||
|         ->setTitle($xaction->getTitle()); |  | ||||||
|  |       $title = $xaction->getTitle(); | ||||||
|  |       if ($xaction->hasChangeDetails()) { | ||||||
|  |         $title = array( | ||||||
|  |           $title, | ||||||
|  |           ' ', | ||||||
|  |           $this->buildChangeDetails($xaction), | ||||||
|  |         ); | ||||||
|  |       } | ||||||
|  |       $event->setTitle($title); | ||||||
|  |  | ||||||
|       if ($this->isPreview) { |       if ($this->isPreview) { | ||||||
|         $event->setIsPreview(true); |         $event->setIsPreview(true); | ||||||
| @@ -73,7 +82,6 @@ class PhabricatorApplicationTransactionView extends AphrontView { | |||||||
|         $anchor++; |         $anchor++; | ||||||
|       } |       } | ||||||
|  |  | ||||||
|  |  | ||||||
|       $has_deleted_comment = $xaction->getComment() && |       $has_deleted_comment = $xaction->getComment() && | ||||||
|         $xaction->getComment()->getIsDeleted(); |         $xaction->getComment()->getIsDeleted(); | ||||||
|  |  | ||||||
| @@ -153,5 +161,60 @@ class PhabricatorApplicationTransactionView extends AphrontView { | |||||||
|     return $engine; |     return $engine; | ||||||
|   } |   } | ||||||
|  |  | ||||||
|  |   private function buildChangeDetails( | ||||||
|  |     PhabricatorApplicationTransaction $xaction) { | ||||||
|  |  | ||||||
|  |     Javelin::initBehavior('phabricator-reveal-content'); | ||||||
|  |  | ||||||
|  |     $show_id = celerity_generate_unique_node_id(); | ||||||
|  |     $hide_id = celerity_generate_unique_node_id(); | ||||||
|  |     $content_id = celerity_generate_unique_node_id(); | ||||||
|  |  | ||||||
|  |     $show_more = javelin_tag( | ||||||
|  |       'a', | ||||||
|  |       array( | ||||||
|  |         'href' => '#', | ||||||
|  |         'sigil' => 'reveal-content', | ||||||
|  |         'mustcapture' => true, | ||||||
|  |         'id' => $show_id, | ||||||
|  |         'meta' => array( | ||||||
|  |           'hideIDs' => array($show_id), | ||||||
|  |           'showIDs' => array($hide_id, $content_id), | ||||||
|  |         ), | ||||||
|  |       ), | ||||||
|  |       pht('(Show Details)')); | ||||||
|  |  | ||||||
|  |     $hide_more = javelin_tag( | ||||||
|  |       'a', | ||||||
|  |       array( | ||||||
|  |         'href' => '#', | ||||||
|  |         'sigil' => 'reveal-content', | ||||||
|  |         'mustcapture' => true, | ||||||
|  |         'id' => $hide_id, | ||||||
|  |         'style' => 'display: none', | ||||||
|  |         'meta' => array( | ||||||
|  |           'hideIDs' => array($hide_id, $content_id), | ||||||
|  |           'showIDs' => array($show_id), | ||||||
|  |         ), | ||||||
|  |       ), | ||||||
|  |       pht('(Hide Details)')); | ||||||
|  |  | ||||||
|  |     $content = phutil_tag( | ||||||
|  |       'div', | ||||||
|  |       array( | ||||||
|  |         'id'    => $content_id, | ||||||
|  |         'style' => 'display: none', | ||||||
|  |         'class' => 'phabricator-timeline-change-details', | ||||||
|  |       ), | ||||||
|  |       $xaction->renderChangeDetails()); | ||||||
|  |  | ||||||
|  |     return array( | ||||||
|  |       $show_more, | ||||||
|  |       $hide_more, | ||||||
|  |       $content, | ||||||
|  |     ); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |  | ||||||
| } | } | ||||||
|  |  | ||||||
|   | |||||||
| @@ -250,3 +250,10 @@ | |||||||
|   padding: 4px 1.25%; |   padding: 4px 1.25%; | ||||||
|   border: solid #c0c5d1 1px 0; |   border: solid #c0c5d1 1px 0; | ||||||
| } | } | ||||||
|  |  | ||||||
|  | .phabricator-timeline-change-details { | ||||||
|  |   padding: 10px 0; | ||||||
|  |   border-style: solid; | ||||||
|  |   border-color: #efefef; | ||||||
|  |   border-width: 1px 0; | ||||||
|  | } | ||||||
|   | |||||||
| @@ -1,33 +0,0 @@ | |||||||
| /** |  | ||||||
|  * @provides javelin-behavior-phabricator-home-reveal-tiles |  | ||||||
|  * @requires javelin-behavior |  | ||||||
|  *           javelin-stratcom |  | ||||||
|  *           javelin-dom |  | ||||||
|  * @javelin |  | ||||||
|  */ |  | ||||||
|  |  | ||||||
| JX.behavior('phabricator-home-reveal-tiles', function(config) { |  | ||||||
|   JX.Stratcom.listen( |  | ||||||
|     'click', |  | ||||||
|     'home-show-applications', |  | ||||||
|     function(e) { |  | ||||||
|       e.kill(); |  | ||||||
|  |  | ||||||
|       for (var ii = 0; ii < config.tileIDs.length; ii++) { |  | ||||||
|         JX.DOM.show(JX.$(config.tileIDs[ii])); |  | ||||||
|       } |  | ||||||
|       JX.DOM.hide(JX.$(config.showID)); |  | ||||||
|     }); |  | ||||||
|  |  | ||||||
|   JX.Stratcom.listen( |  | ||||||
|     'click', |  | ||||||
|     'home-hide-applications', |  | ||||||
|     function(e) { |  | ||||||
|       e.kill(); |  | ||||||
|  |  | ||||||
|       for (var ii = 0; ii < config.tileIDs.length; ii++) { |  | ||||||
|         JX.DOM.hide(JX.$(config.tileIDs[ii])); |  | ||||||
|       } |  | ||||||
|       JX.DOM.show(JX.$(config.showID)); |  | ||||||
|     }); |  | ||||||
| }); |  | ||||||
							
								
								
									
										23
									
								
								webroot/rsrc/js/application/core/behavior-reveal-content.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										23
									
								
								webroot/rsrc/js/application/core/behavior-reveal-content.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,23 @@ | |||||||
|  | /** | ||||||
|  |  * @provides javelin-behavior-phabricator-reveal-content | ||||||
|  |  * @requires javelin-behavior | ||||||
|  |  *           javelin-stratcom | ||||||
|  |  *           javelin-dom | ||||||
|  |  * @javelin | ||||||
|  |  */ | ||||||
|  |  | ||||||
|  | JX.behavior('phabricator-reveal-content', function(config) { | ||||||
|  |   JX.Stratcom.listen( | ||||||
|  |     'click', | ||||||
|  |     'reveal-content', | ||||||
|  |     function(e) { | ||||||
|  |       e.kill(); | ||||||
|  |       var nodes = e.getNodeData('reveal-content'); | ||||||
|  |       for (var ii = 0; ii < nodes.showIDs.length; ii++) { | ||||||
|  |         JX.DOM.show(JX.$(nodes.showIDs[ii])); | ||||||
|  |       } | ||||||
|  |       for (var ii = 0; ii < nodes.hideIDs.length; ii++) { | ||||||
|  |         JX.DOM.hide(JX.$(nodes.hideIDs[ii])); | ||||||
|  |       } | ||||||
|  |     }); | ||||||
|  | }); | ||||||
		Reference in New Issue
	
	Block a user
	 epriestley
					epriestley