-
Notifications
You must be signed in to change notification settings - Fork 59
Fixed issue #814 - [$100] Topcoder Member Profile: Redesign ratings graph #815
Changes from all commits
7a75dd1
2c3adca
87f0674
8bc8b4b
80f1c47
8799f4d
57f16f2
8803f42
971d353
d5dc2d9
d82a31a
5415f67
414474c
c2331d4
4201416
6cd651a
19eda22
00aea17
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,15 +1,11 @@ | ||
.distribution-graph-directive(ng-show="graphState.show == 'distribution'") | ||
|
||
.graph-viewer | ||
.distribution-graph | ||
.graph-title | ||
.text Rating Distribution Graph | ||
.button-group | ||
button.tc-btn.tc-btn-s(ng-click="graphState.show = 'history'") View Rating History | ||
button.tc-btn.tc-btn-s.active(ng-click="graphState.show = 'distribution'") View Rating Distribution | ||
|
||
.info-port | ||
.coders(ng-if="displayCoders", style="background: {{highlightedRating || rating | ratingColor}}") | ||
.num {{numCoders}} | ||
.label CODERS | ||
.coders(ng-if="!displayCoders", style="background: {{rating | ratingColor}}") | ||
.num {{rating}} | ||
.label RATING | ||
button.tc-btn.tc-btn-s.compare(ng-click="graphState.show = 'history'") | ||
| View Rating History | ||
.graph-viewer | ||
|
||
.distribution-graph |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,9 @@ | ||
import angular from 'angular' | ||
import moment from 'moment' | ||
import d3 from 'd3' | ||
import React from 'react' // eslint-disable-line no-unused-vars | ||
import ReactDOM from 'react-dom' | ||
import Tooltip from 'appirio-tech-react-components/components/Tooltip/Tooltip.jsx' | ||
|
||
(function() { | ||
'use strict' | ||
|
@@ -16,11 +19,11 @@ import d3 from 'd3' | |
rating: '=', | ||
graphState: '=' | ||
}, | ||
controller: ['$scope', HistoryGraphController] | ||
controller: ['$scope', '$state', '$filter', 'CONSTANTS', HistoryGraphController] | ||
} | ||
} | ||
|
||
function HistoryGraphController($scope) { | ||
function HistoryGraphController($scope, $state, $filter, CONSTANTS) { | ||
$scope.colors = [ | ||
// grey | ||
{ | ||
|
@@ -59,7 +62,7 @@ import d3 from 'd3' | |
} | ||
] | ||
var measurements = { | ||
w: 600, | ||
w: 900, | ||
h: 400, | ||
padding: { | ||
top: 20, | ||
|
@@ -156,7 +159,6 @@ import d3 from 'd3' | |
.attr('width', w + padding.left + padding.right) | ||
.attr('height', h + padding.top + padding.bottom) | ||
|
||
|
||
svg.append('rect') | ||
.attr('x', padding.left) | ||
.attr('y', padding.top) | ||
|
@@ -243,7 +245,21 @@ import d3 from 'd3' | |
return y | ||
} | ||
} | ||
|
||
|
||
/* render react tooltip component */ | ||
ReactDOM.unmountComponentAtNode(document.getElementById('chart-tooltip')) | ||
ReactDOM.render(<Tooltip popMethod='click'> | ||
<div className='tooltip-target'></div> | ||
<div className='tooltip-body'> | ||
<div className='tooltip-rating'></div> | ||
<div className='tooltip-challenge'> | ||
<div className='challenge-name'></div> | ||
<div className='challenge-date'></div> | ||
</div> | ||
</div> | ||
</Tooltip> | ||
, document.getElementById('chart-tooltip')) | ||
|
||
svg.selectAll('circle') | ||
.data(history) | ||
.enter() | ||
|
@@ -261,20 +277,44 @@ import d3 from 'd3' | |
$scope.historyRating = d.newRating | ||
$scope.historyDate = moment(d.ratingDate).format('YYYY-MM-DD') | ||
$scope.historyChallenge = d.challengeName | ||
$('#chart-tooltip .tooltip-container').on('click', function(){ | ||
if($state.params && ($state.params.subTrack === 'SRM' || $state.params.subTrack === 'MARATHON_MATCH')) | ||
location.href = $filter('challengeLinks')({'rounds': [{id: d.challengeId, forumId: null}], 'track': $state.params.track, 'subTrack': $state.params.subTrack}, 'detail') | ||
else | ||
location.href = $filter('challengeLinks')({id: d.challengeId, 'track': $state.params.track, 'subTrack': $state.params.subTrack}, 'detail') | ||
}) | ||
|
||
/* update tooltip location on mouseover, feature currently not inbuilt in react tooltip component */ | ||
d3.select('#chart-tooltip') | ||
.style('left', (d3.event.pageX-5) + 'px') | ||
.style('top', (d3.event.pageY-5) + 'px') | ||
d3.select('#chart-tooltip .tooltip-container') | ||
.style('left', '20px !important') | ||
.style('top', '-20px !important') | ||
d3.select('#chart-tooltip .tooltip-container .tooltip-pointer') | ||
.style('left', '-5.5px !important') | ||
.style('bottom', '25px !important') | ||
|
||
d3.select('#chart-tooltip .challenge-name').text($scope.historyChallenge) | ||
d3.select('#chart-tooltip .challenge-date').text(moment(d.ratingDate).format('MMM DD, YYYY')) | ||
d3.select('#chart-tooltip .tooltip-rating').text($scope.historyRating) | ||
d3.select('#chart-tooltip .tooltip-rating').style('background', ratingToColor($scope.colors, $scope.historyRating)) | ||
$('#chart-tooltip').removeClass('distribution') | ||
$scope.$digest() | ||
d3.select(this) | ||
.attr('r', 6.0) | ||
}) | ||
.on('mouseout', function(d) { | ||
$scope.historyRating = undefined | ||
$scope.$digest() | ||
d3.select(this) | ||
.attr('r', 4.5) | ||
.attr('stroke', 'none') | ||
.attr('stroke-width', '0px') | ||
}) | ||
.attr('r', 4.5) | ||
|
||
/* hide tooltip when clicked anywhere outside */ | ||
d3.select('body').on('click', function(){ | ||
if((d3.event.target.classList[0] != 'tooltip-target') && !$('#chart-tooltip .tooltip-container').hasClass('tooltip-hide') && | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think this logic can be simplified to a great extent by using traversing the event.target's parents. What I understood from this code is that you are trying to detected if the mouse is NOT clicked on the tooltip itself, for that, we can iterate the event.target's parents and check if we find the root class of the tooltip i.e. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. @vikasrohit I think there is no parent info for event.target in d3.js, I already tried many options. And we have to use d3.event.target to handle clicks inside the chart. Only, thing is we can optimize condition to shorten it, which I am doing. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Gotcha. Try your best to optimize the condition so that it is more readable. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Also, most of the conditions have different meaning other than the classes inside tooltip, so those can't be optimized more. It is because we have to handle clicks inside d3js svg also. I have done best possible as per my understanding. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Okay. Lets proceed without this optimization thing. Will take care of this after this challenge. |
||
(d3.event.target.tagName.toLowerCase()!='circle') && !(d3.event.target.tagName.toLowerCase()=='rect' && d3.event.target.classList[0] == 'hover')) { | ||
$('#chart-tooltip .tooltip-target').trigger('click') | ||
$('#chart-tooltip .tooltip-container').off('click') | ||
} | ||
}) | ||
|
||
} | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,13 +1,11 @@ | ||
.history-graph-directive(ng-show="graphState.show == 'history'") | ||
.history-graph-container | ||
|
||
.history-graph | ||
.graph-title | ||
.text Rating History Graph | ||
.button-group | ||
button.tc-btn.tc-btn-s.active(ng-click="graphState.show = 'history'") View Rating History | ||
button.tc-btn.tc-btn-s(ng-click="graphState.show = 'distribution'") View Rating Distribution | ||
|
||
.history-graph-container | ||
|
||
.info-port | ||
.rating(style="background: {{historyRating || rating | ratingColor}}") | ||
.num {{historyRating || rating}} | ||
.label RATING | ||
.history-info | ||
.challenge(ng-if="historyRating") {{historyChallenge}} | ||
.date(ng-if="historyRating") {{historyDate | date}} | ||
button.tc-btn.tc-btn-s.compare(ng-click="graphState.show = 'distribution'") View Rating Distribution | ||
.history-graph |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -36,3 +36,5 @@ html | |
.fold-pusher | ||
|
||
div(ui-view="footer") | ||
|
||
#chart-tooltip | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think chart tooltip element does not makes sense in all pages, can we move it to profile page's jade file? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. No, we can't do that as we need it the end of body, to position it relatively to body. Otherwise, it will not display at correct position. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Okay, we would revisit this after this challenge. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Code can be simplified, as suggested in similar place for the history graph.