Skip to content

Commit

Permalink
Merge PR #28 from yooian/pie-chart-hover
Browse files Browse the repository at this point in the history
Add Pie Chart Hover
  • Loading branch information
GeorgeBerdovskiy authored Mar 10, 2024
2 parents 2c58988 + c1eb46f commit 7a3a3dd
Show file tree
Hide file tree
Showing 3 changed files with 49 additions and 110 deletions.
118 changes: 29 additions & 89 deletions app/views/_pie.html.erb
Original file line number Diff line number Diff line change
@@ -1,91 +1,31 @@
<div class="pieContainer">
<div class="pieBackground"></div>
<div id="pie-slice-1" class="hold"><div class="pie"></div></div>
<div id="pie-slice-2" class="hold"><div class="pie"></div></div>
<div id="pie-slice-3" class="hold"><div class="pie"></div></div>
<div id="pie-slice-4" class="hold"><div class="pie"></div></div>
<div id="pie-slice-5" class="hold"><div class="pie"></div></div>
<div id="pie-slice-6" class="hold"><div class="pie"></div></div>
<div class="chart-flex-container" style="width: fit-content">
<div class="pie">
<%# Create svg and align viewbox %>
<svg height="250" width="250" viewBox="0 0 300 300">
<%# Orient first slice at top of circle %>
<circle r="125" cx="150" cy="150" fill="white" />
<%- angle = -90 %>
<%# For each slice, create circle with stroke border, where gap between strokes = circumference (to make 1 slice) %>
<%- data.each_with_index do |object, index| %>
<%# Circle radius should be 1/4 of bg circle dimension %>
<circle class="pie-slice <%= index %>" r='62.5' cx='150' cy='150' fill='none'
stroke="<%= object[:color] %>"
stroke-width='125'
stroke-dasharray='calc(<%= object[:percent_value] %> * 2 * pi * 62.5) calc(2 * pi * 62.5)'
transform='rotate(<%= angle %>, 150, 150)'/>

<circle class="pie-slice-hover" r='135' cx='150' cy='150' fill='none'
stroke="<%= object[:color] %>"
stroke-width='16'
stroke-dasharray='calc(<%= object[:percent_value] %> * 2 * pi * 135) calc(2 * pi * 135)'
stroke-opacity='0'
transform='rotate(<%= angle %>, 150, 150)'/>

<%- angle += 360 * object[:percent_value]%>
<% end %>
</svg>
</div>
<%# Insert the key here %>
</div>

<style>
.pieContainer {
height: 250px;
width: 250px;
position: relative;
}

.pieBackground {
position: absolute;
width: 250px;
height: 250px;
border-radius: 100%;
}

.pie {
transition: all 1s;
position: absolute;
width: 250px;
height: 250px;
border-radius: 100%;
clip: rect(0px, 125px, 250px, 0px);
}

.hold {
position: absolute;
width: 250px;
height: 250px;
border-radius: 100%;
clip: rect(0px, 250px, 250px, 125px);
}

#pie-slice-1 .pie {
background-color: #2ed573;
transform:rotate(30deg);
}

#pie-slice-2 {
transform: rotate(30deg);
}

#pie-slice-2 .pie {
background-color: #ffa502;
transform: rotate(60deg);
}

#pie-slice-3 {
transform: rotate(90deg);
}

#pie-slice-3 .pie {
background-color: #5352ed;
transform: rotate(120deg);
}

#pie-slice-4 {
transform: rotate(210deg);
}

#pie-slice-4 .pie {
background-color: #ff4757;
transform: rotate(10deg);
}

#pie-slice-5 {
transform: rotate(220deg);
}

#pie-slice-5 .pie {
background-color: #1e90ff;
transform: rotate(70deg);
}

#pie-slice-6 {
transform: rotate(290deg);
}

#pie-slice-6 .pie {
background-color: #ff7f50;
transform: rotate(70deg);
}
</style>
<%= render :partial => '/styles' %>
14 changes: 14 additions & 0 deletions app/views/_styles.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,20 @@ h4.purechart {
z-index: 1;
}

.pie {
color: transparent
}

.pie-slice:hover {
stroke-opacity: 0.8;
transition: 0.25s all ease;
}

.pie-slice:hover:nth-child(1n + 0) + .pie-slice-hover:nth-child(1n+0) {
stroke-opacity: 0.25;
transition: 0.05s all ease;
}

.bar-chart-bar {
height: 16px;
}
Expand Down
27 changes: 6 additions & 21 deletions lib/purechart/chart_helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -131,29 +131,14 @@ def pie_chart(data)
data.each do |object|
total_value += object[:value]
end

# Create svg and align viewbox
result = '''<svg height="250" width="250" viewBox="0 0 250 250">
<circle r="125" cx="125" cy="125" fill="white" />'''

# Orient first slice at top of circle
angle = -90

# For each slice, create circle with stroke border, where gap between strokes = circumference (to make 1 slice)
for object in data do
# Circle radius should be 1/4 of bg circle dimension
result += "<circle r='62.5' cx='125' cy='125' fill='transparent'
stroke='#{object[:color]}'
stroke-width='125'
stroke-dasharray='calc(#{object[:value]}/#{total_value} * 2 * pi * 62.5) calc(2 * pi * 62.5)'
transform='rotate(#{angle}, 125, 125)'/>"

# TODO - Fix error accumulated by pie slices (0.5 is temporary offset)
angle += 360 * object[:value] / total_value + 0.5
# Calculate percentages for each data point
data.each do |object|
object[:percent_value] = Float(object[:value]) / total_value
end

result += "</svg>"
result.html_safe
ActionController::Base.render partial: '/pie', locals: {
data: data
}
end

def box_plot(data)
Expand Down

0 comments on commit 7a3a3dd

Please sign in to comment.