diff --git a/src/__celerity_resource_map__.php b/src/__celerity_resource_map__.php index d50c0b928e..927ceb8589 100644 --- a/src/__celerity_resource_map__.php +++ b/src/__celerity_resource_map__.php @@ -9,7 +9,7 @@ celerity_register_resource_map(array( 'aphront-dialog-view-css' => array( - 'uri' => '/res/d98e6292/rsrc/css/aphront/dialog-view.css', + 'uri' => '/res/a05107ae/rsrc/css/aphront/dialog-view.css', 'type' => 'css', 'requires' => array( @@ -100,7 +100,7 @@ celerity_register_resource_map(array( ), 'differential-changeset-view-css' => array( - 'uri' => '/res/658d181a/rsrc/css/application/differential/changeset-view.css', + 'uri' => '/res/11e7232a/rsrc/css/application/differential/changeset-view.css', 'type' => 'css', 'requires' => array( @@ -190,7 +190,7 @@ celerity_register_resource_map(array( ), 'phabricator-core-dialog-css' => array( - 'uri' => '/res/d9580553/rsrc/css/core/dialog.css', + 'uri' => '/res/f66cec41/rsrc/css/core/dialog.css', 'type' => 'css', 'requires' => array( @@ -237,7 +237,7 @@ celerity_register_resource_map(array( ), 'javelin-behavior-differential-edit-inline-comments' => array( - 'uri' => '/res/51d7da98/rsrc/js/application/differential/behavior-edit-inline-comments.js', + 'uri' => '/res/be5ed33e/rsrc/js/application/differential/behavior-edit-inline-comments.js', 'type' => 'js', 'requires' => array( @@ -276,7 +276,7 @@ celerity_register_resource_map(array( ), 'javelin-init-prod' => array( - 'uri' => '/res/ce6bff38/rsrc/js/javelin/init.min.js', + 'uri' => '/res/1267c868/rsrc/js/javelin/init.min.js', 'type' => 'js', 'requires' => array( @@ -285,7 +285,7 @@ celerity_register_resource_map(array( ), 'javelin-lib-dev' => array( - 'uri' => '/res/29c9b6b4/rsrc/js/javelin/javelin.dev.js', + 'uri' => '/res/53784c9a/rsrc/js/javelin/javelin.dev.js', 'type' => 'js', 'requires' => array( @@ -294,7 +294,7 @@ celerity_register_resource_map(array( ), 'javelin-lib-prod' => array( - 'uri' => '/res/ef13c830/rsrc/js/javelin/javelin.min.js', + 'uri' => '/res/2f2b3b2e/rsrc/js/javelin/javelin.min.js', 'type' => 'js', 'requires' => array( @@ -312,7 +312,7 @@ celerity_register_resource_map(array( ), 'javelin-typeahead-prod' => array( - 'uri' => '/res/593d9bb8/rsrc/js/javelin/typeahead.min.js', + 'uri' => '/res/69d5fad1/rsrc/js/javelin/typeahead.min.js', 'type' => 'js', 'requires' => array( @@ -321,7 +321,7 @@ celerity_register_resource_map(array( ), 'javelin-workflow-dev' => array( - 'uri' => '/res/2d740661/rsrc/js/javelin/workflow.dev.js', + 'uri' => '/res/7e690e16/rsrc/js/javelin/workflow.dev.js', 'type' => 'js', 'requires' => array( @@ -340,7 +340,7 @@ celerity_register_resource_map(array( ), array ( 'packages' => array ( - 'dc2390af' => + '4bb7e37f' => array ( 'name' => 'core.pkg.css', 'symbols' => @@ -357,10 +357,10 @@ celerity_register_resource_map(array( 9 => 'aphront-typeahead-control-css', 10 => 'phabricator-directory-css', ), - 'uri' => '/res/pkg/dc2390af/core.pkg.css', + 'uri' => '/res/pkg/4bb7e37f/core.pkg.css', 'type' => 'css', ), - '69b11588' => + 'f399aad7' => array ( 'name' => 'differential.pkg.css', 'symbols' => @@ -371,27 +371,27 @@ celerity_register_resource_map(array( 3 => 'differential-revision-history-css', 4 => 'differential-table-of-contents-css', ), - 'uri' => '/res/pkg/69b11588/differential.pkg.css', + 'uri' => '/res/pkg/f399aad7/differential.pkg.css', 'type' => 'css', ), ), 'reverse' => array ( - 'phabricator-core-css' => 'dc2390af', - 'phabricator-core-buttons-css' => 'dc2390af', - 'phabricator-standard-page-view' => 'dc2390af', - 'aphront-dialog-view-css' => 'dc2390af', - 'aphront-form-view-css' => 'dc2390af', - 'aphront-panel-view-css' => 'dc2390af', - 'aphront-side-nav-view-css' => 'dc2390af', - 'aphront-table-view-css' => 'dc2390af', - 'aphront-tokenizer-control-css' => 'dc2390af', - 'aphront-typeahead-control-css' => 'dc2390af', - 'phabricator-directory-css' => 'dc2390af', - 'differential-core-view-css' => '69b11588', - 'differential-changeset-view-css' => '69b11588', - 'differential-revision-detail-css' => '69b11588', - 'differential-revision-history-css' => '69b11588', - 'differential-table-of-contents-css' => '69b11588', + 'phabricator-core-css' => '4bb7e37f', + 'phabricator-core-buttons-css' => '4bb7e37f', + 'phabricator-standard-page-view' => '4bb7e37f', + 'aphront-dialog-view-css' => '4bb7e37f', + 'aphront-form-view-css' => '4bb7e37f', + 'aphront-panel-view-css' => '4bb7e37f', + 'aphront-side-nav-view-css' => '4bb7e37f', + 'aphront-table-view-css' => '4bb7e37f', + 'aphront-tokenizer-control-css' => '4bb7e37f', + 'aphront-typeahead-control-css' => '4bb7e37f', + 'phabricator-directory-css' => '4bb7e37f', + 'differential-core-view-css' => 'f399aad7', + 'differential-changeset-view-css' => 'f399aad7', + 'differential-revision-detail-css' => 'f399aad7', + 'differential-revision-history-css' => 'f399aad7', + 'differential-table-of-contents-css' => 'f399aad7', ), )); diff --git a/src/__phutil_library_map__.php b/src/__phutil_library_map__.php index b40da8afca..ed66f1dc3e 100644 --- a/src/__phutil_library_map__.php +++ b/src/__phutil_library_map__.php @@ -91,6 +91,8 @@ phutil_register_library_map(array( 'DifferentialDiffViewController' => 'applications/differential/controller/diffview', 'DifferentialHunk' => 'applications/differential/storage/hunk', 'DifferentialInlineComment' => 'applications/differential/storage/inlinecomment', + 'DifferentialInlineCommentEditController' => 'applications/differential/controller/inlinecommentedit', + 'DifferentialInlineCommentView' => 'applications/differential/view/inlinecomment', 'DifferentialLintStatus' => 'applications/differential/constants/lintstatus', 'DifferentialMail' => 'applications/differential/mail/base', 'DifferentialMarkupEngineFactory' => 'applications/differential/parser/markup', @@ -266,6 +268,8 @@ phutil_register_library_map(array( 'DifferentialDiffViewController' => 'DifferentialController', 'DifferentialHunk' => 'DifferentialDAO', 'DifferentialInlineComment' => 'DifferentialDAO', + 'DifferentialInlineCommentEditController' => 'DifferentialController', + 'DifferentialInlineCommentView' => 'AphrontView', 'DifferentialNewDiffMail' => 'DifferentialReviewRequestMail', 'DifferentialReviewRequestMail' => 'DifferentialMail', 'DifferentialRevision' => 'DifferentialDAO', diff --git a/src/aphront/default/configuration/AphrontDefaultApplicationConfiguration.php b/src/aphront/default/configuration/AphrontDefaultApplicationConfiguration.php index 85367d98f0..748e384c30 100644 --- a/src/aphront/default/configuration/AphrontDefaultApplicationConfiguration.php +++ b/src/aphront/default/configuration/AphrontDefaultApplicationConfiguration.php @@ -91,7 +91,7 @@ class AphrontDefaultApplicationConfiguration 'save/$' => 'DifferentialCommentSaveController', 'inline/' => array( 'preview/$' => 'DifferentialInlineCommentPreviewController', - 'edit/$' => 'DifferentialInlineCommentEditController', + 'edit/(?\d+)/$' => 'DifferentialInlineCommentEditController', ), ), ), @@ -166,6 +166,11 @@ class AphrontDefaultApplicationConfiguration $response = new AphrontWebpageResponse(); $response->setContent($view->render()); return $response; + } else { + return id(new AphrontAjaxResponse()) + ->setContent(array( + 'dialog' => $response->buildResponseString(), + )); } } else if ($response instanceof Aphront404Response) { diff --git a/src/aphront/default/configuration/__init__.php b/src/aphront/default/configuration/__init__.php index ea6f86450a..0da64e03d9 100644 --- a/src/aphront/default/configuration/__init__.php +++ b/src/aphront/default/configuration/__init__.php @@ -8,12 +8,14 @@ phutil_require_module('phabricator', 'aphront/applicationconfiguration'); phutil_require_module('phabricator', 'aphront/request'); +phutil_require_module('phabricator', 'aphront/response/ajax'); phutil_require_module('phabricator', 'aphront/response/webpage'); phutil_require_module('phabricator', 'applications/base/controller/404'); phutil_require_module('phabricator', 'view/page/failure'); phutil_require_module('phabricator', 'view/page/standard'); phutil_require_module('phutil', 'markup'); +phutil_require_module('phutil', 'utils'); phutil_require_source('AphrontDefaultApplicationConfiguration.php'); diff --git a/src/applications/differential/controller/changesetview/DifferentialChangesetViewController.php b/src/applications/differential/controller/changesetview/DifferentialChangesetViewController.php index f8d7cab6c2..d10e5789f4 100644 --- a/src/applications/differential/controller/changesetview/DifferentialChangesetViewController.php +++ b/src/applications/differential/controller/changesetview/DifferentialChangesetViewController.php @@ -23,6 +23,7 @@ class DifferentialChangesetViewController extends DifferentialController { $request = $this->getRequest(); $id = $request->getStr('id'); + $author_phid = $request->getUser()->getPHID(); $changeset = id(new DifferentialChangeset())->load($id); if (!$changeset) { @@ -53,6 +54,22 @@ class DifferentialChangesetViewController extends DifferentialController { $parser = new DifferentialChangesetParser(); $parser->setChangeset($changeset); + + $phids = array(); + $inlines = $this->loadInlineComments($id, $author_phid); + foreach ($inlines as $inline) { + $parser->parseInlineComment($inline); + $phids[$inline->getAuthorPHID()] = true; + } + $phids = array_keys($phids); + + $handles = id(new PhabricatorObjectHandleData($phids)) + ->loadHandles(); + $parser->setHandles($handles); + + $factory = new DifferentialMarkupEngineFactory(); + $engine = $factory->newDifferentialCommentMarkupEngine(); + $parser->setMarkupEngine($engine); $output = $parser->render(null, $range_s, $range_e, $mask); @@ -85,4 +102,12 @@ class DifferentialChangesetViewController extends DifferentialController { )); } + private function loadInlineComments($changeset_id, $author_phid) { + return id(new DifferentialInlineComment())->loadAllWhere( + 'changesetID = %d AND (commentID IS NOT NULL OR authorPHID = %s)', + $changeset_id, + $author_phid); + } + + } diff --git a/src/applications/differential/controller/inlinecommentedit/DifferentialInlineCommentEditController.php b/src/applications/differential/controller/inlinecommentedit/DifferentialInlineCommentEditController.php new file mode 100644 index 0000000000..674db18520 --- /dev/null +++ b/src/applications/differential/controller/inlinecommentedit/DifferentialInlineCommentEditController.php @@ -0,0 +1,116 @@ +revisionID = $data['id']; + } + + public function processRequest() { + $request = $this->getRequest(); + + $changeset = $request->getInt('changeset'); + $is_new = $request->getInt('is_new'); + $on_right = $request->getInt('on_right'); + $number = $request->getInt('number'); + $length = $request->getInt('length'); + $text = $request->getStr('text'); + $op = $request->getStr('op'); + + $user = $request->getUser(); + + $submit_uri = '/differential/comment/inline/edit/'.$this->revisionID.'/'; + + switch ($op) { + case 'delete': + if ($request->isFormPost()) { + // do the delete; + return new AphrontAjaxResponse(); + } + + $dialog = new AphrontDialogView(); + $dialog->setTitle('Really delete this comment?'); + + return id(new AphrontDialogResponse())->setDialog($dialog); + case 'edit': + $dialog = new AphrontDialogView(); + + return id(new AphrontDialogResponse())->setDialog($dialog); + case 'create': + + if (!$request->isFormPost() || !strlen($text)) { + return new AphrontAjaxResponse(); + } + + $factory = new DifferentialMarkupEngineFactory(); + $engine = $factory->newDifferentialCommentMarkupEngine(); + + $phids = array($user->getPHID()); + + $handles = id(new PhabricatorObjectHandleData($phids)) + ->loadHandles(); + + $inline = id(new DifferentialInlineComment()) + ->setRevisionID($this->revisionID) + ->setChangesetID($changeset) + ->setCommentID(null) + ->setAuthorPHID($user->getPHID()) + ->setLineNumber($number) + ->setLineLength($length) + ->setIsNewFile($is_new) + ->setContent($text) + ->save(); + + $view = new DifferentialInlineCommentView(); + $view->setInlineComment($inline); + $view->setOnRight($on_right); + $view->setBuildScaffolding(true); + $view->setMarkupEngine($engine); + $view->setHandles($handles); + + return id(new AphrontAjaxResponse()) + ->setContent( + array( + 'inlineCommentID' => $inline->getID(), + 'markup' => $view->render(), + )); + default: + $dialog = new AphrontDialogView(); + $dialog->setUser($user); + $dialog->setTitle('New Inline Comment'); + $dialog->setSubmitURI($submit_uri); + + $dialog->addHiddenInput('op', 'create'); + $dialog->addHiddenInput('changeset', $changeset); + $dialog->addHiddenInput('is_new', $is_new); + $dialog->addHiddenInput('on_right', $on_right); + $dialog->addHiddenInput('number', $number); + $dialog->addHiddenInput('length', $length); + + $dialog->addSubmitButton(); + $dialog->addCancelButton('#'); + $dialog->appendChild(''); + + return id(new AphrontDialogResponse())->setDialog($dialog); + } + } + +} diff --git a/src/applications/differential/controller/inlinecommentedit/__init__.php b/src/applications/differential/controller/inlinecommentedit/__init__.php new file mode 100644 index 0000000000..59e55ef5fc --- /dev/null +++ b/src/applications/differential/controller/inlinecommentedit/__init__.php @@ -0,0 +1,19 @@ +filetype = end(explode('.', $filename)); } } + + public function setHandles(array $handles) { + $this->handles = $handles; + return $this; + } + + public function setMarkupEngine(PhutilMarkupEngine $engine) { + $this->markupEngine = $engine; + return $this; + } public function parseHunk(DifferentialHunk $hunk) { $this->parsedHunk = true; @@ -773,11 +785,12 @@ EOSYNTHETIC; $new_mask = array(); $feedback_mask = array(); - $handles = array(); if ($this->comments) { foreach ($this->comments as $comment) { $start = max($comment->getLineNumber() - self::LINES_CONTEXT, 0); - $end = $comment->getFinalLine() + self::LINES_CONTEXT; + $end = $comment->getLineNumber() + + $comment->getLineLength() + + self::LINES_CONTEXT; $new = $this->isCommentInNewFile($comment); for ($ii = $start; $ii <= $end; $ii++) { if ($new) { @@ -799,22 +812,16 @@ EOSYNTHETIC; $feedback_mask[$ii] = true; } } -/* - $handle_ids = mpull($this->comments, 'getUserPHID'); - $handles = array(); - $handle_data = new ToolsHandleData($handle_ids, $handles); - $handle_data->needNames(); - prep($handle_data); - $this->comments = msort($this->comments, 'getID'); foreach ($this->comments as $comment) { + $final = $comment->getLineNumber() + + $comment->getLineLength(); if ($this->isCommentInNewFile($comment)) { - $new_comments[$comment->getFinalLine()][] = $comment; + $new_comments[$final][] = $comment; } else { - $old_comments[$comment->getFinalLine()][] = $comment; + $old_comments[$final][] = $comment; } } -*/ } $html = $this->renderTextChange( @@ -823,7 +830,6 @@ EOSYNTHETIC; $mask_force, $feedback_mask, $viewer_context, - $handles, $old_comments, $new_comments); @@ -879,7 +885,6 @@ EOSYNTHETIC; $mask_force, $feedback_mask, $viewer_context, - $handles, array $old_comments, array $new_comments) { @@ -1080,8 +1085,7 @@ EOSYNTHETIC; foreach ($old_comments[$o_num] as $comment) { $xhp = $this->renderInlineComment( $comment, - $viewer_context, - $handles); + $viewer_context); $html[] = ''. $xhp. @@ -1092,8 +1096,7 @@ EOSYNTHETIC; foreach ($new_comments[$n_num] as $comment) { $xhp = $this->renderInlineComment( $comment, - $viewer_context, - $handles); + $viewer_context); $html[] = ''. $xhp. @@ -1107,23 +1110,20 @@ EOSYNTHETIC; private function renderInlineComment( DifferentialInlineComment $comment, - $viewer_context, - $handles) { + $viewer_context) { $edit = $viewer_context && - ($comment->getUserPHID() == $viewer_context->getUserID()) && + ($comment->getAuthorPHID() == $viewer_context->getUserID()) && (!$comment->getFeedbackID()); $is_new = $this->isCommentInNewFile($comment); - return ''; -/* - return getUserPHID()]} />; -*/ + return id(new DifferentialInlineCommentView()) + ->setInlineComment($comment) + ->setOnRight($is_new) + ->setHandles($this->handles) + ->setMarkupEngine($this->markupEngine) + ->render(); } protected function renderPropertyChangeHeader($changeset) { @@ -1146,6 +1146,8 @@ EOSYNTHETIC; return null; /* + TODO + $table = ; $table->appendChild( diff --git a/src/applications/differential/view/changesetdetailview/DifferentialChangesetDetailView.php b/src/applications/differential/view/changesetdetailview/DifferentialChangesetDetailView.php index 8a57f48a36..ccba6739db 100644 --- a/src/applications/differential/view/changesetdetailview/DifferentialChangesetDetailView.php +++ b/src/applications/differential/view/changesetdetailview/DifferentialChangesetDetailView.php @@ -48,6 +48,10 @@ class DifferentialChangesetDetailView extends AphrontView { 'div', array( 'sigil' => 'differential-changeset', + 'meta' => array( + 'left' => $this->changeset->getID(), + 'right' => $this->changeset->getID(), + ), 'class' => $class, ), ''. diff --git a/src/applications/differential/view/changesetlistview/DifferentialChangesetListView.php b/src/applications/differential/view/changesetlistview/DifferentialChangesetListView.php index 3a9b21bf17..a4b2261464 100644 --- a/src/applications/differential/view/changesetlistview/DifferentialChangesetListView.php +++ b/src/applications/differential/view/changesetlistview/DifferentialChangesetListView.php @@ -121,7 +121,7 @@ class DifferentialChangesetListView extends AphrontView { if ($this->editable) { $revision = $this->revision; Javelin::initBehavior('differential-edit-inline-comments', array( - 'uri' => '/differential/inline/edit/'.$revision->getID().'/', + 'uri' => '/differential/comment/inline/edit/'.$revision->getID().'/', )); } diff --git a/src/applications/differential/view/inlinecomment/DifferentialInlineCommentView.php b/src/applications/differential/view/inlinecomment/DifferentialInlineCommentView.php new file mode 100644 index 0000000000..d81e7cd97c --- /dev/null +++ b/src/applications/differential/view/inlinecomment/DifferentialInlineCommentView.php @@ -0,0 +1,131 @@ +inlineComment = $comment; + return $this; + } + + public function setOnRight($on_right) { + $this->onRight = $on_right; + return $this; + } + + public function setBuildScaffolding($scaffold) { + $this->buildScaffolding = $scaffold; + return $this; + } + + public function setHandles(array $handles) { + $this->handles = $handles; + return $this; + } + + public function setMarkupEngine(PhutilMarkupEngine $engine) { + $this->markupEngine = $engine; + return $this; + } + + public function render() { + + $inline = $this->inlineComment; + + $start = $inline->getLineNumber(); + $length = $inline->getLineLength(); + if ($length) { + $end = $start + $length; + $line = 'Lines '.number_format($start).'-'.number_format($end); + } else { + $line = 'Line '.number_format($start); + } + + $metadata = array( + 'number' => $inline->getLineNumber(), + 'length' => $inline->getLineLength(), + 'on_right' => $this->onRight, // TODO + ); + + $sigil = 'differential-inline-comment'; + + $links = 'xxx'; + $content = $inline->getContent(); + $handles = $this->handles; + + if ($links) { + $links = + ''. + $links. + ''; + } + + $content = $this->markupEngine->markupText($content); + + $markup = javelin_render_tag( + 'div', + array( + 'class' => 'differential-inline-comment', + 'sigil' => $sigil, + 'meta' => $metadata, + ), + '
'. + $links. + ''.$line.''. + $handles[$inline->getAuthorPHID()]->renderLink(). + '
'. + $content); + + return $this->scaffoldMarkup($markup); + } + + private function scaffoldMarkup($markup) { + if (!$this->buildScaffolding) { + return $markup; + } + + if ($this->onRight) { + return + '
'. + ''. + ''. + ''. + ''. + ''. + ''. + '
'.$markup.'
'; + } else { + return + ''. + ''. + ''. + ''. + ''. + ''. + ''. + '
'.$markup.'
'; + } + } + +} diff --git a/src/applications/differential/view/inlinecomment/__init__.php b/src/applications/differential/view/inlinecomment/__init__.php new file mode 100644 index 0000000000..6b3db812a1 --- /dev/null +++ b/src/applications/differential/view/inlinecomment/__init__.php @@ -0,0 +1,12 @@ +query( 'UPDATE %T SET %Q, version = version + 1 WHERE %C = %d AND %C = %d', @@ -811,15 +811,17 @@ abstract class LiskDAO { $this->willWriteData($data); - $columns = array_keys($data); - foreach ($columns as $k => $property) { - $columns[$k] = $property; - } - $conn = $this->getConnection('w'); + $columns = array_keys($data); + + foreach ($data as $key => $value) { + $data[$key] = qsprintf($conn, '%ns', $value); + } + $data = implode(', ', $data); + $conn->query( - '%Q INTO %T (%LC) VALUES (%Ls)', + '%Q INTO %T (%LC) VALUES (%Q)', $mode, $this->getTableName(), $columns, diff --git a/src/view/dialog/AphrontDialogView.php b/src/view/dialog/AphrontDialogView.php index e6225f460c..83433b88b1 100755 --- a/src/view/dialog/AphrontDialogView.php +++ b/src/view/dialog/AphrontDialogView.php @@ -22,6 +22,13 @@ class AphrontDialogView extends AphrontView { private $submitButton; private $cancelURI; private $submitURI; + private $user; + private $hidden = array(); + + public function setUser(PhabricatorUser $user) { + $this->user = $user; + return $this; + } public function setSubmitURI($uri) { $this->submitURI = $uri; @@ -47,6 +54,11 @@ class AphrontDialogView extends AphrontView { return $this; } + public function addHiddenInput($key, $value) { + $this->hidden[$key] = $value; + return $this; + } + final public function render() { require_celerity_resource('aphront-dialog-view-css'); @@ -59,15 +71,35 @@ class AphrontDialogView extends AphrontView { } if ($this->cancelURI) { - $buttons[] = phutil_render_tag( + $buttons[] = javelin_render_tag( 'a', array( 'href' => $this->cancelURI, 'class' => 'button grey', + 'name' => '__cancel__', + 'sigil' => 'jx-workflow-button', ), 'Cancel'); } + if (!$this->user) { + throw new Exception( + "You must call setUser() when rendering an AphrontDialogView."); + } + $csrf = $this->user->getCSRFToken(); + + $hidden_inputs = array(); + foreach ($this->hidden as $key => $value) { + $hidden_inputs[] = phutil_render_tag( + 'input', + array( + 'type' => 'hidden', + 'name' => $key, + 'value' => $value, + )); + } + $hidden_inputs = implode("\n", $hidden_inputs); + return javelin_render_tag( 'form', array( @@ -77,6 +109,8 @@ class AphrontDialogView extends AphrontView { 'sigil' => 'jx-dialog', ), ''. + ''. + $hidden_inputs. '
'. phutil_escape_html($this->title). '
'. diff --git a/webroot/rsrc/css/application/differential/changeset-view.css b/webroot/rsrc/css/application/differential/changeset-view.css index 7395e5a669..00f316712d 100644 --- a/webroot/rsrc/css/application/differential/changeset-view.css +++ b/webroot/rsrc/css/application/differential/changeset-view.css @@ -130,3 +130,37 @@ left: 0px; } +.differential-inline-comment { + background: #f9f9f1; + border: 1px solid #aaaa88; + font-family: Verdana; + font-size: 11px; + margin: 4px 0px; + max-width: 81ch; + padding: 8px 10px; + width: 100%; + -moz-box-sizing: border-box; + -webkit-box-sizing: border-box; +} + +.differential-inline-comment-head { + font-weight: bold; + color: #333333; + border-bottom: 1px solid #ccccaa; + padding-bottom: 6px; + margin-bottom: 4px; +} + +.differential-inline-comment-links, +.differential-inline-comment-line { + font-weight: normal; + font-style: italic; + color: #666666; + float: right; + white-space: nowrap; +} + +.differential-inline-comment-edit { + padding-left: 8px; + font-style: normal; +} diff --git a/webroot/rsrc/js/application/differential/behavior-edit-inline-comments.js b/webroot/rsrc/js/application/differential/behavior-edit-inline-comments.js index a63526bb71..e1294b522d 100644 --- a/webroot/rsrc/js/application/differential/behavior-edit-inline-comments.js +++ b/webroot/rsrc/js/application/differential/behavior-edit-inline-comments.js @@ -53,9 +53,14 @@ JX.behavior('differential-edit-inline-comments', function(config) { finishSelect(); } - function isNewFile(node) { + function isOnRight(node) { return node.parentNode.firstChild != node; } + + function isNewFile(node) { + var data = JX.Stratcom.getData(root); + return isOnRight(node) || (data.left != data.right); + } function getRowNumber(th_node) { try { @@ -81,10 +86,10 @@ JX.behavior('differential-edit-inline-comments', function(config) { origin = target = e.getTarget(); var data = e.getNodeData('differential-changeset'); - if (isNewFile(target)) { - changeset = data.oid; + if (isOnRight(target)) { + changeset = data.left; } else { - changeset = data.nid; + changeset = data.right; } updateReticle(); @@ -99,7 +104,7 @@ JX.behavior('differential-edit-inline-comments', function(config) { if (!selecting || workflow || (getRowNumber(e.getTarget()) === undefined) || - (isNewFile(e.getTarget()) != isNewFile(origin)) || + (isOnRight(e.getTarget()) != isOnRight(origin)) || (e.getNode('differential-changeset') !== root)) { return; } @@ -136,7 +141,8 @@ JX.behavior('differential-edit-inline-comments', function(config) { changeset: changeset, number: o, length: len, - is_new: isNewFile(target) ? 1 : 0 + is_new: isNewFile(target) ? 1 : 0, + on_right: isOnRight(target) ? 1 : 0 }; workflow = true; @@ -155,9 +161,7 @@ JX.behavior('differential-edit-inline-comments', function(config) { } drawInlineComment(insert.parentNode, target, r); finishSelect(); - JX.Stratcom.invoke('inline-comment-update', - null, - {id : r.inlineCommentID}); + JX.Stratcom.invoke('differential-inline-comment-update'); }) .setCloseHandler(finishSelect); @@ -175,7 +179,7 @@ JX.behavior('differential-edit-inline-comments', function(config) { JX.Stratcom.listen( ['mouseover', 'mouseout'], - 'inline-comment', + 'differential-inline-comment', function(e) { if (selecting || workflow) { return; @@ -184,21 +188,21 @@ JX.behavior('differential-edit-inline-comments', function(config) { if (e.getType() == 'mouseout') { hideReticle(); } else { - var data = e.getNodeData('inline-comment'); - var change = e.getNodeData('differential-changeset'); - root = e.getNode('differential-changeset'); - var prefix = 'C' + change; + var data = e.getNodeData('differential-inline-comment'); + var change = e.getNodeData('differential-changeset'); - if (data.is_new) { - prefix += 'NL'; + var prefix; + if (data.on_right) { + prefix = 'C' + (change.left) + 'NL'; } else { - prefix += 'OL'; + prefix = 'C' + (change.right) + 'OL'; } origin = JX.$(prefix + data.number); - target = JX.$(prefix + (data.number + data.length)); + target = JX.$(prefix + (parseInt(data.number, 10) + + parseInt(data.length, 10))); updateReticle(); } @@ -206,16 +210,18 @@ JX.behavior('differential-edit-inline-comments', function(config) { JX.Stratcom.listen( 'click', - [['inline-comment', 'delete'], - ['inline-comment', 'edit']], + [['differential-inline-comment', 'delete'], + ['differential-inline-comment', 'edit']], function(e) { var data = { op: e.getNode('edit') ? 'edit' : 'delete', - id: e.getNodeData('inline-comment').id + id: e.getNodeData('differential-inline-comment').id }; new JX.Workflow(config.uri, data) .setHandler(function(r) { - var base_row = e.getNode('inline-comment').parentNode.parentNode; + var base_row = e.getNode('differential-inline-comment') + .parentNode + .parentNode; if (data.op == 'edit' && r.markup) { drawInlineComment(base_row.parentNode, base_row, r); } diff --git a/webroot/rsrc/js/javelin/javelin.dev.js b/webroot/rsrc/js/javelin/javelin.dev.js index 7fc3cfbe28..77cc59f031 100644 --- a/webroot/rsrc/js/javelin/javelin.dev.js +++ b/webroot/rsrc/js/javelin/javelin.dev.js @@ -2684,17 +2684,19 @@ JX.install('DOM', { * @task stratcom * @param Node The node to listen for events underneath. * @param string|list One or more event types to listen for. - * @param list? A path to listen on. + * @param list? A path to listen on, or a list of paths. * @param function Callback to invoke when a matching event occurs. * @return object A reference to the installed listener. You can later * remove the listener by calling this object's remove() * method. */ listen : function(node, type, path, callback) { - return JX.Stratcom.listen( - type, - ['id:'+JX.DOM.uniqID(node)].concat(JX.$AX(path || [])), - callback); + var id = ['id:' + JX.DOM.uniqID(node)]; + path = JX.$AX(path || []); + for (var ii = 0; ii < path.length; ii++) { + path[ii] = id.concat(JX.$AX(path[ii])); + } + return JX.Stratcom.listen(type, path, callback); }, uniqID : function(node) { diff --git a/webroot/rsrc/js/javelin/workflow.dev.js b/webroot/rsrc/js/javelin/workflow.dev.js index 27fc83a262..94710abf32 100644 --- a/webroot/rsrc/js/javelin/workflow.dev.js +++ b/webroot/rsrc/js/javelin/workflow.dev.js @@ -111,6 +111,7 @@ JX.install('Workflow', { if (JX.Workflow._disabled) { return; } + var t = event.getTarget(); if (t.name == '__cancel__' || t.name == '__close__') { JX.Workflow._pop(); @@ -152,7 +153,7 @@ JX.install('Workflow', { JX.DOM.listen( this._root, 'click', - 'tag:button', + [['jx-workflow-button'], ['tag:button']], JX.Workflow._onbutton); document.body.appendChild(this._root); var d = JX.$V.getDim(this._root);