Merge pull request #288 from sharelatex/pr-log-hints-negative-feedback

Log hints - negative feedback details
This commit is contained in:
Paulo Jorge Reis 2016-07-26 15:15:32 +01:00 committed by GitHub
commit e7483ed9e5
4 changed files with 154 additions and 4 deletions

View file

@ -108,7 +108,7 @@ div.full-size.pdf(ng-controller="PdfController")
'alert-info': entry.level == 'typesetting'\ 'alert-info': entry.level == 'typesetting'\
}" }"
ng-click="openInEditor(entry)" ng-click="openInEditor(entry)"
ng-init="feedbackSent = false;" ng-init="feedbackSent = false; showNegFeedbackUI = false; negFeedbackReason = ''; negFeedbackReasonFreeText = ''"
) )
span.line-no span.line-no
i.fa.fa-link(aria-hidden="true") i.fa.fa-link(aria-hidden="true")
@ -135,7 +135,7 @@ div.full-size.pdf(ng-controller="PdfController")
i.fa.fa-external-link i.fa.fa-external-link
| #{translate("log_hint_extra_info")} | #{translate("log_hint_extra_info")}
.card-hint-feedback( .card-hint-feedback(
ng-show="!feedbackSent" ng-hide="feedbackSent || showNegFeedbackUI"
ng-class="entry.ruleId" ng-class="entry.ruleId"
) )
label.card-hint-feedback-label #{translate("log_hint_feedback_label")} label.card-hint-feedback-label #{translate("log_hint_feedback_label")}
@ -145,11 +145,57 @@ div.full-size.pdf(ng-controller="PdfController")
) #{translate("answer_yes")} ) #{translate("answer_yes")}
span  /  span  / 
a.card-hint-feedback-negative( a.card-hint-feedback-negative(
ng-click="trackLogHintsNegativeFeedback(entry.ruleId); feedbackSent = true;" ng-click="trackLogHintsNegativeFeedback(entry.ruleId); showNegFeedbackUI = true;"
href href
) #{translate("answer_no")} ) #{translate("answer_no")}
.card-hint-extra-feedback(ng-hide="!showNegFeedbackUI || feedbackSent")
p.card-hint-extra-feedback-label #{translate("log_hint_ask_extra_feedback")}
.radio: label
input(
type="radio"
name="{{ 'neg-feedback-reason-' + $index }}"
ng-model="negFeedbackReason"
value="{{ logHintsNegFeedbackValues.DIDNT_UNDERSTAND }}"
)
| #{translate("log_hint_extra_feedback_didnt_understand")}
.radio: label
input(
type="radio"
name="{{ 'neg-feedback-reason-' + $index }}"
ng-model="negFeedbackReason"
value="{{ logHintsNegFeedbackValues.NOT_APPLICABLE }}"
)
| #{translate("log_hint_extra_feedback_not_applicable")}
.radio: label
input(
type="radio"
name="{{ 'neg-feedback-reason-' + $index }}"
ng-model="negFeedbackReason"
value="{{ logHintsNegFeedbackValues.INCORRECT }}"
)
| #{translate("log_hint_extra_feedback_incorrect")}
.radio: label
input(
type="radio"
name="{{ 'neg-feedback-reason-' + $index }}"
ng-model="negFeedbackReason"
value="{{ logHintsNegFeedbackValues.OTHER }}"
)
| #{translate("log_hint_extra_feedback_other")}
textarea.form-control(
ng-show="negFeedbackReason === logHintsNegFeedbackValues.OTHER"
ng-model="negFeedbackReasonFreeText"
rows="2"
)
.clearfix
button.btn.btn-default.btn-sm.pull-right(
ng-disabled="!negFeedbackReason"
ng-click="trackLogHintsNegFeedbackDetails(entry.ruleId, negFeedbackReason, negFeedbackReasonFreeText); feedbackSent = true;"
) #{translate("log_hint_extra_feedback_submit")}
.card-hint-feedback(ng-show="feedbackSent") .card-hint-feedback(ng-show="feedbackSent")
label.card-hint-feedback-label #{translate("log_hint_feedback_gratitude")} label.card-hint-feedback-label #{translate("log_hint_feedback_gratitude")}
p.entry-content(ng-show="entry.content") {{ entry.content.trim() }} p.entry-content(ng-show="entry.content") {{ entry.content.trim() }}
p p

View file

@ -3,8 +3,9 @@ define [
"ace/ace" "ace/ace"
"ide/human-readable-logs/HumanReadableLogs" "ide/human-readable-logs/HumanReadableLogs"
"libs/bib-log-parser" "libs/bib-log-parser"
"services/log-hints-feedback"
], (App, Ace, HumanReadableLogs, BibLogParser) -> ], (App, Ace, HumanReadableLogs, BibLogParser) ->
App.controller "PdfController", ($scope, $http, ide, $modal, synctex, event_tracking, localStorage) -> App.controller "PdfController", ($scope, $http, ide, $modal, synctex, event_tracking, logHintsFeedback, localStorage) ->
# enable per-user containers by default # enable per-user containers by default
perUserCompile = true perUserCompile = true
@ -32,6 +33,8 @@ define [
$scope.shouldDropUp = getFilesDropdownTopCoordAsRatio() > 0.65 $scope.shouldDropUp = getFilesDropdownTopCoordAsRatio() > 0.65
# log hints tracking # log hints tracking
$scope.logHintsNegFeedbackValues = logHintsFeedback.feedbackOpts
$scope.trackLogHintsLearnMore = () -> $scope.trackLogHintsLearnMore = () ->
event_tracking.sendCountly "logs-hints-learn-more" event_tracking.sendCountly "logs-hints-learn-more"
@ -39,6 +42,9 @@ define [
event_tracking.send "log-hints", (if isPositive then "feedback-positive" else "feedback-negative"), hintId event_tracking.send "log-hints", (if isPositive then "feedback-positive" else "feedback-negative"), hintId
event_tracking.sendCountly (if isPositive then "log-hints-feedback-positive" else "log-hints-feedback-negative"), { hintId } event_tracking.sendCountly (if isPositive then "log-hints-feedback-positive" else "log-hints-feedback-negative"), { hintId }
$scope.trackLogHintsNegFeedbackDetails = (hintId, feedbackOpt, feedbackOtherVal) ->
logHintsFeedback.submitFeedback hintId, feedbackOpt, feedbackOtherVal
$scope.trackLogHintsPositiveFeedback = (hintId) -> trackLogHintsFeedback true, hintId $scope.trackLogHintsPositiveFeedback = (hintId) -> trackLogHintsFeedback true, hintId
$scope.trackLogHintsNegativeFeedback = (hintId) -> trackLogHintsFeedback false, hintId $scope.trackLogHintsNegativeFeedback = (hintId) -> trackLogHintsFeedback false, hintId

View file

@ -0,0 +1,57 @@
define [
"base"
], (App) ->
App.factory "logHintsFeedback", ($http, $q) ->
hintsFeedbackFormAPIHash = "rl4xgvr1v5t64a"
idStampVal = "OPkEWEFHUFAm7hKlraQMhiOXQabafWo8NipRvLT397w="
hintFieldAPIId = "3"
reasonFieldAPIId = "1"
reasonOtherFieldAPIId = "1_other_other"
submitEndpoint = "https://sharelatex.wufoo.eu/forms/#{ hintsFeedbackFormAPIHash }/#public"
feedbackOpts =
DIDNT_UNDERSTAND: "didnt_understand"
NOT_APPLICABLE: "not_applicable"
INCORRECT: "incorrect"
OTHER: "other"
createRequest = (hintId, feedbackOpt, feedbackOtherVal = "") ->
formData = new FormData()
formData.append "Field#{ hintFieldAPIId }", hintId
formData.append "Field#{ reasonFieldAPIId }", feedbackOpt
formData.append "Field#{ reasonOtherFieldAPIId }", feedbackOtherVal
formData.append "idstamp", idStampVal
# Allow user to specify "other" without any extra details; an empty string
# would trigger an error submitting.
if feedbackOpt == feedbackOpts.OTHER and feedbackOtherVal == ""
formData.set "Field#{ reasonOtherFieldAPIId }", "#{ feedbackOpts.OTHER } empty"
req =
method: 'POST'
url: submitEndpoint
# This will effectively disable Angular's default serialization mechanisms,
# forcing the XHR to be done with whatever data we provide (in this case,
# form data). Without this, Angular will forcefully try to serialize data
# to JSON.
transformRequest: angular.identity
data: formData
headers :
# This will tell Angular to use the browser-provided value, which is
# computed according to the data being sent (in this case, multipart
# form + browser-specific multipart boundary). Without this, Angular
# will set JSON.
"Content-Type": undefined
return req
submitFeedback = (hintId, feedbackOpt, feedbackOtherVal = "") ->
submitRequest = createRequest hintId, feedbackOpt, feedbackOtherVal
$http(submitRequest)
service =
feedbackOpts: feedbackOpts
submitFeedback: submitFeedback
return service

View file

@ -203,6 +203,17 @@
white-space: nowrap; white-space: nowrap;
} }
@keyframes expand-feedback-area {
from {
max-height: 0;
}
to {
max-height: 500px;
}
}
.card-hint:extend(.card-thin) { .card-hint:extend(.card-thin) {
margin-top: 10px; margin-top: 10px;
padding-bottom: 7px; padding-bottom: 7px;
@ -280,9 +291,39 @@
float: right; float: right;
} }
&-extra-feedback {
color: @gray-dark;
font-size: 0.8rem;
margin-top: 10px;
padding-bottom: 5px;
animation: 0.5s ease-out expand-feedback-area;
overflow: hidden;
&-label {
margin: 5px 0 10px;
padding-top: 5px;
border-top: solid 1px @gray-lighter;
}
.radio {
margin: 5px;
}
textarea {
font-size: 0.8rem;
margin-bottom: 10px;
padding: 5px;
}
input[type="radio"] {
margin-top: 2px;
}
}
& + p { & + p {
margin-top: 20px; margin-top: 20px;
} }
} }
.files-dropdown-container { .files-dropdown-container {