forked from enviPath/enviPy
[Feature] Modern UI roll out (#236)
This PR moves all the collection pages into the new UI in a rough push. I did not put the same amount of care into these as into search, index, and predict. ## Major changes - All modals are now migrated to a state based alpine.js implementation. - jQuery is no longer present in the base layout; ajax is replace by native fetch api - most of the pps.js is now obsolte (as I understand it; the code is not referenced any more @jebus please double check) - in-memory pagination for large result lists (set to 50; we can make that configurable later; performance degrades at around 1k) stukk a bit rough tracked in #235 ## Minor things - Sarch and index also use alpine now - The loading spinner is now CSS animated (not sure if it currently gets correctly called) ## Not done - Ihave not even cheked the admin pages. Not sure If these need migrations - The temporary migration pages still use the old template. Not sure what is supposed to happen with those? @jebus ## What I did to test - opend all pages in browse, and user ; plus all pages reachable from there. - Interacted and tested the functionality of each modal superfically with exception of the API key modal (no functional test). --- This PR is massive sorry for that; just did not want to push half-brokenn state. @jebus @liambrydon I would be glad if you could click around and try to break it :) Finally closes #133 Co-authored-by: Tim Lorsbach <tim@lorsba.ch> Reviewed-on: enviPath/enviPy#236 Co-authored-by: Tobias O <tobias.olenyi@envipath.com> Co-committed-by: Tobias O <tobias.olenyi@envipath.com>
This commit is contained in:
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -10,171 +10,146 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="rule-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ rule.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/rule.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ rule.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/rule.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">{{ rule.description|safe }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if rule.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in rule.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ rule.description|safe }}</p>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if rule.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in rule.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Reaction Patterns -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-reaction-patterns-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-reaction-patterns"
|
||||
>Reaction Patterns</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-reaction-patterns" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Reaction Patterns -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reaction Patterns</div>
|
||||
<div class="collapse-content">
|
||||
<div class="space-y-4">
|
||||
{% for r in rule.srs %}
|
||||
<a class="list-group-item" href="{{ r.url }}">{{ r.name|safe }}</a>
|
||||
<div align="center">
|
||||
<p>{{ r.as_svg|safe }}</p>
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<a href="{{ r.url }}" class="link link-primary font-semibold"
|
||||
>{{ r.name }}</a
|
||||
>
|
||||
<div class="mt-2 flex justify-center">{{ r.as_svg|safe }}</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Scenarios -->
|
||||
{% if rule.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Scenarios -->
|
||||
{% if rule.scenarios.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in rule.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if rule.enzymelinks %}
|
||||
<!-- EC Numbers -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-ec-numbers-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-ec-numbers"
|
||||
>EC Numbers</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-ec-numbers" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% if rule.enzymelinks %}
|
||||
<!-- EC Numbers -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">EC Numbers</div>
|
||||
<div class="collapse-content">
|
||||
<div class="space-y-2">
|
||||
{% for k, v in rule.get_grouped_enzymelinks.items %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="{{ k|slugify }}_Link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#{{ k|slugify }}_Accordion"
|
||||
href="#{{ k|slugify }}"
|
||||
>
|
||||
{{ k }}
|
||||
</a>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="{{ k|slugify }}" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for enzyme in v %}
|
||||
<a class="list-group-item" href="{{ enzyme.url }}">
|
||||
{{ enzyme.ec_number }}
|
||||
<div style="position:absolute;bottom:10px;left:100px;">
|
||||
{{ enzyme.name }}
|
||||
</div>
|
||||
<div style="float:right;">
|
||||
{{ enzyme.linking_method }}
|
||||
</div>
|
||||
</a>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">{{ k }}</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for enzyme in v %}
|
||||
<li>
|
||||
<a href="{{ enzyme.url }}" class="hover:bg-base-300">
|
||||
<div class="flex w-full items-center justify-between">
|
||||
<span>{{ enzyme.ec_number }}</span>
|
||||
<span class="text-sm opacity-70"
|
||||
>{{ enzyme.linking_method }}</span
|
||||
>
|
||||
</div>
|
||||
<div class="text-sm opacity-60">
|
||||
{{ enzyme.name }}
|
||||
</div>
|
||||
</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -12,360 +12,261 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="compound-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ compound.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/compound.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ compound.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/compound.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>
|
||||
<p class="mt-2">
|
||||
The structures stored in this compound can be found at
|
||||
<a target="_blank" href="{{ compound.url }}/structure" role="button"
|
||||
<a
|
||||
target="_blank"
|
||||
href="{{ compound.url }}/structure"
|
||||
class="link link-primary"
|
||||
>Compound structures >></a
|
||||
>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if compound.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% if compound.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in compound.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-desc-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-desc"
|
||||
>Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-desc" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ compound.description|safe }}
|
||||
</div>
|
||||
</div>
|
||||
<!-- Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Description</div>
|
||||
<div class="collapse-content">{{ compound.description }}</div>
|
||||
</div>
|
||||
|
||||
<!-- Image -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">
|
||||
{{ compound.default_structure.as_svg|safe }}
|
||||
</div>
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">
|
||||
{{ compound.default_structure.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMILES -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-smiles-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-smiles"
|
||||
>SMILES Representation</a
|
||||
>
|
||||
</h4>
|
||||
<!-- SMILES Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMILES Representation
|
||||
</div>
|
||||
<div id="compound-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ compound.default_structure.smiles }}
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
{{ compound.default_structure.smiles }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Canonical SMILES -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-canonical-smiles-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-canonical-smiles"
|
||||
>Canonical SMILES Representation</a
|
||||
>
|
||||
</h4>
|
||||
<!-- Canonical SMILES Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Canonical SMILES Representation
|
||||
</div>
|
||||
<div id="compound-canonical-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ compound.default_structure.canonical_smiles }}
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
{{ compound.default_structure.canonical_smiles }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- InChiKey -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-inchi-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-inchi"
|
||||
>InChIKey</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-inchi" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ compound.default_structure.inchikey }}
|
||||
</div>
|
||||
<!-- InChIKey -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">InChIKey</div>
|
||||
<div class="collapse-content">
|
||||
{{ compound.default_structure.inchikey }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Reactions -->
|
||||
{% if compound.related_reactions %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-reaction-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-reaction"
|
||||
>Reactions</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-reaction" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Reactions -->
|
||||
{% if compound.related_reactions %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reactions</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in compound.related_reactions %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }} <i>({{ r.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200"
|
||||
>{{ r.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Pathways -->
|
||||
{% if compound.related_pathways %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-pathway-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-pathway"
|
||||
>Pathways</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-pathway" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Pathways -->
|
||||
{% if compound.related_pathways %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Pathways</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in compound.related_pathways %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }} <i>({{ r.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200"
|
||||
>{{ r.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Scenarios -->
|
||||
{% if compound.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Scenarios -->
|
||||
{% if compound.scenarios.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in compound.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- External Identifiers -->
|
||||
{% if compound.get_external_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-external-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-detail"
|
||||
href="#compound-external-identifier"
|
||||
>External Identifier</a
|
||||
>
|
||||
</h4>
|
||||
<!-- External Identifiers -->
|
||||
{% if compound.get_external_identifiers %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
External Identifier
|
||||
</div>
|
||||
<div
|
||||
id="compound-external-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
<div class="panel-body list-group-item">
|
||||
<div class="collapse-content">
|
||||
<div class="space-y-2">
|
||||
{% if compound.get_pubchem_compound_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-pubchem-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-external-identifier"
|
||||
href="#compound-pubchem-identifier"
|
||||
>PubChem Compound Identifier</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="compound-pubchem-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
{% for eid in compound.get_pubchem_compound_identifiers %}
|
||||
<a class="list-group-item" href="{{ eid.external_url }}"
|
||||
>CID{{ eid.identifier_value }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">
|
||||
PubChem Compound Identifier
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for eid in compound.get_pubchem_compound_identifiers %}
|
||||
<li>
|
||||
<a
|
||||
href="{{ eid.external_url }}"
|
||||
class="hover:bg-base-300"
|
||||
>CID{{ eid.identifier_value }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if compound.get_pubchem_substance_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-pubchem-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-external-identifier"
|
||||
href="#compound-pubchem-identifier"
|
||||
>PubChem Substance Identifier</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="compound-pubchem-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
{% for eid in compound.get_pubchem_substance_identifiers %}
|
||||
<a class="list-group-item" href="{{ eid.external_url }}"
|
||||
>SID{{ eid.identifier_value }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">
|
||||
PubChem Substance Identifier
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for eid in compound.get_pubchem_substance_identifiers %}
|
||||
<li>
|
||||
<a
|
||||
href="{{ eid.external_url }}"
|
||||
class="hover:bg-base-300"
|
||||
>SID{{ eid.identifier_value }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if compound.get_chebi_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-chebi-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-external-identifier"
|
||||
href="#compound-chebi-identifier"
|
||||
>ChEBI Identifier</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="compound-chebi-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
{% for eid in compound.get_chebi_identifiers %}
|
||||
<a class="list-group-item" href="{{ eid.external_url }}"
|
||||
>CHEBI:{{ eid.identifier_value }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">
|
||||
ChEBI Identifier
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for eid in compound.get_chebi_identifiers %}
|
||||
<li>
|
||||
<a
|
||||
href="{{ eid.external_url }}"
|
||||
class="hover:bg-base-300"
|
||||
>CHEBI:{{ eid.identifier_value }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -10,141 +10,109 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="compound-structure-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ compound_structure.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/compound_structure.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ compound_structure.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/compound_structure.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">{{ compound_structure.description }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">
|
||||
{{ compound_structure.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMILES Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMILES Representation
|
||||
</div>
|
||||
<div class="collapse-content">{{ compound_structure.smiles }}</div>
|
||||
</div>
|
||||
|
||||
{% if compound_structure.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in compound_structure.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ compound_structure.description|safe }}</p>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Image -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-structure-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-structure-detail"
|
||||
href="#compound-structure-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-structure-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">
|
||||
{{ compound_structure.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMILES -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-structure-smiles-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-structure-detail"
|
||||
href="#compound-structure-smiles"
|
||||
>SMILES Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-structure-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ compound_structure.smiles }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if compound_structure.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-structure-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-structure-detail"
|
||||
href="#compound-structure-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="compound-structure-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in compound_structure.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if compound_structure.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="compound-structure-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#compound-structure-detail"
|
||||
href="#compound-structure-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="compound-structure-scenario"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
<div class="panel-body list-group-item">
|
||||
{% if compound_structure.scenarios.all %}
|
||||
<!-- Scenarios -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in compound_structure.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Reactions -->
|
||||
|
||||
<!-- Pathways -->
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -9,214 +9,165 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="edge-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ edge.edge_label.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/edge.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ edge.edge_label.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/edge.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Description</div>
|
||||
<div class="collapse-content">{{ edge.description }}</div>
|
||||
</div>
|
||||
|
||||
{% if edge.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in edge.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-desc-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-desc"
|
||||
>Description</a
|
||||
>
|
||||
</h4>
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">{{ edge.edge_label.as_svg|safe }}</div>
|
||||
</div>
|
||||
<div id="edge-desc" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ edge.description|safe }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if edge.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in edge.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Image -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">
|
||||
{{ edge.edge_label.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Reaction Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-description-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-description-detail"
|
||||
href="#edge-description-smiles"
|
||||
>Reaction Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-description-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for educt in edge.start_nodes.all %}
|
||||
<a class="btn btn-default" href="{{ educt.url }}"
|
||||
>{{ educt.name|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<span
|
||||
class="glyphicon glyphicon-arrow-right"
|
||||
style="margin-left:5em;margin-right:5em;"
|
||||
aria-hidden="true"
|
||||
></span>
|
||||
{% for product in edge.end_nodes.all %}
|
||||
<a class="btn btn-default" href="{{ product.url }}"
|
||||
>{{ product.name|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMIRKS -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-smirks-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-smirks"
|
||||
>SMIRKS Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-smirks" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ edge.edge_label.smirks }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if edge.edge_label.rules.all %}
|
||||
<!-- Rules -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-rules-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-rules"
|
||||
>Rules</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-rules" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for r in edge.edge_label.rules.all %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if edge.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="edge-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#edge-detail"
|
||||
href="#edge-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="edge-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for s in edge.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<!-- Reaction Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reaction Description</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex flex-wrap items-center justify-center gap-4">
|
||||
{% for educt in edge.start_nodes.all %}
|
||||
<a href="{{ educt.url }}" class="btn btn-outline btn-sm"
|
||||
>{{ educt.name }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="24"
|
||||
height="24"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-arrow-right"
|
||||
>
|
||||
<path d="M5 12h14" />
|
||||
<path d="m12 5 7 7-7 7" />
|
||||
</svg>
|
||||
{% for product in edge.end_nodes.all %}
|
||||
<a href="{{ product.url }}" class="btn btn-outline btn-sm"
|
||||
>{{ product.name }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMIRKS Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMIRKS Representation
|
||||
</div>
|
||||
<div class="collapse-content">{{ edge.edge_label.smirks }}</div>
|
||||
</div>
|
||||
|
||||
{% if edge.edge_label.rules.all %}
|
||||
<!-- Rules -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Rules</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in edge.edge_label.rules.all %}
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200">{{ r.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if edge.scenarios.all %}
|
||||
<!-- Scenarios -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in edge.scenarios.all %}
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,163 +1,109 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
<div class="panel-group" id="enzyme-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ enzymelink.ec_number }}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<h2 class="card-title text-2xl">{{ enzymelink.ec_number }}</h2>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Name -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-name-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-name"
|
||||
>Enzyme Name</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-name" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">{{ enzymelink.name }}</div>
|
||||
</div>
|
||||
<!-- Enzyme Name -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Enzyme Name</div>
|
||||
<div class="collapse-content">{{ enzymelink.name }}</div>
|
||||
</div>
|
||||
|
||||
<!-- Linking Method -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-linking-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-linking"
|
||||
>Linking Method</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-linking" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ enzymelink.linking_method }}. <a
|
||||
href="https://wiki.envipath.org/index.php/Rules#EnzymeLinks"
|
||||
target="#"
|
||||
>Learn more >></a
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if enzymelink.kegg_reaction_links %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
<!-- Linking Method -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Linking Method</div>
|
||||
<div class="collapse-content">
|
||||
{{ enzymelink.linking_method }}. <a
|
||||
href="https://wiki.envipath.org/index.php/Rules#EnzymeLinks"
|
||||
target="_blank"
|
||||
class="link link-primary"
|
||||
>Learn more >></a
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-evidence-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-evidence"
|
||||
>Linking Evidence</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-evidence" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if enzymelink.kegg_reaction_links %}
|
||||
<!-- Linking Evidence -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Linking Evidence</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for kl in enzymelink.kegg_reaction_links %}
|
||||
<a class="list-group-item" href="{{ kl.external_url }}"
|
||||
>{{ kl.identifier_value }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ kl.external_url }}" class="hover:bg-base-200"
|
||||
>{{ kl.identifier_value }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if enzymelink.reaction_evidence.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-reaction-evidence-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-reaction-evidence"
|
||||
>Linking Evidence - enviPath Reactions</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-reaction-evidence" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for r in enzymelink.reaction_evidence.all %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if enzymelink.edge_evidence.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-edge-evidence-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-edge-evidence"
|
||||
>Linking Evidence - enviPath Pathways</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-edge-evidence" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for e in enzymelink.edge_evidence.all %}
|
||||
<a class="list-group-item" href="{{ e.pathway.url }}"
|
||||
>{{ e.pathway.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- External DB Reference -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="enzyme-external-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#enzyme-detail"
|
||||
href="#enzyme-external-identifier"
|
||||
>External DB References</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="enzyme-external-identifier" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<a
|
||||
class="list-group-item"
|
||||
href="http://www.brenda-enzymes.org/enzyme.php?ecno={{ enzymelink.ec_number }}"
|
||||
target="_blank"
|
||||
>
|
||||
Brenda entry for {{ enzymelink.ec_number }}</a
|
||||
>
|
||||
{% endif %}
|
||||
|
||||
{% if enzymelink.reaction_evidence.all %}
|
||||
<!-- Linking Evidence - enviPath Reactions -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Linking Evidence - enviPath Reactions
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in enzymelink.reaction_evidence.all %}
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200"
|
||||
>{{ r.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if enzymelink.edge_evidence.all %}
|
||||
<!-- Linking Evidence - enviPath Pathways -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Linking Evidence - enviPath Pathways
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for e in enzymelink.edge_evidence.all %}
|
||||
<li>
|
||||
<a href="{{ e.pathway.url }}" class="hover:bg-base-200"
|
||||
>{{ e.pathway.name }} <i>({{ e.pathway.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- External DB References -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
External DB References
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<a
|
||||
href="http://www.brenda-enzymes.org/enzyme.php?ecno={{ enzymelink.ec_number }}"
|
||||
target="_blank"
|
||||
class="link link-primary"
|
||||
>Brenda entry for {{ enzymelink.ec_number }}</a
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -8,84 +8,92 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="package-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ group.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/group.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ group.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/group.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ group.description|safe }}</p>
|
||||
<p class="mt-2">{{ group.description }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<p></p>
|
||||
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
id="member-panel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
class="panel-heading"
|
||||
>
|
||||
Members
|
||||
<!-- Members -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<h3 class="card-title mb-4 text-xl">Members</h3>
|
||||
<p class="mb-4">List of members of this group</p>
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for um in group.user_member.all %}
|
||||
<li>
|
||||
<a href="{{ um.url }}" class="hover:bg-base-300"
|
||||
>{{ um.username }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
{% for gm in group.group_member.all %}
|
||||
<li>
|
||||
<a href="{{ gm.url }}" class="hover:bg-base-300">{{ gm.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>List of members of this group</p>
|
||||
</div>
|
||||
<ul class="list-group">
|
||||
{% for um in group.user_member.all %}
|
||||
<a class="list-group-item" href="{{ um.url }}"
|
||||
>{{ um.username|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
{% for gm in group.group_member.all %}
|
||||
<a class="list-group-item" href="{{ gm.url }}">{{ gm.name|safe }}</a>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<p></p>
|
||||
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
id="package-panel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
class="panel-heading"
|
||||
>
|
||||
Packages
|
||||
<!-- Packages -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<h3 class="card-title mb-4 text-xl">Packages</h3>
|
||||
<p class="mb-4">Packages where this group has access to</p>
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for p in packages %}
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-300">{{ p.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>Packages where this group has access to</p>
|
||||
</div>
|
||||
<ul class="list-group">
|
||||
{% for p in packages %}
|
||||
<a class="list-group-item" href="{{ p.url }}">{{ p.name|safe }}</a>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
{% load static %}
|
||||
{% load envipytags %}
|
||||
{% block content %}
|
||||
@ -18,509 +18,458 @@
|
||||
rel="stylesheet"
|
||||
/>
|
||||
|
||||
<div class="panel-group" id="model-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ model.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/model.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ model.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/model.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">{{ model.description }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if model|classname == 'MLRelativeReasoning' or model|classname == 'RuleBasedRelativeReasoning' %}
|
||||
<!-- Rule Packages -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Rule Packages</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box w-full">
|
||||
{% for p in model.rule_packages.all %}
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-200">{{ p.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ model.description|safe }}</p>
|
||||
</div>
|
||||
{% if model|classname == 'MLRelativeReasoning' or model|classname == 'RuleBasedRelativeReasoning' %}
|
||||
<!-- Rule Packages -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-package-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#rule-package"
|
||||
>Rule Packages</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-package" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for p in model.rule_packages.all %}
|
||||
<a class="list-group-item" href="{{ p.url }}"
|
||||
>{{ p.name|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
<!-- Reaction Packages -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-package-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#reaction-package"
|
||||
>Data Packages</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-package" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Reaction Packages -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reaction Packages</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box w-full">
|
||||
{% for p in model.data_packages.all %}
|
||||
<a class="list-group-item" href="{{ p.url }}"
|
||||
>{{ p.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-200">{{ p.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% if model.eval_packages.all|length > 0 %}
|
||||
<!-- Eval Packages -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="eval-package-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#eval-package"
|
||||
>Evaluation Packages</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="eval-package" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
</div>
|
||||
{% if model.eval_packages.all|length > 0 %}
|
||||
<!-- Eval Packages -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Eval Packages</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box w-full">
|
||||
{% for p in model.eval_packages.all %}
|
||||
<a class="list-group-item" href="{{ p.url }}"
|
||||
>{{ p.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-200"
|
||||
>{{ p.name }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
<!-- Model Status -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="model-status-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#model-status"
|
||||
>Model Status</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="model-status" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">{{ model.status }}</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if model.ready_for_prediction %}
|
||||
<!-- Predict Panel -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="predict-smiles-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#predict-smiles"
|
||||
>Predict</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="predict-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div class="input-group">
|
||||
<!-- Model Status -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Model Status</div>
|
||||
<div class="collapse-content">{{ model.status }}</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if model.ready_for_prediction %}
|
||||
<!-- Predict Panel -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Predict</div>
|
||||
<div class="collapse-content">
|
||||
<div class="form-control">
|
||||
<div class="join w-full">
|
||||
<input
|
||||
id="smiles-to-predict"
|
||||
type="text"
|
||||
class="form-control"
|
||||
class="input input-bordered join-item grow"
|
||||
placeholder="CCN(CC)C(=O)C1=CC(=CC=C1)C"
|
||||
/>
|
||||
<span class="input-group-btn">
|
||||
<button
|
||||
class="btn btn-default"
|
||||
type="submit"
|
||||
id="predict-button"
|
||||
>
|
||||
Predict!
|
||||
</button>
|
||||
</span>
|
||||
<button
|
||||
class="btn btn-primary join-item"
|
||||
type="button"
|
||||
id="predict-button"
|
||||
>
|
||||
Predict!
|
||||
</button>
|
||||
</div>
|
||||
<div id="predictLoading"></div>
|
||||
<div id="predictResultTable"></div>
|
||||
</div>
|
||||
<div id="predictLoading" class="mt-2"></div>
|
||||
<div id="predictResultTable" class="mt-4"></div>
|
||||
</div>
|
||||
<!-- End Predict Panel -->
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if model.ready_for_prediction and model.app_domain %}
|
||||
<!-- App Domain -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="app-domain-assessment-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#app-domain-assessment"
|
||||
>Applicability Domain Assessment</a
|
||||
>
|
||||
</h4>
|
||||
{% if model.ready_for_prediction and model.app_domain %}
|
||||
<!-- App Domain -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Applicability Domain Assessment
|
||||
</div>
|
||||
<div id="app-domain-assessment" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div class="input-group">
|
||||
<div class="collapse-content">
|
||||
<div class="form-control">
|
||||
<div class="join w-full">
|
||||
<input
|
||||
id="smiles-to-assess"
|
||||
type="text"
|
||||
class="form-control"
|
||||
class="input input-bordered join-item grow"
|
||||
placeholder="CCN(CC)C(=O)C1=CC(=CC=C1)C"
|
||||
/>
|
||||
<span class="input-group-btn">
|
||||
<button
|
||||
class="btn btn-default"
|
||||
type="submit"
|
||||
id="assess-button"
|
||||
>
|
||||
Assess!
|
||||
</button>
|
||||
</span>
|
||||
</div>
|
||||
<div id="appDomainLoading"></div>
|
||||
<div id="appDomainAssessmentResultTable"></div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- End App Domain -->
|
||||
{% endif %}
|
||||
|
||||
{% if model.model_status == 'FINISHED' %}
|
||||
<!-- Single Gen Curve Panel -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="sg-curve-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#model-detail"
|
||||
href="#sg-curve"
|
||||
>Precision Recall Curve</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="sg-curve" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Center container contents -->
|
||||
<div
|
||||
class="container"
|
||||
style="display: flex;justify-content: center;"
|
||||
>
|
||||
<div id="sg-curve-plotdiv" class="chart">
|
||||
<div id="sg-chart"></div>
|
||||
</div>
|
||||
<button
|
||||
class="btn btn-primary join-item"
|
||||
type="button"
|
||||
id="assess-button"
|
||||
>
|
||||
Assess!
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div id="appDomainLoading" class="mt-2"></div>
|
||||
<div id="appDomainAssessmentResultTable" class="mt-4"></div>
|
||||
</div>
|
||||
{# prettier-ignore-start #}
|
||||
<script>
|
||||
$(function () {
|
||||
if (!($('#sg-chart').length > 0)) {
|
||||
return;
|
||||
}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
var x = ['Recall'];
|
||||
var y = ['Precision'];
|
||||
var thres = ['threshold'];
|
||||
|
||||
// Compare function for the given array
|
||||
function compare(a, b) {
|
||||
if (a.threshold < b.threshold)
|
||||
return -1;
|
||||
else if (a.threshold > b.threshold)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
function getIndexForValue(data, val, val_name) {
|
||||
for (var idx in data) {
|
||||
if (data[idx][val_name] == val) {
|
||||
return idx;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
var data = {{ model.pr_curve|safe }}
|
||||
var dataLength = Object.keys(data).length;
|
||||
data.sort(compare);
|
||||
|
||||
for (var idx in data) {
|
||||
var d = data[idx];
|
||||
x.push(d.recall);
|
||||
y.push(d.precision);
|
||||
thres.push(d.threshold);
|
||||
}
|
||||
var chart = c3.generate({
|
||||
bindto: '#sg-chart',
|
||||
data: {
|
||||
onclick: function (d, e) {
|
||||
var idx = d.index;
|
||||
var thresh = data[dataLength - idx - 1].threshold;
|
||||
|
||||
//onclick(thresh)
|
||||
|
||||
},
|
||||
x: 'Recall',
|
||||
y: 'Precision',
|
||||
columns: [
|
||||
x,
|
||||
y,
|
||||
//thres
|
||||
]
|
||||
},
|
||||
size: {
|
||||
height: 400, // TODO: Make variable to current modal width
|
||||
width: 480
|
||||
},
|
||||
axis: {
|
||||
x: {
|
||||
max: 1,
|
||||
min: 0,
|
||||
label: 'Recall',
|
||||
padding: 0,
|
||||
tick: {
|
||||
fit: true,
|
||||
values: [0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0]
|
||||
}
|
||||
},
|
||||
y: {
|
||||
max: 1,
|
||||
min: 0,
|
||||
label: 'Precision',
|
||||
padding: 0,
|
||||
tick: {
|
||||
fit: true,
|
||||
values: [0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0]
|
||||
}
|
||||
}
|
||||
},
|
||||
point: {
|
||||
r: 4
|
||||
},
|
||||
tooltip: {
|
||||
format: {
|
||||
title: function (recall) {
|
||||
idx = getIndexForValue(data, recall, "recall");
|
||||
if (idx != -1) {
|
||||
return "Threshold: " + data[idx].threshold;
|
||||
}
|
||||
return "";
|
||||
},
|
||||
value: function (precision, ratio, id) {
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
},
|
||||
zoom: {
|
||||
enabled: true
|
||||
}
|
||||
});
|
||||
});
|
||||
</script>
|
||||
{# prettier-ignore-end #}
|
||||
<!-- End Single Gen Curve Panel -->
|
||||
{% endif %}
|
||||
</div>
|
||||
{% if model.model_status == 'FINISHED' %}
|
||||
<!-- Single Gen Curve Panel -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Precision Recall Curve
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">
|
||||
<div id="sg-chart"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
function handlePredictionResponse(data) {
|
||||
res = "<table class='table table-striped'>";
|
||||
res += "<thead>";
|
||||
res += "<th scope='col'>#</th>";
|
||||
{# prettier-ignore-start #}
|
||||
{# FIXME: This is a hack to get the precision recall curve data into the JavaScript code. #}
|
||||
<script>
|
||||
function handlePredictionResponse(data) {
|
||||
let res = "<table class='table table-zebra'>"
|
||||
res += "<thead>"
|
||||
res += "<th scope='col'>#</th>"
|
||||
|
||||
columns = ["products", "image", "probability", "btrule"];
|
||||
const columns = ['products', 'image', 'probability', 'btrule']
|
||||
|
||||
for (col in columns) {
|
||||
res += "<th scope='col'>" + columns[col] + "</th>";
|
||||
}
|
||||
|
||||
res += "</thead>";
|
||||
res += "<tbody>";
|
||||
var cnt = 1;
|
||||
for (transformation in data) {
|
||||
res += "<tr>";
|
||||
res += "<th scope='row'>" + cnt + "</th>";
|
||||
res +=
|
||||
"<th scope='row'>" +
|
||||
data[transformation]["products"][0].join(", ") +
|
||||
"</th>";
|
||||
res +=
|
||||
"<th scope='row'>" +
|
||||
"<img width='400' src='{% url 'depict' %}?smiles=" +
|
||||
encodeURIComponent(data[transformation]["products"][0].join(".")) +
|
||||
"'></th>";
|
||||
res +=
|
||||
"<th scope='row'>" +
|
||||
data[transformation]["probability"].toFixed(3) +
|
||||
"</th>";
|
||||
if (data[transformation]["btrule"] != null) {
|
||||
res +=
|
||||
"<th scope='row'>" +
|
||||
"<a href='" +
|
||||
data[transformation]["btrule"]["url"] +
|
||||
"'>" +
|
||||
data[transformation]["btrule"]["name"] +
|
||||
"</a>" +
|
||||
"</th>";
|
||||
} else {
|
||||
res += "<th scope='row'>N/A</th>";
|
||||
}
|
||||
res += "</tr>";
|
||||
cnt += 1;
|
||||
}
|
||||
|
||||
res += "</tbody>";
|
||||
res += "</table>";
|
||||
$("#predictResultTable").append(res);
|
||||
}
|
||||
|
||||
function clear(divid) {
|
||||
$("#" + divid).removeClass("alert alert-danger");
|
||||
$("#" + divid).empty();
|
||||
}
|
||||
|
||||
if ($("#predict-button").length > 0) {
|
||||
$("#predict-button").on("click", function (e) {
|
||||
e.preventDefault();
|
||||
|
||||
clear("predictResultTable");
|
||||
|
||||
data = {
|
||||
smiles: $("#smiles-to-predict").val(),
|
||||
classify: "ILikeCats!",
|
||||
};
|
||||
|
||||
if (data["smiles"].trim() === "") {
|
||||
$("#predictResultTable").addClass("alert alert-danger");
|
||||
$("#predictResultTable").append(
|
||||
"Please enter a SMILES string to predict!",
|
||||
);
|
||||
return;
|
||||
}
|
||||
|
||||
makeLoadingGif("#predictLoading", "{% static '/images/wait.gif' %}");
|
||||
$.ajax({
|
||||
type: "get",
|
||||
data: data,
|
||||
url: "",
|
||||
success: function (data, textStatus) {
|
||||
try {
|
||||
$("#predictLoading").empty();
|
||||
handlePredictionResponse(data);
|
||||
} catch (error) {
|
||||
$("#predictLoading").empty();
|
||||
$("#predictResultTable").addClass("alert alert-danger");
|
||||
$("#predictResultTable").append(
|
||||
"Error while processing response :/",
|
||||
);
|
||||
for (const col of columns) {
|
||||
res += "<th scope='col'>" + col + "</th>"
|
||||
}
|
||||
res += "</thead>"
|
||||
res += "<tbody>"
|
||||
let cnt = 1;
|
||||
for (const transformation in data) {
|
||||
res += "<tr>"
|
||||
res += "<th scope='row'>" + cnt + "</th>"
|
||||
res += "<th scope='row'>" + data[transformation]['products'][0].join(', ') + "</th>"
|
||||
res += "<th scope='row'>" + "<img width='400' src='{% url 'depict' %}?smiles=" + encodeURIComponent(data[transformation]['products'][0].join('.')) + "'></th>"
|
||||
res += "<th scope='row'>" + data[transformation]['probability'].toFixed(3) + "</th>"
|
||||
if (data[transformation]['btrule'] != null) {
|
||||
res += "<th scope='row'>" + "<a href='" + data[transformation]['btrule']['url'] + "' class='link link-primary'>" + data[transformation]['btrule']['name'] + "</a>" + "</th>"
|
||||
} else {
|
||||
res += "<th scope='row'>N/A</th>"
|
||||
}
|
||||
res += "</tr>"
|
||||
cnt += 1;
|
||||
}
|
||||
},
|
||||
error: function (jqXHR, textStatus, errorThrown, x) {
|
||||
$("#predictLoading").empty();
|
||||
$("#predictResultTable").addClass("alert alert-danger");
|
||||
$("#predictResultTable").append(jqXHR.responseJSON.error);
|
||||
},
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
if ($("#assess-button").length > 0) {
|
||||
$("#assess-button").on("click", function (e) {
|
||||
e.preventDefault();
|
||||
|
||||
clear("appDomainAssessmentResultTable");
|
||||
|
||||
data = {
|
||||
smiles: $("#smiles-to-assess").val(),
|
||||
"app-domain-assessment": "ILikeCats!",
|
||||
};
|
||||
|
||||
if (data["smiles"].trim() === "") {
|
||||
$("#appDomainAssessmentResultTable").addClass("alert alert-danger");
|
||||
$("#appDomainAssessmentResultTable").append(
|
||||
"Please enter a SMILES string to predict!",
|
||||
);
|
||||
return;
|
||||
res += "</tbody>"
|
||||
res += "</table>"
|
||||
const resultTable = document.getElementById("predictResultTable");
|
||||
if (resultTable) {
|
||||
resultTable.innerHTML = res;
|
||||
}
|
||||
}
|
||||
|
||||
makeLoadingGif("#appDomainLoading", "{% static '/images/wait.gif' %}");
|
||||
$.ajax({
|
||||
type: "get",
|
||||
data: data,
|
||||
url: "",
|
||||
success: function (data, textStatus) {
|
||||
try {
|
||||
$("#appDomainLoading").empty();
|
||||
handleAssessmentResponse("{% url 'depict' %}", data);
|
||||
console.log(data);
|
||||
} catch (error) {
|
||||
$("#appDomainLoading").empty();
|
||||
$("#appDomainAssessmentResultTable").addClass(
|
||||
"alert alert-danger",
|
||||
);
|
||||
$("#appDomainAssessmentResultTable").append(
|
||||
"Error while processing response :/",
|
||||
);
|
||||
function clear(divid) {
|
||||
const element = document.getElementById(divid);
|
||||
if (element) {
|
||||
element.classList.remove("alert", "alert-error");
|
||||
element.innerHTML = "";
|
||||
}
|
||||
}
|
||||
|
||||
function makeLoadingGif(selector, gifPath) {
|
||||
const element = document.querySelector(selector);
|
||||
if (element) {
|
||||
element.innerHTML = '<img src="' + gifPath + '" alt="Loading...">';
|
||||
}
|
||||
}
|
||||
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
// Show actions button if there are actions
|
||||
const actionsButton = document.getElementById('actionsButton');
|
||||
const actionsList = actionsButton?.querySelector('ul');
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove('hidden');
|
||||
}
|
||||
|
||||
{% if model.model_status == 'FINISHED' %}
|
||||
// Precision Recall Curve
|
||||
const sgChart = document.getElementById('sg-chart');
|
||||
if (sgChart) {
|
||||
const x = ['Recall'];
|
||||
const y = ['Precision'];
|
||||
const thres = ['threshold'];
|
||||
|
||||
function compare(a, b) {
|
||||
if (a.threshold < b.threshold)
|
||||
return -1;
|
||||
else if (a.threshold > b.threshold)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
function getIndexForValue(data, val, val_name) {
|
||||
for (const idx in data) {
|
||||
if (data[idx][val_name] == val) {
|
||||
return idx;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
var data = {{ model.pr_curve|safe }};
|
||||
if (!data || data.length === 0) {
|
||||
console.warn('PR curve data is empty');
|
||||
return;
|
||||
}
|
||||
const dataLength = data.length;
|
||||
data.sort(compare);
|
||||
|
||||
for (const idx in data) {
|
||||
const d = data[idx];
|
||||
x.push(d.recall);
|
||||
y.push(d.precision);
|
||||
thres.push(d.threshold);
|
||||
}
|
||||
const chart = c3.generate({
|
||||
bindto: '#sg-chart',
|
||||
data: {
|
||||
onclick: function (d, e) {
|
||||
const idx = d.index;
|
||||
const thresh = data[dataLength - idx - 1].threshold;
|
||||
},
|
||||
x: 'Recall',
|
||||
y: 'Precision',
|
||||
columns: [
|
||||
x,
|
||||
y,
|
||||
]
|
||||
},
|
||||
size: {
|
||||
height: 400,
|
||||
width: 480
|
||||
},
|
||||
axis: {
|
||||
x: {
|
||||
max: 1,
|
||||
min: 0,
|
||||
label: 'Recall',
|
||||
padding: 0,
|
||||
tick: {
|
||||
fit: true,
|
||||
values: [0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0]
|
||||
}
|
||||
},
|
||||
y: {
|
||||
max: 1,
|
||||
min: 0,
|
||||
label: 'Precision',
|
||||
padding: 0,
|
||||
tick: {
|
||||
fit: true,
|
||||
values: [0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0]
|
||||
}
|
||||
}
|
||||
},
|
||||
point: {
|
||||
r: 4
|
||||
},
|
||||
tooltip: {
|
||||
format: {
|
||||
title: function (recall) {
|
||||
const idx = getIndexForValue(data, recall, "recall");
|
||||
if (idx != -1) {
|
||||
return "Threshold: " + data[idx].threshold;
|
||||
}
|
||||
return "";
|
||||
},
|
||||
value: function (precision, ratio, id) {
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
},
|
||||
zoom: {
|
||||
enabled: true
|
||||
}
|
||||
});
|
||||
}
|
||||
{% endif %}
|
||||
|
||||
// Predict button handler
|
||||
const predictButton = document.getElementById('predict-button');
|
||||
if (predictButton) {
|
||||
predictButton.addEventListener('click', function(e) {
|
||||
e.preventDefault();
|
||||
|
||||
clear("predictResultTable");
|
||||
|
||||
const smilesInput = document.getElementById('smiles-to-predict');
|
||||
const smiles = smilesInput ? smilesInput.value.trim() : '';
|
||||
|
||||
if (smiles === "") {
|
||||
const resultTable = document.getElementById("predictResultTable");
|
||||
if (resultTable) {
|
||||
resultTable.classList.add("alert", "alert-error");
|
||||
resultTable.innerHTML = "Please enter a SMILES string to predict!";
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
makeLoadingGif("#predictLoading", "{% static '/images/wait.gif' %}");
|
||||
|
||||
const params = new URLSearchParams({
|
||||
smiles: smiles,
|
||||
classify: "ILikeCats!"
|
||||
});
|
||||
|
||||
fetch('?' + params.toString(), {
|
||||
method: 'GET',
|
||||
headers: {
|
||||
'X-CSRFToken': document.querySelector('[name=csrf-token]').content
|
||||
}
|
||||
})
|
||||
.then(response => {
|
||||
if (!response.ok) {
|
||||
return response.json().then(err => { throw err; });
|
||||
}
|
||||
return response.json();
|
||||
})
|
||||
.then(data => {
|
||||
const loadingEl = document.getElementById("predictLoading");
|
||||
if (loadingEl) loadingEl.innerHTML = "";
|
||||
handlePredictionResponse(data);
|
||||
})
|
||||
.catch(error => {
|
||||
const loadingEl = document.getElementById("predictLoading");
|
||||
if (loadingEl) loadingEl.innerHTML = "";
|
||||
const resultTable = document.getElementById("predictResultTable");
|
||||
if (resultTable) {
|
||||
resultTable.classList.add("alert", "alert-error");
|
||||
resultTable.innerHTML = error.error || "Error while processing response :/";
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
// Assess button handler
|
||||
const assessButton = document.getElementById('assess-button');
|
||||
if (assessButton) {
|
||||
assessButton.addEventListener('click', function(e) {
|
||||
e.preventDefault();
|
||||
|
||||
clear("appDomainAssessmentResultTable");
|
||||
|
||||
const smilesInput = document.getElementById('smiles-to-assess');
|
||||
const smiles = smilesInput ? smilesInput.value.trim() : '';
|
||||
|
||||
if (smiles === "") {
|
||||
const resultTable = document.getElementById("appDomainAssessmentResultTable");
|
||||
if (resultTable) {
|
||||
resultTable.classList.add("alert", "alert-error");
|
||||
resultTable.innerHTML = "Please enter a SMILES string to predict!";
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
makeLoadingGif("#appDomainLoading", "{% static '/images/wait.gif' %}");
|
||||
|
||||
const params = new URLSearchParams({
|
||||
smiles: smiles,
|
||||
"app-domain-assessment": "ILikeCats!"
|
||||
});
|
||||
|
||||
fetch('?' + params.toString(), {
|
||||
method: 'GET',
|
||||
headers: {
|
||||
'X-CSRFToken': document.querySelector('[name=csrf-token]').content
|
||||
}
|
||||
})
|
||||
.then(response => {
|
||||
if (!response.ok) {
|
||||
return response.json().then(err => { throw err; });
|
||||
}
|
||||
return response.json();
|
||||
})
|
||||
.then(data => {
|
||||
const loadingEl = document.getElementById("appDomainLoading");
|
||||
if (loadingEl) loadingEl.innerHTML = "";
|
||||
if (typeof handleAssessmentResponse === 'function') {
|
||||
handleAssessmentResponse("{% url 'depict' %}", data);
|
||||
}
|
||||
console.log(data);
|
||||
})
|
||||
.catch(error => {
|
||||
const loadingEl = document.getElementById("appDomainLoading");
|
||||
if (loadingEl) loadingEl.innerHTML = "";
|
||||
const resultTable = document.getElementById("appDomainAssessmentResultTable");
|
||||
if (resultTable) {
|
||||
resultTable.classList.add("alert", "alert-error");
|
||||
resultTable.innerHTML = error.error || "Error while processing response :/";
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
},
|
||||
error: function (jqXHR, textStatus, errorThrown) {
|
||||
$("#appDomainLoading").empty();
|
||||
$("#appDomainAssessmentResultTable").addClass("alert alert-danger");
|
||||
$("#appDomainAssessmentResultTable").append(
|
||||
jqXHR.responseJSON.error,
|
||||
);
|
||||
},
|
||||
});
|
||||
});
|
||||
}
|
||||
</script>
|
||||
</script>
|
||||
{# prettier-ignore-end #}
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -9,167 +9,135 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="node-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ node.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/node.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ node.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/node.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">
|
||||
The underlying structure can be found
|
||||
<a href="{{ node.default_node_label.url }}" class="link link-primary"
|
||||
>here</a
|
||||
>.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Description</div>
|
||||
<div class="collapse-content">{{ node.description }}</div>
|
||||
</div>
|
||||
|
||||
{% if node.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in node.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
The underlying structure can be found
|
||||
<a href="{{ node.default_node_label.url }}">here</a>.
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="node-desc-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#node-detail"
|
||||
href="#node-desc"
|
||||
>Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="node-desc" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ node.description|safe }}
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">
|
||||
{{ node.default_node_label.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if node.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="node-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#node-detail"
|
||||
href="#node-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="node-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in node.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Image -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="node-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#node-detail"
|
||||
href="#node-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="node-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">
|
||||
{{ node.default_node_label.as_svg|safe }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMILES -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="node-smiles-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#node-detail"
|
||||
href="#node-smiles"
|
||||
>SMILES Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="node-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ node.default_node_label.smiles }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if node.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="node-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#node-detail"
|
||||
href="#node-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="node-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for s in node.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if app_domain_assessment_data %}
|
||||
<div id="appDomainAssessmentResultTable"></div>
|
||||
{# prettier-ignore-start #}
|
||||
<script>
|
||||
$(document).ready(function () {
|
||||
handleAssessmentResponse("{% url 'depict' %}", {{ app_domain_assessment_data|safe }})
|
||||
})
|
||||
</script>
|
||||
{# prettier-ignore-end #}
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<!-- SMILES Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMILES Representation
|
||||
</div>
|
||||
<div class="collapse-content">{{ node.default_node_label.smiles }}</div>
|
||||
</div>
|
||||
|
||||
{% if node.scenarios.all %}
|
||||
<!-- Scenarios -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in node.scenarios.all %}
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if app_domain_assessment_data %}
|
||||
<div id="appDomainAssessmentResultTable"></div>
|
||||
{# prettier-ignore-start #}
|
||||
{# FIXME: This is a hack to get the app domain assessment data into the JavaScript code. #}
|
||||
<script>
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
if (typeof handleAssessmentResponse === 'function') {
|
||||
handleAssessmentResponse("{% url 'depict' %}", {{ app_domain_assessment_data|safe }});
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{# prettier-ignore-end #}
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -11,69 +11,87 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="package-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ package.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/package.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ package.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/package.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">{{ package.description|safe }}</p>
|
||||
<ul class="menu bg-base-200 rounded-box mt-4 w-full">
|
||||
<li>
|
||||
<a href="{{ package.url }}/pathway" class="hover:bg-base-300"
|
||||
>Pathways ({{ package.pathways.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="{{ package.url }}/rule" class="hover:bg-base-300"
|
||||
>Rules ({{ package.rules.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="{{ package.url }}/compound" class="hover:bg-base-300"
|
||||
>Compounds ({{ package.compounds.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="{{ package.url }}/reaction" class="hover:bg-base-300"
|
||||
>Reactions ({{ package.reactions.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="{{ package.url }}/model" class="hover:bg-base-300"
|
||||
>Models ({{ package.models.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="{{ package.url }}/scenario" class="hover:bg-base-300"
|
||||
>Scenarios ({{ package.scenarios.count }})</a
|
||||
>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ package.description|safe }}</p>
|
||||
</div>
|
||||
<ul class="list-group">
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/pathway"
|
||||
>Pathways ({{ package.pathways.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/rule">Rules ({{ package.rules.count }})</a>
|
||||
</li>
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/compound"
|
||||
>Compounds ({{ package.compounds.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/reaction"
|
||||
>Reactions ({{ package.reactions.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/model"
|
||||
>Models ({{ package.models.count }})</a
|
||||
>
|
||||
</li>
|
||||
<li class="list-group-item">
|
||||
<a href="{{ package.url }}/scenario"
|
||||
>Scenarios ({{ package.scenarios.count }})</a
|
||||
>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
{% load static %}
|
||||
{% block content %}
|
||||
<script src="https://d3js.org/d3.v7.min.js"></script>
|
||||
@ -7,6 +7,7 @@
|
||||
width: 100%;
|
||||
height: 600px;
|
||||
background: white;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#pwsvg {
|
||||
@ -18,6 +19,7 @@
|
||||
.link {
|
||||
stroke: #999;
|
||||
stroke-opacity: 0.6;
|
||||
/* marker-end: url(#arrow); */
|
||||
}
|
||||
|
||||
.link_no_arrow {
|
||||
@ -63,15 +65,6 @@
|
||||
stroke: red;
|
||||
stroke-width: 3px;
|
||||
}
|
||||
|
||||
.tooltip {
|
||||
position: absolute;
|
||||
background: lightgrey;
|
||||
padding: 5px;
|
||||
border-radius: 5px;
|
||||
visibility: hidden;
|
||||
opacity: 1;
|
||||
}
|
||||
</style>
|
||||
<script src="{% static 'js/pw.js' %}"></script>
|
||||
|
||||
@ -90,141 +83,217 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<p></p>
|
||||
<div id="pwcontent">
|
||||
<div class="panel-group" id="pwAccordion">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ pathway.name|safe }}
|
||||
</div>
|
||||
</div>
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="vizLink"
|
||||
data-toggle="collapse"
|
||||
data-parent="#pwAccordion"
|
||||
href="#viz"
|
||||
>
|
||||
Graphical Representation
|
||||
</a>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="viz" class="panel-collapse in collapse">
|
||||
<nav role="navigation" class="navbar navbar-default" style="margin: 0;">
|
||||
<div class="navbar-header"></div>
|
||||
<div id="editbarCollapse" class="navbar-collapse collapse">
|
||||
<ul class="nav navbar-nav">
|
||||
<li class="dropdown requiresWritePerm">
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
>
|
||||
<span class="glyphicon glyphicon-edit"></span>
|
||||
Edit
|
||||
<span class="caret"></span
|
||||
></a>
|
||||
<ul id="editingList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/pathway.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</li>
|
||||
{% if pathway.setting.model.app_domain %}
|
||||
<li class="dropdown">
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
>
|
||||
<span class="glyphicon glyphicon-eye-open"></span>
|
||||
View
|
||||
<span class="caret"></span
|
||||
></a>
|
||||
<ul id="editingList" class="dropdown-menu">
|
||||
<li>
|
||||
<a class="button" id="app-domain-toggle-button">
|
||||
<i
|
||||
id="app-domain-toggle-button"
|
||||
class="glyphicon glyphicon-eye-open"
|
||||
></i>
|
||||
App Domain View</a
|
||||
>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
{% endif %}
|
||||
</ul>
|
||||
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
<li>
|
||||
<a
|
||||
role="button"
|
||||
data-toggle="modal"
|
||||
onclick="goFullscreen('vizdiv')"
|
||||
>
|
||||
<span class="glyphicon glyphicon-fullscreen"></span>
|
||||
Fullscreen
|
||||
</a>
|
||||
</li>
|
||||
<li>
|
||||
{% if pathway.completed %}
|
||||
<button
|
||||
type="button"
|
||||
class="btn btn-default navbar-btn"
|
||||
data-toggle="popover"
|
||||
id="status"
|
||||
data-original-title=""
|
||||
title=""
|
||||
data-content="Pathway prediction complete."
|
||||
>
|
||||
<span class="glyphicon glyphicon-ok"></span>
|
||||
</button>
|
||||
{% elif pathway.failed %}
|
||||
<button
|
||||
type="button"
|
||||
class="btn btn-default navbar-btn"
|
||||
data-toggle="popover"
|
||||
id="status"
|
||||
data-original-title=""
|
||||
title=""
|
||||
data-content="Pathway prediction failed."
|
||||
>
|
||||
<span class="glyphicon glyphicon-remove"></span>
|
||||
</button>
|
||||
{% else %}
|
||||
<button
|
||||
type="button"
|
||||
class="btn btn-default navbar-btn"
|
||||
data-toggle="popover"
|
||||
id="status"
|
||||
data-original-title=""
|
||||
title=""
|
||||
data-content="Pathway prediction running."
|
||||
>
|
||||
<img height="20" src="{% static '/images/wait.gif' %}" />
|
||||
</button>
|
||||
{% endif %}
|
||||
|
||||
</li>
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ pathway.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/pathway.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</nav>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Graphical Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Graphical Representation
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<div class="bg-base-100 mb-2 rounded-lg p-2">
|
||||
<div class="navbar bg-base-100 rounded-lg">
|
||||
<div class="flex-1">
|
||||
{% if meta.can_edit %}
|
||||
<div class="dropdown">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-edit"
|
||||
>
|
||||
<path
|
||||
d="M11 4H4a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-7"
|
||||
/>
|
||||
<path
|
||||
d="M18.5 2.5a2.121 2.121 0 0 1 3 3L12 15l-4 1 1-4 9.5-9.5z"
|
||||
/>
|
||||
</svg>
|
||||
Edit
|
||||
</div>
|
||||
<ul
|
||||
tabindex="0"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% include "actions/objects/pathway.html" %}
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if pathway.setting.model.app_domain %}
|
||||
<div class="dropdown">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-eye"
|
||||
>
|
||||
<path d="M2 12s3-7 10-7 10 7 10 7-3 7-10 7-10-7-10-7Z" />
|
||||
<circle cx="12" cy="12" r="3" />
|
||||
</svg>
|
||||
View
|
||||
</div>
|
||||
<ul
|
||||
tabindex="0"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
<li>
|
||||
<a id="app-domain-toggle-button" class="cursor-pointer">
|
||||
<svg
|
||||
id="app-domain-icon"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-eye"
|
||||
>
|
||||
<path
|
||||
d="M2 12s3-7 10-7 10 7 10 7-3 7-10 7-10-7-10-7Z"
|
||||
/>
|
||||
<circle cx="12" cy="12" r="3" />
|
||||
</svg>
|
||||
App Domain View
|
||||
</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
<div class="flex-none gap-2">
|
||||
<button
|
||||
class="btn btn-ghost btn-sm"
|
||||
onclick="goFullscreen('vizdiv')"
|
||||
>
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-maximize"
|
||||
>
|
||||
<path
|
||||
d="M8 3H5a2 2 0 0 0-2 2v3m18 0V5a2 2 0 0 0-2-2h-3m0 18h3a2 2 0 0 0 2-2v-3M3 16v3a2 2 0 0 0 2 2h3"
|
||||
/>
|
||||
</svg>
|
||||
Fullscreen
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div id="vizdiv">
|
||||
{% if pathway.completed %}
|
||||
<div class="tooltip tooltip-bottom absolute top-4 right-4 z-10">
|
||||
<div class="tooltip-content">Pathway prediction complete.</div>
|
||||
<div id="status" class="flex items-center">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-check"
|
||||
>
|
||||
<path d="M20 6 9 17l-5-5" />
|
||||
</svg>
|
||||
</div>
|
||||
</div>
|
||||
{% elif pathway.failed %}
|
||||
<div class="tooltip tooltip-bottom absolute top-4 right-4 z-10">
|
||||
<div class="tooltip-content">Pathway prediction failed.</div>
|
||||
<div id="status" class="flex items-center">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-x"
|
||||
>
|
||||
<path d="M18 6 6 18" />
|
||||
<path d="M6 6l12 12" />
|
||||
</svg>
|
||||
</div>
|
||||
</div>
|
||||
{% else %}
|
||||
<div class="tooltip tooltip-bottom absolute top-4 right-4 z-10">
|
||||
<div class="tooltip-content">Pathway prediction running.</div>
|
||||
<div id="status" class="flex items-center">
|
||||
<div
|
||||
id="status-loading-spinner"
|
||||
style="width: 20px; height: 20px;"
|
||||
></div>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
<svg id="pwsvg">
|
||||
<defs>
|
||||
<marker
|
||||
@ -266,184 +335,137 @@
|
||||
</defs>
|
||||
<g id="zoomable"></g>
|
||||
</svg>
|
||||
<div id="tooltip" class="tooltip"></div>
|
||||
</div>
|
||||
</div>
|
||||
<!-- Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="DescriptionLink"
|
||||
data-toggle="collapse"
|
||||
data-parent="#pathwayAccordion"
|
||||
href="#Description"
|
||||
>Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="Description" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item" id="DescriptionContent">
|
||||
{{ pathway.description | safe }}
|
||||
<div id="tooltip" class="tooltip-content"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if pathway.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="pathway-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#pathway-detail"
|
||||
href="#pathway-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="pathway-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Description</div>
|
||||
<div class="collapse-content">
|
||||
<div id="DescriptionContent">{{ pathway.description | safe }}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if pathway.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in pathway.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if pathway.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="pathway-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#pathway-detail"
|
||||
href="#pathway-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="pathway-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% if pathway.scenarios.all %}
|
||||
<!-- Scenarios -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in pathway.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200">
|
||||
{{ s.name }}
|
||||
<span class="text-sm opacity-70">({{ s.package.name }})</span>
|
||||
</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if pathway.setting %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="pathwaySettingLink"
|
||||
data-toggle="collapse"
|
||||
data-parent="#pathwayAccordion"
|
||||
href="#pathwaySetting"
|
||||
>Setting</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="pathwaySetting" class="panel-collapse collapse">
|
||||
<div class="panel-body list-group-item" id="pathwaySettingContent">
|
||||
<table class="table-bordered table-hover table">
|
||||
<tr style="background-color: rgba(0, 0, 0, 0.08);">
|
||||
<th scope="col" width="20%">Parameter</th>
|
||||
<th scope="col" width="80%">Value</th>
|
||||
</tr>
|
||||
{% if pathway.setting %}
|
||||
<!-- Setting -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" />
|
||||
<div class="collapse-title text-xl font-medium">Setting</div>
|
||||
<div class="collapse-content">
|
||||
<div class="overflow-x-auto">
|
||||
<table class="table-zebra table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Parameter</th>
|
||||
<th>Value</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% if pathway.setting.model %}
|
||||
<tr>
|
||||
<td width="20%">Model</td>
|
||||
<td width="80%">
|
||||
<table
|
||||
width="100%"
|
||||
class="table-bordered table-hover table"
|
||||
>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
<li class="list-group-item">
|
||||
<a href="{{ pathway.setting.model.url }}">
|
||||
{{ pathway.setting.model.name|safe }}
|
||||
</a>
|
||||
</li>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th width="20%">Model Parameter</th>
|
||||
<th width="80%">Parameter Value</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td width="20%">Threshold</td>
|
||||
<td width="80%">
|
||||
{{ pathway.setting.model_threshold }}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<td>Model</td>
|
||||
<td>
|
||||
<div class="space-y-2">
|
||||
<div>
|
||||
<a
|
||||
href="{{ pathway.setting.model.url }}"
|
||||
class="link link-primary"
|
||||
>
|
||||
{{ pathway.setting.model.name }}
|
||||
</a>
|
||||
</div>
|
||||
<div class="overflow-x-auto">
|
||||
<table class="table-xs table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Model Parameter</th>
|
||||
<th>Parameter Value</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>Threshold</td>
|
||||
<td>{{ pathway.setting.model_threshold }}</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
{% if pathway.setting.rule_packages.all %}
|
||||
<tr>
|
||||
<td width="20%">Rule Packages</td>
|
||||
<td width="80%">
|
||||
<table
|
||||
width="100%"
|
||||
class="table-bordered table-hover table"
|
||||
>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
{% for p in pathway.setting.rule_packages.all %}
|
||||
<li class="list-group-item">
|
||||
<a href="{{ p.url }}"> {{ p.name|safe }} </a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<td>Rule Packages</td>
|
||||
<td>
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for p in pathway.setting.rule_packages.all %}
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-200"
|
||||
>{{ p.name }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
<tr>
|
||||
<td>
|
||||
<p>Max Nodes</p>
|
||||
</td>
|
||||
<td>
|
||||
<p>{{ pathway.setting.max_nodes }}</p>
|
||||
</td>
|
||||
<td>Max Nodes</td>
|
||||
<td>{{ pathway.setting.max_nodes }}</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<p>Max Depth</p>
|
||||
</td>
|
||||
<td>
|
||||
<p>{{ pathway.setting.max_depth }}</p>
|
||||
</td>
|
||||
<td>Max Depth</td>
|
||||
<td>{{ pathway.setting.max_depth }}</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{# prettier-ignore-start #}
|
||||
{# FIXME: This is a hack to get the pathway data into the JavaScript code. #}
|
||||
|
||||
<script>
|
||||
// Global switch for app domain view
|
||||
var appDomainViewEnabled = false;
|
||||
@ -461,15 +483,17 @@
|
||||
return text.replace(/\[\s*(http[^\]|]+)\s*\|\s*([^\]]+)\s*\]/g, '<a target="parent" href="$1">$2</a>');
|
||||
}
|
||||
|
||||
pathway = {{ pathway.d3_json | safe }};
|
||||
|
||||
$(function () {
|
||||
var pathway = {{ pathway.d3_json | safe }};
|
||||
|
||||
$('#status').popover({
|
||||
trigger: 'manual',
|
||||
placement: 'bottom',
|
||||
html: true
|
||||
});
|
||||
document.addEventListener('DOMContentLoaded', function() {
|
||||
// Initialize loading spinner if pathway is running
|
||||
if (pathway.status === 'running') {
|
||||
const spinnerContainer = document.getElementById('status-loading-spinner');
|
||||
if (spinnerContainer) {
|
||||
showLoadingSpinner(spinnerContainer);
|
||||
}
|
||||
}
|
||||
|
||||
// If prediction is still running, regularly check status
|
||||
if (pathway.status === 'running') {
|
||||
@ -481,29 +505,32 @@
|
||||
const data = await response.json();
|
||||
|
||||
if (data.modified > last_modified) {
|
||||
var msg = 'Prediction '
|
||||
var btn = '<button type="button" onclick="location.reload()" class="btn btn-primary" id="reloadBtn">Reload page</button>'
|
||||
var msg = 'Prediction ';
|
||||
var btn = '<button type="button" onclick="location.reload()" class="btn btn-primary btn-sm mt-2" id="reloadBtn">Reload page</button>';
|
||||
|
||||
if (data.status === "running") {
|
||||
msg += 'is still running. But the Pathway was updated.<br>' + btn;
|
||||
|
||||
} else if (data.status === "completed") {
|
||||
msg += 'is completed. Reload the page to see the updated Pathway.<br>' + btn;
|
||||
} else if (data.status === "failed") {
|
||||
msg += 'failed. Reload the page to see the current shape<br>' + btn;
|
||||
msg += 'failed. Reload the page to see the current shape.<br>' + btn;
|
||||
}
|
||||
|
||||
$('#status').attr(
|
||||
'data-content', msg
|
||||
).popover('show');
|
||||
showStatusPopover(msg);
|
||||
}
|
||||
|
||||
if (data.status === "completed" || data.status === "failed") {
|
||||
$('#status img').remove();
|
||||
const statusBtn = document.getElementById('status');
|
||||
const tooltipContent = statusBtn.parentElement.querySelector('.tooltip-content');
|
||||
const spinner = statusBtn.querySelector('#status-loading-spinner');
|
||||
if (spinner) spinner.remove();
|
||||
|
||||
if (data.status === "completed") {
|
||||
$('#status').append('<span class="glyphicon glyphicon-ok"></span>')
|
||||
statusBtn.innerHTML = `<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-check"><path d="M20 6 9 17l-5-5"/></svg>`;
|
||||
tooltipContent.textContent = 'Pathway prediction complete.';
|
||||
} else {
|
||||
$('#status').append('<span class="glyphicon glyphicon-remove"></span>')
|
||||
statusBtn.innerHTML = `<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-x"><path d="M18 6 6 18"/><path d="M6 6l12 12"/></svg>`;
|
||||
tooltipContent.textContent = 'Pathway prediction failed.';
|
||||
}
|
||||
clearInterval(pollInterval);
|
||||
}
|
||||
@ -515,54 +542,68 @@
|
||||
}
|
||||
|
||||
draw(pathway, 'vizdiv');
|
||||
// TODO fix somewhere else...
|
||||
var newDesc = transformReferences($('#DescriptionContent')[0].innerText);
|
||||
$('#DescriptionContent').html(newDesc);
|
||||
|
||||
// Transform references in description
|
||||
const descContent = document.getElementById('DescriptionContent');
|
||||
if (descContent) {
|
||||
const newDesc = transformReferences(descContent.innerText);
|
||||
descContent.innerHTML = newDesc;
|
||||
}
|
||||
|
||||
$('#app-domain-toggle-button').on('click', function () {
|
||||
// glyphicon glyphicon-eye-close
|
||||
// glyphicon glyphicon-eye-open
|
||||
appDomainViewEnabled = !appDomainViewEnabled;
|
||||
// App domain toggle
|
||||
const appDomainBtn = document.getElementById('app-domain-toggle-button');
|
||||
if (appDomainBtn) {
|
||||
appDomainBtn.addEventListener('click', function() {
|
||||
appDomainViewEnabled = !appDomainViewEnabled;
|
||||
const icon = document.getElementById('app-domain-icon');
|
||||
|
||||
if (appDomainViewEnabled) {
|
||||
$('#app-domain-toggle-button > i').removeClass('glyphicon-eye-open');
|
||||
$('#app-domain-toggle-button > i').addClass('glyphicon-eye-close');
|
||||
nodes.forEach((x) => {
|
||||
if(x.app_domain) {
|
||||
if (x.app_domain.inside_app_domain) {
|
||||
d3.select(x.el).select("circle").classed("inside_app_domain", true);
|
||||
} else {
|
||||
d3.select(x.el).select("circle").classed("outside_app_domain", true);
|
||||
if (appDomainViewEnabled) {
|
||||
// Change to eye-off icon
|
||||
icon.innerHTML = '<path d="M9.88 9.88a3 3 0 1 0 4.24 4.24"/><path d="M10.73 5.08A10.43 10.43 0 0 1 12 5c7 0 10 7 10 7a13.16 13.16 0 0 1-1.67 2.68"/><path d="M6.61 6.61A13.526 13.526 0 0 0 2 12s3 7 10 7a9.74 9.74 0 0 0 5.39-1.61"/><line x1="2" x2="22" y1="2" y2="22"/>';
|
||||
|
||||
nodes.forEach((x) => {
|
||||
if(x.app_domain) {
|
||||
if (x.app_domain.inside_app_domain) {
|
||||
d3.select(x.el).select("circle").classed("inside_app_domain", true);
|
||||
} else {
|
||||
d3.select(x.el).select("circle").classed("outside_app_domain", true);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
links.forEach((x) => {
|
||||
if(x.app_domain) {
|
||||
if (x.app_domain.passes_app_domain) {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow_passes_app_domain)");
|
||||
d3.select(x.el).classed("passes_app_domain", true);
|
||||
} else {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow_fails_app_domain)");
|
||||
d3.select(x.el).classed("fails_app_domain", true);
|
||||
});
|
||||
links.forEach((x) => {
|
||||
if(x.app_domain) {
|
||||
if (x.app_domain.passes_app_domain) {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow_passes_app_domain)");
|
||||
d3.select(x.el).classed("passes_app_domain", true);
|
||||
} else {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow_fails_app_domain)");
|
||||
d3.select(x.el).classed("fails_app_domain", true);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
} else {
|
||||
$('#app-domain-toggle-button > i').removeClass('glyphicon-eye-close');
|
||||
$('#app-domain-toggle-button > i').addClass('glyphicon-eye-open');
|
||||
nodes.forEach((x) => {
|
||||
d3.select(x.el).select("circle").classed("inside_app_domain", false);
|
||||
d3.select(x.el).select("circle").classed("outside_app_domain", false);
|
||||
});
|
||||
links.forEach((x) => {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow)");
|
||||
d3.select(x.el).classed("passes_app_domain", false);
|
||||
d3.select(x.el).classed("fails_app_domain", false);
|
||||
});
|
||||
}
|
||||
})
|
||||
});
|
||||
} else {
|
||||
// Change back to eye icon
|
||||
icon.innerHTML = '<path d="M2 12s3-7 10-7 10 7 10 7-3 7-10 7-10-7-10-7Z"/><circle cx="12" cy="12" r="3"/>';
|
||||
|
||||
nodes.forEach((x) => {
|
||||
d3.select(x.el).select("circle").classed("inside_app_domain", false);
|
||||
d3.select(x.el).select("circle").classed("outside_app_domain", false);
|
||||
});
|
||||
links.forEach((x) => {
|
||||
d3.select(x.el).attr("marker-end", d => d.target.pseudo ? "" : "url(#arrow)");
|
||||
d3.select(x.el).classed("passes_app_domain", false);
|
||||
d3.select(x.el).classed("fails_app_domain", false);
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// Show actions button if there are actions
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
|
||||
</script>
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -11,343 +11,257 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="reaction-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ reaction.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/reaction.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ reaction.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/reaction.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Description</div>
|
||||
<div class="collapse-content">{{ reaction.description }}</div>
|
||||
</div>
|
||||
|
||||
{% if reaction.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in reaction.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-desc-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-desc"
|
||||
>Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-desc" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{{ reaction.description|safe }}
|
||||
</div>
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">{{ reaction.as_svg|safe }}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if reaction.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in reaction.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Image -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">{{ reaction.as_svg|safe }}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Reaction Description -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-description-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-description-detail"
|
||||
href="#reaction-description-smiles"
|
||||
>Reaction Description</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-description-smiles" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Reaction Description -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reaction Description</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex flex-wrap items-center justify-center gap-4">
|
||||
{% for educt in reaction.educts.all %}
|
||||
<a class="btn btn-default" href="{{ educt.url }}"
|
||||
>{{ educt.name|safe }}</a
|
||||
<a href="{{ educt.url }}" class="btn btn-outline btn-sm"
|
||||
>{{ educt.name }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<span
|
||||
class="glyphicon glyphicon-arrow-right"
|
||||
style="margin-left:5em;margin-right:5em;"
|
||||
aria-hidden="true"
|
||||
></span>
|
||||
{% for product in reaction.products.all %}
|
||||
<a class="btn btn-default" href="{{ product.url }}"
|
||||
>{{ product.name|safe }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMIRKS -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-smirks-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-smirks"
|
||||
>SMIRKS Representation</a
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="24"
|
||||
height="24"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-arrow-right"
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-smirks" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">{{ reaction.smirks }}</div>
|
||||
</div>
|
||||
|
||||
{% if reaction.rules.all %}
|
||||
<!-- Rules -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-rules-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-rules"
|
||||
>Rules</a
|
||||
<path d="M5 12h14" />
|
||||
<path d="m12 5 7 7-7 7" />
|
||||
</svg>
|
||||
{% for product in reaction.products.all %}
|
||||
<a href="{{ product.url }}" class="btn btn-outline btn-sm"
|
||||
>{{ product.name }}</a
|
||||
>
|
||||
</h4>
|
||||
{% endfor %}
|
||||
</div>
|
||||
<div id="reaction-rules" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMIRKS Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMIRKS Representation
|
||||
</div>
|
||||
<div class="collapse-content">{{ reaction.smirks }}</div>
|
||||
</div>
|
||||
|
||||
<!-- Rules -->
|
||||
{% if reaction.rules.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Rules</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in reaction.rules.all %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200">{{ r.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if reaction.get_related_enzymes %}
|
||||
<!-- EC Numbers -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-ec-numbers-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-ec-numbers"
|
||||
>EC Numbers</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-ec-numbers" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- EC Numbers -->
|
||||
{% if reaction.get_related_enzymes %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">EC Numbers</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for e in reaction.get_related_enzymes %}
|
||||
<a
|
||||
class="list-group-item"
|
||||
href="http://www.brenda-enzymes.org/enzyme.php?ecno={{ e.ec_number }}"
|
||||
>{{ e.name }}</a
|
||||
>
|
||||
<li>
|
||||
<a
|
||||
href="http://www.brenda-enzymes.org/enzyme.php?ecno={{ e.ec_number }}"
|
||||
class="hover:bg-base-200"
|
||||
>{{ e.name }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if reaction.related_pathways %}
|
||||
<!-- Pathways -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-pathway-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-pathway"
|
||||
>Pathways</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-pathway" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Pathways -->
|
||||
{% if reaction.related_pathways %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Pathways</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in reaction.related_pathways %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200"
|
||||
>{{ r.name }} <i>({{ r.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if reaction.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="reaction-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Scenarios -->
|
||||
{% if reaction.scenarios.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in reaction.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }} <i>({{ s.package.name|safe }})</i></a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200"
|
||||
>{{ s.name }} <i>({{ s.package.name }})</i></a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- External Identifiers -->
|
||||
{% if reaction.get_external_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-external-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-detail"
|
||||
href="#reaction-external-identifier"
|
||||
>External Identifier</a
|
||||
>
|
||||
</h4>
|
||||
<!-- External Identifiers -->
|
||||
{% if reaction.get_external_identifiers %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
External Identifier
|
||||
</div>
|
||||
<div
|
||||
id="reaction-external-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
<div class="panel-body list-group-item">
|
||||
<div class="collapse-content">
|
||||
<div class="space-y-2">
|
||||
{% if reaction.get_rhea_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-rhea-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-external-identifier"
|
||||
href="#reaction-rhea-identifier"
|
||||
>Rhea</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="reaction-rhea-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
{% for eid in reaction.get_rhea_identifiers %}
|
||||
<a class="list-group-item" href="{{ eid.external_url }}"
|
||||
>{{ eid.identifier_value }}</a
|
||||
>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">Rhea</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for eid in reaction.get_rhea_identifiers %}
|
||||
<li>
|
||||
<a
|
||||
href="{{ eid.external_url }}"
|
||||
class="hover:bg-base-300"
|
||||
>{{ eid.identifier_value }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if reaction.get_uniprot_identifiers %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="reaction-uniprot-identifier-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#reaction-external-identifier"
|
||||
href="#reaction-uniprot-identifier"
|
||||
>UniProt</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="reaction-uniprot-identifier"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
{% for eid in reaction.get_uniprot_identifiers %}
|
||||
<a class="list-group-item" href="{{ eid.external_url }}"
|
||||
>10 SwissProt entries ({{ eid.identifier_value }})</a
|
||||
>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">UniProt</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for eid in reaction.get_uniprot_identifiers %}
|
||||
<li>
|
||||
<a
|
||||
href="{{ eid.external_url }}"
|
||||
class="hover:bg-base-300"
|
||||
>10 SwissProt entries ({{ eid.identifier_value }})</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -7,115 +7,169 @@
|
||||
{% include "modals/objects/update_scenario_additional_information_modal.html" %}
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
<div class="panel-group" id="scenario-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ scenario.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/scenario.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ scenario.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/scenario.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Description -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<h3 class="card-title mb-2 text-lg">Description</h3>
|
||||
<p>{{ scenario.description }}</p>
|
||||
<p class="mt-2"><strong>Type:</strong> {{ scenario.scenario_type }}</p>
|
||||
<p><strong>Reported:</strong> {{ scenario.scenario_date }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Additional Information Table -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<h3 class="card-title mb-4 text-lg">Additional Information</h3>
|
||||
<div class="overflow-x-auto">
|
||||
<table class="table-zebra table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Property</th>
|
||||
<th>Value</th>
|
||||
<th>Unit</th>
|
||||
{% if meta.can_edit %}
|
||||
<th>Remove</th>
|
||||
{% endif %}
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for ai in scenario.get_additional_information %}
|
||||
<tr>
|
||||
<td>{{ ai.property_name|safe }}</td>
|
||||
<td>{{ ai.property_data|safe }}</td>
|
||||
<td>{{ ai.property_unit|safe }}</td>
|
||||
{% if meta.can_edit %}
|
||||
<td>
|
||||
<form
|
||||
action="{% url 'package scenario detail' scenario.package.uuid scenario.uuid %}"
|
||||
method="post"
|
||||
>
|
||||
{% csrf_token %}
|
||||
<input
|
||||
type="hidden"
|
||||
name="uuid"
|
||||
value="{{ ai.uuid }}"
|
||||
/>
|
||||
<input
|
||||
type="hidden"
|
||||
name="hidden"
|
||||
value="delete-additional-information"
|
||||
/>
|
||||
<button type="submit" class="btn btn-sm btn-ghost">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-minus"
|
||||
>
|
||||
<path d="M5 12h14" />
|
||||
</svg>
|
||||
</button>
|
||||
</form>
|
||||
</td>
|
||||
{% endif %}
|
||||
</tr>
|
||||
{% endfor %}
|
||||
{% if meta.can_edit %}
|
||||
<tr>
|
||||
<td></td>
|
||||
<td></td>
|
||||
<td>Delete all</td>
|
||||
<td>
|
||||
<form
|
||||
action="{% url 'package scenario detail' scenario.package.uuid scenario.uuid %}"
|
||||
method="post"
|
||||
>
|
||||
{% csrf_token %}
|
||||
<input
|
||||
type="hidden"
|
||||
name="hidden"
|
||||
value="delete-all-additional-information"
|
||||
/>
|
||||
<button type="submit" class="btn btn-sm btn-ghost">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-trash"
|
||||
>
|
||||
<path d="M3 6h18" />
|
||||
<path d="M19 6v14c0 1-1 2-2 2H7c-1 0-2-1-2-2V6" />
|
||||
<path d="M8 6V4c0-1 1-2 2-2h4c1 0 2 1 2 2v2" />
|
||||
</svg>
|
||||
</button>
|
||||
</form>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-heading">Description</div>
|
||||
<div class="panel-body">
|
||||
{{ scenario.description|safe }}
|
||||
<br />
|
||||
{{ scenario.scenario_type }}
|
||||
<br />
|
||||
Reported {{ scenario.scenario_date }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="table-responsive">
|
||||
<table
|
||||
id="scenario-table"
|
||||
class="table-bordered table-striped table-hover table"
|
||||
>
|
||||
<tbody>
|
||||
<tr>
|
||||
<th>Property</th>
|
||||
<th>Value</th>
|
||||
<th>Unit</th>
|
||||
{% if meta.can_edit %}
|
||||
<th>Remove</th>
|
||||
{% endif %}
|
||||
</tr>
|
||||
|
||||
{% for ai in scenario.get_additional_information %}
|
||||
<tr>
|
||||
<td>{{ ai.property_name|safe }}</td>
|
||||
<td>{{ ai.property_data|safe }}</td>
|
||||
<td>{{ ai.property_unit|safe }}</td>
|
||||
{% if meta.can_edit %}
|
||||
<td>
|
||||
<form
|
||||
action="{% url 'package scenario detail' scenario.package.uuid scenario.uuid %}"
|
||||
method="post"
|
||||
>
|
||||
{% csrf_token %}
|
||||
<input type="hidden" name="uuid" value="{{ ai.uuid }}" />
|
||||
<input
|
||||
type="hidden"
|
||||
name="hidden"
|
||||
value="delete-additional-information"
|
||||
/>
|
||||
<button type="submit" class="btn">
|
||||
<span class="glyphicon glyphicon-minus"></span>
|
||||
</button>
|
||||
</form>
|
||||
</td>
|
||||
{% endif %}
|
||||
</tr>
|
||||
{% endfor %}
|
||||
{% if meta.can_edit %}
|
||||
<tr>
|
||||
<td></td>
|
||||
<td></td>
|
||||
<td>Delete all</td>
|
||||
<td>
|
||||
<form
|
||||
action="{% url 'package scenario detail' scenario.package.uuid scenario.uuid %}"
|
||||
method="post"
|
||||
>
|
||||
{% csrf_token %}
|
||||
<input
|
||||
type="hidden"
|
||||
name="hidden"
|
||||
value="delete-all-additional-information"
|
||||
/>
|
||||
<button type="submit" class="btn">
|
||||
<span class="glyphicon glyphicon-trash"></span>
|
||||
</button>
|
||||
</form>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -10,359 +10,243 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="rule-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ rule.name|safe }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/rule.html" %}
|
||||
{% endblock %}
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ rule.name }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/rule.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<p class="mt-2">{{ rule.description }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{% if rule.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Aliases</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for alias in rule.aliases %}
|
||||
<li><a class="hover:bg-base-200">{{ alias }}</a></li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>{{ rule.description|safe }}</p>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if rule.aliases %}
|
||||
<!-- Aliases -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-aliases-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-aliases"
|
||||
>Aliases</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-aliases" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for alias in rule.aliases %}
|
||||
<a class="list-group-item">{{ alias }}</a>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
<!-- Image Representation -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Image Representation</div>
|
||||
<div class="collapse-content">
|
||||
<div class="flex justify-center">{{ rule.as_svg|safe }}</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Representation -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-image-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-image"
|
||||
>Image Representation</a
|
||||
>
|
||||
</h4>
|
||||
<!-- SMIRKS -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
SMIRKS Representation
|
||||
</div>
|
||||
<div id="rule-image" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div id="image-div" align="center">{{ rule.as_svg|safe }}</div>
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<p>{{ rule.smirks }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- SMIRKS -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-smirks-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-smirks"
|
||||
>SMIRKS Representation</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-smirks" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<p>{{ rule.smirks }}</p>
|
||||
</div>
|
||||
<!-- Reactants SMARTS -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Reactant SMARTS</div>
|
||||
<div class="collapse-content">
|
||||
<p>{{ rule.reactants_smarts }}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Reactants SMARTS -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-reactants-smarts-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-reactants-smarts"
|
||||
>Reactant SMARTS</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-reactants-smarts" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<p>{{ rule.reactants_smarts }}</p>
|
||||
<!-- Reactant Filter SMARTS -->
|
||||
{% if rule.reactant_filter_smarts %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Reactant Filter SMARTS
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<p>{{ rule.reactant_filter_smarts }}</p>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Reactant Filter SMARTS -->
|
||||
{% if rule.reactant_filter_smarts %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-reactant-filter-smarts-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-reactant-filter-smarts"
|
||||
>Reactant Filter SMARTS</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div
|
||||
id="rule-reactant-filter-smarts"
|
||||
class="panel-collapse in collapse"
|
||||
>
|
||||
<div class="panel-body list-group-item">
|
||||
<p>{{ rule.reactant_filter_smarts }}</p>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Products SMARTS -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-products-smarts-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-products-smarts"
|
||||
>Reactant SMARTS</a
|
||||
>
|
||||
</h4>
|
||||
<!-- Products SMARTS -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Products SMARTS</div>
|
||||
<div class="collapse-content">
|
||||
<p>{{ rule.products_smarts }}</p>
|
||||
</div>
|
||||
<div id="rule-products-smarts" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<p>{{ rule.products_smarts }}</p>
|
||||
</div>
|
||||
|
||||
<!-- Product Filter SMARTS -->
|
||||
{% if rule.product_filter_smarts %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Product Filter SMARTS
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<p>{{ rule.product_filter_smarts }}</p>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Product Filter SMARTS -->
|
||||
{% if rule.product_filter_smarts %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-product-filter-smarts-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-product-filter-smarts"
|
||||
>Product Filter SMARTS</a
|
||||
>
|
||||
</h4>
|
||||
<!-- Included in Composite Rules -->
|
||||
{% if rule.parallelrule_set.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Included in Composite Rules
|
||||
</div>
|
||||
<div id="rule-product-filter-smarts" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<p>{{ rule.product_filter_smarts }}</p>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Included in Composite Rules -->
|
||||
{% if rule.parallelrule_set.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-composite-rule-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-composite-rule"
|
||||
>Included in Composite Rules</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-composite-rule" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for cr in rule.parallelrule_set.all %}
|
||||
<a class="list-group-item" href="{{ cr.url }}"
|
||||
>{{ cr.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ cr.url }}" class="hover:bg-base-200"
|
||||
>{{ cr.name }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Scenarios -->
|
||||
{% if rule.scenarios.all %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-scenario-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-scenario"
|
||||
>Scenarios</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-scenario" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Scenarios -->
|
||||
{% if rule.scenarios.all %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Scenarios</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for s in rule.scenarios.all %}
|
||||
<a class="list-group-item" href="{{ s.url }}"
|
||||
>{{ s.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ s.url }}" class="hover:bg-base-200">{{ s.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Reactions -->
|
||||
{% if rule.related_reactions %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-reaction-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-reaction"
|
||||
>Reactions</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-reaction" class="panel-collapse collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Reactions -->
|
||||
{% if rule.related_reactions %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" />
|
||||
<div class="collapse-title text-xl font-medium">Reactions</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in rule.related_reactions %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200">{{ r.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Pathways -->
|
||||
{% if rule.related_pathways %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-pathway-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-pathway"
|
||||
>Pathways</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-pathway" class="panel-collapse collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<!-- Pathways -->
|
||||
{% if rule.related_pathways %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" />
|
||||
<div class="collapse-title text-xl font-medium">Pathways</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for r in rule.related_pathways %}
|
||||
<a class="list-group-item" href="{{ r.url }}"
|
||||
>{{ r.name|safe }}</a
|
||||
>
|
||||
<li>
|
||||
<a href="{{ r.url }}" class="hover:bg-base-200">{{ r.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
{% if rule.enzymelinks %}
|
||||
<!-- EC Numbers -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="rule-ec-numbers-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#rule-detail"
|
||||
href="#rule-ec-numbers"
|
||||
>EC Numbers</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="rule-ec-numbers" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% if rule.enzymelinks %}
|
||||
<!-- EC Numbers -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">EC Numbers</div>
|
||||
<div class="collapse-content">
|
||||
<div class="space-y-2">
|
||||
{% for k, v in rule.get_grouped_enzymelinks.items %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="{{ k|slugify }}_Link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#{{ k|slugify }}_Accordion"
|
||||
href="#{{ k|slugify }}"
|
||||
>
|
||||
{{ k }}
|
||||
</a>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="{{ k|slugify }}" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for enzyme in v %}
|
||||
<a class="list-group-item" href="{{ enzyme.url }}">
|
||||
{{ enzyme.ec_number }}
|
||||
<div style="position:absolute;bottom:10px;left:100px;">
|
||||
{{ enzyme.name }}
|
||||
</div>
|
||||
<div style="float:right;">
|
||||
{{ enzyme.linking_method }}
|
||||
</div>
|
||||
</a>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-100 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-lg font-medium">{{ k }}</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for enzyme in v %}
|
||||
<li>
|
||||
<a href="{{ enzyme.url }}" class="hover:bg-base-300">
|
||||
<div class="flex w-full items-center justify-between">
|
||||
<span>{{ enzyme.ec_number }}</span>
|
||||
<span class="text-sm opacity-70"
|
||||
>{{ enzyme.linking_method }}</span
|
||||
>
|
||||
</div>
|
||||
<div class="text-sm opacity-60">
|
||||
{{ enzyme.name }}
|
||||
</div>
|
||||
</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
@ -1,4 +1,4 @@
|
||||
{% extends "framework.html" %}
|
||||
{% extends "framework_modern.html" %}
|
||||
|
||||
{% block content %}
|
||||
|
||||
@ -10,187 +10,161 @@
|
||||
{% include "modals/objects/generic_delete_modal.html" %}
|
||||
{% endblock action_modals %}
|
||||
|
||||
<div class="panel-group" id="user-detail">
|
||||
<div class="panel panel-default">
|
||||
<div
|
||||
class="panel-heading"
|
||||
id="headingPanel"
|
||||
style="font-size:2rem;height: 46px"
|
||||
>
|
||||
{{ user.username }}
|
||||
<div
|
||||
id="actionsButton"
|
||||
style="float: right;font-weight: normal;font-size: medium;position: relative; top: 50%; transform: translateY(-50%);z-index:100;display: none;"
|
||||
class="dropdown"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="dropdown-toggle"
|
||||
data-toggle="dropdown"
|
||||
role="button"
|
||||
aria-haspopup="true"
|
||||
aria-expanded="false"
|
||||
><span class="glyphicon glyphicon-wrench"></span> Actions
|
||||
<span class="caret"></span><span style="padding-right:1em"></span
|
||||
></a>
|
||||
<ul id="actionsList" class="dropdown-menu">
|
||||
{% block actions %}
|
||||
{% include "actions/objects/user.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
<div class="space-y-2 p-4">
|
||||
<!-- Header Section -->
|
||||
<div class="card bg-base-100">
|
||||
<div class="card-body">
|
||||
<div class="flex items-center justify-between">
|
||||
<h2 class="card-title text-2xl">{{ user.username }}</h2>
|
||||
<div id="actionsButton" class="dropdown dropdown-end hidden">
|
||||
<div tabindex="0" role="button" class="btn btn-ghost btn-sm">
|
||||
<svg
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
width="16"
|
||||
height="16"
|
||||
viewBox="0 0 24 24"
|
||||
fill="none"
|
||||
stroke="currentColor"
|
||||
stroke-width="2"
|
||||
stroke-linecap="round"
|
||||
stroke-linejoin="round"
|
||||
class="lucide lucide-wrench"
|
||||
>
|
||||
<path
|
||||
d="M14.7 6.3a1 1 0 0 0 0 1.4l1.6 1.6a1 1 0 0 0 1.4 0l3.77-3.77a6 6 0 0 1-7.94 7.94l-6.91 6.91a2.12 2.12 0 0 1-3-3l6.91-6.91a6 6 0 0 1 7.94-7.94l-3.76 3.76z"
|
||||
/>
|
||||
</svg>
|
||||
Actions
|
||||
</div>
|
||||
<ul
|
||||
tabindex="-1"
|
||||
class="dropdown-content menu bg-base-100 rounded-box z-50 w-52 p-2"
|
||||
>
|
||||
{% block actions %}
|
||||
{% include "actions/objects/user.html" %}
|
||||
{% endblock %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="panel-body">
|
||||
<p>
|
||||
<p class="mt-2">
|
||||
On this page you can modify your account or set preferences such as
|
||||
prediction settings.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Default Package -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="default-package-link"
|
||||
data-toggle="collapse"
|
||||
data-parent="#user-detail"
|
||||
href="#default-package"
|
||||
>Default Package</a
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Default Package</div>
|
||||
<div class="collapse-content">
|
||||
<a href="{{ user.default_package.url }}" class="link link-primary"
|
||||
>{{ user.default_package.name }}</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="default-package" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<li class="list-group-item">
|
||||
<a href="{{ user.default_package.url }}">
|
||||
{{ user.default_package.name|safe }}</a
|
||||
>
|
||||
</li>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Groups -->
|
||||
{% if meta.available_groups|length > 0 %}
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="group-links"
|
||||
data-toggle="collapse"
|
||||
data-parent="#user-detail"
|
||||
href="#groups"
|
||||
>Groups</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="groups" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
{% for g in meta.available_groups %}
|
||||
<li class="list-group-item">
|
||||
<a href="{{ g.url }}"> {{ g.name|safe }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">Groups</div>
|
||||
<div class="collapse-content">
|
||||
<ul class="menu bg-base-100 rounded-box">
|
||||
{% for g in meta.available_groups %}
|
||||
<li>
|
||||
<a href="{{ g.url }}" class="hover:bg-base-200">{{ g.name }}</a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
||||
<!-- Current Prediction Settings -->
|
||||
<div
|
||||
class="panel panel-default panel-heading list-group-item"
|
||||
style="background-color:silver"
|
||||
>
|
||||
<h4 class="panel-title">
|
||||
<a
|
||||
id="current-prediction-setting-links"
|
||||
data-toggle="collapse"
|
||||
data-parent="#user-detail"
|
||||
href="#current-prediction-setting"
|
||||
>Current Prediction Setting</a
|
||||
>
|
||||
</h4>
|
||||
</div>
|
||||
<div id="current-prediction-setting" class="panel-collapse in collapse">
|
||||
<div class="panel-body list-group-item">
|
||||
<table class="table-bordered table-hover table">
|
||||
<tr style="background-color: rgba(0, 0, 0, 0.08);">
|
||||
<th scope="col" width="20%">Parameter</th>
|
||||
<th scope="col" width="80%">Value</th>
|
||||
</tr>
|
||||
<tbody>
|
||||
{% if user.default_setting.model %}
|
||||
<!-- Current Prediction Setting -->
|
||||
<div class="collapse-arrow bg-base-200 collapse">
|
||||
<input type="checkbox" checked />
|
||||
<div class="collapse-title text-xl font-medium">
|
||||
Current Prediction Setting
|
||||
</div>
|
||||
<div class="collapse-content">
|
||||
<div class="overflow-x-auto">
|
||||
<table class="table-zebra table">
|
||||
<thead>
|
||||
<tr>
|
||||
<td width="20%">Model</td>
|
||||
<td width="80%">
|
||||
<table width="100%" class="table-bordered table-hover table">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
<li class="list-group-item">
|
||||
<a href="{{ user.default_setting.model.url }}">
|
||||
{{ user.default_setting.model.name|safe }}
|
||||
</a>
|
||||
</li>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th width="20%">Model Parameter</th>
|
||||
<th width="80%">Parameter Value</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td width="20%">Threshold</td>
|
||||
<td width="80%">
|
||||
{{ user.default_setting.model_threshold }}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</td>
|
||||
<th>Parameter</th>
|
||||
<th>Value</th>
|
||||
</tr>
|
||||
{% endif %}
|
||||
{% if user.default_setting.rule_packages.all %}
|
||||
</thead>
|
||||
<tbody>
|
||||
{% if user.default_setting.model %}
|
||||
<tr>
|
||||
<td>Model</td>
|
||||
<td>
|
||||
<div class="space-y-2">
|
||||
<a
|
||||
href="{{ user.default_setting.model.url }}"
|
||||
class="link link-primary"
|
||||
>
|
||||
{{ user.default_setting.model.name }}
|
||||
</a>
|
||||
<table class="table-xs table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Model Parameter</th>
|
||||
<th>Parameter Value</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>Threshold</td>
|
||||
<td>{{ user.default_setting.model_threshold }}</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
{% if user.default_setting.rule_packages.all %}
|
||||
<tr>
|
||||
<td>Rule Packages</td>
|
||||
<td>
|
||||
<ul class="menu bg-base-200 rounded-box">
|
||||
{% for p in user.default_setting.rule_packages.all %}
|
||||
<li>
|
||||
<a href="{{ p.url }}" class="hover:bg-base-300"
|
||||
>{{ p.name }}</a
|
||||
>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
<tr>
|
||||
<td width="20%">Rule Packages</td>
|
||||
<td width="80%">
|
||||
<table width="100%" class="table-bordered table-hover table">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td colspan="2">
|
||||
{% for p in user.default_setting.rule_packages.all %}
|
||||
<li class="list-group-item">
|
||||
<a href="{{ p.url }}"> {{ p.name|safe }} </a>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</td>
|
||||
<td>Max Nodes</td>
|
||||
<td>{{ user.default_setting.max_nodes }}</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
<tr>
|
||||
<td>
|
||||
<p>Max Nodes</p>
|
||||
</td>
|
||||
<td>
|
||||
<p>{{ user.default_setting.max_nodes }}</p>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<p>Max Depth</p>
|
||||
</td>
|
||||
<td>
|
||||
<p>{{ user.default_setting.max_depth }}</p>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<tr>
|
||||
<td>Max Depth</td>
|
||||
<td>{{ user.default_setting.max_depth }}</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
// Show actions button if there are actions
|
||||
document.addEventListener("DOMContentLoaded", function () {
|
||||
const actionsButton = document.getElementById("actionsButton");
|
||||
const actionsList = actionsButton?.querySelector("ul");
|
||||
if (actionsList && actionsList.children.length > 0) {
|
||||
actionsButton?.classList.remove("hidden");
|
||||
}
|
||||
});
|
||||
</script>
|
||||
{% endblock content %}
|
||||
|
||||
Reference in New Issue
Block a user