Skip to content

Commit

Permalink
Download graph as SVG
Browse files Browse the repository at this point in the history
  • Loading branch information
TheFirstAvenger committed Jun 15, 2024
1 parent eade0ed commit 87ae6c6
Show file tree
Hide file tree
Showing 4 changed files with 52 additions and 31 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

## Next

- Add "Download graph as SVG" feature
- `Phoenix.HTML` 4.0
- Bandit.Pipeline.run as default MFA when available (it's now the default in `mix phx_new`)
- Fix issue with changeset form not honoring initial node
Expand Down
6 changes: 6 additions & 0 deletions lib/flame_on/component.ex
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ defmodule FlameOn.Component do
|> assign(:capture_timed_out?, false)
|> assign(:root_block, root_block)
|> assign(:viewing_block, root_block)
|> assign(:html_render, nil)
|> assign(:view_block_path, [])

{:ok, socket}
Expand All @@ -30,6 +31,10 @@ defmodule FlameOn.Component do
{:ok, socket}
end

def update(%{html_render: html}, socket) do
{:ok, assign(socket, :html_render, html)}
end

def update(assigns, socket) do
target_node = Map.get(assigns, :node, Node.self())
capture_changeset = Map.put(CaptureSchema.changeset(target_node), :action, :validate)
Expand All @@ -45,6 +50,7 @@ defmodule FlameOn.Component do
|> assign(:capture_timed_out?, false)
|> assign(:id, assigns.id)
|> assign(:target_node, target_node)
|> assign(:html_render, nil)
else
socket
end
Expand Down
4 changes: 4 additions & 0 deletions lib/flame_on/component.html.heex
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,10 @@
Capture Timed Out<br />
<% end %>

<%= if @html_render do %>
<a href={"data:image/svg+xml;base64," <> Base.encode64(@html_render)} download="flame_on.svg" target="_blank">Download graph as SVG</a>
<% end %>

<%= if not is_nil(@viewing_block) do %>
<%= if @view_block_path do %>
<%= for %Block{} = block <- @view_block_path do %>
Expand Down
72 changes: 41 additions & 31 deletions lib/flame_on/svg.ex
Original file line number Diff line number Diff line change
Expand Up @@ -12,36 +12,46 @@ defmodule FlameOn.SVG do
|> assign(:block_height, 25)
|> assign(:top_block, top_block)

~H"""
<svg width="1276" height={@block_height * @top_block.max_child_level} style="background-color: white;">
<style>
svg > svg {
cursor: pointer;
}
svg > svg > rect {
stroke: white;
rx: 5px;
}
svg > svg > text {
font-size: <%= @block_height / 2 %>px;
font-family: monospace;
dominant-baseline: middle;
}
</style>
<%= for block <- @blocks do %>
<%= render_flame_on_block(%{
block: block,
block_height: @block_height,
duration_ratio: @duration_ratio,
top_block: @top_block,
parent: @parent,
socket: @socket
}) %>
<% end %>
</svg>
"""
rendered =
~H"""
<svg width="1276" height={@block_height * @top_block.max_child_level} style="background-color: white;" xmlns="http://www.w3.org/2000/svg">
<style>
svg > svg {
cursor: pointer;
}
svg > svg > rect {
stroke: white;
rx: 5px;
}
svg > svg > text {
font-size: <%= @block_height / 2 %>px;
font-family: monospace;
dominant-baseline: middle;
}
</style>
<%= for block <- @blocks do %>
<%= render_flame_on_block(%{
block: block,
block_height: @block_height,
duration_ratio: @duration_ratio,
top_block: @top_block,
parent: @parent,
socket: @socket
}) %>
<% end %>
</svg>
"""

html =
rendered
|> Phoenix.HTML.Safe.to_iodata()
|> IO.iodata_to_binary()

send_update(assigns.parent, html_render: html)

rendered
end

defp render_flame_on_block(%{block: %Block{function: nil}}), do: ""
Expand All @@ -63,7 +73,7 @@ defmodule FlameOn.SVG do
<rect width="100%" height="100%" style={"fill: #{color_for_function(@block.function)};"}></rect>
<text x={@block_height / 4} y={@block_height * 0.5}><%= mfa_to_string(@block.function) %></text>
<title>
<%= format_integer(@block.duration) %>&micro;s (<%= trunc(@block.duration * 100 / @top_block.duration) %>%) <%= mfa_to_string(@block.function) %>
<%= format_integer(@block.duration) %>&#181;s (<%= trunc(@block.duration * 100 / @top_block.duration) %>%) <%= mfa_to_string(@block.function) %>
</title>
</svg>
<% end %>
Expand Down

0 comments on commit 87ae6c6

Please sign in to comment.