guli-tools 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,5 @@
1
+ Metadata-Version: 2.4
2
+ Name: guli-tools
3
+ Version: 0.1.0
4
+ Summary: My reusable modules
5
+ Requires-Python: >=3.8
@@ -0,0 +1,5 @@
1
+ Metadata-Version: 2.4
2
+ Name: guli-tools
3
+ Version: 0.1.0
4
+ Summary: My reusable modules
5
+ Requires-Python: >=3.8
@@ -0,0 +1,11 @@
1
+ pyproject.toml
2
+ guli_tools.egg-info/PKG-INFO
3
+ guli_tools.egg-info/SOURCES.txt
4
+ guli_tools.egg-info/dependency_links.txt
5
+ guli_tools.egg-info/top_level.txt
6
+ modules/ANSI.py
7
+ modules/G_anicurves.py
8
+ modules/G_perlin.py
9
+ modules/Goosefull.py
10
+ modules/guli_progress_bar.py
11
+ modules/render.py
@@ -0,0 +1 @@
1
+ modules
@@ -0,0 +1,257 @@
1
+ # usefull for projects that use the terminal allat
2
+ filename = __file__.split("\\")[-1]
3
+ print(f"(Loading module: {filename}..")
4
+
5
+ class F:
6
+ BOLD = "\033[1m"
7
+ FAINT = "\033[2m"
8
+ DIM = "\033[22m"
9
+ ITALIC = "\033[3m"
10
+ UNDERLINE= "\033[4m"
11
+ NEGATIVE = "\033[7m"
12
+ CROSSED = "\033[9m"
13
+ END = "\033[0m"
14
+
15
+ def UP(lines):
16
+ return f"\033[{lines}A"
17
+
18
+ def DOWN(lines):
19
+ return f"\033[{lines}B"
20
+
21
+ def RIGHT(amount):
22
+ return f"\033[{amount}C"
23
+
24
+ def LEFT(amount):
25
+ return f"\033[{amount}D"
26
+
27
+ def COLUMN(column):
28
+ return f"\033[{column}G"
29
+
30
+ def SET_POS(line, column):
31
+ return f"\033[{line};{column}H"
32
+
33
+ def CLEAR_TERMINAL():
34
+ return f"\033[2J"
35
+
36
+ def CLEAR_LINE():
37
+ return f"\r\033[2K"
38
+
39
+ def grad(text="\nU DIDN'T ADD TEXT DUMBASS\n", color_list=[[200,200,200],[200,200,200]], size=0):
40
+ if size > 0:
41
+ color_list = list(color_list) + [color_list[0]]
42
+ steps = len(text)
43
+ num_segments = len(color_list) - 1
44
+ steps_per_segment = (size if size > 0 else steps) / num_segments
45
+ result = []
46
+
47
+ for i, char in enumerate(text):
48
+ cycle_i = i % (size if size > 0 else steps)
49
+ if steps > 1:
50
+ segment = min(int(cycle_i / steps_per_segment), num_segments - 1)
51
+ seg_start = segment * steps_per_segment
52
+ seg_end = (segment + 1) * steps_per_segment
53
+ factor = (cycle_i - seg_start) / (seg_end - seg_start)
54
+ else:
55
+ segment, factor = 0, 0.0
56
+
57
+ c1 = color_list[segment]
58
+ c2 = color_list[segment + 1]
59
+
60
+ r = int(c1[0] + (c2[0] - c1[0]) * factor)
61
+ g = int(c1[1] + (c2[1] - c1[1]) * factor)
62
+ b = int(c1[2] + (c2[2] - c1[2]) * factor)
63
+
64
+ result.append(f"\x1b[38;2;{r};{g};{b}m{char}")
65
+
66
+ return "".join(result) + "\x1b[0m"
67
+
68
+ def RGB_end():
69
+ return "\x1b[0m"
70
+
71
+ class C:
72
+ # --- THE CLASSICS ---
73
+ RAINBOW = [(255, 0, 0), (255, 127, 0), (255, 255, 0), (0, 255, 0), (0, 255, 255), (0, 0, 255), (139, 0, 255)]
74
+ SUNSET = [(255, 94, 87), (255, 159, 67), (255, 205, 86), (253, 121, 168), (108, 92, 231)]
75
+ TWILIGHT = [(15, 32, 67), (84, 90, 182), (179, 107, 202), (249, 133, 133), (255, 211, 153)]
76
+
77
+ # --- CYBER & SCI-FI ---
78
+ VAPORWAVE = [(255, 113, 206), (1, 205, 254), (5, 255, 161), (185, 103, 255), (255, 251, 150)]
79
+ AURORA = [(5, 230, 140), (0, 180, 216), (123, 44, 191), (224, 170, 255)]
80
+ MATRIX_DRIFT = [(0, 15, 0), (0, 75, 15), (0, 150, 30), (50, 255, 70), (200, 255, 210)]
81
+
82
+ # --- NATURE & MOODS ---
83
+ DEEP_OCEAN = [(0, 7, 45), (0, 28, 85), (0, 53, 102), (0, 119, 182), (72, 202, 228)]
84
+ FOREST_FIRE = [(34, 76, 56), (143, 184, 112), (247, 147, 30), (218, 44, 56), (106, 4, 15)]
85
+ GLACIER = [(224, 251, 252), (152, 193, 217), (61, 90, 128), (41, 50, 65)]
86
+
87
+ # Standard
88
+ red_light = (255, 100, 100)
89
+ red = (255, 0, 0 )
90
+ red_dark = (180, 0, 0 )
91
+ green_light = (100, 255, 100)
92
+ green = (0, 200, 0 )
93
+ green_dark = (0, 120, 0 )
94
+ blue_light = (70, 130, 255)
95
+ blue = (10, 20, 255)
96
+ blue_dark = (10, 10, 180)
97
+ cyan_light = (100, 255, 255)
98
+ cyan = (0, 255, 255)
99
+ cyan_dark = (0, 180, 180)
100
+ yellow_light = (255, 255, 100)
101
+ yellow = (255, 255, 0 )
102
+ yellow_dark = (180, 180, 0 )
103
+ magenta_light= (255, 100, 255)
104
+ magenta = (255, 0, 255)
105
+ magenta_dark = (180, 0, 180)
106
+ orange_light = (255, 180, 80 )
107
+ orange = (255, 140, 0 )
108
+ orange_dark = (180, 90, 0 )
109
+ white = (255, 255, 255)
110
+ gray_light = (200, 200, 200)
111
+ gray = (128, 128, 128)
112
+ gray_dark = (60, 60, 60 )
113
+ black = (0, 0, 0 )
114
+
115
+ # Neon & Cyberpunk Colors
116
+ neon_pink = (255, 0, 128)
117
+ neon_purple = (187, 0, 255)
118
+ electric_cyan= (0, 225, 255)
119
+ toxic_green = (57, 255, 20)
120
+
121
+ # Soft Pastels
122
+ pastel_pink = (255, 179, 186)
123
+ pastel_peach = (255, 223, 186)
124
+ pastel_yellow= (255, 255, 186)
125
+ pastel_green = (186, 255, 201)
126
+ pastel_blue = (186, 225, 255)
127
+
128
+ # Earthy & Rich Tones
129
+ crimson = (220, 20, 60)
130
+ gold = (255, 215, 0)
131
+ lime = (50, 205, 50)
132
+ teal = (0, 128, 128)
133
+ indigo = (75, 0, 130)
134
+
135
+ # Monochromes
136
+ white = (255, 255, 255)
137
+ gray = (128, 128, 128)
138
+ black = (0, 0, 0)
139
+
140
+ def grad_x(x, color_list, length=100):
141
+ x = max(0.0, min(1.0, x / length))
142
+ num_segments = len(color_list) - 1
143
+ segment = min(int(x * num_segments), num_segments - 1)
144
+ factor = (x * num_segments) - segment
145
+
146
+ c1 = color_list[segment]
147
+ c2 = color_list[segment + 1]
148
+
149
+ r = int(c1[0] + (c2[0] - c1[0]) * factor)
150
+ g = int(c1[1] + (c2[1] - c1[1]) * factor)
151
+ b = int(c1[2] + (c2[2] - c1[2]) * factor)
152
+
153
+ result = f"\x1b[38;2;{r};{g};{b}m"
154
+ return result
155
+
156
+
157
+ def rgb(r=200, g=200, b=200):
158
+ if isinstance(r, tuple):
159
+ r, g, b = r
160
+ return f"\x1b[38;2;{r};{g};{b}m"
161
+
162
+ def progress_bar(percent, color_list, length=20):
163
+ filled = int((percent / 100) * length)
164
+ bar = "".join(
165
+ grad_x(i, color_list, length) + '█' if i < filled else rgb(C.gray_dark) + '░'
166
+ for i in range(length)
167
+ )
168
+ return f"[{bar}{F.END}] {grad(f'{percent}%', color_list)} {rgb(C.gray_dark)}| {rgb(C.red_light)}{100 - percent}% remaining{F.END}"
169
+
170
+ def info_colors(show=["colors", "example", "use", "alternate", "class"]):
171
+ entries = [name for name, value in vars(C).items() if not name.startswith('_') and isinstance(value, list)]
172
+
173
+ if "colors" in show:
174
+ print()
175
+ for name in entries:
176
+ colors = colors = getattr(C, name)
177
+ print(grad(name, colors), end=" "*(15-len(name)))
178
+ print(grad("█"*40, colors), grad("█"*40, colors, 20))
179
+ print()
180
+ for name, value in vars(C).items():
181
+ if not name.startswith('_') and isinstance(value, tuple):
182
+ print(rgb(*value) + name, "▇"*(30-len(name)), F.END)
183
+ if "dark" in name or name == "black" or name in ("toxic_green", "pastel_blue", "lime", "white"):
184
+ print()
185
+
186
+ if "example" in show:
187
+ print(
188
+ f"\n {F.BOLD}grad{F.END}(text, color_list, size=0)\n"
189
+ f" {rgb(C.gray_dark)}basic {F.END}{grad('grad(\"hello\", [(255,0,0),(0,0,255)])', [(255,0,0),(0,0,255)])}\n"
190
+ f" {rgb(C.gray_dark)}G class {F.END}{grad('grad(\"hello\", C.RAINBOW)', C.RAINBOW)}\n"
191
+ f" {rgb(C.gray_dark)}tiling {F.END}{grad('grad(\"hello\", C.AURORA, 10) ← cycle size, empty for no cycle', C.AURORA, 10)}\n"
192
+ f"\n {F.BOLD}rgb{F.END}(r, g, b)\n"
193
+ f" {rgb(C.gray_dark)}usage {F.END}{rgb(255,100,50)}rgb(255,100,50) + your text{F.END}\n"
194
+ f" {rgb(C.gray_dark)}C class {F.END}{rgb(C.neon_pink)}rgb(C.neon_pink) + your text{F.END}\n"
195
+ f"\n {F.BOLD}grad_x{F.END}(x, color_list, length=100)\n"
196
+ f" {rgb(C.gray_dark)}usage {F.END}{grad_x(0, C.SUNSET, 3)}x=0 {grad_x(1, C.SUNSET, 3)}x=1 {grad_x(2, C.SUNSET, 3)}x=2{F.END} ← x is position along length\n"
197
+ f" {rgb(C.gray_dark)}tip {F.END}{rgb(C.gray_dark)}use in loops: grad_x(i, C.SUNSET, total){F.END}\n"
198
+ f"\n {F.BOLD}alternate{F.END}(text, colors)\n"
199
+ f" {rgb(C.gray_dark)}basic {F.END}{alternate('alternate(\"hello\", [C.cyan_light, C.blue_dark])', [C.cyan_light, C.blue_dark])}\n"
200
+ f" {rgb(C.gray_dark)}multi {F.END}{alternate('alternate(\"hello\", [C.pastel_blue, C.pastel_green, C.pastel_yellow, C.pastel_pink])', [C.pastel_blue, C.pastel_green, C.pastel_yellow, C.pastel_pink])}\n"
201
+ f" {rgb(C.gray_dark)}tip {F.END}{rgb(C.gray_dark)}cycles through colors per character{F.END}\n"
202
+ )
203
+
204
+ if "use" in show:
205
+ print(
206
+ f"\n"
207
+ f" {grad(' ANSI use 101 ', C.SUNSET)}\n"
208
+ f"\n"
209
+ f" {rgb(C.gray_dark)}Solid color with rgb():{F.END}\n"
210
+ f" {rgb(C.red_dark)}✦ error:{F.END} file not found\n"
211
+ f" {rgb(C.toxic_green)}✦ success:{F.END} connected\n"
212
+ f" {rgb(C.yellow)}✦ warning:{F.END} retrying in 3s\n"
213
+ f"\n"
214
+ f" {rgb(C.gray_dark)}Gradient label with grad():{F.END}\n"
215
+ f" {grad(' LOADING ', C.AURORA)} ← status badge\n"
216
+ f" {grad(' WARNING ', C.SUNSET)} ← swap palette for tone\n"
217
+ f" {grad(' SUCCESS ', C.MATRIX_DRIFT)} ← any color_list works\n"
218
+ f"\n"
219
+ f" {rgb(C.gray_dark)}Progress_bar() made with grad_x():{F.END}\n"
220
+ f" {(progress_bar(75, C.DEEP_OCEAN))}\n"
221
+ f" {(progress_bar(40, C.SUNSET))}\n"
222
+ f"\n"
223
+ f" {rgb(C.gray_dark)}Combine them:{F.END}\n"
224
+ f" {grad(' ★ TOP SCORE ', C.VAPORWAVE)} {rgb(C.gold)}{F.BOLD}9,420pts{F.END}\n"
225
+ f" {rgb(C.gray_dark)}user:{F.END} {grad('guli', C.AURORA)} {rgb(C.gray_dark)}status:{F.END} {grad('online', [(0,220,100),(0,180,80)])}\n"
226
+ )
227
+ if "class" in show:
228
+ print(
229
+ f"\n"
230
+ f" {F.BOLD}Class Overview{F.END}\n"
231
+ f" {rgb(C.gray_dark)}C {F.END}= Colors {rgb(C.gray_dark)}→{F.END} tuples like {rgb(C.cyan)}(r, g, b){F.END} used with {F.BOLD}rgb(){F.END} or {F.BOLD}grad(){F.END}\n"
232
+ f" {rgb(C.gray_dark)}F {F.END}= Formats {rgb(C.gray_dark)}→{F.END} ANSI escape codes for {F.BOLD}bold{F.END}, {F.ITALIC}italic{F.END}, {F.UNDERLINE}underline{F.END}, etc.\n"
233
+ f" {rgb(C.gray_dark)}tip {F.END}combine them: {rgb(C.neon_pink)+F.BOLD}rgb(C.neon_pink) + F.BOLD{F.END}\n"
234
+ f"\n"
235
+ )
236
+ def alternate(text, colors):
237
+ result = []
238
+ color_len = len(colors)
239
+ for i in range(len(text)):
240
+ r = colors[i%color_len][0]
241
+ g = colors[i%color_len][1]
242
+ b = colors[i%color_len][2]
243
+
244
+ result.append(f"\x1b[38;2;{r};{g};{b}m{text[i]}")
245
+
246
+ return "".join(result) + "\x1b[0m"
247
+
248
+
249
+
250
+ def credit():
251
+ print(
252
+ f"{UP(1)+CLEAR_LINE()+rgb(C.green_dark)}Loaded Module:{F.END} Guli's {F.BOLD+alternate("ANSI", [C.cyan_light, C.blue_light, C.red_light, C.yellow_light])} decoder."
253
+ )
254
+ credit()
255
+
256
+ if __name__ == "__main__":
257
+ info_colors()
@@ -0,0 +1,67 @@
1
+ import math
2
+ import ANSI
3
+ import Goosefull as goose
4
+
5
+ filename = __file__.split("\\")[-1]
6
+ print(f"(Loading module: {filename}..")
7
+
8
+ # Definieer de tekst en RGB-kleuren
9
+ blue = (0, 0, 255)
10
+ green = (0, 255, 0)
11
+
12
+
13
+ def _bounce_out(t):
14
+ n, d = 7.5625, 2.75
15
+ if t < 1/d: return n * t * t
16
+ elif t < 2/d: t -= 1.5/d; return n*t*t + 0.75
17
+ elif t < 2.5/d: t -= 2.25/d; return n*t*t + 0.9375
18
+ else: t -= 2.625/d; return n*t*t + 0.984375
19
+
20
+ def _ease_out(f, t): return 1 - f(1 - t)
21
+ def _ease_in_out(f, t): return f(2*t) / 2 if t < 0.5 else 1 - f(2 - 2*t) / 2
22
+
23
+ _in = {
24
+ "Sine": lambda t: 1 - math.cos((t * math.pi) / 2),
25
+ "Quad": lambda t: t ** 2,
26
+ "Cubic": lambda t: t ** 3,
27
+ "Quart": lambda t: t ** 4,
28
+ "Quint": lambda t: t ** 5,
29
+ "Expo": lambda t: 0 if t == 0 else 2 ** (10*t - 10),
30
+ "Circ": lambda t: 1 - math.sqrt(1 - t**2),
31
+ "Back": lambda t: 2.70158*t**3 - 1.70158*t**2,
32
+ "Elastic": lambda t: 0 if t==0 else 1 if t==1 else -(2**(10*t-10)) * math.sin((t*10-10.75)*(2*math.pi)/3),
33
+ "Bounce": lambda t: 1 - _bounce_out(1 - t),
34
+ }
35
+
36
+ _easings = {}
37
+ for name, f in _in.items():
38
+ _easings[f"easeIn{name}"] = f
39
+ _easings[f"easeOut{name}"] = lambda t, f=f: _ease_out(f, t)
40
+ _easings[f"easeInOut{name}"] = lambda t, f=f: _ease_in_out(f, t)
41
+
42
+ copya = _easings.copy()
43
+ for k,v in copya.items():
44
+ _easings[k.lower()] = v
45
+
46
+ def curve(x, ease="easeInSine", start=0, end=1, strength=1):
47
+ ease = ease.lower()
48
+ x = (x - start) / (end - start)
49
+ x = max(0.0, min(1.0, x))
50
+ t = _easings[ease](x)
51
+ t = t ** (1 / strength) if t >= 0 else -((-t) ** (1 / strength))
52
+ return start + (end - start) * t
53
+
54
+ def lerp(progress, start, end):
55
+ return (end - start) * progress
56
+
57
+ def curve_info():
58
+ goose.print_set(_in, True)
59
+
60
+
61
+ def credit():
62
+ print(
63
+ f"{ANSI.UP(1)+ANSI.CLEAR_LINE()+ANSI.C.GREEN}Loaded Module:{ANSI.C.END} Guli's {ANSI.C.END}", end=""
64
+ )
65
+ print(ANSI.grad("AnimationCurves", [blue, green])+ANSI.C.END+".")
66
+ credit()
67
+
@@ -0,0 +1,3 @@
1
+ import ANSI
2
+ import G_anicurves as cruves
3
+ import Goosefull
@@ -0,0 +1,251 @@
1
+ import time
2
+ import math
3
+ from datetime import datetime
4
+ from . import ANSI
5
+ import numpy as np
6
+ import random
7
+ from scipy.signal import fftconvolve
8
+ from scipy import ndimage
9
+
10
+ print("Loading module: Goosefull..")
11
+
12
+ # this is basicly Juliano's trash bin of usefull stuff
13
+
14
+
15
+ # =========================
16
+ # -------GRID STUFF-------
17
+ # =========================
18
+
19
+ opposite_dir = {0: 2, 1: 3, 2: 0, 3: 1} # N<->S, E<->W
20
+
21
+ def give_neighbours(grid, x, y, mode='+'):
22
+ result = []
23
+ if mode == '3x3':
24
+ offsets = [(dx, dy) for dx in [-1,0,1] for dy in [-1,0,1] if not (dx==0 and dy==0)]
25
+ elif mode == '+':
26
+ offsets = [(0,-1),(1,0),(0,1),(-1,0)]
27
+
28
+ for i, (dx, dy) in enumerate(offsets): # N E S W
29
+ nx, ny = x + dx, y + dy
30
+ if 0 <= nx < len(grid) and 0 <= ny < len(grid[0]):
31
+ val = grid[nx][ny]
32
+ if val != -1:
33
+ result.append((val, i))
34
+ return result
35
+
36
+ def count_neighbours(grid, x, y, mode='3x3'):
37
+ counts = {}
38
+ if mode == '3x3':
39
+ offsets = [(dx, dy) for dx in [-1,0,1] for dy in [-1,0,1] if not (dx==0 and dy==0)]
40
+ elif mode == '+':
41
+ offsets = [(0,-1),(1,0),(0,1),(-1,0)]
42
+ elif mode == "5x5":
43
+ offsets = [(dx, dy) for dx in [-2,-1,0,1,2] for dy in [-2-1,0,1,2] if not (dx==0 and dy==0)]
44
+
45
+ for dx, dy in offsets:
46
+ nx, ny = x + dx, y + dy
47
+ if 0 <= nx < len(grid) and 0 <= ny < len(grid[0]):
48
+ val = grid[nx][ny]
49
+ counts[val] = counts.get(val, 0) + 1
50
+ return counts
51
+
52
+ def count_neighbours_np(grid_np, mode='3x3', max_val=None, kernel_cache={}):
53
+ if mode not in kernel_cache:
54
+ if mode[0] == 'c':
55
+ r = int(mode[1:])
56
+ size = 2*r + 1
57
+ center = r
58
+ kernel = np.zeros((size, size))
59
+ for dx in range(-r, r+1):
60
+ for dy in range(-r, r+1):
61
+ if 0 < dx**2 + dy**2 <= r**2:
62
+ kernel[dx+center, dy+center] = 1
63
+ elif mode == '3x3':
64
+ kernel = np.ones((3, 3)); kernel[1,1] = 0
65
+ elif mode == '+':
66
+ kernel = np.array([[0,1,0],[1,0,1],[0,1,0]])
67
+ elif mode == '5x5':
68
+ kernel = np.ones((5, 5)); kernel[2,2] = 0
69
+ kernel_cache[mode] = kernel
70
+ else:
71
+ kernel = kernel_cache[mode]
72
+
73
+ max_val = max(int(grid_np.max()), max_val) if max_val is not None else int(grid_np.max())
74
+ h, w = grid_np.shape
75
+ pad_h, pad_w = kernel.shape[0]//2, kernel.shape[1]//2
76
+
77
+ # tile-pad for toroidal wrap, then valid-convolve, avoids per-color loop overhead from mode='wrap' in ndimage
78
+ padded_grid = np.pad(grid_np, ((pad_h,pad_h),(pad_w,pad_w)), mode='wrap')
79
+
80
+ counts = np.zeros((max_val + 1, h, w), dtype=np.int32)
81
+ for v in range(max_val + 1):
82
+ mask = (padded_grid == v).astype(np.float32)
83
+ conv = fftconvolve(mask, kernel, mode='valid')
84
+ counts[v] = np.round(conv)
85
+
86
+ return counts
87
+
88
+ def superposition_entropy(neighbours, all_superpos, biasses):
89
+ '''
90
+ neighbours acces: neighbours[direction] = [neighbours]
91
+ all_superpos acces: all_superpos = [ter, ter, ter, ter, ter, ter]
92
+ biasses acces: biasses[terrain][direction] = [terrain, bias]
93
+ '''
94
+ allowed = set(all_superpos)
95
+ if not neighbours:
96
+ return allowed, len(allowed)
97
+
98
+ for direction, neighbour_list in neighbours.items():
99
+ allowed_from_dir = set()
100
+ for neighbour_terrain in neighbour_list:
101
+ for terrain, bias in biasses[neighbour_terrain][opposite_dir[direction]]:
102
+ if bias > 0:
103
+ allowed_from_dir.add(terrain)
104
+ allowed &= allowed_from_dir # intersect: must be valid from ALL directions
105
+
106
+ entropy = len(allowed)
107
+ return allowed, entropy
108
+
109
+ def List_is_list_2D(list1, list2):
110
+ for x in range(len(list1)):
111
+ for y in range(len(list1[x])):
112
+ if list1[x][y] != list2[x][y]:
113
+ return False
114
+ return True
115
+
116
+ def list_in_history(list, history):
117
+ for past in history:
118
+ if List_is_list_2D(list, past):
119
+ return True
120
+ return False
121
+
122
+ def leftover_2D(grid, search):
123
+ count = 0
124
+ for row in grid:
125
+ for item in row:
126
+ if item == search:
127
+ count += 1
128
+ return count
129
+
130
+ def print_grid(grid, align=4):
131
+ height = len(grid)
132
+ width = len(grid[0])
133
+ print()
134
+ print("╋━"+"━"*(align*width)+"━━╋")
135
+ print("┃"," "*(align*width)," ┃")
136
+ for row in range(height):
137
+ print("┃ ", end="")
138
+ for column in range(width):
139
+ item = str(grid[row][column])
140
+ print(item.rjust(align), end="")
141
+ print(" ┃")
142
+ print("┃"," "*(align*width)," ┃")
143
+ print("╋━"+"━"*(align*width)+"━━╋", )
144
+
145
+ def make_grid(length, width=None, values=(-1,), map_type=0, density=1.0, points=2):
146
+ if not width:
147
+ width = length
148
+
149
+ if map_type == 0:
150
+ return np.random.choice(values, size=(length, width))
151
+
152
+ if map_type == 1:
153
+ unique = [v for v in dict.fromkeys(values) if v != 0]
154
+
155
+ if isinstance(density, float):
156
+ density = [density for _ in range(len(unique))]
157
+
158
+ seeds_yx = []
159
+ seeds_val = []
160
+ for v in unique:
161
+ for _ in range(points):
162
+ seeds_yx.append((random.randint(0, length - 1), random.randint(0, width - 1)))
163
+ seeds_val.append(v)
164
+
165
+ if not seeds_yx:
166
+ return np.zeros((length, width), dtype=int), np.zeros((length, width), dtype=int)
167
+
168
+ seeds_yx = np.array(seeds_yx) # (N, 2)
169
+ seeds_val = np.array(seeds_val) # (N,)
170
+
171
+ yy, xx = np.indices((length, width)) # (length, width) each
172
+
173
+ # toroidal distance per seed
174
+ dy = np.abs(yy[..., None] - seeds_yx[:, 0]) # (length, width, N)
175
+ dy = np.minimum(dy, length - dy)
176
+ dx = np.abs(xx[..., None] - seeds_yx[:, 1])
177
+ dx = np.minimum(dx, width - dx)
178
+ dist2 = dy**2 + dx**2
179
+
180
+ closest_idx = np.argmin(dist2, axis=-1) # (length, width)
181
+ voronoi_map = seeds_val[closest_idx]
182
+
183
+ seed_to_value_idx = np.array([unique.index(v) for v in seeds_val]) # (N,)
184
+ density = np.array(density)
185
+ cell_density = density[seed_to_value_idx[closest_idx]]
186
+ mask = np.random.random((length, width)) < cell_density
187
+ grid = np.where(mask, voronoi_map, 0)
188
+
189
+ return grid, voronoi_map
190
+
191
+
192
+
193
+ # =========================
194
+ # -------INFO STUFF-------
195
+ # =========================
196
+
197
+ def info_time(asc_start, time1, asc_end, time2, message="Total time is: {difference}"):
198
+ print("\nStarted at:",asc_start)
199
+ print("Finished at:", asc_end)
200
+
201
+ dt1 = datetime.fromtimestamp(time1)
202
+ dt2 = datetime.fromtimestamp(time2)
203
+
204
+ difference = dt2 - dt1
205
+ print(message.format(difference = difference))
206
+
207
+ def print_set(a_set, name_only):
208
+ if not name_only:
209
+ for item in a_set:
210
+ print(f"{item}: {a_set[item]}")
211
+ else:
212
+ for item in a_set:
213
+ print(item)
214
+ # =========================
215
+ # -------MATH STUFF-------
216
+ # =========================
217
+
218
+ def lerp(x, start, end):
219
+ return round((end-start)*x*0.01, 2)
220
+
221
+ def smoothstep(x, start, end):
222
+ t = (x - start) / (end - start)
223
+ t = min(1, max(0, t))
224
+ return t * t * (3 - 2 * t)
225
+
226
+ def ease_in_out_spring(x, start, end):
227
+ if start == end:
228
+ return 0.0
229
+
230
+ t = (x - start) / (end - start)
231
+ t = max(0.0, min(1.0, t))
232
+
233
+ # damped oscillator centered at 0.5
234
+ damping = 10
235
+ frequency = 8 * math.pi
236
+
237
+ if t == 0 or t == 1:
238
+ return t
239
+
240
+ return (
241
+ 1
242
+ - math.exp(-damping * t)
243
+ * math.cos(frequency * t)
244
+ )
245
+
246
+
247
+ def credit():
248
+ print(
249
+ f"{ANSI.UP(1)+ANSI.CLEAR_LINE()+ANSI.rgb(ANSI.C.green_dark)}Loaded Module:{ANSI.F.END} Guli's {ANSI.rgb(ANSI.C.neon_purple)}goose{ANSI.rgb(ANSI.C.blue)}full{ANSI.F.END} stuff."
250
+ )
251
+ credit()
@@ -0,0 +1,83 @@
1
+ import ANSI
2
+ filename = __file__.split("\\")[-1]
3
+ print(f"(Loading module: {filename}..")
4
+
5
+ # this is just cool
6
+
7
+ def progress_bar(progress, max_progress, on="█", off="|", color_on=ANSI.C.GREEN, color_off=ANSI.C.RED, bar_width=5, bar_length=100, form=1, stick_out=0, name=""):
8
+ bar_width = max(3, bar_width)
9
+ print(ANSI.UP(bar_width + 2 + (1 if len(name) else 0)), end="")
10
+ padding = (bar_length + stick_out - len(name)) // 2
11
+ if len(name):
12
+ print(color_on +"=" * (padding+(len(name)%2==0)) + name + "=" * padding + ANSI.C.END)
13
+
14
+ on = on[0]
15
+ off = off[0]
16
+ if form==1:
17
+ bar_length += stick_out
18
+ percent = -(-progress*bar_length // max_progress)
19
+ print(color_on +"╔" + "═"*(bar_length-stick_out-1) + "╗")
20
+ print(color_on +"║"+on*min(percent, bar_length-stick_out-1) + color_off + off*(bar_length-percent-stick_out-1)+color_on+f"╚{"═"*stick_out}╗")
21
+
22
+ for i in range(bar_width-2):
23
+ print(color_on+"║" + on*percent +color_off + off*(bar_length-percent)+color_on+"║")
24
+
25
+ print(color_on +"║"+on*min(percent, bar_length-stick_out-1) + color_off + off*(bar_length-percent-stick_out-1) + color_on + f"╔{"═"*stick_out}╝")
26
+ print(color_on +"╚" + "═"*(bar_length-stick_out-1) + f"╝ {progress}/{max_progress}"+ANSI.C.END)
27
+ if form==0:
28
+ percent = -(-progress*bar_length // max_progress)
29
+ if percent == bar_length:
30
+ color_off = color_on
31
+ off = on # wouw
32
+ print(color_on+"╔" + "═"*bar_length + "╗")
33
+ for i in range(bar_width):
34
+ print(color_on+"║"+on*percent + color_off + off*(bar_length-percent)+ color_on +"║")
35
+ print(color_on+"╚" + "═"*bar_length + f"╝ {progress}/{max_progress}", color_off)
36
+
37
+ def INFO():
38
+ print(
39
+ f"{ANSI.C.FAINT}{'='*80}{ANSI.C.END}\n"
40
+ f"{ANSI.C.BOLD}Welcome to {ANSI.C.GREEN}PROGRESS{ANSI.C.RED}BAR{ANSI.C.END}\n\n"
41
+ f"{ANSI.C.BOLD}Usage:{ANSI.C.END}\n"
42
+ f" {ANSI.C.BLUE}progress_bar(progress, max_progress, [optional stuff]){ANSI.C.END}\n\n"
43
+ f"{ANSI.C.BOLD}Optional stuff:{ANSI.C.END}\n"
44
+ f" on Character for filled portion (default: '█')\n"
45
+ f" off Character for empty portion (default: '|')\n"
46
+ f" color_on Color for filled portion (default: GREEN)\n"
47
+ f" color_off Color for empty portion (default: RED)\n"
48
+ f" bar_width Height of the bar (default: 5, min: 3)\n"
49
+ f" bar_length Width of the bar (default: 100)\n"
50
+ f" form Shape: 0=flat, 1=battery (default: 1)\n"
51
+ f" stick_out Battery end size (default: 0)\n"
52
+ f" name Label shown above the bar (default: '')\n\n"
53
+ f"{ANSI.C.RED}NOTE: Print empty lines before calling progress_bar() - at least (bar_width + 2).{ANSI.C.END}\n\n"
54
+ f"Made by {ANSI.C.BOLD}{ANSI.C.UNDERLINE}GULI GULI{ANSI.C.END}\n"
55
+ f"{ANSI.C.FAINT}{'='*80}{ANSI.C.END}\n"
56
+ )
57
+
58
+
59
+
60
+
61
+ def main():
62
+ bigness = int(input("bigness: "))
63
+ width = 6 # AT LEAST 3
64
+ print("\n"*(width+2))
65
+ for i in range(bigness+1):
66
+ progress_bar(i, bigness, "█", "|", bar_width=width, bar_length=50, stick_out=1)
67
+ #time.sleep(0.1)
68
+ print("\n")
69
+
70
+
71
+
72
+ def credit():
73
+ print(
74
+ f"{ANSI.UP(1)+ANSI.CLEAR_LINE()+ANSI.C.GREEN}Loaded Module:{ANSI.C.END} Guli's {ANSI.C.BOLD+ANSI.C.GREEN}PROGRESS{ANSI.C.RED}BAR{ANSI.C.END}."
75
+ )
76
+ credit()
77
+
78
+ if __name__ == "__main__":
79
+ main()
80
+ INFO()
81
+
82
+
83
+
@@ -0,0 +1,53 @@
1
+ import pygame as pyg
2
+ import numpy as np
3
+
4
+
5
+ def init_window():
6
+ global window
7
+ window = pyg.display.set_mode((1920, 1080), pyg.RESIZABLE)
8
+
9
+ background = window
10
+
11
+ def resize_grid(grid, scale):
12
+ grid_scale = len(grid)
13
+ delta = scale - grid_scale
14
+
15
+ if delta > 0:
16
+ grid = [
17
+ row + [0] * delta
18
+ for row in grid
19
+ ]
20
+ grid.extend([[0] * scale for _ in range(delta)])
21
+
22
+ elif delta < 0:
23
+ grid = [
24
+ row[:scale]
25
+ for r, row in enumerate(grid)
26
+ if r < scale
27
+ ]
28
+
29
+ return grid # fix: was missing
30
+
31
+
32
+ def grid_to_surface(grid, colors, surface, grid_px, transparent_alive=0, transparent_dead=0, ghost=False):
33
+ alive_alpha = 255 - transparent_alive
34
+ dead_alpha = 255 - transparent_dead
35
+
36
+ arr = np.array(grid)
37
+ all_colors = np.array(colors, dtype=np.uint8)
38
+
39
+ if ghost:
40
+ all_colors = (all_colors // 3).astype(np.uint8)
41
+
42
+ mapped = np.where(arr == 0, len(colors) - 1, arr - 1)
43
+ mapped = np.where(arr > len(colors) - 1, arr - 1, mapped)
44
+
45
+ rgb_array = all_colors[mapped]
46
+ surf = pyg.surfarray.make_surface(rgb_array.transpose(1, 0, 2))
47
+
48
+ surf = surf.convert_alpha()
49
+ alpha = np.where(arr.T == 0, dead_alpha, alive_alpha).astype(np.uint8)
50
+ pyg.surfarray.pixels_alpha(surf)[:] = alpha
51
+
52
+ scaled = pyg.transform.scale(surf, (grid_px, surface.get_height()))
53
+ surface.blit(scaled, (0, 0))
@@ -0,0 +1,9 @@
1
+ [build-system]
2
+ requires = ["setuptools>=61.0"]
3
+ build-backend = "setuptools.build_meta"
4
+
5
+ [project]
6
+ name = "guli-tools"
7
+ version = "0.1.0"
8
+ description = "My reusable modules"
9
+ requires-python = ">=3.8"
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+