awacke1 commited on
Commit
6dbef36
1 Parent(s): 187e695

Create backup3.app.py

Browse files
Files changed (1) hide show
  1. backup3.app.py +147 -0
backup3.app.py ADDED
@@ -0,0 +1,147 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import streamlit as st
2
+ import os
3
+ from PIL import Image
4
+ import random
5
+ from io import BytesIO
6
+ import datetime
7
+ import base64
8
+
9
+ # Adjust Streamlit layout to wide mode
10
+ st.set_page_config(layout="wide")
11
+
12
+ # Function to arrange images dynamically
13
+ def arrange_images(image_files, canvas_size=(3000, 3000)):
14
+ if not image_files:
15
+ return None
16
+
17
+ positions = [] # Keeps track of image positions (x1, y1, x2, y2)
18
+ canvas = Image.new("RGBA", canvas_size, "white")
19
+
20
+ def get_center(pos):
21
+ """Calculate center of a bounding box (x1, y1, x2, y2)."""
22
+ return ((pos[0] + pos[2]) // 2, (pos[1] + pos[3]) // 2)
23
+
24
+ def does_overlap(new_box, existing_boxes):
25
+ """Check if a new bounding box overlaps any existing boxes."""
26
+ for box in existing_boxes:
27
+ if (
28
+ new_box[0] < box[2]
29
+ and new_box[2] > box[0]
30
+ and new_box[1] < box[3]
31
+ and new_box[3] > box[1]
32
+ ):
33
+ return True
34
+ return False
35
+
36
+ # Place the first image at the center of the canvas
37
+ first_img_path = os.path.join(map_dir, image_files[0])
38
+ with Image.open(first_img_path) as img:
39
+ width, height = img.size
40
+ x1 = (canvas_size[0] - width) // 2
41
+ y1 = (canvas_size[1] - height) // 2
42
+ x2, y2 = x1 + width, y1 + height
43
+ positions.append((x1, y1, x2, y2))
44
+ canvas.paste(img, (x1, y1))
45
+
46
+ # Place remaining images
47
+ for img_file in image_files[1:]:
48
+ placed = False
49
+ img_path = os.path.join(map_dir, img_file)
50
+
51
+ with Image.open(img_path) as img:
52
+ width, height = img.size
53
+
54
+ while not placed:
55
+ target_box = random.choice(positions)
56
+ target_center = get_center(target_box)
57
+ side = random.choice(["top", "bottom", "left", "right"])
58
+
59
+ if side == "top":
60
+ x1 = target_center[0] - width // 2
61
+ y1 = target_box[1] - height
62
+ elif side == "bottom":
63
+ x1 = target_center[0] - width // 2
64
+ y1 = target_box[3]
65
+ elif side == "left":
66
+ x1 = target_box[0] - width
67
+ y1 = target_center[1] - height // 2
68
+ elif side == "right":
69
+ x1 = target_box[2]
70
+ y1 = target_center[1] - height // 2
71
+
72
+ x2, y2 = x1 + width, y1 + height
73
+
74
+ if not does_overlap((x1, y1, x2, y2), positions):
75
+ positions.append((x1, y1, x2, y2))
76
+ canvas.paste(img, (x1, y1))
77
+ placed = True
78
+
79
+ buffer = BytesIO()
80
+ canvas.save(buffer, format="PNG")
81
+ buffer.seek(0)
82
+ return buffer, canvas
83
+
84
+ # Function to create a base64 download link
85
+ def create_download_link(image_bytes, filename):
86
+ b64 = base64.b64encode(image_bytes.getvalue()).decode()
87
+ href = f'<a href="data:image/png;base64,{b64}" download="{filename}">📥 Download {filename}</a>'
88
+ return href
89
+
90
+ # Streamlit App
91
+ st.title("Dynamic Dungeon Map Generator")
92
+
93
+ # Directory for images
94
+ map_dir = "."
95
+ canvas_size = 3000
96
+
97
+ # Initialize session state
98
+ if "layout_image" not in st.session_state:
99
+ st.session_state["layout_image"] = None
100
+ if "canvas" not in st.session_state:
101
+ st.session_state["canvas"] = None
102
+
103
+ # Generate map if layout_image is empty
104
+ if st.session_state["layout_image"] is None:
105
+ image_files = [f for f in os.listdir(map_dir) if f.endswith(".png")]
106
+ if image_files:
107
+ layout_image, canvas = arrange_images(image_files, canvas_size=(canvas_size, canvas_size))
108
+ st.session_state["layout_image"] = layout_image
109
+ st.session_state["canvas"] = canvas
110
+
111
+ # Display map with scroll and zoom controls
112
+ if st.session_state["layout_image"] is not None:
113
+ st.image(
114
+ st.session_state["layout_image"],
115
+ caption="Generated Dungeon Map Layout",
116
+ use_container_width=True,
117
+ output_format="PNG",
118
+ clamp=True,
119
+ )
120
+
121
+ # Sidebar Controls
122
+ st.sidebar.title("Map Controls")
123
+ if st.sidebar.button("💾 Save Map"):
124
+ now = datetime.datetime.now()
125
+ filename = f"dungeon_map_{now.strftime('%Y%m%d_%H%M%S')}.png"
126
+ st.session_state["canvas"].save(filename)
127
+ st.sidebar.success(f"Map saved as {filename}")
128
+
129
+ if st.sidebar.button("🗺️ Regenerate Map"):
130
+ image_files = [f for f in os.listdir(map_dir) if f.endswith(".png")]
131
+ if image_files:
132
+ layout_image, canvas = arrange_images(image_files, canvas_size=(canvas_size, canvas_size))
133
+ st.session_state["layout_image"] = layout_image
134
+ st.session_state["canvas"] = canvas
135
+ st.rerun()
136
+
137
+ # Zoom controls
138
+ st.sidebar.title("Zoom")
139
+ zoom_level = st.sidebar.slider("Zoom Level", min_value=0.5, max_value=2.0, value=1.0, step=0.1)
140
+ st.image(
141
+ st.session_state["layout_image"],
142
+ caption="Zoomed Dungeon Map Layout",
143
+ use_container_width=False,
144
+ output_format="PNG",
145
+ clamp=True,
146
+ width=int(canvas_size * zoom_level),
147
+ )