Codeez / app.py
masadonline's picture
Update app.py
e1dd757 verified
raw
history blame
4.02 kB
import streamlit as st
import ast
import base64
import streamlit.components.v1 as components
from transformers import pipeline
from gtts import gTTS
st.set_page_config(page_title="AR/VR Code Visualizer", layout="wide")
st.title("πŸ‘“ AR/VR Code Visualizer with Call Relationships + Narration")
@st.cache_resource
def load_model():
return pipeline("summarization", model="philschmid/bart-large-cnn-samsum")
summarizer = load_model()
uploaded_file = st.file_uploader("πŸ“ Upload a Python file", type=["py"])
if uploaded_file:
code = uploaded_file.read().decode("utf-8")
st.code(code, language="python")
# Parse AST for functions and call relationships
tree = ast.parse(code)
class FunctionCallVisitor(ast.NodeVisitor):
def __init__(self):
self.calls = {}
def visit_FunctionDef(self, node):
caller = node.name
self.calls[caller] = []
for child in ast.walk(node):
if isinstance(child, ast.Call) and isinstance(child.func, ast.Name):
self.calls[caller].append(child.func.id)
self.generic_visit(node)
visitor = FunctionCallVisitor()
visitor.visit(tree)
call_graph = visitor.calls
all_functions = list(call_graph.keys())
# Show call relationships
st.subheader("πŸ“Š Call Relationships")
for fn, callees in call_graph.items():
st.write(f"πŸ”Ή `{fn}` calls: {', '.join(callees) if callees else 'None'}")
# Hugging Face summarization
prompt = f"Explain the structure and purpose of the following functions and how they call each other: {call_graph}"
summary = summarizer(prompt, max_length=60, min_length=15, do_sample=False)
summary_text = summary[0]['summary_text']
st.success(summary_text)
# Voice narration
st.subheader("πŸ”Š Voice Narration of Code Summary")
tts = gTTS(text=summary_text)
tts.save("summary.mp3")
audio_file = open("summary.mp3", "rb")
st.audio(audio_file.read(), format="audio/mp3")
# Generate A-Frame scene
def generate_aframe(call_graph):
spacing = 3
boxes = []
lines = []
positions = {}
for i, fn in enumerate(call_graph):
x = i * spacing
positions[fn] = (x, 1, -3)
boxes.append(f'''
<a-box position="{x} 1 -3" depth="0.5" height="0.5" width="2" color="#FFC65D"></a-box>
<a-text value="{fn}" position="{x} 1.8 -3" align="center" color="#000"></a-text>
''')
for caller, callees in call_graph.items():
for callee in callees:
if callee in positions:
x1, y1, z1 = positions[caller]
x2, y2, z2 = positions[callee]
lines.append(f'''
<a-entity line="start: {x1} {y1} {z1}; end: {x2} {y2} {z2}; color: red"></a-entity>
''')
html = f'''
<!DOCTYPE html>
<html>
<head>
<script src="https://aframe.io/releases/1.3.0/aframe.min.js"></script>
</head>
<body>
<a-scene background="color: #ECECEC">
<a-entity position="0 1.6 3">
<a-camera wasd-controls-enabled="true" look-controls-enabled="true"></a-camera>
</a-entity>
<a-light type="ambient" color="#FFF"></a-light>
<a-plane rotation="-90 0 0" width="40" height="40" color="#7BC8A4"></a-plane>
{''.join(boxes)}
{''.join(lines)}
</a-scene>
</body>
</html>
'''
return html
aframe_html = generate_aframe(call_graph)
b64 = base64.b64encode(aframe_html.encode()).decode()
data_url = f"data:text/html;base64,{b64}"
st.subheader("🌐 3D Call Relationship Visualization")
components.iframe(data_url, height=500)
else:
st.info("Upload a Python file to visualize its structure, relationships, and get narrated summary.")