mirror of
https://we.phorge.it/source/phorge.git
synced 2024-11-26 00:32:42 +01:00
Conpherence - people widget
Summary: adds ye olde people widget. Features include - handle-based display, so we get status for free. (Note less pretty than M14 would have it!) - can add a person - can remove a person - can see the people already in the conpherence Test Plan: added and removed people and noted they joined / re-added as appropriate. Tried to add someone already in the conpherence and got a "transaction has no effect" message Reviewers: epriestley, chad Reviewed By: epriestley CC: aran, Korvin Maniphest Tasks: T2399 Differential Revision: https://secure.phabricator.com/D5466
This commit is contained in:
parent
5bd54e35bc
commit
a97968b9ff
13 changed files with 485 additions and 95 deletions
|
@ -903,7 +903,7 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'conpherence-widget-pane-css' =>
|
||||
array(
|
||||
'uri' => '/res/bd8ca250/rsrc/css/application/conpherence/widget-pane.css',
|
||||
'uri' => '/res/65c7c73f/rsrc/css/application/conpherence/widget-pane.css',
|
||||
'type' => 'css',
|
||||
'requires' =>
|
||||
array(
|
||||
|
@ -1253,7 +1253,7 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'javelin-behavior-conpherence-menu' =>
|
||||
array(
|
||||
'uri' => '/res/35811cd4/rsrc/js/application/conpherence/behavior-menu.js',
|
||||
'uri' => '/res/29585411/rsrc/js/application/conpherence/behavior-menu.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
|
@ -1283,7 +1283,7 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'javelin-behavior-conpherence-widget-pane' =>
|
||||
array(
|
||||
'uri' => '/res/45d53f1f/rsrc/js/application/conpherence/behavior-widget-pane.js',
|
||||
'uri' => '/res/c0990399/rsrc/js/application/conpherence/behavior-widget-pane.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
|
|
|
@ -239,6 +239,7 @@ phutil_register_library_map(array(
|
|||
'ConpherenceParticipantQuery' => 'applications/conpherence/query/ConpherenceParticipantQuery.php',
|
||||
'ConpherenceParticipationStatus' => 'applications/conpherence/constants/ConpherenceParticipationStatus.php',
|
||||
'ConpherencePeopleMenuEventListener' => 'applications/conpherence/events/ConpherencePeopleMenuEventListener.php',
|
||||
'ConpherencePeopleWidgetView' => 'applications/conpherence/view/ConpherencePeopleWidgetView.php',
|
||||
'ConpherenceReplyHandler' => 'applications/conpherence/mail/ConpherenceReplyHandler.php',
|
||||
'ConpherenceSettings' => 'applications/conpherence/constants/ConpherenceSettings.php',
|
||||
'ConpherenceThread' => 'applications/conpherence/storage/ConpherenceThread.php',
|
||||
|
@ -252,6 +253,7 @@ phutil_register_library_map(array(
|
|||
'ConpherenceUpdateController' => 'applications/conpherence/controller/ConpherenceUpdateController.php',
|
||||
'ConpherenceViewController' => 'applications/conpherence/controller/ConpherenceViewController.php',
|
||||
'ConpherenceWidgetController' => 'applications/conpherence/controller/ConpherenceWidgetController.php',
|
||||
'ConpherenceWidgetView' => 'applications/conpherence/view/ConpherenceWidgetView.php',
|
||||
'DarkConsoleController' => 'aphront/console/DarkConsoleController.php',
|
||||
'DarkConsoleCore' => 'aphront/console/DarkConsoleCore.php',
|
||||
'DarkConsoleDataController' => 'aphront/console/DarkConsoleDataController.php',
|
||||
|
@ -1941,7 +1943,7 @@ phutil_register_library_map(array(
|
|||
'ConpherenceController' => 'PhabricatorController',
|
||||
'ConpherenceDAO' => 'PhabricatorLiskDAO',
|
||||
'ConpherenceEditor' => 'PhabricatorApplicationTransactionEditor',
|
||||
'ConpherenceFileWidgetView' => 'AphrontView',
|
||||
'ConpherenceFileWidgetView' => 'ConpherenceWidgetView',
|
||||
'ConpherenceFormDragAndDropUploadControl' => 'AphrontFormControl',
|
||||
'ConpherenceImageData' => 'ConpherenceConstants',
|
||||
'ConpherenceLayoutView' => 'AphrontView',
|
||||
|
@ -1952,6 +1954,7 @@ phutil_register_library_map(array(
|
|||
'ConpherenceParticipantQuery' => 'PhabricatorOffsetPagedQuery',
|
||||
'ConpherenceParticipationStatus' => 'ConpherenceConstants',
|
||||
'ConpherencePeopleMenuEventListener' => 'PhutilEventListener',
|
||||
'ConpherencePeopleWidgetView' => 'ConpherenceWidgetView',
|
||||
'ConpherenceReplyHandler' => 'PhabricatorMailReplyHandler',
|
||||
'ConpherenceSettings' => 'ConpherenceConstants',
|
||||
'ConpherenceThread' =>
|
||||
|
@ -1969,6 +1972,7 @@ phutil_register_library_map(array(
|
|||
'ConpherenceUpdateController' => 'ConpherenceController',
|
||||
'ConpherenceViewController' => 'ConpherenceController',
|
||||
'ConpherenceWidgetController' => 'ConpherenceController',
|
||||
'ConpherenceWidgetView' => 'AphrontView',
|
||||
'DarkConsoleController' => 'PhabricatorController',
|
||||
'DarkConsoleDataController' => 'PhabricatorController',
|
||||
'DarkConsoleErrorLogPlugin' => 'DarkConsolePlugin',
|
||||
|
|
|
@ -38,7 +38,7 @@ final class ConpherenceUpdateController
|
|||
|
||||
$action = $request->getStr('action', 'metadata');
|
||||
$latest_transaction_id = null;
|
||||
$fancy_ajax_style = true;
|
||||
$response_mode = 'ajax';
|
||||
$error_view = null;
|
||||
$e_file = array();
|
||||
$errors = array();
|
||||
|
@ -56,11 +56,36 @@ final class ConpherenceUpdateController
|
|||
switch ($action) {
|
||||
case 'message':
|
||||
$message = $request->getStr('text');
|
||||
$latest_transaction_id = $request->getInt('latest_transaction_id');
|
||||
$xactions = $editor->generateTransactionsFromText(
|
||||
$conpherence,
|
||||
$message);
|
||||
break;
|
||||
case 'add_person':
|
||||
$xactions = array();
|
||||
$person_tokenizer = $request->getArr('add_person');
|
||||
$person_phid = reset($person_tokenizer);
|
||||
if ($person_phid) {
|
||||
$xactions[] = id(new ConpherenceTransaction())
|
||||
->setTransactionType(
|
||||
ConpherenceTransactionType::TYPE_PARTICIPANTS)
|
||||
->setNewValue(array('+' => array($person_phid)));
|
||||
}
|
||||
break;
|
||||
case 'remove_person':
|
||||
$xactions = array();
|
||||
if (!$request->isContinueRequest()) {
|
||||
// do nothing; we'll display a confirmation dialogue instead
|
||||
break;
|
||||
}
|
||||
$person_phid = $request->getStr('remove_person');
|
||||
if ($person_phid && $person_phid == $user->getPHID()) {
|
||||
$xactions[] = id(new ConpherenceTransaction())
|
||||
->setTransactionType(
|
||||
ConpherenceTransactionType::TYPE_PARTICIPANTS)
|
||||
->setNewValue(array('-' => array($person_phid)));
|
||||
$response_mode = 'go-home';
|
||||
}
|
||||
break;
|
||||
case 'notifications':
|
||||
$notifications = $request->getStr('notifications');
|
||||
$participant = $conpherence->getParticipant($user->getPHID());
|
||||
|
@ -116,7 +141,7 @@ final class ConpherenceUpdateController
|
|||
// use the existing title in this image upload case
|
||||
$title = $conpherence->getTitle();
|
||||
$updated = true;
|
||||
$fancy_ajax_style = false;
|
||||
$response_mode = 'redirect';
|
||||
}
|
||||
|
||||
// all other metadata updates are continue requests
|
||||
|
@ -159,20 +184,29 @@ final class ConpherenceUpdateController
|
|||
if ($xactions) {
|
||||
try {
|
||||
$xactions = $editor->applyTransactions($conpherence, $xactions);
|
||||
if ($fancy_ajax_style) {
|
||||
} catch (PhabricatorApplicationTransactionNoEffectException $ex) {
|
||||
return id(new PhabricatorApplicationTransactionNoEffectResponse())
|
||||
->setCancelURI($this->getApplicationURI($conpherence_id.'/'))
|
||||
->setException($ex);
|
||||
}
|
||||
switch ($response_mode) {
|
||||
case 'ajax':
|
||||
$latest_transaction_id = $request->getInt('latest_transaction_id');
|
||||
$content = $this->loadAndRenderUpdates(
|
||||
$conpherence_id,
|
||||
$latest_transaction_id);
|
||||
return id(new AphrontAjaxResponse())
|
||||
->setContent($content);
|
||||
} else {
|
||||
break;
|
||||
case 'go-home':
|
||||
return id(new AphrontRedirectResponse())
|
||||
->setURI($this->getApplicationURI());
|
||||
break;
|
||||
case 'redirect':
|
||||
default:
|
||||
return id(new AphrontRedirectResponse())
|
||||
->setURI($this->getApplicationURI($conpherence->getID().'/'));
|
||||
}
|
||||
} catch (PhabricatorApplicationTransactionNoEffectException $ex) {
|
||||
return id(new PhabricatorApplicationTransactionNoEffectResponse())
|
||||
->setCancelURI($this->getApplicationURI($conpherence_id.'/'))
|
||||
->setException($ex);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -185,6 +219,9 @@ final class ConpherenceUpdateController
|
|||
}
|
||||
|
||||
switch ($action) {
|
||||
case 'remove_person':
|
||||
$dialogue = $this->renderRemovePersonDialogue($conpherence);
|
||||
break;
|
||||
case 'metadata':
|
||||
default:
|
||||
$dialogue = $this->renderMetadataDialogue($conpherence, $error_view);
|
||||
|
@ -201,6 +238,37 @@ final class ConpherenceUpdateController
|
|||
|
||||
}
|
||||
|
||||
private function renderRemovePersonDialogue(
|
||||
ConpherenceThread $conpherence) {
|
||||
|
||||
$request = $this->getRequest();
|
||||
$user = $request->getUser();
|
||||
$remove_person = $request->getStr('remove_person');
|
||||
$participants = $conpherence->getParticipants();
|
||||
$message = pht(
|
||||
'Are you sure you want to remove yourself from this conpherence? ');
|
||||
if (count($participants) == 1) {
|
||||
$message .= pht(
|
||||
'The conpherence will be inaccessible forever and ever.');
|
||||
} else {
|
||||
$message .= pht(
|
||||
'Someone else in the conpherence can add you back later.');
|
||||
}
|
||||
$body = phutil_tag(
|
||||
'p',
|
||||
array(
|
||||
),
|
||||
$message);
|
||||
|
||||
require_celerity_resource('conpherence-update-css');
|
||||
return id(new AphrontDialogView())
|
||||
->setTitle(pht('Update Conpherence Participants'))
|
||||
->addHiddenInput('action', 'remove_person')
|
||||
->addHiddenInput('__continue__', true)
|
||||
->addHiddenInput('remove_person', $remove_person)
|
||||
->appendChild($body);
|
||||
}
|
||||
|
||||
private function renderMetadataDialogue(
|
||||
ConpherenceThread $conpherence,
|
||||
$error_view) {
|
||||
|
@ -225,15 +293,15 @@ final class ConpherenceUpdateController
|
|||
'src' =>
|
||||
$conpherence->loadImageURI(ConpherenceImageData::SIZE_HEAD),
|
||||
))))
|
||||
->appendChild(
|
||||
id(new AphrontFormCropControl())
|
||||
->setLabel(pht('Crop Image'))
|
||||
->setValue($image)
|
||||
->setWidth(ConpherenceImageData::HEAD_WIDTH)
|
||||
->setHeight(ConpherenceImageData::HEAD_HEIGHT))
|
||||
->appendChild(
|
||||
id(new ConpherenceFormDragAndDropUploadControl())
|
||||
->setLabel(pht('Change Image')));
|
||||
->appendChild(
|
||||
id(new AphrontFormCropControl())
|
||||
->setLabel(pht('Crop Image'))
|
||||
->setValue($image)
|
||||
->setWidth(ConpherenceImageData::HEAD_WIDTH)
|
||||
->setHeight(ConpherenceImageData::HEAD_HEIGHT))
|
||||
->appendChild(
|
||||
id(new ConpherenceFormDragAndDropUploadControl())
|
||||
->setLabel(pht('Change Image')));
|
||||
} else {
|
||||
$form
|
||||
->appendChild(
|
||||
|
@ -274,11 +342,15 @@ final class ConpherenceUpdateController
|
|||
|
||||
$header = $this->buildHeaderPaneContent($conpherence);
|
||||
|
||||
$widget_uri = $this->getApplicationURI('update/'.$conpherence->getID().'/');
|
||||
$file_widget = id(new ConpherenceFileWidgetView())
|
||||
->setUser($this->getRequest()->getUser())
|
||||
->setConpherence($conpherence)
|
||||
->setUpdateURI(
|
||||
$this->getApplicationURI('update/'.$conpherence->getID().'/'));
|
||||
->setUpdateURI($widget_uri);
|
||||
$people_widget = id(new ConpherencePeopleWidgetView())
|
||||
->setUser($user)
|
||||
->setConpherence($conpherence)
|
||||
->setUpdateURI($widget_uri);
|
||||
|
||||
$content = array(
|
||||
'transactions' => $rendered_transactions,
|
||||
|
@ -286,7 +358,8 @@ final class ConpherenceUpdateController
|
|||
'nav_item' => hsprintf('%s', $nav_item),
|
||||
'conpherence_phid' => $conpherence->getPHID(),
|
||||
'header' => hsprintf('%s', $header),
|
||||
'file_widget' => $file_widget->render()
|
||||
'file_widget' => $file_widget->render(),
|
||||
'people_widget' => $people_widget->render()
|
||||
);
|
||||
return $content;
|
||||
}
|
||||
|
|
|
@ -69,6 +69,9 @@ final class ConpherenceWidgetController extends
|
|||
Javelin::initBehavior(
|
||||
'conpherence-widget-pane',
|
||||
array(
|
||||
'header' => 'conpherence-header-pane',
|
||||
'messages' => 'conpherence-messages',
|
||||
'people_widget' => 'widgets-people',
|
||||
'file_widget' => 'widgets-files',
|
||||
'settings_widget' => 'widgets-settings',
|
||||
'widgetRegistery' => array(
|
||||
|
@ -83,7 +86,8 @@ final class ConpherenceWidgetController extends
|
|||
|
||||
$conpherence = $this->getConpherence();
|
||||
|
||||
$widgets = phutil_tag(
|
||||
$widgets = array();
|
||||
$widgets[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-header'
|
||||
|
@ -167,50 +171,50 @@ final class ConpherenceWidgetController extends
|
|||
'class' => 'sprite-conpherence conpherence_settings_off',
|
||||
),
|
||||
'')
|
||||
))).
|
||||
phutil_tag(
|
||||
)));
|
||||
$user = $this->getRequest()->getUser();
|
||||
// now the widget bodies
|
||||
$widgets[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-people',
|
||||
'style' => 'display: none;'
|
||||
),
|
||||
$this->renderPeopleWidgetPaneContent()).
|
||||
javelin_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-files',
|
||||
'sigil' => 'conpherence-widget-files',
|
||||
),
|
||||
id(new ConpherenceFileWidgetView())
|
||||
->setUser($this->getRequest()->getUser())
|
||||
->setConpherence($conpherence)
|
||||
->setUpdateURI(
|
||||
$this->getApplicationURI('update/'.$conpherence->getID().'/'))
|
||||
->render()).
|
||||
phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-calendar',
|
||||
'style' => 'display: none;'
|
||||
),
|
||||
$this->renderCalendarWidgetPaneContent()).
|
||||
phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-settings',
|
||||
'style' => 'display: none'
|
||||
),
|
||||
$this->renderSettingsWidgetPaneContent());
|
||||
id(new ConpherencePeopleWidgetView())
|
||||
->setUser($user)
|
||||
->setConpherence($conpherence)
|
||||
->setUpdateURI($this->getWidgetURI()));
|
||||
$widgets[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-files',
|
||||
),
|
||||
id(new ConpherenceFileWidgetView())
|
||||
->setUser($user)
|
||||
->setConpherence($conpherence)
|
||||
->setUpdateURI($this->getWidgetURI()));
|
||||
$widgets[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-calendar',
|
||||
'style' => 'display: none;'
|
||||
),
|
||||
$this->renderCalendarWidgetPaneContent());
|
||||
$widgets[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'widgets-body',
|
||||
'id' => 'widgets-settings',
|
||||
'style' => 'display: none'
|
||||
),
|
||||
$this->renderSettingsWidgetPaneContent());
|
||||
|
||||
return array('widgets' => $widgets);
|
||||
}
|
||||
|
||||
private function renderPeopleWidgetPaneContent() {
|
||||
return 'TODO - people';
|
||||
// without this implosion we get "," between each element in our widgets
|
||||
// array
|
||||
return array('widgets' => phutil_implode_html('', $widgets));
|
||||
}
|
||||
|
||||
private function renderSettingsWidgetPaneContent() {
|
||||
|
@ -244,8 +248,6 @@ final class ConpherenceWidgetController extends
|
|||
->setName('notifications')
|
||||
->setValue($notifications);
|
||||
|
||||
$href = $this->getApplicationURI(
|
||||
'update/'.$conpherence->getID().'/');
|
||||
$layout = array(
|
||||
$options,
|
||||
phutil_tag(
|
||||
|
@ -268,7 +270,7 @@ final class ConpherenceWidgetController extends
|
|||
$user,
|
||||
array(
|
||||
'method' => 'POST',
|
||||
'action' => $href,
|
||||
'action' => $this->getWidgetURI(),
|
||||
),
|
||||
$layout);
|
||||
}
|
||||
|
@ -369,4 +371,9 @@ final class ConpherenceWidgetController extends
|
|||
return $timestamps;
|
||||
}
|
||||
|
||||
private function getWidgetURI() {
|
||||
$conpherence = $this->getConpherence();
|
||||
return $this->getApplicationURI('update/'.$conpherence->getID().'/');
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -159,23 +159,35 @@ final class ConpherenceEditor extends PhabricatorApplicationTransactionEditor {
|
|||
}
|
||||
break;
|
||||
case ConpherenceTransactionType::TYPE_PARTICIPANTS:
|
||||
$participants = array();
|
||||
foreach ($xaction->getNewValue() as $participant) {
|
||||
if ($participant == $this->getActor()->getPHID()) {
|
||||
|
||||
$participants = $object->getParticipants();
|
||||
|
||||
$old_map = array_fuse($xaction->getOldValue());
|
||||
$new_map = array_fuse($xaction->getNewValue());
|
||||
|
||||
$remove = array_keys(array_diff_key($old_map, $new_map));
|
||||
foreach ($remove as $phid) {
|
||||
$remove_participant = $participants[$phid];
|
||||
$remove_participant->delete();
|
||||
unset($participants[$phid]);
|
||||
}
|
||||
|
||||
$add = array_keys(array_diff_key($new_map, $old_map));
|
||||
foreach ($add as $phid) {
|
||||
if ($phid == $this->getActor()->getPHID()) {
|
||||
$status = ConpherenceParticipationStatus::UP_TO_DATE;
|
||||
} else {
|
||||
$status = ConpherenceParticipationStatus::BEHIND;
|
||||
}
|
||||
$participants[] =
|
||||
$participants[$phid] =
|
||||
id(new ConpherenceParticipant())
|
||||
->setConpherencePHID($object->getPHID())
|
||||
->setParticipantPHID($participant)
|
||||
->setParticipantPHID($phid)
|
||||
->setParticipationStatus($status)
|
||||
->setDateTouched(time())
|
||||
->setBehindTransactionPHID($xaction->getPHID())
|
||||
->save();
|
||||
}
|
||||
$participants = mpull($participants, null, 'getParticipantPHID');
|
||||
$object->attachParticipants($participants);
|
||||
break;
|
||||
}
|
||||
|
@ -224,11 +236,14 @@ final class ConpherenceEditor extends PhabricatorApplicationTransactionEditor {
|
|||
}
|
||||
|
||||
protected function getMailTo(PhabricatorLiskDAO $object) {
|
||||
$to_phids = array();
|
||||
$participants = $object->getParticipants();
|
||||
if (empty($participants)) {
|
||||
return $to_phids;
|
||||
}
|
||||
$preferences = id(new PhabricatorUserPreferences())
|
||||
->loadAllWhere('userPHID in (%Ls)', array_keys($participants));
|
||||
$preferences = mpull($preferences, null, 'getUserPHID');
|
||||
$to_phids = array();
|
||||
foreach ($participants as $phid => $participant) {
|
||||
$default = ConpherenceSettings::EMAIL_ALWAYS;
|
||||
$preference = idx($preferences, $phid);
|
||||
|
|
|
@ -21,6 +21,17 @@ final class ConpherenceTransaction extends PhabricatorApplicationTransaction {
|
|||
return pht('conpherence');
|
||||
}
|
||||
|
||||
public function getNoEffectDescription() {
|
||||
switch ($this->getTransactionType()) {
|
||||
case ConpherenceTransactionType::TYPE_PARTICIPANTS:
|
||||
return pht(
|
||||
'You can not add a participant who has already been added.');
|
||||
break;
|
||||
}
|
||||
|
||||
return parent::getNoEffectDescription();
|
||||
}
|
||||
|
||||
public function shouldHide() {
|
||||
$old = $this->getOldValue();
|
||||
|
||||
|
|
|
@ -1,25 +1,9 @@
|
|||
<?php
|
||||
|
||||
final class ConpherenceFileWidgetView extends AphrontView {
|
||||
|
||||
private $conpherence;
|
||||
private $updateURI;
|
||||
|
||||
public function setUpdateURI($update_uri) {
|
||||
$this->updateURI = $update_uri;
|
||||
return $this;
|
||||
}
|
||||
public function getUpdateURI() {
|
||||
return $this->updateURI;
|
||||
}
|
||||
|
||||
public function setConpherence(ConpherenceThread $conpherence) {
|
||||
$this->conpherence = $conpherence;
|
||||
return $this;
|
||||
}
|
||||
public function getConpherence() {
|
||||
return $this->conpherence;
|
||||
}
|
||||
/**
|
||||
* @group conpherence
|
||||
*/
|
||||
final class ConpherenceFileWidgetView extends ConpherenceWidgetView {
|
||||
|
||||
public function render() {
|
||||
require_celerity_resource('sprite-docs-css');
|
||||
|
|
|
@ -0,0 +1,110 @@
|
|||
<?php
|
||||
/**
|
||||
* @group conpherence
|
||||
*/
|
||||
final class ConpherencePeopleWidgetView extends ConpherenceWidgetView {
|
||||
|
||||
public function render() {
|
||||
$conpherence = $this->getConpherence();
|
||||
$widget_data = $conpherence->getWidgetData();
|
||||
$user = $this->getUser();
|
||||
$conpherence = $this->getConpherence();
|
||||
$participants = $conpherence->getParticipants();
|
||||
$handles = $conpherence->getHandles();
|
||||
|
||||
// ye olde add people widget
|
||||
$add_widget = phabricator_form(
|
||||
$user,
|
||||
array(
|
||||
'method' => 'POST',
|
||||
'action' => $this->getUpdateURI(),
|
||||
),
|
||||
array(
|
||||
id(new AphrontFormTokenizerControl())
|
||||
->setPlaceholder(pht('Add a person...'))
|
||||
->setName('add_person')
|
||||
->setUser($user)
|
||||
->setDatasource('/typeahead/common/users/')
|
||||
->setLimit(1),
|
||||
javelin_tag(
|
||||
'button',
|
||||
array(
|
||||
'sigil' => 'add-person',
|
||||
'class' => 'people-add-button',
|
||||
'meta' => array(
|
||||
'action' => 'add_person',
|
||||
'latest_transaction_id' => $this->getLatestTransactionID()
|
||||
)
|
||||
),
|
||||
pht('Add'))
|
||||
));
|
||||
$header = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'people-widget-header'
|
||||
),
|
||||
array(
|
||||
phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'add-people-widget',
|
||||
),
|
||||
$add_widget),
|
||||
phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'divider'
|
||||
),
|
||||
'')
|
||||
));
|
||||
|
||||
$body = array();
|
||||
// future proof by using participants to iterate through handles;
|
||||
// we may have non-people handles sooner or later
|
||||
foreach ($participants as $user_phid => $participant) {
|
||||
$handle = $handles[$user_phid];
|
||||
$remove_html = '';
|
||||
if ($user_phid == $user->getPHID()) {
|
||||
$remove_html = javelin_tag(
|
||||
'a',
|
||||
array(
|
||||
'class' => 'remove',
|
||||
'sigil' => 'remove-person',
|
||||
'meta' => array(
|
||||
'remove_person' => $handle->getPHID(),
|
||||
'action' => 'remove_person',
|
||||
'latest_transaction_id' => $this->getLatestTransactionID()
|
||||
)
|
||||
),
|
||||
phutil_tag(
|
||||
'span',
|
||||
array(
|
||||
'class' => 'icon'
|
||||
),
|
||||
'x'));
|
||||
}
|
||||
$body[] = phutil_tag(
|
||||
'div',
|
||||
array(
|
||||
'class' => 'person-entry'
|
||||
),
|
||||
array(
|
||||
phutil_tag(
|
||||
'a',
|
||||
array(
|
||||
'class' => 'pic',
|
||||
),
|
||||
phutil_tag(
|
||||
'img',
|
||||
array(
|
||||
'src' => $handle->getImageURI()
|
||||
),
|
||||
'')),
|
||||
$handle->renderLink(),
|
||||
$remove_html));
|
||||
}
|
||||
|
||||
return array($header, $body);
|
||||
|
||||
}
|
||||
}
|
33
src/applications/conpherence/view/ConpherenceWidgetView.php
Normal file
33
src/applications/conpherence/view/ConpherenceWidgetView.php
Normal file
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* @group conpherence
|
||||
*/
|
||||
abstract class ConpherenceWidgetView extends AphrontView {
|
||||
|
||||
private $conpherence;
|
||||
private $updateURI;
|
||||
|
||||
public function setUpdateURI($update_uri) {
|
||||
$this->updateURI = $update_uri;
|
||||
return $this;
|
||||
}
|
||||
public function getUpdateURI() {
|
||||
return $this->updateURI;
|
||||
}
|
||||
|
||||
public function setConpherence(ConpherenceThread $conpherence) {
|
||||
$this->conpherence = $conpherence;
|
||||
return $this;
|
||||
}
|
||||
public function getConpherence() {
|
||||
return $this->conpherence;
|
||||
}
|
||||
|
||||
public function getLatestTransactionID() {
|
||||
$transactions = $this->getConpherence()->getTransactions();
|
||||
$latest = end($transactions);
|
||||
return $latest->getID();
|
||||
}
|
||||
|
||||
}
|
|
@ -217,6 +217,13 @@ abstract class PhabricatorBaseEnglishTranslation
|
|||
),
|
||||
),
|
||||
|
||||
'%d people(s)' => array(
|
||||
array(
|
||||
'%d person',
|
||||
'%d people',
|
||||
),
|
||||
),
|
||||
|
||||
'%s Line(s)' => array(
|
||||
'%s Line',
|
||||
'%s Lines',
|
||||
|
|
|
@ -192,6 +192,91 @@
|
|||
padding-bottom: 1px;
|
||||
}
|
||||
|
||||
/* people widget */
|
||||
.conpherence-widget-pane .people-widget-header {
|
||||
float: left;
|
||||
width: 280px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .people-widget-header .divider {
|
||||
float: left;
|
||||
clear: both;
|
||||
width: 260px;
|
||||
margin: 0px 0px 0px 10px;
|
||||
border: 1px dashed #bfbfbf;
|
||||
}
|
||||
.conpherence-widget-pane .people-widget-header .add-people-widget {
|
||||
float: left;
|
||||
padding: 10px 0px 10px 0px;
|
||||
width: 280px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .people-widget-header .add-people-widget
|
||||
.aphront-form-control-tokenizer {
|
||||
float: left;
|
||||
width: 180px;
|
||||
padding: 0px 0px 0px 10px
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .people-widget-header .add-people-widget
|
||||
.jx-tokenizer-input {
|
||||
padding: 1px 3px 1px 3px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .people-widget-header .add-people-widget
|
||||
.people-add-button {
|
||||
float: right;
|
||||
margin: 0px 10px 0px 0px;
|
||||
padding: 3px 16px 4px 16px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry {
|
||||
float: left;
|
||||
width: 270px;
|
||||
clear: both;
|
||||
padding: 10px 0px 0px 8px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry a {
|
||||
float: left;
|
||||
clear: none;
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
width: 166px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry .pic {
|
||||
float: left;
|
||||
clear: left;
|
||||
margin: 0px 10px 0px 0px;
|
||||
width: 50px;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry .remove {
|
||||
float: right;
|
||||
clear: right;
|
||||
margin: 0;
|
||||
width: 34px;
|
||||
height: 36px;
|
||||
text-align: center;
|
||||
font-size: 22px;
|
||||
font-weight: bold;
|
||||
padding: 8px 0px 8px 0px;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry .remove:hover {
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry .remove .icon {
|
||||
color: #bfbfbf;
|
||||
}
|
||||
|
||||
.conpherence-widget-pane .person-entry .remove:hover .icon {
|
||||
color: #18559d;
|
||||
}
|
||||
|
||||
/* settings widget */
|
||||
.conpherence-widget-pane .notifications-update {
|
||||
margin: 2px 0px 0px 8px;
|
||||
|
|
|
@ -136,11 +136,17 @@ JX.behavior('conpherence-menu', function(config) {
|
|||
JX.$H(r.header)
|
||||
);
|
||||
|
||||
// update the menu entry as well
|
||||
// update the menu entry
|
||||
JX.DOM.replace(
|
||||
JX.$(r.conpherence_phid + '-nav-item'),
|
||||
JX.$H(r.nav_item)
|
||||
);
|
||||
|
||||
// update the people widget
|
||||
JX.DOM.setContent(
|
||||
JX.$(config.people_widget),
|
||||
JX.$H(r.people_widget)
|
||||
);
|
||||
})
|
||||
.start();
|
||||
});
|
||||
|
|
|
@ -39,6 +39,61 @@ JX.behavior('conpherence-widget-pane', function(config) {
|
|||
}
|
||||
);
|
||||
|
||||
/* people widget */
|
||||
var peopleRoot = JX.$(config.people_widget);
|
||||
var peopleUpdateHandler = function (r) {
|
||||
// update the transactions
|
||||
var messages = JX.$(config.messages);
|
||||
JX.DOM.appendContent(messages, JX.$H(r.transactions));
|
||||
messages.scrollTop = messages.scrollHeight;
|
||||
|
||||
// update the menu entry as well
|
||||
JX.DOM.replace(
|
||||
JX.$(r.conpherence_phid + '-nav-item'),
|
||||
JX.$H(r.nav_item)
|
||||
);
|
||||
|
||||
// update the header
|
||||
JX.DOM.setContent(
|
||||
JX.$(config.header),
|
||||
JX.$H(r.header)
|
||||
);
|
||||
|
||||
// update the people widget
|
||||
JX.DOM.setContent(
|
||||
JX.$(config.people_widget),
|
||||
JX.$H(r.people_widget)
|
||||
);
|
||||
};
|
||||
|
||||
JX.DOM.listen(
|
||||
peopleRoot,
|
||||
['click'],
|
||||
'add-person',
|
||||
function (e) {
|
||||
e.kill();
|
||||
var form = JX.DOM.find(peopleRoot, 'form');
|
||||
var data = e.getNodeData('add-person');
|
||||
JX.Workflow.newFromForm(form, data)
|
||||
.setHandler(peopleUpdateHandler)
|
||||
.start();
|
||||
}
|
||||
);
|
||||
|
||||
JX.DOM.listen(
|
||||
peopleRoot,
|
||||
['click'],
|
||||
'remove-person',
|
||||
function (e) {
|
||||
var form = JX.DOM.find(peopleRoot, 'form');
|
||||
var data = e.getNodeData('remove-person');
|
||||
JX.Workflow.newFromForm(form, data)
|
||||
.setHandler(peopleUpdateHandler)
|
||||
.start();
|
||||
}
|
||||
);
|
||||
|
||||
/* settings widget */
|
||||
var settingsRoot = JX.$(config.settings_widget);
|
||||
|
||||
var onsubmitSettings = function (e) {
|
||||
|
|
Loading…
Reference in a new issue