Kottaszerkesztés LilyPonddal OSX-en

A LilyPond ugyanaz a kottaszedésben, mint a LaTeX dokumentumszedésben, minden szempontból: tipográfiai szabványoknak és konvencióknak eleget tevő, gyönyörű kimenetet generál egy szöveges formában megadott forrásfájlból. Azonban nincs könnyű dolguk azoknak, akik össze szeretnék házasítani kedvenc Leopardjukkal. Sem a LilyPond grafikus felülete, sem a magyar fejlesztésű, nagyon sokat tudó LilyPondTool nevű jEdit plugin nem működik az OSX legújabb verziója alatt.

Kompromisszumos megoldásként nekem a TeXShop használata jött be. Amit így kapunk, az a PDF-előnézet, az ismerős munkafolyamat és a szintaxiskiemelés. Sajnos a hangról forrásfájlra ugrás nem működik, valamint a generált MIDI-t is kézzel kell megnyitnunk.

  1. Telepítés: Töltsük le innen a 2.12 verziót MacOS X alá, méghozzá a G3, G4, G5 Macs (sic!) változatot, akkor is, ha Intel alapú Mac-ünk van! Szokásos módon tegyük az /Applications könyvtárba a LilyPond.app-ot.
  2. Parancssori támogatás: A PDF-generálás sajnos ékezetes fájlneveknél nem működik, így írtam egy cseles shell scriptet, ami ezt megoldja, és az ideiglenes PostScript fájlt is eltakarítja:

    #! /bin/sh
    dirname=$(dirname "$1")
    basename=$(basename "$1" .ly)
    filename="${dirname}/${basename}"
    tempname="${dirname}/.tmp"
    /Applications/LilyPond.app/Contents/Resources/bin/lilypond -o "${tempname}" "$1"
    if [ -f "${tempname}.pdf" ]; then
    mv "${tempname}.pdf" "${filename}.pdf"
    fi
    if [ -f "${tempname}.midi" ]; then
    mv "${tempname}.midi" "${filename}.midi"
    fi
    rm -f "${tempname}.ps"

    Mentsük el /usr/bin/lilypond néven, és varázsoljuk futtathatóvá:

    sudo chmod +x /usr/bin/lilypond
  3. TexShop támogatás: Mivel a piszkos munkát elvégzi a fenti script, már csak az alábbi hihetetlenül bonyolult TeXShop engine-nel kell bővíteni a repertoárt ([cci]~/Library/TeXShop/Engines/LilyPond.engine[/cci]):

    #! /bin/sh
    echo "Processing..."
    lilypond "$1"
    echo "Done."

    Itt van még egy dummy LilyPond template ([cci]~/Library/TeXShop/Templates/LilyPond.tex[/cci]):
    [cc]
    \version “2.12.2”

    \header {
    title = “”
    composer = “”
    tagline = “”
    }

    \score {
    <>

    \midi {
    }

    \layout {
    }
    }

    \paper {
    }[/cc]

    Ezután nincs más dolgunk, mint hozzátársítani a [cci].ly[/cci] kiterjesztést a TeXShop.app-hoz, és készen is vagyunk.

Még egy dolog. Ha Finale vagy Sibelius kottáinkat át szeretnénk konvertálni LilyPondba, a migrációs folyamat köztes lépéseként a MusicXML formátumot vehetjük igénybe. A Finale alapból tartalmaz MusicXML plugint, a File/MusicXML/Export… paranccsal végezhető el az exportálás. Sibeliushoz külön le kell tölteni a megfelelő plugint, ehhez ez az oldal nyújt segítséget. (A plugin batch mode-ot is támogat, ezt érdemes kihasználni.)

A MusicXML fájlokat a [cci]/Applications/LilyPond.app/Contents/Resources/bin/musicxml2ly[/cci] programmal konvertálhatjuk LilyPondba. Ez nem tökéletes, sajnos még picit bugzik a segédprogram, én főleg a dalszövegek melizmáinál tapasztaltam problémát, úgyhogy ne felejtsük el utólag átnézni az eredményt, és szükség esetén kézzel finomhangolni.

Források

Java kimenet UTF-8 kódolásban – második felvonás

Ezt nem lehet megunni, újra és újra hasonló problémákba ütközök. Most kivételesen nem parancssorban kellett UTF-8 kimenetet generálnom, hanem a Java 6 beépített HTTP szerveréről a kliens felé adott generált válaszban merült fel ugyanez a probléma. A különös az volt, hogy működött, mindenféle konverzió nélkül, tehát teljesen nyugodt voltam, hogy ez a kódrészletet jól írtam meg. Órákba tellet rájönnöm, hogy ez a feltételezés hibás volt.

