LCKB
[TOOL] Texture Coordinates - Printable Version

+- LCKB (https://lckb.dev/forum)
+-- Forum: ** OLD LCKB DATABASE ** (https://lckb.dev/forum/forumdisplay.php?fid=109)
+--- Forum: Release Zone (https://lckb.dev/forum/forumdisplay.php?fid=190)
+---- Forum: General Releases (https://lckb.dev/forum/forumdisplay.php?fid=127)
+----- Forum: General Tools Releases (https://lckb.dev/forum/forumdisplay.php?fid=214)
+----- Thread: [TOOL] Texture Coordinates (/showthread.php?tid=5101)



- Scura - 09-01-2024


Just releasing a private tool developed by me, written some times ago, it allow you to get the coordinates usefull for when you working with XML to get the right position.

 

import tkinter as tk
from tkinter import filedialog, Button, Entry, Toplevel
from tkinterdnd2 import DND_FILES, TkinterDnD
from PIL import Image, ImageTk
import cv2

class ImageCropper:
def __init__(self, root):
self.root = root
self.root.title("Image Cropper")
self.root.geometry("800x600")

self.load_button = Button(root, text="Load Image", command=self.open_image_window)
self.load_button.pack(expand=True)

self.root.drop_target_register(DND_FILES)
self.root.dnd_bind('<<Drop>>', self.on_drop)

self.image_window = None

def open_image_window(self):
file_path = filedialog.askopenfilename(filetypes=[("Image files", "*.png;*.jpg;*.jpeg;*.bmp")])
if file_path:
self.create_image_window(file_path)

def on_drop(self, event):
file_paths = self.root.tk.splitlist(event.data)
if file_paths:
self.create_image_window(file_paths[0])

def create_image_window(self, file_path):
if self.image_window:
self.image_window.destroy()

self.image_window = Toplevel(self.root)
self.image_window.title("Crop Image")

self.canvas = tk.Canvas(self.image_window, cursor="cross", bg="gray")
self.canvas.pack(side=tk.LEFT, fill=tk.BOTH, expand=True)

self.coord_frame = tk.Frame(self.image_window)
self.coord_frame.pack(side=tk.RIGHT, fill=tk.Y)

self.reset_button = Button(self.coord_frame, text="Reset Selection", command=self.reset_selection)
self.reset_button.pack(side=tk.TOP)

self.coord_entry = Entry(self.coord_frame, width=40)
self.coord_entry.pack(side=tk.TOP)

self.image = cv2.cvtColor(cv2.imread(file_path), cv2.COLOR_BGR2RGB)
self.original_image = self.image.copy()
self.scale = 1.0
self.update_display_image()

self.canvas.bind("<ButtonPress-1>", self.on_button_press)
self.canvas.bind("<B1-Motion>", self.on_drag)
self.canvas.bind("<ButtonRelease-1>", self.on_button_release)
self.canvas.bind("<MouseWheel>", self.zoom_image)
self.canvas.bind("<ButtonPress-2>", self.start_pan)
self.canvas.bind("<B2-Motion>", self.pan_image)

def update_display_image(self):
height, width, _ = self.image.shape
if width > 1920 or height > 1080:
scale_factor = min(1920/width, 1080/height)
width, height = int(width * scale_factor), int(height * scale_factor)
self.image = cv2.resize(self.image, (width, height))
self.original_image = self.image.copy()
self.scale = 1.0

self.canvas.config(width=width * self.scale, height=height * self.scale)
resized_image = cv2.resize(self.image, (int(width * self.scale), int(height * self.scale)))
self.tk_image = ImageTk.PhotoImage(image=Image.fromarray(resized_image))
self.canvas.create_image(0, 0, anchor="nw", image=self.tk_image)
self.canvas.config(scrollregion=self.canvas.bbox(tk.ALL))

def zoom_image(self, event):
if event.state == 0x04: # Ctrl key is pressed
if event.delta > 0:
self.scale *= 1.1
elif event.delta < 0:
self.scale *= 0.9
self.update_display_image()

def start_pan(self, event):
self.canvas.scan_mark(event.x, event.y)

def pan_image(self, event):
self.canvas.scan_dragto(event.x, event.y, gain=1)

def on_button_press(self, event):
if hasattr(self, 'rect_id'):
self.canvas.delete(self.rect_id)
self.start_x = self.canvas.canvasx(event.x)
self.start_y = self.canvas.canvasy(event.y)
self.rect_id = self.canvas.create_rectangle(self.start_x, self.start_y, self.start_x, self.start_y, outline="red")

def on_drag(self, event):
curX, curY = self.canvas.canvasx(event.x), self.canvas.canvasy(event.y)
self.canvas.coords(self.rect_id, self.start_x, self.start_y, curX, curY)

def on_button_release(self, event):
l, t, r, b = self.canvas.coords(self.rect_id)
self.coord_entry.delete(0, tk.END)
self.coord_entry.insert(0, f"l = {l/self.scale:.2f}, t = {t/self.scale:.2f}, r = {r/self.scale:.2f}, b = {b/self.scale:.2f}")

def reset_selection(self):
if hasattr(self, 'rect_id'):
self.canvas.delete(self.rect_id)
delattr(self, 'rect_id')

if __name__ == "__main__":
root = TkinterDnD.Tk()
app = ImageCropper(root)
root.mainloop()


Quote




#Requirements



Pillow==10.4.0

opencv-python==4.10.0.84

tkinterdnd2==0.1.0

numpy==2.1.0

 




2







Not sure which version is this .. may have some bugs, i just found it, and i thought about release. I wanted to add the zoom functionality but i never finish it. 




- kdy - 09-01-2024


good job ❤️




- Artox - 09-01-2024


nice release




- Scura - 09-01-2024







- NoopyyGaming - 09-01-2024


Nice job !