Bästa svaret
Jag kan inte tro att ingen har sagt Vim än. Vim!
När du kommer över den inledande inlärningskurvan, det är ett fantastiskt verktyg för att automatisera bort vardagliga programmeringsuppgifter. Jag ger dig ett exempel som jag använde tidigare idag.
Jag skapade en XML-läsarklass (ärvd från en bas-XML-klass) för en del av vår kodbas. .Xml såg ut så här.
...
Problemet var (på grund av den befintliga arkitekturen) att dessa fältvärden alla behövde vara privata datamedlemmar i Some\_XML\_Class i koden. Vilket innebar att jag skulle göra mycket meningslöst arbete med att omvandla field-one till std :: string m\_field\_one , för vart och ett av dessa fält.
Det är där Vim kommer in. I stället för att döda 20 minuter på det svåra sättet. Jag klistrade in ovanstående kodavsnitt och spelade in ett makro.
^xistd::string m\_
Denna serie vim-kommandon gör följande. Går till radens första tecken och raderar den (blir borttagen). Går in i infogningsläge och förbereder std :: string m\_ till fält . Sedan hittar den den första förekomsten av – och ersätter den med \_. Sedan hoppar den till slutet av ordet fält\_N , går in i tilläggsläge och lägger till ett semikolon och flyttar markören till höger. Så att vi nu har
std::string m\_field\_one;value="value1" />
Men vi är inte klara. Vi går sedan in i kommandoläge och tar bort resten av raden och hoppar ner till nästa. Så att vi har:
std::string m\_field\_one;
Observera att rad en är perfekt formaterad, och markören är för närvarande på rad två.
Den här nästa delen om där magin kommer in. Innan vi körde kommandot började vi spela in ett makro för att registrera a . Med kommandot q följt av a . Således gör du det fullständiga kommandot enligt följande (där det sista q används för att indikera makroavslutningen).
qa^xistd::string m\_
Nu, om väl, välj det makrot med Vim-kommandot:
@a
Det körs om makrot och formaterar automatiskt din nästa rad:
std::string m\_field\_one;
std::string m\_field\_two;
Men vänta, vi har fortfarande N-2-rader med liknande struktur! Låt oss anta att i detta fall var N lika med 100. Inga problem. Vi skriver helt enkelt kommandot:
98@a
Detta kör ovanstående makro 98 gånger till och formaterar automatiskt resten av din kod !! Vi har nu:
std::string m\_field\_one;
std::string m\_field\_two;
std::string m\_field\_three;
...
std::string m\_field\_ninetynine
std::string m\_field\_onehundered;
Stupendous .
* PS: Först kan dessa kommandon verka främmande och läskiga för dig, men när du väl har spenderat lite tid med Vim som din primära redaktör blir de andra natur. Exempelmakronet tog mig 10 sekunder att skriva och sparade mycket tid.
* PPS: Jag vet att exempelkoden är ganska dum, men jag använde den bara för att illustrera en punkt. Men i den verkliga världen kommer du att stöta på liknande fall.
Svar
Tack för att du frågade.
Jag kom hit ursprungligen för att varna för ett sådant mål, endast baserat på titeln … I grund och botten skulle du idag skriva en textredigerare för att:
- Du har ett mycket specifikt behov (men i det här fallet bör du fortfarande börja från en befintlig bas snarare än går från grunden, såvida du inte har väldigt nya idéer);
- ELLER tycker du det är en intressant övning i programmering; vilket verkligen är ditt mål.
För att, uppriktigt sagt, om du inte hittar din drömredaktör i hundratals, om inte tusentals befintliga, är du väldigt kräsen!; -)
Jag var också frestad att säga att att skriva en textredigerare från grunden kan vara lite skrämmande för en nybörjare; låt oss säga att det är en uppgift på mellannivå: lite svårt för en absolut nybörjare, görs en gång du får lite erfarenhet.
Som sagt, jag skrev min egen textredigerare medan jag fortfarande var nybörjare: nyligen ut ur universitetet, kodad bara lite i C, utan något riktigt projekt. Men jag var på en dator med SCO Unix som bara hade vi som redaktör. Och jag ogillar det på grund av dess två lägen (navigering mot utgåva) som alltid förvirrar mig (börjar skriva, ser min text först efter första jag …).
Så jag började bara koda min redaktör i C, med Curses som gränssnitt, gjorde mina egna datastrukturer (förmodligen ineffektiva, men vi hanterade små filer då), etc.
Jag hade mycket kul, jag lärde mig mycket, och när andra användare började använda det också, fick jag reda på att de alltid gör oväntade saker, som att blanda flikar och mellanslag … 🙂
Återigen, om du är en nybörjare bör du börja med mindre projekt, lära dig mer om språket (slingor, matriser, etc.), om datastrukturer, hur man läser och skriver textfiler osv.
Det är svårt att ge råd för ett språk … För ett JVM-baserat projekt skulle jag använda Ceylon, kanske med JavaFX eller SWT. För ett ”nära metallprojektet” skulle jag använda Rust (det finns ett startprojekt om att skriva en textredigerare i Rust, verkar lovande), medan andra skulle rekommendera att använda C ++ (vilket kan vara överväldigande för en nybörjare!). För ett enklare språk skulle Lua kanske passa bra (andra skulle rekommendera att använda Python, men jag har ingen erfarenhet av det). Eller kanske JavaScript, med Node.js och Electron-plattformen, ett trenderalternativ … (Atom, Visual Studio Code och Brackets har skrivits med det. Men det är knappt ”från början” eftersom de använder befintliga JS-kodredigerare. )
Allmänt råd: utforma först din datastruktur (den tvådelade strategin som används av Scintilla-projektet är bra; rep, som används av Rust-projektet, är lite mer / för mycket avancerade), hur du manipulerar data: hur man lägger till eller tar bort en karaktär, en rad, ett urval osv.
Tänk sedan på användargränssnittet. Helst separera de två (datahantering och datavisning). På det här sättet någon gång du kan ändra UI-målet (från Swing till JavaFX, från GTK + till Qt, vad som helst) med små eller inga förändringar i din baslogik. Bra för bärbarhet.