Ezt nem lehet megunni, újra és újra hasonló problémákba ütközök. Most kivételesen nem parancssorban kellett UTF-8 kimenetet generálnom, hanem a Java 6 beépített HTTP szerveréről a kliens felé adott generált válaszban merült fel ugyanez a probléma. A különös az volt, hogy működött, mindenféle konverzió nélkül, tehát teljesen nyugodt voltam, hogy ez a kódrészletet jól írtam meg. Órákba tellet rájönnöm, hogy ez a feltételezés hibás volt.

A problémakör egyszerű, bár érdekes. Widget-alapú AJAX-os webalkalmazást fejlesztek az önálló laboromhoz, de erről később. A lényeg az, hogy amikor a felhasználó csatlakozik a szerverhez, az egy generált HTML oldallal válaszol, és minden további feladatra JavaScript kódot küld, amit a kliens lefuttat. A javascript kódban a szövegeket előrelátóan Base64 kódolásban vittem át, így ezekkel probléma nem volt. Nem ez volt a helyzet azonban a generált HTML kóddal. Arra lettem figyelmes, hogy a webalkalmazást megváltoztatva a böngészőben nem jelenik meg semmi..

A helyzet felettébb furcsa volt, a generálás során nem merült fel hiba, sőt, a generált kimenet a szerver oldalon jó volt és az átvitel sem dobott kivételt. A kliens oldalon megérkeztek a fejléc sorai, de nem kapott kimenetet. Nem értettem a problémát, hiszen addig jó volt, és azon a részen nem változtattam. Hosszas próbálgatás és debugolás után rájöttem, hogy a hiba megjelenése erősen korrelál azzal a ténnyel, hogy a generált kimenetben szerepel-e ékezetes karakter. Ekkor merült fel bennem, hogy a probléma a kódolással van.

Tehát, a megoldás az, hogy előkeresem a [intlink id=”556″ type=”post”]korábbi cikkemet[/intlink], és az ott szereplő megoldást extrapolálom az én esetemre. Azaz, amikor a HttpExchange kimeneti adatfolyamát lekérem, egy egyszerű PrintStream helyett a következő módon wrappolom, és a böngészőt is értesítem róla, hogy milyen kódolásban kap adatot:


PrintStream out = new PrintStream(arg0.getResponseBody(),true,"UTF-8");
arg0.getResponseHeaders().add("Content-Type","text/html; charset=UTF-8");

A nagyobbik fejtörést az okozta, hogy még így se működött, a hiba ugyanaz maradt, csak annyi változott, hogy a Web dev toolbar már kijelezte az újonann beadott header sort is. Ekkor megakadt a szemem a következő soron:


arg0.sendResponseHeaders(200, text.toCharArray().length);
out.print(text);

Ezzel ugye elküldöm a kliensnek hibakódot (200 = OK), illetve a küldött tartalom hosszát. Ez automatikusan hozzáad egy “Content-Length” sort a header-ekhez. Amikor ezt írtam, jó ötletnek tünt. De! A java belső UCS kódolásában a karakterek száma nem egyezik meg a byte-ok számával a karakterlánc UTF-8 -beli kódolásában. A megoldás: a sendResponseHeaders() metódus második argumentuma legyen 0. Ez azt jelenti, hogy tetszőleges hosszúságú tartalmat küldhetünk el, a bytesorozat végét az jelzi, hogy bezárjuk a kapcsolatot.

Így tényleg működik. csak az érdekesség kedvéért egy rövid idézet a HttpExchange dokumentációjából:

"If the call to sendResponseHeaders() specified a fixed response body length, then the exact number of bytes specified in that call must be written to this stream. If too many bytes are written, then write() will throw an IOException. If too few bytes are written then the stream close() will throw an IOException. In both cases, the exchange is aborted and the underlying TCP connection closed."

Hogy mi ezzel a probléma? Csak az, hogy a dokumentáció szerint kivételt kellett volna kapnom, amikor úgy zárom le, hogy a küldött byte-ok száma nem egyezik az előre megadottal. Ez viszont nem történt meg, hanem egy furcsa, és visszakövethetetlen hibajelenségbe ütköztem. Talán gyorsabban megtalálom a hibát, ha kapok egy értelmes hibaüzenetet.

