Page MenuHomePhabricator

D10178.diff
No OneTemporary

D10178.diff

diff --git a/resources/celerity/map.php b/resources/celerity/map.php
--- a/resources/celerity/map.php
+++ b/resources/celerity/map.php
@@ -415,7 +415,7 @@
'rsrc/js/application/policy/behavior-policy-rule-editor.js' => 'fe9a552f',
'rsrc/js/application/ponder/behavior-votebox.js' => '4e9b766b',
'rsrc/js/application/projects/behavior-boards-dropdown.js' => '0ec56e1d',
- 'rsrc/js/application/projects/behavior-project-boards.js' => '21171a56',
+ 'rsrc/js/application/projects/behavior-project-boards.js' => 'f47fa23b',
'rsrc/js/application/projects/behavior-project-create.js' => '065227cc',
'rsrc/js/application/projects/behavior-reorder-columns.js' => '09eee344',
'rsrc/js/application/releeph/releeph-preview-branch.js' => 'b2b4fbaf',
@@ -639,7 +639,7 @@
'javelin-behavior-policy-control' => 'f3fef818',
'javelin-behavior-policy-rule-editor' => 'fe9a552f',
'javelin-behavior-ponder-votebox' => '4e9b766b',
- 'javelin-behavior-project-boards' => '21171a56',
+ 'javelin-behavior-project-boards' => 'f47fa23b',
'javelin-behavior-project-create' => '065227cc',
'javelin-behavior-refresh-csrf' => '7814b593',
'javelin-behavior-releeph-preview-branch' => 'b2b4fbaf',
@@ -983,14 +983,6 @@
'javelin-util',
'javelin-magical-init',
),
- '21171a56' => array(
- 'javelin-behavior',
- 'javelin-dom',
- 'javelin-util',
- 'javelin-stratcom',
- 'javelin-workflow',
- 'phabricator-draggable-list',
- ),
'2290aeef' => array(
'javelin-install',
'javelin-dom',
@@ -1852,6 +1844,14 @@
'phuix-action-view',
'javelin-workflow',
),
+ 'f47fa23b' => array(
+ 'javelin-behavior',
+ 'javelin-dom',
+ 'javelin-util',
+ 'javelin-stratcom',
+ 'javelin-workflow',
+ 'phabricator-draggable-list',
+ ),
'f51afce0' => array(
'javelin-behavior',
'javelin-request',
diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php
--- a/src/__phutil_library_map__.php
+++ b/src/__phutil_library_map__.php
@@ -3831,6 +3831,7 @@
'PassphraseCredential' => array(
'PassphraseDAO',
'PhabricatorPolicyInterface',
+ 'PhabricatorDestructibleInterface',
),
'PassphraseCredentialControl' => 'AphrontFormControl',
'PassphraseCredentialCreateController' => 'PassphraseController',
diff --git a/src/applications/maniphest/controller/ManiphestTaskEditController.php b/src/applications/maniphest/controller/ManiphestTaskEditController.php
--- a/src/applications/maniphest/controller/ManiphestTaskEditController.php
+++ b/src/applications/maniphest/controller/ManiphestTaskEditController.php
@@ -11,7 +11,9 @@
public function processRequest() {
$request = $this->getRequest();
$user = $request->getUser();
+
$response_type = $request->getStr('responseType', 'task');
+ $order = $request->getStr('order', PhabricatorProjectColumn::DEFAULT_ORDER);
$can_edit_assign = $this->hasApplicationCapability(
ManiphestEditAssignCapability::CAPABILITY);
@@ -531,6 +533,7 @@
->setUser($user)
->addHiddenInput('template', $template_id)
->addHiddenInput('responseType', $response_type)
+ ->addHiddenInput('order', $order)
->addHiddenInput('columnPHID', $request->getStr('columnPHID'));
if ($parent_task) {
diff --git a/src/applications/project/controller/PhabricatorProjectBoardViewController.php b/src/applications/project/controller/PhabricatorProjectBoardViewController.php
--- a/src/applications/project/controller/PhabricatorProjectBoardViewController.php
+++ b/src/applications/project/controller/PhabricatorProjectBoardViewController.php
@@ -8,6 +8,8 @@
private $handles;
private $queryKey;
private $filter;
+ private $sortKey;
+ private $showHidden;
public function shouldAllowPublic() {
return true;
@@ -25,6 +27,7 @@
$viewer = $request->getUser();
$show_hidden = $request->getBool('hidden');
+ $this->showHidden = $show_hidden;
$project = id(new PhabricatorProjectQuery())
->setViewer($viewer)
@@ -42,6 +45,17 @@
$this->setProject($project);
$this->id = $project->getID();
+ $sort_key = $request->getStr('order');
+ switch ($sort_key) {
+ case PhabricatorProjectColumn::ORDER_NATURAL:
+ case PhabricatorProjectColumn::ORDER_PRIORITY:
+ break;
+ default:
+ $sort_key = PhabricatorProjectColumn::DEFAULT_ORDER;
+ break;
+ }
+ $this->sortKey = $sort_key;
+
$column_query = id(new PhabricatorProjectColumnQuery())
->setViewer($viewer)
->withProjectPHIDs(array($project->getPHID()));
@@ -90,13 +104,15 @@
$saved = $engine->buildSavedQueryFromRequest($request);
$engine->saveQuery($saved);
return id(new AphrontRedirectResponse())->setURI(
- $engine->getQueryResultsPageURI($saved->getQueryKey()));
+ $this->getURIWithState(
+ $engine->getQueryResultsPageURI($saved->getQueryKey())));
}
$query_key = $this->queryKey;
if (!$query_key) {
$query_key = 'open';
}
+ $this->queryKey = $query_key;
$custom_query = null;
if ($engine->isBuiltinQuery($query_key)) {
@@ -180,6 +196,7 @@
'projectPHID' => $project->getPHID(),
'moveURI' => $this->getApplicationURI('move/'.$project->getID().'/'),
'createURI' => '/maniphest/task/create/',
+ 'order' => $this->sortKey,
));
$this->handles = ManiphestTaskListView::loadTaskHandles($viewer, $tasks);
@@ -235,6 +252,10 @@
'boards-dropdown',
array());
+ $sort_menu = $this->buildSortMenu(
+ $viewer,
+ $sort_key);
+
$filter_menu = $this->buildFilterMenu(
$viewer,
$custom_query,
@@ -256,6 +277,7 @@
->setNoBackground(true)
->setImage($project->getProfileImageURI())
->setImageURL($this->getApplicationURI('view/'.$project->getID().'/'))
+ ->addActionLink($sort_menu)
->addActionLink($filter_menu)
->addActionLink($manage_menu)
->setPolicyObject($project);
@@ -274,6 +296,57 @@
));
}
+ private function buildSortMenu(
+ PhabricatorUser $viewer,
+ $sort_key) {
+
+ $sort_icon = id(new PHUIIconView())
+ ->setIconFont('fa-sort-amount-asc bluegrey');
+
+ $named = array(
+ PhabricatorProjectColumn::ORDER_NATURAL => pht('Natural'),
+ PhabricatorProjectColumn::ORDER_PRIORITY => pht('Sort by Priority'),
+ );
+
+ $base_uri = $this->getURIWithState();
+
+ $items = array();
+ foreach ($named as $key => $name) {
+ $is_selected = ($key == $sort_key);
+ if ($is_selected) {
+ $active_order = $name;
+ }
+
+ $item = id(new PhabricatorActionView())
+ ->setIcon('fa-sort-amount-asc')
+ ->setSelected($is_selected)
+ ->setName($name);
+
+ $uri = $base_uri->alter('order', $key);
+ $item->setHref($uri);
+
+ $items[] = $item;
+ }
+
+ $sort_menu = id(new PhabricatorActionListView())
+ ->setUser($viewer);
+ foreach ($items as $item) {
+ $sort_menu->addAction($item);
+ }
+
+ $sort_button = id(new PHUIButtonView())
+ ->setText(pht('Sort: %s', $active_order))
+ ->setIcon($sort_icon)
+ ->setTag('a')
+ ->setHref('#')
+ ->addSigil('boards-dropdown-menu')
+ ->setMetadata(
+ array(
+ 'items' => hsprintf('%s', $sort_menu),
+ ));
+
+ return $sort_button;
+ }
private function buildFilterMenu(
PhabricatorUser $viewer,
$custom_query,
@@ -314,14 +387,16 @@
->setName($name);
if ($is_custom) {
- $item->setHref(
- $this->getApplicationURI(
- 'board/'.$this->id.'/filter/query/'.$key.'/'));
+ $uri = $this->getApplicationURI(
+ 'board/'.$this->id.'/filter/query/'.$key.'/');
$item->setWorkflow(true);
} else {
- $item->setHref($engine->getQueryResultsPageURI($key));
+ $uri = $engine->getQueryResultsPageURI($key);
}
+ $uri = $this->getURIWithState($uri);
+ $item->setHref($uri);
+
$items[] = $item;
}
@@ -383,12 +458,12 @@
->setWorkflow(true);
if ($show_hidden) {
- $hidden_uri = $request->getRequestURI()
+ $hidden_uri = $this->getURIWithState()
->setQueryParam('hidden', null);
$hidden_icon = 'fa-eye-slash';
$hidden_text = pht('Hide Hidden Columns');
} else {
- $hidden_uri = $request->getRequestURI()
+ $hidden_uri = $this->getURIWithState()
->setQueryParam('hidden', 'true');
$hidden_icon = 'fa-eye';
$hidden_text = pht('Show Hidden Columns');
@@ -446,4 +521,34 @@
->setDialog($dialog);
}
+
+ /**
+ * Add current state parameters (like order and the visibility of hidden
+ * columns) to a URI.
+ *
+ * This allows actions which toggle or adjust one piece of state to keep
+ * the rest of the board state persistent. If no URI is provided, this method
+ * starts with the request URI.
+ *
+ * @param string|null URI to add state parameters to.
+ * @return PhutilURI URI with state parameters.
+ */
+ private function getURIWithState($base = null) {
+ if ($base === null) {
+ $base = $this->getRequest()->getRequestURI();
+ }
+
+ $base = new PhutilURI($base);
+
+ if ($this->sortKey != PhabricatorProjectColumn::DEFAULT_ORDER) {
+ $base->setQueryParam('order', $this->sortKey);
+ } else {
+ $base->setQueryParam('order', null);
+ }
+
+ $base->setQueryParam('hidden', $this->showHidden ? 'true' : null);
+
+ return $base;
+ }
+
}
diff --git a/src/applications/project/storage/PhabricatorProjectColumn.php b/src/applications/project/storage/PhabricatorProjectColumn.php
--- a/src/applications/project/storage/PhabricatorProjectColumn.php
+++ b/src/applications/project/storage/PhabricatorProjectColumn.php
@@ -9,6 +9,10 @@
const STATUS_ACTIVE = 0;
const STATUS_HIDDEN = 1;
+ const DEFAULT_ORDER = 'natural';
+ const ORDER_NATURAL = 'natural';
+ const ORDER_PRIORITY = 'priority';
+
protected $name;
protected $status;
protected $projectPHID;
diff --git a/webroot/rsrc/js/application/projects/behavior-project-boards.js b/webroot/rsrc/js/application/projects/behavior-project-boards.js
--- a/webroot/rsrc/js/application/projects/behavior-project-boards.js
+++ b/webroot/rsrc/js/application/projects/behavior-project-boards.js
@@ -81,6 +81,8 @@
data.beforePHID = before_phid;
}
+ data.order = config.order;
+
var workflow = new JX.Workflow(config.moveURI, data)
.setHandler(function(response) {
onresponse(response, item, list);
@@ -148,11 +150,13 @@
e.kill();
var column = e.getNode('project-column');
var request_data = {
- 'responseType' : 'card',
- 'columnPHID' : JX.Stratcom.getData(column).columnPHID };
+ responseType: 'card',
+ columnPHID: JX.Stratcom.getData(column).columnPHID,
+ order: config.order
+ };
new JX.Workflow(e.getNode('tag:a').href, request_data)
- .setHandler(JX.bind(null, onedit, column))
- .start();
+ .setHandler(JX.bind(null, onedit, column))
+ .start();
});
JX.Stratcom.listen(
@@ -162,9 +166,11 @@
e.kill();
var column_phid = e.getNodeData('column-add-task').columnPHID;
var request_data = {
- 'responseType' : 'card',
- 'columnPHID' : column_phid,
- 'projects' : config.projectPHID };
+ responseType: 'card',
+ columnPHID: column_phid,
+ projects: config.projectPHID,
+ order: config.order
+ };
var cols = JX.DOM.scry(JX.$(config.boardID), 'ul', 'project-column');
var ii;
var column;
@@ -175,7 +181,7 @@
}
}
new JX.Workflow(config.createURI, request_data)
- .setHandler(JX.bind(null, onedit, column))
- .start();
+ .setHandler(JX.bind(null, onedit, column))
+ .start();
});
});

File Metadata

Mime Type
text/plain
Expires
Thu, Mar 13, 4:23 AM (1 w, 5 d ago)
Storage Engine
blob
Storage Format
Encrypted (AES-256-CBC)
Storage Handle
7604950
Default Alt Text
D10178.diff (11 KB)

Event Timeline