• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Czcionka OTF

0 głosów
175 wizyt
pytanie zadane 21 maja w Python przez Bg98 Nowicjusz (120 p.)

Witam,

Szukam wskazówek dotyczących tworzenia czcionki (.otf) w pythonie. Jestem totalnym amatorem, nigdy się tym nie zajmowałem. Udało mi się wygenerować czcionkę na podstawie plików graficznych .SVG, ale że czcionka posiada polskie znaki to litery ze zmiękczeniami generują się mniejsze od tych podstawowych, jest ktoś w stanie naprawić ten KOD ? 

proszę o odpowiedź jak dla amatora, nie znam się na programowaniu i potrzebuje prostej instrukcji.

import fontforge
import psMat
import os

# === KONFIGURACJA ===
SVG_DIR = r"C:\fontprojekt\svg"
OUTPUT_FONT = "MyFont.otf"

font = fontforge.font()
font.encoding = "UnicodeFull"
font.em = 1000
font.ascent = 800
font.descent = 200

font.fontname = "MyFont"
font.familyname = "MyFont"
font.fullname = "MyFont-Regular"
font.version = "1.0"

# === MAPOWANIE SVG → ZNAK ===
mapping = {
    "A.svg": "A", "Ą.svg": "Ą", "B.svg": "B", "C.svg": "C", "Ć.svg": "Ć",
    "D.svg": "D", "E.svg": "E", "Ę.svg": "Ę", "F.svg": "F", "G.svg": "G",
    "H.svg": "H", "I.svg": "I", "J.svg": "J", "K.svg": "K", "L.svg": "L",
    "Ł.svg": "Ł", "M.svg": "M", "N.svg": "N", "Ń.svg": "Ń", "O.svg": "O",
    "Ó.svg": "Ó", "P.svg": "P", "Q.svg": "Q", "R.svg": "R", "S.svg": "S",
    "Ś.svg": "Ś", "T.svg": "T", "U.svg": "U", "V.svg": "V", "W.svg": "W",
    "X.svg": "X", "Y.svg": "Y", "Z.svg": "Z", "Ź.svg": "Ź", "Ż.svg": "Ż",

    "0.svg": "0", "1.svg": "1", "2.svg": "2", "3.svg": "3", "4.svg": "4",
    "5.svg": "5", "6.svg": "6", "7.svg": "7", "8.svg": "8", "9.svg": "9",

    "KROPKA.svg": ".", "PRZECINEK.svg": ",",
    "MYSLNIK.svg": "-", "GWIAZDA.svg": "*", "KRZYZ.svg": "+"
}

# === PARAMETRY ===
MAX_HEIGHT = 700
SIDE_BEARING = 60

# === IMPORT SVG ===
for filename, char in mapping.items():
    filepath = os.path.join(SVG_DIR, filename)

    if not os.path.exists(filepath):
        print("Missing:", filename)
        continue

    print("Importing:", filename)

    glyph = font.createChar(ord(char))
    glyph.importOutlines(filepath)

    # 1. baseline correction
    bbox = glyph.boundingBox()
    glyph.transform(psMat.translate(0, -bbox[1]))

    # 2. scale do wysokości
    bbox = glyph.boundingBox()
    height = bbox[3] - bbox[1]

    if height > 0:
        scale = MAX_HEIGHT / height
        glyph.transform(psMat.scale(scale))

    # 3. nowy bbox po skali
    bbox = glyph.boundingBox()
    xmin, ymin, xmax, ymax = bbox

    # 4. wyśrodkowanie + margines
    glyph.transform(psMat.translate(-xmin + SIDE_BEARING, 0))

    # 5. FINAL bbox po wszystkich transformacjach
    bbox = glyph.boundingBox()
    xmin, ymin, xmax, ymax = bbox

    # 6. ustaw WIDTH NA KOŃCU (KLUCZ!)
    glyph.width = int((xmax - xmin) + 2 * SIDE_BEARING)

    # 7. czyszczenie geometrii
    glyph.removeOverlap()
    glyph.correctDirection()
    glyph.round()

# === FINALIZACJA FONTU ===
font.autoHint()
font.generate(OUTPUT_FONT, flags=("opentype",))

print("Font generated:", OUTPUT_FONT)

Był bym ogromnie wdzięczny!

Z góry dziękuję,

Pozdrawiam !

1 odpowiedź

+1 głos
odpowiedź 22 maja przez Oscar Nałogowiec (29,420 p.)

Skoro masz skalowanie wyrównujące wysokość to literki z różnych kreseczkami i ogonkami wyjdą bazowo mniejsze. Po prostu nie rób tego skalowania. Trochę nie rozumiem tego zastosowania plików SVG, ale nie znam Pythona więc nie znam też odpowiednich sposobów na bezpośrednie otwarcie właściwego fontu, robiłem to w Java - tam znalazłem odpowiednie funkcje:

        // FontsEngine - klasa pochodna od FontRenderContext, tam można przechwycić opis wektorowy
   	FontsEngine f2g = new FontsEngine();
        // ft - tekstowy opis fontu
    	Font f = Font.decode(ft);
        // text - sam źródłowy napis do zrenderowania
    	GlyphVector glyphs = f.createGlyphVector(f2g, text);
    	Rectangle2D box = glyphs.getVisualBounds();

 

Przypuszczam, że pythonie będą dostępne analogiczne metody. W wyniku otrzymuje się PathIterator, który opisuje kształt literek - trzeba tam się trochę pobawić z krzywymi Bezziera. Ja robiłem to w celu wygenerowania GCode do sterowania maszyną CNC - więc dodatkowo miałem narzuconą rozdzielczość wynikającą w rozmiaru narzędzia.

komentarz 22 maja przez Bg98 Nowicjusz (120 p.)
Dziękuję za odpowiedź, będę miał jakiś punkt zaczepienia i spróbuję coś wskórać analogicznie.

Podobne pytania

0 głosów
0 odpowiedzi 208 wizyt
pytanie zadane 13 sierpnia 2020 w HTML i CSS przez Ferrow Początkujący (360 p.)
0 głosów
1 odpowiedź 268 wizyt
pytanie zadane 3 lutego 2019 w PHP przez kon.bed21 Obywatel (1,610 p.)
0 głosów
3 odpowiedzi 2,106 wizyt
pytanie zadane 2 lutego 2019 w HTML i CSS przez GaryNJ Nowicjusz (240 p.)

93,742 zapytań

142,680 odpowiedzi

323,299 komentarzy

63,328 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj

Twierdza Linux. Bezpieczeństwo dla dociekliwych

Aby uzyskać rabat -10%, użyjcie kodu pasja-linux, wpisując go w specjalne pole w koszyku.

...