Created
March 16, 2025 20:27
-
-
Save colincowie/3d877f05340eff6c8f8931528e262673 to your computer and use it in GitHub Desktop.
CSV to PyVis Network using FontAwesome Icons
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| import pandas as pd | |
| from pyvis.network import Network | |
| # Read the CSV file | |
| csv_file = "demo.csv" # Replace with your actual file path | |
| data = pd.read_csv(csv_file) | |
| # Ensure 'from' and 'to' columns are strings and handle missing values | |
| data['from'] = data['from'].fillna('').astype(str).str.strip() | |
| data['to'] = data['to'].fillna('').astype(str).str.strip() | |
| # Initialize the PyVis network | |
| graph = Network(height='750px', width='100%', bgcolor='#222222', font_color='white') | |
| # Pre-process nodes to collect icon and color information | |
| node_icons = {} | |
| for index, row in data.iterrows(): | |
| from_node = row['from'] | |
| # Skip empty nodes | |
| if not from_node: | |
| continue | |
| from_icon = row.get('from_icon', None) | |
| from_color = row.get('from_color', "#F5A623") # Default color if not set | |
| # Process FontAwesome icons | |
| if pd.notna(from_icon) and from_icon.startswith("\\u"): | |
| try: | |
| unicode_icon = chr(int(from_icon.replace("\\u", "0x"), 16)) | |
| node_icons[from_node] = {"icon": {"face": "FontAwesome", "code": unicode_icon, "color": from_color}} | |
| except ValueError: | |
| node_icons[from_node] = {"icon": None} | |
| else: | |
| node_icons[from_node] = {"icon": None} | |
| # Collect all unique non-empty nodes | |
| all_nodes = set(data['from']).union(set(data['to'])) - {''} # Remove empty strings | |
| # Add nodes to the graph | |
| for node in all_nodes: | |
| if node in node_icons: | |
| icon_settings = node_icons[node]['icon'] | |
| graph.add_node(node, label=node, title=node, shape='icon' if icon_settings else 'dot', icon=icon_settings) | |
| else: | |
| graph.add_node(node, label=node, title=node, shape='dot') | |
| # Iterate through the DataFrame and add edges (ignore empty and self-looping edges) | |
| for index, row in data.iterrows(): | |
| if row['from'] and row['to'] and row['from'] != row['to']: # Avoid self-loops | |
| graph.add_edge(row['from'], row['to']) | |
| # Customize the visualization | |
| graph.force_atlas_2based() | |
| # Save and modify the HTML file | |
| html_file = "graph.html" | |
| graph.write_html(html_file) | |
| # Inject FontAwesome library into the HTML | |
| with open(html_file, "r", encoding="utf-8") as f: | |
| html_content = f.read() | |
| fontawesome_link = '<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.0.0/css/all.min.css">' | |
| html_content = html_content.replace("</head>", f"{fontawesome_link}</head>") | |
| with open(html_file, "w", encoding="utf-8") as f: | |
| f.write(html_content) | |
| print(f"Report saved to {html_file}") |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment