From b109e5573e37eea2e7e7bb76b9500abf755b38b7 Mon Sep 17 00:00:00 2001 From: tebarius Date: Sat, 26 Jul 2025 00:47:29 +0200 Subject: [PATCH] klopfcode, maptiles, quadtree --- app/app.py | 23 ++++-- app/tools.py | 217 +++++++++++++++++++++++---------------------------- 2 files changed, 113 insertions(+), 127 deletions(-) diff --git a/app/app.py b/app/app.py index 75eb78b..f217fb9 100644 --- a/app/app.py +++ b/app/app.py @@ -207,12 +207,20 @@ def auswahl_verarbeiten(): elif auswahl == "Polybios dekodieren": st.session_state.output_text = tools.polybios_decode(text, additional_parameter) st.session_state.map_data = None - elif auswahl == "REPLACE": - st.session_state.output_text = tools.REPLACE(text) + elif auswahl == "Klopfcode kodieren": + st.session_state.output_text = tools.klopfcode_encode(text) st.session_state.map_data = None - elif auswahl == "REPLACE": - st.session_state.output_text = tools.REPLACE(text) + elif auswahl == "Klopfcode dekodieren": + st.session_state.output_text = tools.klopfcode_decode(text) st.session_state.map_data = None + elif auswahl == "Maptiles/Kachelkoord.": + output, mapd = tools.maptiles_kachelkoordinaten(text) + st.session_state.output_text = output + st.session_state.map_data = mapd + elif auswahl == "Quadtree/Quadkey": + output, mapd = tools.quadtreekoordinaten(text) + st.session_state.output_text = output + st.session_state.map_data = mapd elif auswahl == "REPLACE": st.session_state.output_text = tools.REPLACE(text) st.session_state.map_data = None @@ -299,9 +307,10 @@ option = st.sidebar.radio("hidden_label", "Autokey-Chiffre", "Polybios kodieren", "Polybios dekodieren", - "", - "", - "", + "Klopfcode kodieren", + "Klopfcode dekodieren", + "Maptiles/Kachelkoord.", + "Quadtree/Quadkey", "Dummy mit Karte", ), key='option', diff --git a/app/tools.py b/app/tools.py index 6731564..a2275f8 100644 --- a/app/tools.py +++ b/app/tools.py @@ -2317,25 +2317,20 @@ def polybios_decode(eingabetext, pw): ausgabetext += f"|dekodiert|{ctext6}|\n" return ausgabetext -''' -def klopfcode_encode(): - hilfetext = """HILFE: [Klopfcode kodieren] -Der Klopfcode ist im Prinzip eine Polybios Chiffre -mit einem festen Schlüsselquadrat bei welchem nicht -I und J sondern C und K zusammengefasst werden. -siehe hier: - 1 2 3 4 5 -1 A B C D E -2 F G H I J -3 L M N O P -4 Q R S T U -5 V W X Y Z -""" - - eingabetext = Eingabe.get(1.0, END) +def klopfcode_encode(eingabetext): + hilfetext = ('"### Klopfcode kodieren\nDer Klopfcode ist im Prinzip eine Polybios Chiffre mit einem festen ' + 'Schlüsselquadrat bei welchem nicht I und J sondern C und K zusammengefasst werden. \n' + 'siehe hier: \n' + '| |1|2|3|4|5|\n' + '|-|-|-|-|-|-|\n' + '|1|A|B|C|D|E|\n' + '|2|F|G|H|I|J|\n' + '|3|L|M|N|O|P|\n' + '|4|Q|R|S|T|U|\n' + '|5|V|W|X|Y|Z|') text = eingabetext.rstrip() if text == "": - Ausgabe.insert(1.0, hilfetext + "\n") + return hilfetext else: qz5 = [11, 12, 13, 14, 15, 21, 22, 23, 24, 25, 31, 32, 33, 34, 35, 41, 42, 43, 44, 45, 51, 52, 53, 54, 55] alpha = "ABCDEFGHIJLMNOPQRSTUVWXYZ" # k wird durch c ersetzt @@ -2351,28 +2346,24 @@ siehe hier: ctext = "" for b in text5: ctext += wb5[b] - Ausgabe.insert(1.0, ctext + "\n") - Ausgabe.insert(1.0, "Klartext: " + text5 + "\n", "gr") + ausgabetext = f"Klartext: {text5} \n" + ausgabetext += f"kodiert: {ctext}" + return ausgabetext - -def klopfcode_decode(): - hilfetext = """HILFE: [Klopfcode dekodieren] -Der Klopfcode ist im Prinzip eine Polybios Chiffre -mit einem festen Schlüsselquadrat bei welchem nicht -I und J sondern C und K zusammengefasst werden. -siehe hier: - 1 2 3 4 5 -1 A B C D E -2 F G H I J -3 L M N O P -4 Q R S T U -5 V W X Y Z -""" - - eingabetext = Eingabe.get(1.0, END) +def klopfcode_decode(eingabetext): + hilfetext = ('"### Klopfcode kodieren\nDer Klopfcode ist im Prinzip eine Polybios Chiffre mit einem festen ' + 'Schlüsselquadrat bei welchem nicht I und J sondern C und K zusammengefasst werden. \n' + 'siehe hier: \n' + '| |1|2|3|4|5|\n' + '|-|-|-|-|-|-|\n' + '|1|A|B|C|D|E|\n' + '|2|F|G|H|I|J|\n' + '|3|L|M|N|O|P|\n' + '|4|Q|R|S|T|U|\n' + '|5|V|W|X|Y|Z|') text = eingabetext.rstrip() if text == "": - Ausgabe.insert(1.0, hilfetext + "\n") + return hilfetext else: qz5 = [11, 12, 14, 15, 21, 22, 23, 24, 25, 31, 32, 33, 34, 35, 41, 42, 43, 44, 45, 51, 52, 53, 54, 55] alpha = "ABDEFGHIJLMNOPQRSTUVWXYZ" # k wird durch c ersetzt @@ -2387,100 +2378,86 @@ siehe hier: if cc in wb: ctext += wb[cc] ctext += " " - Ausgabe.insert(1.0, ctext + "\n") - Ausgabe.insert(1.0, "Klopfcode dekodiert:\n", "bu") + return f"Klopfcode dekodiert: \n{ctext}" - -def maptiles_kachelkoordinaten(): - hilfetext = """HILFE: [Maptiles / Kachelkoordinaten] -Bei vielen Online-Kartendiensten wie Openstreetmap oder Google-Maps erfolgt die -Kartendarstellung über vorberechnete "Kachel"-Grafikdateien, welche ein -Adressierungssystem benötigen damit je nach Koordinate und Zoomstufe auch der -richtige Kartenausschnitt dargestellt und klar ist welche Kacheln daneben -darzustellen ist wird.Bei OSM ist eine solche Kachel eine PNG-Grafik mit 256x256 -Pixeln und je nach Zoomstufe ist eine unterschiedliche Anzahl solcher -Kacheln/Tiles notwendig um die ganze Welt abzubilden. Da je Zoomstufe sich die -Anzahl der benötigten Kacheln vervierfacht ist bei den meisten Diensten bei -Zoomlevel 18 Schluß, OSM geht bis Zoomlevel 19. -Um die einzelnen Kacheln beim tilemap-Server abzufragen braucht man die -Zoomstufe, einen X und einen Y-Wert wobei dies alles ganzzahlige Werte sind. -Aufgerufen von den Servern werden die Kacheln dann nach dem Muster: -"http://servername/Zoom/X/Y.png" Den Fernsehturm mit Zoomstufe 18 findet man -z.B. bei Openstreetmap hier:https://tile.openstreetmap.org/18/140836/85970.png - -Die Funktion arbeitet hier auf die Art und Weise, daß man 2 durch ein -Freizeichen getrennte Zahlen eingibt. Handelt es sich bei den angegebenen Zahlen -um "Kommazahlen" welche allerdings mit Punkt anzugeben sind -(Bsp: 52.520803 13.4088653 ) geht die Funktion davon aus, daß es sich um -Koordinaten in Dezimalgrad handelt und sofern es gültige Koordinaten sind -erfolgt eine Ausgabe der X und Y Werte für die Zoomstufen und 1-30. -(Positive Zahlen stehen für Nord und Ost, negative für Süd und West) - -Handelt es sich bei den beiden Zahlen um Ganzzahlen wird davon ausgegangen, daß -es sich um X und Y Werte handelt und es werde für alle Zoomstufen von 1-30 -Koordinaten in Dezimalminuten und Dezimalgrad ausgegeben, sofern dies sinnvolle -Koordinaten ergibt. -""" +def maptiles_kachelkoordinaten(eingabetext): + hilfetext = ('### Maptiles / Kachelkoordinaten\n' + 'Bei vielen Online-Kartendiensten wie Openstreetmap oder Google-Maps erfolgt die Kartendarstellung ' + 'über vorberechnete "Kachel"-Grafikdateien, welche ein Adressierungssystem benötigen damit je nach ' + 'Koordinate und Zoomstufe auch der richtige Kartenausschnitt dargestellt wird und klar ist welche ' + 'Kacheln daneben darzustellen sind. \n' + 'Solche Kacheln sind typischer Weise PNG-Grafiken mit 256x256 oder ' + '512x512 Pixeln und je nach Zoomstufe ist eine unterschiedliche Anzahl solcher Kacheln/Tiles ' + 'notwendig um die ganze Welt abzubilden. Da je Zoomstufe sich die Anzahl der benötigten Kacheln ' + 'vervierfacht und damit auch die Datenmenge werden in der Praxis keine Zoomlevel über 20 ' + 'verwendet. \n' + 'Um die einzelnen Kacheln beim tilemap-Server abzufragen braucht man die Zoomstufe, einen X- und ' + 'einen Y-Wert wobei dies alles ganzzahlige Werte sind. Abgerufen vom Tilemap-Server werden die ' + 'Kacheln dann nach dem Muster: `http://servername/Zoom/X/Y.png` Den Fernsehturm mit Zoomstufe 18 ' + 'findet man z.B. bei Openstreetmap hier: https://tile.openstreetmap.org/18/140836/85970.png \n' + 'Die Funktion arbeitet hier auf die Art und Weise, dass man 2 durch ein Freizeichen getrennte Zahlen ' + 'eingibt. Handelt es sich bei den angegebenen Zahlen um "Kommazahlen" welche allerdings mit Punkt ' + 'anzugeben sind (Bsp: 52.520803 13.4088653 ) geht die Funktion davon aus, daß es sich um Koordinaten ' + 'in Dezimalgrad handelt und sofern es gültige Koordinaten sind erfolgt eine Ausgabe der X und Y Werte ' + 'für die Zoomstufen und 1-25. (Positive Zahlen stehen für Nord und Ost, negative für Süd und West) ' + 'Handelt es sich bei den beiden Zahlen um Ganzzahlen wird davon ausgegangen, dass es sich um X und Y ' + 'Werte handelt und es werden für alle Zoomstufen von 1-25 Koordinaten in Dezimalminuten und ' + 'Dezimalgrad ausgegeben, sofern dies sinnvolle Koordinaten ergibt und sie werden auf einer Karte ' + 'angezeigt.') - eingabetext = Eingabe.get(1.0, END) text = eingabetext.rstrip() if text == "": - Ausgabe.insert(1.0, hilfetext + "\n") + return hilfetext, None else: text = text.split() if "." in text[0] and len(text) == 2: - for zoom in range(30, 0, -1): + ausgabetext = "DEC -> Maptiles \n|Zoom|X|Y|\n|-|-|-|\n" + for zoom in range(1, 26): try: la = float(text[0]) lo = float(text[1]) - if not la < -180 and not la > 180 and not lo < -180 and not lo > 180: + if not la < -85.05113 and not la > 85.05113 and not lo < -180 and not lo > 180: x, y = helper.dec_to_maptiles(la, lo, zoom) - Ausgabe.insert(1.0, "Zoom:{:>2} X:{:<10} Y:{}\n".format(zoom, x, y)) + ausgabetext += f"|{zoom:>2}|{x:<10}|{y}|\n" except ValueError: pass - Ausgabe.insert(1.0, "DEC -> Maptiles\n", "bu") + return ausgabetext, None elif len(text) == 2: - for zoom in range(30, 0, -1): + ausgabetext = "Maptiles->DEG,DEC \n|Zoom|DEG|DEC|\n|-|-|-|\n" + lat_list, lon_list = [], [] + for zoom in range(2, 26): try: la, lo = helper.maptiles_to_dec(int(text[0]), int(text[1]), zoom) - if not la < -180 and not la > 180 and not lo < -180 and not lo > 180: - Ausgabe.insert(1.0, "Zoom:{:>2} DEG: {:<23} DEC: {} {}\n".format(zoom, helper.dec_to_deg(la, lo), - round(la, 5), round(lo, 5))) - except ValueError: + if not la < -85.05113 and not la > 85.05113 and not lo < -180 and not lo > 180: + ausgabetext += f"|{zoom:>2}|{helper.dec_to_deg(la, lo):<23}|{round(la, 5)} {round(lo, 5)}| \n" + lat_list.append(la) + lon_list.append(lo) + except OverflowError: pass - Ausgabe.insert(1.0, "Maptiles->DEG,DEC\n", "bu") + return ausgabetext, pd.DataFrame({'lat': lat_list, 'lon': lon_list}) else: - Ausgabe.insert(1.0, "Zahlen konnten nicht ermittelt werden!\n", "re") + return "Zahlen konnten nicht ermittelt werden!", None - -def quadtreekoordinaten(): - hilfetext = """HILFE: [Quadtree-/Quadkeykoordinaten] -Diese Koordinatenkodierung spielt in der alltäglichen Praxis eigentlich -kaum noch ein Rolle, außer scheinbar bei bing-maps und beim Geocaching. -Sie dient ähnlich wie das Maptiles-System dazu Grafikdateien für -unterschiedliche Zoomstufen einer Karte zu adressieren. -Die Länge der Zahl entspricht hier zugleich auch dem Detailgrad bzw. -der Zoomstufe. Es finden nur die Zahlen 0,1,2 und 3 Verwendung, wobei -die 0 den Nordwestlichen Quadranten, 1 den Nordöstlichen, 2 SW und 3 SO. -Ein kleines Beispiel: 230 würde bedeuten es geht im südwestlichen -Quadranten (2) um den südöstlichen Quadranten(3) und in diesem wiederum -um den nordwestlichen Quadranten. -Je länger also diese Zahlenreihe aus 0,1,2 und 3 wird um so genauer wird -ein bestimmter Ort angegeben. -Weitere Infos gibt es unter folgendem Link zu finden: -https://docs.microsoft.com/en-us/bingmaps/articles/bing-maps-tile-system - -Die Funktion ermittelt aus einer Quadtreekoordinate die Maptileskoordinaten -und die WGS-Koordinaten. -""" - - eingabetext = Eingabe.get(1.0, END) +def quadtreekoordinaten(eingabetext): + hilfetext = ("### Quadtree-/Quadkeykoordinaten\n" + "Diese Koordinatenkodierung spielt in der alltäglichen Praxis eigentlich kaum noch ein Rolle, " + "außer scheinbar bei bing-maps und beim Geocaching. Sie dient ähnlich wie das Maptiles-System dazu " + "Grafikdateien für unterschiedliche Zoomstufen einer Karte zu adressieren. Die Länge der Zahl " + "entspricht hier zugleich auch dem Detailgrad bzw. der Zoomstufe. Es finden nur die Zahlen 0,1,2 " + "und 3 Verwendung, wobei die 0 den Nordwestlichen Quadranten, 1 den Nordöstlichen, 2 SW und 3 SO. \n" + "Ein kleines Beispiel: 230 würde bedeuten es geht im südwestlichen Quadranten (2) um den " + "südöstlichen Quadranten(3) und in diesem wiederum um den nordwestlichen Quadranten. Je länger " + "also diese Zahlenreihe aus 0,1,2 und 3 wird um so genauer wird ein bestimmter Ort angegeben. \n" + "Weitere Infos gibt es unter folgendem Link zu finden: " + "https://docs.microsoft.com/en-us/bingmaps/articles/bing-maps-tile-system \n" + "Die Funktion ermittelt aus einer Quadtreekoordinate die Maptileskoordinaten und die " + "WGS84-Koordinaten und zeigt diese auf einer Karte an.") text = eingabetext.rstrip() if text == "": - Ausgabe.insert(1.0, hilfetext + "\n") + return hilfetext, None else: - tilex = 0 - tiley = 0 + tile_x = 0 + tile_y = 0 quadkey = text fehler = 0 zoom = len(quadkey) @@ -2489,28 +2466,28 @@ und die WGS-Koordinaten. if quadkey[zoom - i] == "0": continue if quadkey[zoom - i] == "1": - tilex |= mask + tile_x |= mask continue if quadkey[zoom - i] == "2": - tiley |= mask + tile_y |= mask continue if quadkey[zoom - i] == "3": - tilex |= mask - tiley |= mask + tile_x |= mask + tile_y |= mask continue else: fehler += 1 - la, lo = maptiles_to_dec(tilex, tiley, zoom) + la, lo = helper.maptiles_to_dec(tile_x, tile_y, zoom) if fehler == 0: - Ausgabe.insert(1.0, "DEG: {}\n".format(dec_to_deg(la, lo))) - Ausgabe.insert(1.0, "DEC: {} {}\n".format(round(la, 5), round(lo, 5))) - Ausgabe.insert(1.0, "Maptiles: X:{} Y:{} Zoom:{}\n".format(tilex, tiley, zoom)) + ausgabetext = f"Maptiles: X:{tile_x} Y:{tile_y} Zoom:{zoom} \n" + ausgabetext += f"DEC: {round(la, 5)} {round(lo, 5)} \n" + ausgabetext += f"DEG: {helper.dec_to_deg(la, lo)}" + return ausgabetext, pd.DataFrame({'lat': [la], 'lon': [lo]}) else: - Ausgabe.insert(1.0, - "Es konnte keine gültige Quadtree-Koordinate erkannt werden.\n" - "(eine Zahl die nur die Ziffern 0,1,2,3 enthält)\n") - + return ("Es konnte keine gültige Quadtree-Koordinate erkannt werden. (eine Zahl die nur die Ziffern " + "0,1,2,3 enthält)"), None +''' def chronogramm(): hilfetext = """HILFE: [Chronogramm/ römische Ziffern zählen] Ein Chronogramm (oder Eteostichon) ist ein Satzteil, ein Satz, ein Sinnspruch