Spaces:
Sleeping
Sleeping
File size: 3,830 Bytes
d8f6f04 7aa8120 d8f6f04 7aa8120 d8f6f04 015baef d8f6f04 857510a d8f6f04 015baef d8f6f04 857510a 015baef 857510a 015baef d8f6f04 015baef d8f6f04 015baef d8f6f04 015baef d8f6f04 015baef d8f6f04 015baef d8f6f04 015baef d8f6f04 857510a d8f6f04 015baef 857510a 015baef 857510a 015baef 857510a d8f6f04 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 |
import json
import random
import streamlit as st
import streamlit.components.v1 as components
# --- CONFIGURATION -------------------------------------------------------------
HEIGHT = 600
DEFAULT_NODES = 10
DEFAULT_EDGES = 12
# --- HELPER FUNCTIONS ----------------------------------------------------------
def random_rgb():
return "#{:02x}{:02x}{:02x}".format(
random.randint(50, 200),
random.randint(50, 200),
random.randint(50, 200)
)
def build_cytoscape_elements(n_nodes, n_edges):
"""Return Cytoscape-compatible elements JSON."""
nodes = [{"data": {"id": str(i), "label": f"Node {i}"}} for i in range(n_nodes)]
edges = [
{
"data": {
"id": f"{u}-{v}",
"source": str(u),
"target": str(v),
"weight": random.randint(1, 5),
}
}
for u, v in [random.sample(range(n_nodes), 2) for _ in range(n_edges)]
]
return nodes + edges
def build_html(elements_json, height):
"""Return complete HTML/JS string for standalone Cytoscape viewer."""
background_color = random_rgb()
return f"""
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/cytoscape.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/dagre.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/[email protected]/cytoscape-dagre.js"></script>
<style>
html, body {{{{ margin: 0; height: 100%; }}}}
#cy {{{{ width: 100%; height: {height}px; border: 1px solid #ccc; }}}}
</style>
</head>
<body>
<div id="cy"></div>
<script>
// Register dagre layout extension
if (typeof cytoscape !== 'undefined' && typeof cytoscape.use === 'function' && typeof dagre !== 'undefined') {{
cytoscape.use(cytoscapeDagre);
}}
const elements = {elements_json};
const cy = cytoscape({{
container: document.getElementById('cy'),
elements: elements,
style: [
{{
selector: 'node',
style: {{
'label': 'data(label)',
'background-color': '{background_color}',
'text-valign': 'center',
'color': '#fff',
'font-size': 12
}}
}},
{{
selector: 'edge',
style: {{
'width': 'mapData(weight, 1, 5, 1, 5)',
'line-color': '#bbb',
'target-arrow-color': '#bbb',
'curve-style': 'bezier',
'target-arrow-shape': 'triangle'
}}
}}
]
}});
// Apply layout after elements are added
cy.layout({{ name: 'dagre', rankDir: 'LR' }}).run();
// Resize handling for Streamlit container
window.addEventListener('resize', () => cy.resize());
</script>
</body>
</html>
"""
# --- STREAMLIT UI --------------------------------------------------------------
st.set_page_config(page_title="Cytoscape + Streamlit Demo", layout="wide")
st.title("Cytoscape Network Viewer in Streamlit")
with st.sidebar:
st.header("Controls")
n_nodes = st.slider("Nodes", 3, 50, DEFAULT_NODES)
n_edges = st.slider("Edges", max(1, n_nodes - 1), 100, DEFAULT_EDGES)
if st.button("Regenerate"):
st.cache_data.clear()
# --- RENDER CYTOSCAPE ----------------------------------------------------------
elements = build_cytoscape_elements(n_nodes, n_edges)
html = build_html(json.dumps(elements), HEIGHT)
components.html(html, height=HEIGHT) |