2D adatszerkezet modellezése Javában

…avagy hogyan lehet pozitív tulajdonság a gyengeség és a lustaság. 🙂

Arról a gyakran előforduló modellről van szó, amikor sorok és oszlopok metszeteiben rácselemek csücsülnek, melyek automatikusan létrejönnek a nekik megfelelő sor-oszlop párra való hivatkozáskor, valamint automatikusan megszűnnek soruk vagy oszlopuk törlése esetén.
A megvalósítás kézenfekvőnek tűnik: a sorokban/oszlopokban egy map-ben tároljuk az oszlopokkal/sorokkal indexelve a rácselemeket.

Valahogy így:
[cc_java]
public class Node {
}

public class Column {
}

public class Row {

protected final Map nodes = new HashMap();

public Map getNodes() {
return nodes;
}

}
[/cc_java]

Mi a gond ezzel?

  • Ha törlünk egy oszlopot, az összes sor map-jében még ott marad a rá mutató referencia, mint kulcs. Ez memory leakhez vezet: a szemétgyűjtő nem tudja eltakarítani a “zombi” oszlopokat és a hozzájuk tartozó, ugyancsak zombi rácselemeket. Ez ráadásul az adatstruktúra perzisztálásánál is problémát jelent.
  • Hogyan s mikor hozzuk létre a rácselemeket? Mindig, amikor létrehozunk egy oszlopot? Ezt jobban lehetne automatizálni, ráadásul ha nem minden rácspontba akarunk elemet tenni, fölöslegesen hozzuk létre ezeket.

Több megoldás is lehetséges, gondolhatnánk elsőre:

  • Gondolkodhatnánk egy címkézett gráfban, és a beépített kollekciók helyett alkalmazhatnánk valamiféle gráfkezelő könyvtárat, pl. a JGraphT-t, mely gondoskodik csúcs törlésekor a hozzá tartozó élekről.
  • Kibővíthetnénk a lista adatszerkezetet eseménykezelőkkel, melyek elem hozzáadásakor és törlésekor végrehajtanak egy megadott kódot.

Azonban a probléma megoldható a Java Collections Framework keretein belül, karöltve természetes kiegészítőjével, a Collections Generic API-val (a Commons Collections generikus változata). Nehogy már egy ilyen általános jelenséget ne tudjunk a megannyi hasznos absztrakciót tartalmazó Java nyelv elemeivel modellezni! A kulcsfogalom a gyenge referencia, mellyel befolyásolhatjuk a garbage collector működését, ezzel rábízva az elárvult elemek törlését.

Javában az alapértelmezett referencia erős (strong), de ezenkívül még létezik a gyenge (weak), lágy (soft) és fantom (phantom) referencia. A weak reference lényege, hogy amennyiben egy objektumra csak ilyenek mutatnak, a szemétgyűjtő teljes lelki nyugalommal eltakarítja. Nekünk pont ez a viselkedés jön kapóra: a map-ben gyenge referenciákat fogunk csak tárolni az oszlopokra/sorokra. (A másik két típus most nem érdekes számunkra, pedig azok is hasznosnak bizonyulhatnak más esetekben.)

A Collections API tartalmazza a WeakHashMap osztályt, mely a HashMap-hez hasonló, azonban kulcsai gyenge referenciák. A WeakHashMap ezeket átlátszóan kezeli, önmagától létrehozva és dereferálva nekünk őket. Így programunkban az automatikus törléshez csak két dolgot kell módosítanunk: HashMap helyett WeakHashMap-et használunk, és a kívánt pillanatban meghívjuk a garbage collectort.

A létrehozás pedig lusta map segítségével történik: a rácselemek példányosítása akkor és csak akkor történik, amikor először hivatkozunk az őket azonosító sor-oszlop párosra. Ehhez is kész eszközt kapunk a kezükbe a Collections Generic Libraryben: a LazyMap-et és az InstantiateFactory-t, melyek a Decorator és a Factory pattern alkalmazásával érik el céljukat.

Imhol a forráskód módosított része. Figyelemreméltó, hogy mennyi minden változott…
[cc_java]
public class Row {

protected final Map nodes = LazyMap.decorate(new WeakHashMap(), new InstantiateFactory(Node.class)); // !

}
[/cc_java]

