@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Add Differential keyboard shortcuts for "mark done" and "hide/show"

Summary:
Fixes T8130. Allows selected comments to be shown/hidden (with "q") or marked done/not-done (with "w").

(These key selections are because "qwer" are right next to each other on QWERTY keyboards, and now mean "hide, done, edit, reply".)

Also, allow "N" and "P" to do next/previous inline, including hidden inlines. This makes "q" to hide/show a little more powerful and a little easier to undo.

Test Plan: Used "q", "w", "N" and "P" to navigate and interact with comments.

Reviewers: chad

Reviewed By: chad

Maniphest Tasks: T8130

Differential Revision: https://secure.phabricator.com/D17906

+109 -23
+11 -11
resources/celerity/map.php
··· 13 13 'core.pkg.js' => '8c5f913d', 14 14 'darkconsole.pkg.js' => '1f9a31bc', 15 15 'differential.pkg.css' => '58712637', 16 - 'differential.pkg.js' => '0bfd141c', 16 + 'differential.pkg.js' => 'e486afd0', 17 17 'diffusion.pkg.css' => 'b93d9b8c', 18 18 'diffusion.pkg.js' => '84c8f8fd', 19 19 'favicon.ico' => '30672e08', ··· 391 391 'rsrc/js/application/dashboard/behavior-dashboard-query-panel-select.js' => '453c5375', 392 392 'rsrc/js/application/dashboard/behavior-dashboard-tab-panel.js' => 'd4eecc63', 393 393 'rsrc/js/application/diff/DiffChangeset.js' => '145c34e2', 394 - 'rsrc/js/application/diff/DiffChangesetList.js' => 'ca3b6387', 395 - 'rsrc/js/application/diff/DiffInline.js' => 'b5b1f167', 394 + 'rsrc/js/application/diff/DiffChangesetList.js' => 'd93e34c2', 395 + 'rsrc/js/application/diff/DiffInline.js' => 'bdf6b568', 396 396 'rsrc/js/application/diff/behavior-preview-link.js' => '051c7832', 397 397 'rsrc/js/application/differential/behavior-comment-jump.js' => '4fdb476d', 398 398 'rsrc/js/application/differential/behavior-comment-preview.js' => 'b064af76', ··· 782 782 'phabricator-darkmessage' => 'c48cccdd', 783 783 'phabricator-dashboard-css' => 'fe5b1869', 784 784 'phabricator-diff-changeset' => '145c34e2', 785 - 'phabricator-diff-changeset-list' => 'ca3b6387', 786 - 'phabricator-diff-inline' => 'b5b1f167', 785 + 'phabricator-diff-changeset-list' => 'd93e34c2', 786 + 'phabricator-diff-inline' => 'bdf6b568', 787 787 'phabricator-drag-and-drop-file-upload' => '58dea2fa', 788 788 'phabricator-draggable-list' => 'bea6e7f4', 789 789 'phabricator-fatal-config-template-css' => '8f18fa41', ··· 1842 1842 'javelin-dom', 1843 1843 'phabricator-draggable-list', 1844 1844 ), 1845 - 'b5b1f167' => array( 1846 - 'javelin-dom', 1847 - ), 1848 1845 'b5c256b8' => array( 1849 1846 'javelin-install', 1850 1847 'javelin-dom', ··· 1892 1889 'javelin-dom', 1893 1890 'javelin-util', 1894 1891 'javelin-request', 1892 + ), 1893 + 'bdf6b568' => array( 1894 + 'javelin-dom', 1895 1895 ), 1896 1896 'bea6e7f4' => array( 1897 1897 'javelin-install', ··· 1984 1984 'phabricator-shaped-request', 1985 1985 'conpherence-thread-manager', 1986 1986 ), 1987 - 'ca3b6387' => array( 1988 - 'javelin-install', 1989 - ), 1990 1987 'ca3f91eb' => array( 1991 1988 'javelin-behavior', 1992 1989 'javelin-dom', ··· 2081 2078 'javelin-dom', 2082 2079 'javelin-util', 2083 2080 'phabricator-shaped-request', 2081 + ), 2082 + 'd93e34c2' => array( 2083 + 'javelin-install', 2084 2084 ), 2085 2085 'de2e896f' => array( 2086 2086 'javelin-behavior',
+15
src/applications/differential/view/DifferentialChangesetListView.php
··· 252 252 pht('You must select a comment to reply to.'), 253 253 'You must select a comment to edit.' => 254 254 pht('You must select a comment to edit.'), 255 + 256 + 'Mark or unmark selected inline comment as done.' => 257 + pht('Mark or unmark selected inline comment as done.'), 258 + 'You must select a comment to mark done.' => 259 + pht('You must select a comment to mark done.'), 260 + 261 + 'Hide or show inline comment.' => 262 + pht('Hide or show inline comment.'), 263 + 'You must select a comment to hide.' => 264 + pht('You must select a comment to hide.'), 265 + 266 + 'Jump to next inline comment, including hidden comments.' => 267 + pht('Jump to next inline comment, including hidden comments.'), 268 + 'Jump to previous inline comment, including hidden comments.' => 269 + pht('Jump to previous inline comment, including hidden comments.'), 255 270 ), 256 271 )); 257 272
+62 -9
webroot/rsrc/js/application/diff/DiffChangesetList.js
··· 106 106 label = pht('Jump to previous inline comment.'); 107 107 this._installJumpKey('p', label, -1, 'comment'); 108 108 109 + label = pht('Jump to next inline comment, including hidden comments.'); 110 + this._installJumpKey('N', label, 1, 'comment', true); 111 + 112 + label = pht( 113 + 'Jump to previous inline comment, including hidden comments.'); 114 + this._installJumpKey('P', label, -1, 'comment', true); 115 + 109 116 label = pht('Jump to the table of contents.'); 110 117 this._installKey('t', label, this._ontoc); 111 118 112 119 label = pht('Reply to selected inline comment.'); 113 - this._installKey('r', label, this._onreply); 120 + this._installKey('r', label, this._onkeyreply); 114 121 115 122 label = pht('Edit selected inline comment.'); 116 - this._installKey('e', label, this._onedit); 123 + this._installKey('e', label, this._onkeyedit); 124 + 125 + label = pht('Mark or unmark selected inline comment as done.'); 126 + this._installKey('w', label, this._onkeydone); 127 + 128 + label = pht('Hide or show inline comment.'); 129 + this._installKey('q', label, this._onkeyhide); 117 130 }, 118 131 119 132 isAsleep: function() { ··· 190 203 .register(); 191 204 }, 192 205 193 - _installJumpKey: function(key, label, delta, filter) { 206 + _installJumpKey: function(key, label, delta, filter, show_hidden) { 194 207 filter = filter || null; 195 - var handler = JX.bind(this, this._onjumpkey, delta, filter); 208 + var handler = JX.bind(this, this._onjumpkey, delta, filter, show_hidden); 196 209 return this._installKey(key, label, handler); 197 210 }, 198 211 ··· 201 214 manager.scrollTo(toc); 202 215 }, 203 216 204 - _onreply: function(manager) { 217 + _onkeyreply: function() { 205 218 var cursor = this._cursorItem; 206 219 207 220 if (cursor) { ··· 220 233 this._warnUser(pht('You must select a comment to reply to.')); 221 234 }, 222 235 223 - _onedit: function(manager) { 236 + _onkeyedit: function() { 224 237 var cursor = this._cursorItem; 225 238 226 239 if (cursor) { ··· 239 252 this._warnUser(pht('You must select a comment to edit.')); 240 253 }, 241 254 255 + _onkeydone: function() { 256 + var cursor = this._cursorItem; 257 + 258 + if (cursor) { 259 + if (cursor.type == 'comment') { 260 + var inline = cursor.target; 261 + if (inline.canDone()) { 262 + this.setFocus(null); 263 + 264 + inline.toggleDone(); 265 + return; 266 + } 267 + } 268 + } 269 + 270 + var pht = this.getTranslations(); 271 + this._warnUser(pht('You must select a comment to mark done.')); 272 + }, 273 + 274 + _onkeyhide: function() { 275 + var cursor = this._cursorItem; 276 + 277 + if (cursor) { 278 + if (cursor.type == 'comment') { 279 + var inline = cursor.target; 280 + if (inline.canHide()) { 281 + this.setFocus(null); 282 + 283 + inline.setHidden(!inline.isHidden()); 284 + return; 285 + } 286 + } 287 + } 288 + 289 + var pht = this.getTranslations(); 290 + this._warnUser(pht('You must select a comment to hide.')); 291 + }, 292 + 242 293 _warnUser: function(message) { 243 294 new JX.Notification() 244 295 .setContent(message) ··· 247 298 .show(); 248 299 }, 249 300 250 - _onjumpkey: function(delta, filter, manager) { 301 + _onjumpkey: function(delta, filter, show_hidden, manager) { 251 302 var state = this._getSelectionState(); 252 303 253 304 var cursor = state.cursor; ··· 286 337 287 338 // If the item is hidden, don't select it when iterating with jump 288 339 // keys. It can still potentially be selected in other ways. 289 - if (items[cursor].hidden) { 290 - continue; 340 + if (!show_hidden) { 341 + if (items[cursor].hidden) { 342 + continue; 343 + } 291 344 } 292 345 293 346 // Otherwise, we've found a valid item to select.
+21 -3
webroot/rsrc/js/application/diff/DiffInline.js
··· 130 130 return true; 131 131 }, 132 132 133 + canDone: function() { 134 + if (!JX.DOM.scry(this._row, 'input', 'differential-inline-done').length) { 135 + return false; 136 + } 137 + 138 + return true; 139 + }, 140 + 141 + canHide: function() { 142 + if (!JX.DOM.scry(this._row, 'a', 'hide-inline').length) { 143 + return false; 144 + } 145 + 146 + return true; 147 + }, 148 + 133 149 _hasAction: function(action) { 134 150 var nodes = JX.DOM.scry(this._row, 'a', 'differential-inline-' + action); 135 151 return (nodes.length > 0); ··· 171 187 .setHandler(JX.bag) 172 188 .start(); 173 189 174 - JX.Stratcom.invoke('resize'); 190 + this._didUpdate(true); 175 191 }, 176 192 177 193 isHidden: function() { ··· 514 530 this._didUpdate(); 515 531 }, 516 532 517 - _didUpdate: function() { 533 + _didUpdate: function(local_only) { 518 534 // After making changes to inline comments, refresh the transaction 519 535 // preview at the bottom of the page. 520 - this.getChangeset().getChangesetList().redrawPreview(); 536 + if (!local_only) { 537 + this.getChangeset().getChangesetList().redrawPreview(); 538 + } 521 539 522 540 this.getChangeset().getChangesetList().redrawCursor(); 523 541