És egy kis tesztosztály, a kiértékelés a kedves olvasó feladata:
[cc_java]
public class GridTest {

public static void main(String[] args) {
Grid grid = new Grid();
for (int i = 0; i < 2; i++) {
grid.getRows().add(new Row());
grid.getColumns().add(new Column());
}
for (Row row : grid.getRows()) {
for (Column column : grid.getColumns()) {
System.out.println(row.getNodes().get(column));
}
}
grid.getColumns().remove(1);
System.gc(); // !
for (Row row : grid.getRows()) {
for (Column column : row.getNodes().keySet()) {
System.out.println(row.getNodes().get(column));
}
}

}

}
[/cc_java]

Hát ilyen power a Collections Framework, amint már Stampie is [intlink id=”587″ type=”post”]rámutatott[/intlink], ami pedig esetleg hiányzik belőle, azt a Collections Generic pótolja. Mi a tanulság? Használjuk ki a nyelvi lehetőségeket, amelyek rendelkezésünkre állnak!

Dokumentumszerkesztés, ahogy Balage csinálja

Folytatva Stampie [[https://cubussapiens.hu/node/597|írását]], most szeretném én is a világ elé tárni az eszközök listáját, amely irodai jellegű munkáimat segíti (vagy gátolja, ez nem mindig triviális). A feladataim, melyek ilyen eszközöket követelnek, nagyjából hasonlóak, mint Stampie esetében, házi feladat dokumentációk, ritkán bemutatók egy-egy előadáshoz, illetve táblázatkezelés a pénzügyeim követésére, és néhány egyszeri számítás elvégzésére (ez alatt tipikusan a “mennyit fogok költeni karácsonyra” jellegű kalkulációkra gondolok).

Folytatva [intlink id=”597″ type=”post”]Stampie írását[/intlink], most szeretném én is a világ elé tárni az eszközök listáját, amely irodai jellegű munkáimat segíti (vagy gátolja, ez nem mindig triviális). A feladataim, melyek ilyen eszközöket követelnek, nagyjából hasonlóak, mint Stampie esetében, házi feladat dokumentációk, ritkán bemutatók egy-egy előadáshoz, illetve táblázatkezelés a pénzügyeim követésére, és néhány egyszeri számítás elvégzésére (ez alatt tipikusan a “mennyit fogok költeni karácsonyra” jellegű kalkulációkra gondolok).

Office csomagok

Linuxon nincs sok értelmesnek nevezhető alternatíva, próbálkoztam KOffice-al is, de a funkcionális gyengeségét nem ellensúlyozza a felhasználói felület egyszerűsége. Amit a jelenleg alpha állapotban lévő KOffice2-ről olvastam, a helyzet sokkal jobb lesz, de ebben az állapotban természetesen még nem alkalmas a komoly használatra.

Így jelenleg szinte kizárólagosan OpenOffice-t használok. Az általam ígényelt funkciókat tudja, a beépített PDF export meg biztosítja, hogy bárhol meg tudják tekinteni az alkotásaimat. A képletszerkesztője kifejezetten jó (tudom TeX-es kollegák most köhécselnek..), az ábrakészítője is használható, bár annál megesett, hogy káromkodva bezártam, és elővettem helyette az Inkscape-et, ami kifejezetten nem erre való, de mégis könnyebben megoldottam vele a feladatomat.

Néha felmerül olyan igény, hogy egy dokumentum jó lenne, ha interneten keresztűl megosztható lenne (megfelelő jogosultsággal, nem publikusan). Ekkor veszem elő a Google Docs nevű eszközt, amelyet az egyszerűség kedvéért Prism-ben futtatok. Ezt az eszközt 90%-ban táblázatkezelésre használtam, amivel meg vagyok elégedve, egyszerű formázásokat, és a megszokott parancsokat tudja. A dokumentumszerkesztő részét alig használtam párszor, de azt hiszem nem is fogom, egyszerűen túl keveset tud (egy képet nem sikerült rendesen beillesztenem a szöveg közé).

Egyéb eszközök

Én sajnos nem tudtam még eleget foglalkozni LaTeX-el, így ez nem szerepel a pallettámon, de DokuWiki-t előszeretettel használok. Bár jelenleg nincs összerakva erre offline rendszerem, de tervbe van véve..

Továbbá kiemelném még gyakran használt eszközként a KNotes nevezetű csodát, mely rövid emlékeztetőkre, feljegyzésekre kiválló. Támogat időzített figyelmeztetéseket, illetve opcionálisan RTF jellegű formázást is.

Körülbelül ennyi lenne. Jelenleg ezek az eszközök merülnek fel bennem hasonló feladat felmerülésekor, bár megjegyezném, ezek korántsem elégítik ki maradéktalanul az igényeimet, a közeljövőben (ahogy az időm engedi) szeretnék a témában változtatni, többek között jó lenne összerakni helyi jegyzetelésre egy wiki-t, illetve el kéne kezdenem foglalkozni LaTeX-el is.

Dokumentumszerkesztés OSX-en Stampie módra

Ez az írás egy tervezett sorozat első darabja: az ötlet (köszönet érte D-neenek) az volt, hogy írjuk le, hogy hogyan/miért úgy használjuk a gépünket különböző feladatok elvégzésére. Miután elméletben erről többen is írunk, ezért van rá esély, hogy a sorozat mások számára is hasznos lehet. Ha nem, akkor csak mi gondoltuk végig, hogy mit hogyan használunk, és ez segíthet abban, hogy még jobban összeszedjük a feladatainkat.

Ennyi bevezető után bele is csapnék a lecsóba: első alkalommal arról beszélnék beszélek írok, hogy mit használok dokumentumszerkesztésre. Illetve még inkább először is azt írnám le, hogy pontosan mit is értek itt dokumentumszerkesztésen. Első körben nagyjából azokat a feladatokat, amiket az Ms Office csomag elemeivel el lehet végezni (többé-kevésbé jó minőségben).

Kicsit részletesebben, illetve az általam végzett feladatokra szabva ez legfőképpen valamiféle szöveg készítése: a tipikus feladatok számomra mérési jegyzőkönyv, házi feladat, esetleg dokumentáció készítése, illetve egy-egy esetben prezentációt, illetve táblázatot készítek. Képeket, ábrákat lényegesen ritkábban készítek, ráadásul az egy külön kategóriát is alkothat a feladatok sokszínűsége miatt, ezért ebbe nem megyek most bele.

Office csomagok

A feladatokhoz nem csak egyféle programot használok, méghozzá azért, mert a különböző részfeladatoknál más-más igényeket kell kielégíteni. De az általánosságban elmondható, hogy Microsoft Office nincs a gépen (egy 2004-es Mac-es változatból volt egy demo fenn, de szerintem egyszer sem indítottam még el…). Office csomagból 2+1-féle van telepítve: egyrészt megvettem az Apple iWork csomagját, másfelől az OpenOffice csomagot használom (ebből nagyjából párhuzamosan használom a hivatalos OO.o buildet, illetve egy alternatív, régebb óta az OSX-re fejlesztett NeoOffice csomagot).

A csomagok közti választás viszonylag egyértelmű: szövegszerkesztési feladatokhoz sokkal egyértelműbb, hogy az OpenOffice/NeoOffice csomag a nyerő, mert a saját formátuma is hordozható, és mellesleg ismerik valamilyen szinten a Word dokumentumot is (meglepően jól egyébként – persze messze nem 100%-osan). Az pedig meglehetősen általános felhasználási scenario, hogy közösen készül egy házi feladat – és a partner nem (mindig) ismeri a LaTeXet… Szóval marad a kompromisszum.

Érdekes módon prezentációkészítésre ha csak egy lehetőségem van, mindig az Apple programját használom. Ez talán azzal magyarázható, hogy a prezentációim gyakorlatilag mindig egyedül készülnek, nem annyira gond az, hogy meg kell osztani másokkal, és így jobban merek engedni a kompatibilitásból. De ez a kompatibilitási probléma azért a bemutathatóságot nem befolyásolja: ugyan a ppt-exportálási opcióban nem hiszek (ha az import sem igazán tökéletesen működik, ez miért lenne jobb?), de a pdf export minden igényt kielégít. Egy prezentációnak amúgy sem az animációkról kell, hogy szóljon – minden másra meg tökéletesen megfelelő formátum a pdf.

De akkor miért is áldozom fel a hordozhatóságot (legalábbis részben)? Azért, mert az Apple Keynote egy hihetetlenül kiforrott program, jól megtervezett felhasználói felülettel. Tele van apró, ügyes megvalósításokkal, mint az elemek egymáshoz való igazítása (bármelyik szélhez, illetve középvonalhoz lehet illeszteni, szükség esetén akár többhöz egyszerre) vagy éppen az Inspector logika a formázások kezelésére. Ez az Inspector egy külön ablak, amiben a formázásokat lehet egységesen kezelni. Hasonló szerepet tölt be, mint az MS Office 2007-ben a Szalag: tematikusan rendezetten tárja elénk a funkciókat, de ugyanakkor kevésbé forradalmian új a felület, így gyorsabb megszokni… Mindenesetre, akinek lehetősége van az iWorks 08-at kipróbálni (értsd: mindenki, akinek Mac OSX van a gépére telepítve), érdemes megpróbálni.

Táblázatkezelés: na, itt nincs egyértelmű preferenciám. Tetszik a Numbers (iWork) új megoldása, miszerint egy munkalaphoz több táblázat is kapcsolódhat, stb., de ennél a pontnál azért lényegesen fontosabb a hordozhatóság, valamint az is problémát okozhat, hogy a Numbers még csak az 1.0-s verziónál tart, szóval nagyon kiforrottnak még nem tekinthető, és ráadásul a funkciókészlete is korlátozott egy kissé – de ha csak alapdolgokról van szó, de azt nagyon színesen-szagosan akarjuk végrehajtani, arra kiváló eszköz (lehet – de részletesen nem teszteltem még).

Egyéb szerkesztőeszközök

Persze jól kifejlett kockafejként nem csak az irodai szoftvercsomagokat használom szerkesztésre. Egyik érdekes koncepció, amit elég hosszú ideje próbálgatok, az a wiki alapú tárolás. Előnyei közé sorolható az abszolút hordozhatóság: megfelelően telepítve akár még a saját gépemre sincs szükség a szerkesztéshez – hátrányai közé viszont az, hogy egy saját leíró nyelvet kell hozzá megtanulni – ami a wikik között nem is hordozható. Az én személyes preferenciám a Dokuwiki – ez egyszerű dokumentáció írására kiváló, de komoly, sokfelhasználós rendszernek (a sok itt nem a több szinonímájaként szerepel – egy pár fős Dokuwiki telepítést évek óta – sztem – sikerrel üzemeltetek) véleményem szerint nem igazán alkalmas.

És végezetül megemlíteném még azt a tényt is, hogy LaTeX szerkesztést is csinálok időnként – korábban erre az Aquamacs program AucTeX környzetét használtam. Ügyes volt benne, hogy inline previewt képes készíteni sokféle formázáshoz, valamint a gyárilag egészen korrektül összelőtt pdfsync támogatás – ez a támogatás annyit jelent, hogy a TeX forrás és a generált pdf fájl kapcsolódó részei között gyorsan tudtam ugrálni.

A múlt idő viszont azért van, hogy az Emacs sosem állt túlságosan közel hozzám, és az Aquamacs nem Macesítette eléggé, hogy könnyen megszokhassam. Viszont helyette segítségemre sietett a fejlesztők abszolút nehéz súlyú eszköze – az Eclipse. Igen, abszolút nehéz súlyú, mert gyakorlatilag csak kávéfőzésre nem lehet megtanítani (ok, ilyen alapon az Emacs-ről is lehetne beszélni, lásd még az XKCD kapcsolódó epizódját), valamint ehhez jobban is értek. Szóval a TeXlipse környezet mellett döntöttem, és ebben próbáltam összelőni a megfelelő kapcsolatot az Eclipse és az általam használt pdfsync kompatibilis szerkesztőprogram között. Némi dokumentációböngészés, valamint egy gyors shell script megírása után (pontosabban a dokumentációban szereplő módosítása után, de ez aztán senkit sem érdekel) már működött is. A részleteket külön írásban fogom közzétenni (ide behivatkozva), hogy annyira ne dobjam szét az írás témáját – noha ez mostanra már nyilván tökéletesen sikerült…

Nagyjából ez az arzenálom, ami a dokumentumszerkesztést illeti – nyilván még egynéhány segédprogrammal támogatom meg ezt az arzenált, hogy a káosz teljes legyen – de ezt megintcsak nem akarom túl részletesen mellékelni, mert akkor nyilván az írás lényegét borítanám. Remélem, van, akinek segített valamit ez az írás – bár gyanítom, hogy aki elolvasta, mostanra a pokolba kíván, hogy ilyenekkel húzom az idejét – de úgy érzem, lesz ez még jobb is. Főleg, ha olyan témát választok, amiről többet tudok írni. (Akkor még több időt fogok elrabolni azoktól, akik végigolvassák, amit írtam… 🙂 )

Update: elkészült a [intlink id=”604″ type=”post”]LaTeX szerkesztésről[/intlink] az ígért cikk.