Kilka pytań odnośnie C#

Kilka pytań odnośnie C#
GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

1.) Czy wydajność (i szybkość uruchamiania) dość rozbudowanej aplikacji okienkowej - kilkanaście okien i po kilkadziesiąt kontrolek w każdym - jest aż na tyle niższa w stosunku do takiej samej aplikacji napisanej w C++ by dało się to odczuć?

2.) Wszyscy pewnie kojarzą funkcję CreateWindow / CreateWindowEx z WinAPI. Tworząc nowe okno lub kontrolkę musieliśmy podawać nazwę klasy okna jako drugi parametr. Czy w C# da się stworzyć okno lub kontrolkę podając własną nazwę klasy bez automatycznie dodawanych prefixów lub sufixów? Jak to się robi? Pokażcie proszę fragment kodu.

3.) Ile MB pamięci RAM zajmie uruchomiona aplikacja posiadająca jedno okno bez żadnych kontrolek? ~ 1 MB podobnie jak aplikacja napisana w C++?

4.) Jak wygląda konwersja liczba<->string? Jakieś metody w stylu toString(), toInt()?

5.) Czy wszystkie natywne w C# okna i kontrolki posiadają zaimplementowany mechanizm podwójnego buforowania, dzięki czemu są tzw. flicker-free? (Zakładam, że tak)

6.) To prawda, że w C# nie da się ręcznie zarządzać zwalnianiem pamięci bo wszystko wykonuje za nas GC? Czy można chociaż wpłynąć na to, kiedy się on uruchomi / na jak długo / ile pamięci zwolni / jakie obiekty zwolni / inne opcje?

edytowany 1x, ostatnio: Goodrock
somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:4 dni
  • Lokalizacja:Wrocław
0
Goodrock napisał(a):

1.) Czy wydajność (i szybkość uruchamiania) dość rozbudowanej aplikacji okienkowej - kilkanaście okien i po kilkadziesiąt kontrolek w każdym - jest aż na tyle niższa w stosunku do takiej samej aplikacji napisanej w C++ by dało się to odczuć?

Zależy jak jest napisana ta aplikacja, jeśli nie jest spierniczona, to na w miarę nowoczesnym komputerze dużej różnicy nie będzie.

2.) Wszyscy pewnie kojarzą funkcję CreateWindow / CreateWindowEx z WinAPI. Tworząc nowe okno lub kontrolkę musieliśmy podawać nazwę klasy okna jako drugi parametr. Czy w C# da się stworzyć okno lub kontrolkę podając własną nazwę klasy bez automatycznie dodawanych prefixów lub sufixów? Jak to się robi? Pokażcie proszę fragment kodu.

Nie, nie wszyscy. Niektórzy mają tę funkcję głęboko gdzieś.
Obiekty okien i kontrolek tworzy się tak samo jak obiekty każdego innego typu.

3.) Ile MB pamięci RAM zajmie uruchomiona aplikacja posiadająca jedno okno bez żadnych kontrolek? ~ 1 MB podobnie jak aplikacja napisana w C++?

Zależy od tego, ile CLR uzna za stosowne, wartość będzie się różniła w zależności od komputera.

4.) Jak wygląda konwersja liczba<->string? Jakieś metody w stylu toString(), toInt()?

Są.

6.) To prawda, że w C# nie da się ręcznie zarządzać zwalnianiem pamięci bo wszystko wykonuje za nas GC? Czy można chociaż wpłynąć na to, kiedy się on uruchomi / na jak długo / ile pamięci zwolni / jakie obiekty zwolni / inne opcje?

Można ręcznie wywołać np. GC.Collect(), ale na to co i ile zwolni nie ma się wpływu. I słusznie.

GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Nie, nie wszyscy. Niektórzy mają tę funkcję głęboko gdzieś.
Obiekty okien i kontrolek tworzy się tak samo jak obiekty każdego innego typu.

Źle mnie zrozumiałeś. Wiem, że w C# nie używa się tej funkcji. Ale chcę wiedzieć czy da się stworzyć okno tak, by jego klasa miała dokładnie taką nazwę jaką poda programista.

Można ręcznie wywołać np. GC.Collect(), ale na to co i ile zwolni nie ma się wpływu. I słusznie.

Czyli w C# też może zdarzyć się sytuacja, że GC odpali się w najmniej odpowiednim momencie powodując niechciany "freeze" aplikacji tak jak zdarza się to podobno w Javie?

somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:4 dni
  • Lokalizacja:Wrocław
0
Goodrock napisał(a):

Źle mnie zrozumiałeś. Wiem, że w C# nie używa się tej funkcji. Ale chcę wiedzieć czy da się stworzyć okno tak, by jego klasa miała dokładnie taką nazwę jaką poda programista.

Nie rozumiem. :)
Okno tworzysz tak:

Kopiuj
MojForm mf = new MojForm();

MojForm to nazwa klasy okna.

Czyli w C# też może zdarzyć się sytuacja, że GC odpali się w najmniej odpowiednim momencie powodując niechciany "freeze" aplikacji tak jak zdarza się to podobno w Javie?

Podobno. A jaki to najmniej oczekiwany moment?

GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Nie rozumiem.

Ok, ale zapewne kojarzysz np. nazwę Shell_TrayWnd? Albo inaczej: tworząc jakieś okno tak jak podałeś, C# wygeneruje coś w stylu:
WindowsForms10.Window.8.app.0.33c0d9d

EDIT: Wg informacji z tej strony nie da się:
http://stackoverflow.com/questions/2937888/winform-friendly-class-name

Podobno. A jaki to najmniej oczekiwany moment?

No jakiś zupełnie przypadkowy. Np. aplikacja wykonuje właśnie jakieś zadanie, które powinno się wykonać jak najszybciej, a tu nagle jep - GC robi nam niespodziankę :-) Wiem, że to już trochę czepianie się, ale interesuje mnie ta kwestia. A da się jakoś oszacować jak często odpala się GC? Kwestia sekund / minut czy raczej o tym decyduje ilość zajmowanej pamięci?

edytowany 1x, ostatnio: Goodrock
Lena(R)
  • Rejestracja:około 14 lat
  • Ostatnio:ponad 4 lata
  • Postów:98
0

Ja też nie bardzo rozumiem o co chodzi i czemu się uparłeś na CreateWindow i te dodatki znane z C++. W C# piszesz po prostu

Kopiuj
 
MojeOkienko okienko = new MojeOkienko();

Koniec, okienko utworzono, a słowo 'MojeOkienko' jest wprost skopiowane z nazwy klasy którą samemu można utworzyć, albo wspomóc się środowiskiem. Teraz wystarczy wywołać funkcję która pokazuje je na ekranie. W WPF będzie to:

Kopiuj
 okienko.Show(); 

albo (w zależności od potrzeby)

Kopiuj
 okienko.ShowDialog(); 

i wszystko działa.

Co do GC, to ja bym się na Twoim miejscu nie przejmował. To w miarę inteligentne narzędzie, które bez potrzeby nie uruchamia się (w Javie i mi się zdarzyło że tamtejszy GC potrafił włączyć się w dziwnym momencie, ale to też nie było zbyt częste, tutaj w sumie nie widać zbytnio jego działania). Jeżeli tak się o to dopytujesz, bo właśnie skończyłeś zabawę z C++ i czujesz potrzebę własnego zarządzania pamięcią, to to jest kwestia przyzwyczajenia się, że 'delete' coś robi za Ciebie. Mnie też to na początku irytowało, ale teraz widzę, że dzięki temu można nieraz fajne skróty w kodzie stosować, bo nie potrzeba myśleć o kasowaniu, przechowywania wskaźnika, sprawdzania czy nie jest NULL itd. Własne uruchamianie GC jest często zbędne, bo jeśli CLR przydziela odpowiednią ilość zasobów, to może się okazać, że GC uruchomi się raz przy wyłączaniu aplikacji (oczywiście, wszystko kwestia złożoności aplikacji).

somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:4 dni
  • Lokalizacja:Wrocław
0
Goodrock napisał(a):

Ok, ale zapewne kojarzysz np. nazwę Shell_TrayWnd?

Nie, a po co?
Nie każdy miał nieprzyjemność pisania w durnym C++.

Albo inaczej: tworząc jakieś okno tak jak podałeś, C# wygeneruje coś w stylu:
WindowsForms10.Window.8.app.0.33c0d9d

Na poziomie WinAPI czy czegoś takiego może tak. Ale jakie to ma znaczenie?

Np. aplikacja wykonuje właśnie jakieś zadanie, które powinno się wykonać jak najszybciej, a tu nagle jep - GC robi nam niespodziankę :-) Wiem, że to już trochę czepianie się, ale interesuje mnie ta kwestia. A da się jakoś oszacować jak często odpala się GC? Kwestia sekund / minut czy raczej o tym decyduje ilość zajmowanej pamięci?

Raczej liczba utworzonych obiektów. GC chyba domyślnie pracuje w trybie współbieżnym, pracując jednocześnie z aplikacją, więc nie powinien powodować jakichś dużych przerw, ale wszystko zależy od aplikacji.

Zobacz pozostały 1 komentarz
somekind
Ależ ja szanuję wszystkie wady C++, dlatego trzymam się od niego z daleka. A ataków się nie boję, bo osób dobrze piszących w C++ jest bardzo, bardzo mało.
ŁF
w dalszym ciągu jest to przemądrzałe zachowanie. zaprzestań.
somekind
"przemądrzały" != "ironiczny"
ŁF
no właśnie...
somekind
Chociaż to nawet niespecjalnie ironiczne nie było, przemądrzałe tym bardziej. Dwa fakty stwierdziłem.
GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Ok to temat GC uznajmy już za zakończony :-)

Wracając do klasy. Mylisz słowo kluczowe "class" służące do zdefiniowania nowej klasy z nazwą klasy windowsowego okna, która jest zwykłym stringiem. Używając RegisterClass() i CreateWindow zawsze trzeba było jako nazwę klasy podać tego samego stringa. W C# też jest to wykonywane (bo MUSI! - tak jest skonstruowany Windows) tyle, że niejawnie - jest to niewidoczne dla użytkownika i nie musi sobie zawracać tym głowy - i słusznie (w 99% przypadków) bo jest to wygodne.

Tworząc okno tak jak podałeś mogę Ci zagwarantować (choć nigdy nie pisałem w C#), że windowsowa klasa okna nie będzie się nazywać "MojeOkienko" lecz przyjmie postać podobną do "WindowsForms10.Window.8.app.0.33c0d9d". Widocznie C# silnie opiera się na tej nazwie zapisując w niej potrzebne informacje, co powoduje, że nie można i nie wolno jej zmieniać.

Teraz uruchom np. spy++ i sprawdź jakie nazwy klasy mają różne okna w systemie. Klasyczne kontrolki typu przycisk będą miały klasę BUTTON (w C# być może inną - jeśli te kontrolki zostały stworzone od nowa), inne np. EDIT, itp. Czasami pisząc aplikacje używało się funkcji FindWindow podając nazwę tej klasy by odnaleźć konkretne okno innej aplikacji (zakładając, że utworzona została tylko jedna instancja tegoż okna).

Ja jednak chciałbym napisać dość specyficzną aplikację, która z pewnych przyczyn technicznych (nie zależnych ode mnie) musi mieć w kilku oknach z góry narzucone nazwy klas. Wygląda na to, że pisząc GUI w C# musiałbym najpierw utworzyć za pomocą WinAPI te okna, a następnie kierować komunikaty do okien stworzonych przy użyciu C# czyli np. do MojeOkienko jak podałeś.

Post napisany w odniesieniu do posta Lena(R).

edytowany 2x, ostatnio: Goodrock
somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:4 dni
  • Lokalizacja:Wrocław
0
Goodrock napisał(a):

Wracając do klasy. Mylisz słowo kluczowe "class" służące do zdefiniowania nowej klasy z nazwą klasy windowsowego okna, która jest zwykłym stringiem.

Słowo klasa w kontekście paradygmatu programowania obiektowego ma bardzo precyzyjne znaczenie, i ani @lena(R), ani ja źle go tutaj nie użyliśmy.

Ja jednak chciałbym napisać dość specyficzną aplikację, która z pewnych przyczyn technicznych (nie zależnych ode mnie) musi mieć w kilku oknach z góry narzucone nazwy klas.

No cóż, ta potrzeba jest tak ekscentryczna i bez praktycznego znaczenia dla ogółu programistów, że faktycznie nie jest to obsługiwane w C#.

GO
Nie twierdzę, że nie znacie tego pojęcia ani, że źle go użyliście. Po prostu Lena pisał o klasie - jak to sam ująłeś - w kontekście paradygmatu programowania obiektowego. Mnie natomiast chodziło o klasę okna windowsowego. Zresztą już wszystko wyjaśnione w tej kwestii.
carck3r
  • Rejestracja:około 16 lat
  • Ostatnio:prawie 10 lat
  • Postów:68
0

1.) Czy wydajność (i szybkość uruchamiania) dość rozbudowanej aplikacji okienkowej - kilkanaście okien i po kilkadziesiąt kontrolek w każdym - jest aż na tyle niższa w stosunku do takiej samej aplikacji napisanej w C++ by dało się to odczuć?

Nie ma dużej różnicy.

2.) Wszyscy pewnie kojarzą funkcję CreateWindow / CreateWindowEx z WinAPI. Tworząc nowe okno lub kontrolkę musieliśmy podawać nazwę klasy okna jako drugi parametr. Czy w C# da się stworzyć okno lub kontrolkę podając własną nazwę klasy bez automatycznie dodawanych prefixów lub sufixów? Jak to się robi? Pokażcie proszę fragment kodu.

Nie da się. Po co Ci to? :)

3.) Ile MB pamięci RAM zajmie uruchomiona aplikacja posiadająca jedno okno bez żadnych kontrolek? ~ 1 MB podobnie jak aplikacja napisana w C++?

Przed chwilą stworzyłem, uruchomiłem i zjada 3060 KB (wg Windowsowskiego Menedżera Zadań). Wg Process Explorer zjada 12352 KB (kolumna Private Bytes). Nie wiem dlaczego taka różnica.

4.) Jak wygląda konwersja liczba<->string? Jakieś metody w stylu toString(), toInt()?

Kopiuj
const int I = 102;
string str = I.ToString(CultureInfo.InvariantCulture);

6.) To prawda, że w C# nie da się ręcznie zarządzać zwalnianiem pamięci bo wszystko wykonuje za nas GC? Czy można chociaż wpłynąć na to, kiedy się on uruchomi / na jak długo / ile pamięci zwolni / jakie obiekty zwolni / inne opcje?

Nigdy tego nie używałem :).

Kopiuj
GC.Collect();

http://msdn.microsoft.com/en-us/library/xe0c2357.aspx

edytowany 2x, ostatnio: carck3r
Azarien
  • Rejestracja:ponad 21 lat
  • Ostatnio:dzień
3

Nie da się. Po co Ci to?
oj tam od razu się nie da.

Kopiuj
        protected override CreateParams CreateParams
        {
            get
            {
                const int CS_GLOBALCLASS = 0x4000;
                CreateParams cp = base.CreateParams;
                cp.ClassName = "ToJestNazwaKlasy";
                cp.ClassStyle = cp.ClassStyle | CS_GLOBALCLASS;
                return cp;
            }
        }

Tylko że klasa musi już (globalnie) istnieć. Można się pobawić w wywołanie RegisterClass() przed utworzeniem okna.

somekind napisał(a)

Powód przeniesienia: Wątek dotyczący podstaw
Pytanie o klasę okna zdecydowanie podstaw nie dotyczy.

edytowany 1x, ostatnio: Azarien
somekind
Ta, ale pozostałe pytania to pytania typowego newbie, któremu się nie chciało skorzystać z Google. A co do "klasy okna", to z pierwszego postu nie wiadomo było dokładnie o co chodzi.
Azarien
  • Rejestracja:ponad 21 lat
  • Ostatnio:dzień
2
Azarien napisał(a)

Można się pobawić w wywołanie RegisterClass() przed utworzeniem okna.

Kopiuj
using System;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace WindowsFormsApplication4
{
    
    public partial class Form1 : Form
    {
        const int CS_GLOBALCLASS = 0x4000;
        const string nazwaKlasy = "ToJestNazwaKlasy";

        [UnmanagedFunctionPointer(CallingConvention.StdCall, SetLastError = true)]
        delegate IntPtr TWndProc(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam);

        [DllImport("user32.dll", SetLastError = true, CharSet=CharSet.Unicode)]
        static extern IntPtr DefWindowProc(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam);

        [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
        struct WNDCLASS
        {
            public uint style;
            public TWndProc lpfnWndProc;
            public int cbClsExtra;
            public int cbWndExtra;
            public IntPtr hInstance;
            public IntPtr hIcon;
            public IntPtr hCursor;
            public IntPtr hbrBackground;
            public string lpszMenuName;
            public string lpszClassName;
        }

        [DllImport("user32.dll", SetLastError = true, CharSet=CharSet.Unicode)]
        static extern ushort RegisterClass([In] ref WNDCLASS lpWndClass);

        public static void ZarejestrujKlasę()
        {
            WNDCLASS wc = new WNDCLASS();
            wc.lpszClassName = nazwaKlasy;
            wc.lpfnWndProc = DefWindowProc;
            wc.style = CS_GLOBALCLASS;
            RegisterClass(ref wc);
            int error = Marshal.GetLastWin32Error();
            if (error != 0)
                throw (new Exception(String.Format("Cannot register window class, GetLastError={0}", error)));
        }

        public Form1()
        {
            InitializeComponent();
        }

        protected override CreateParams CreateParams
        {
            get
            {
                CreateParams cp = base.CreateParams;
                cp.ClassName = nazwaKlasy;
                cp.ClassStyle = cp.ClassStyle | CS_GLOBALCLASS;
                return cp;
            }
        }
    }  
}

...

Kopiuj
using System;
using System.Windows.Forms;

namespace WindowsFormsApplication4
{
    static class Program
    {
        [STAThread]
        static void Main()
        {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
            Form1.ZarejestrujKlasę(); // ### tutaj ###
            Application.Run(new Form1());
        }
    }
}
edytowany 2x, ostatnio: Azarien
S3
  • Rejestracja:prawie 14 lat
  • Ostatnio:prawie 11 lat
  • Postów:61
0
Goodrock napisał(a):

1.) Czy wydajność (i szybkość uruchamiania) dość rozbudowanej aplikacji okienkowej - kilkanaście okien i po kilkadziesiąt kontrolek w każdym - jest aż na tyle niższa w stosunku do takiej samej aplikacji napisanej w C++ by dało się to odczuć?

Wg mnie tak. Widziałem aplikację (bardzo rozbudowaną) napisaną w WPF + EDM oraz realizującą podobną logikę napisaną w MFC + czyste Ado.net, różnica była ogromna - odświeżenie grida z kilkudziesięcioma rekordami w MFC było praktycznie niezauważalne, w WPFie trwało to kilka sekund.

somekind
No dobra, ale on o WinFormsy pyta.
GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Ściągnąłem sobie Visual C# 2010 Express i wykorzystałem kod tej klasy (2gi post):
http://stackoverflow.com/questions/128561/registering-a-custom-win32-window-class-from-c-sharp?answertab=votes#tab-top
Działa OK i na razie mi to wystarcza, ale dzięki Azarien za przedstawienie pozostałych rozwiązań - pewnie przyda mi się to później.

Nie da się. Po co Ci to?

Nie mogę napisać bo dyskusja pójdzie w złą stronę. Ale mam swoje powody.

Teraz zastanawiają mnie jeszcze inne kwestie:
1.) Co z tzw. Activation Contexts - C# ma jakieś wbudowane obiekty do obsługi tego czy znowu trzeba się bawić Windows API? Potrzebuję załadować obiekty shella, które tego wymagają.
2.) Jak zrzutować IntPtr by móc bezpośrednio wykonać np. "->zmiennaZeStruktury = 10;" czyli bez tworzenia jej kopii?

Azarien
  • Rejestracja:ponad 21 lat
  • Ostatnio:dzień
1

Coś mi się wydaje, że
albo wcale nie potrzebujesz pisać tak niskopoziomowo, tylko ci się wydaje;
albo wiesz co robisz (i nie mylisz się), ale C# nie jest najlepszym wyborem jeśli chodzi o język w takim razie.

GO
Raczej ta druga opcja, bo mimo wszystko i tak będę zmuszony wykonywać wiele operacji niskopoziomowych. Opiera się to głównie na wykorzystywaniu różnorakich funkcji "shell api". Sam C# bardzo by mi pomógł w szybszym stworzeniu interfejsu. A okien i kontrolek będzie masa. Ale dzięki tej dyskusji przynajmniej wiem jak ma się sytuacja.
somekind
Moderator
  • Rejestracja:około 17 lat
  • Ostatnio:4 dni
  • Lokalizacja:Wrocław
0

@Goodrock, to czemu interfejsu nie napiszesz w C#, a logiki niskopoziomowej w C++/CLI?

Azarien
  • Rejestracja:ponad 21 lat
  • Ostatnio:dzień
0

Opiera się to głównie na wykorzystywaniu różnorakich funkcji "shell api"
No to możesz używać, ale ograniczając to do wymaganego minimum — po co chcesz tworzyć okno od początku w WinAPI?

GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Na razie chyba będę dalej kodował w WinAPI bo już daleko zaszedłem i aplikacja zaczyna powoli coś sobą reprezentować.

to czemu interfejsu nie napiszesz w C#, a logiki niskopoziomowej w C++/CLI?

Bo aplikacja, którą tworzę wymaga sporego nakładu pracy i ostrożności. Nie znam ani C# (dopiero wczoraj i dziś zacząłem mu się przyglądać) ani C++/CLI. Mam obawę, że jak dorzucę sobie jeszcze konieczność używania dodatkowo C# i C++/CLI nie znając ich dobrze to skomplikuję sobie sprawę jeszcze bardziej i przez to znacząco wydłużę czas pracy. Poza tym dochodzi jeszcze reverse-engineering.

No to możesz używać, ale ograniczając to do wymaganego minimum

Cały czas staram się to ograniczać do minimum, ale pewne funkcjonalności i tak muszę oprzeć na tych funkcjach.

po co chcesz tworzyć okno od początku w WinAPI?

Nie chcę. I mogę zastosować drugie rozwiązanie jakie podałeś. Ale to już nie chodzi o to, bo teraz pojawiła się kwestia wczytywania tych obiektów COM. Potem mogą się pojawić inne niskopoziomowe sprawy...

Azarien
COM w C# akurat nie jest takie strasznie niskopoziomowe, bo jest wspierane przez sam język...
GO
  • Rejestracja:prawie 17 lat
  • Ostatnio:ponad 10 lat
0

Ja potrzebuję móc wywołać funkcje:

Kopiuj
CreateActCtxW();
ActivateActCtx();
DeactivateActCtx();
ReleaseActCtx();

itp. Da się bez WinAPI?

edytowany 4x, ostatnio: Goodrock
Kliknij, aby dodać treść...

Pomoc 1.18.8

Typografia

Edytor obsługuje składnie Markdown, w której pojedynczy akcent *kursywa* oraz _kursywa_ to pochylenie. Z kolei podwójny akcent **pogrubienie** oraz __pogrubienie__ to pogrubienie. Dodanie znaczników ~~strike~~ to przekreślenie.

Możesz dodać formatowanie komendami , , oraz .

Ponieważ dekoracja podkreślenia jest przeznaczona na linki, markdown nie zawiera specjalnej składni dla podkreślenia. Dlatego by dodać podkreślenie, użyj <u>underline</u>.

Komendy formatujące reagują na skróty klawiszowe: Ctrl+B, Ctrl+I, Ctrl+U oraz Ctrl+S.

Linki

By dodać link w edytorze użyj komendy lub użyj składni [title](link). URL umieszczony w linku lub nawet URL umieszczony bezpośrednio w tekście będzie aktywny i klikalny.

Jeżeli chcesz, możesz samodzielnie dodać link: <a href="link">title</a>.

Wewnętrzne odnośniki

Możesz umieścić odnośnik do wewnętrznej podstrony, używając następującej składni: [[Delphi/Kompendium]] lub [[Delphi/Kompendium|kliknij, aby przejść do kompendium]]. Odnośniki mogą prowadzić do Forum 4programmers.net lub np. do Kompendium.

Wspomnienia użytkowników

By wspomnieć użytkownika forum, wpisz w formularzu znak @. Zobaczysz okienko samouzupełniające nazwy użytkowników. Samouzupełnienie dobierze odpowiedni format wspomnienia, zależnie od tego czy w nazwie użytkownika znajduje się spacja.

Znaczniki HTML

Dozwolone jest używanie niektórych znaczników HTML: <a>, <b>, <i>, <kbd>, <del>, <strong>, <dfn>, <pre>, <blockquote>, <hr/>, <sub>, <sup> oraz <img/>.

Skróty klawiszowe

Dodaj kombinację klawiszy komendą notacji klawiszy lub skrótem klawiszowym Alt+K.

Reprezentuj kombinacje klawiszowe używając taga <kbd>. Oddziel od siebie klawisze znakiem plus, np <kbd>Alt+Tab</kbd>.

Indeks górny oraz dolny

Przykład: wpisując H<sub>2</sub>O i m<sup>2</sup> otrzymasz: H2O i m2.

Składnia Tex

By precyzyjnie wyrazić działanie matematyczne, użyj składni Tex.

<tex>arcctg(x) = argtan(\frac{1}{x}) = arcsin(\frac{1}{\sqrt{1+x^2}})</tex>

Kod źródłowy

Krótkie fragmenty kodu

Wszelkie jednolinijkowe instrukcje języka programowania powinny być zawarte pomiędzy obróconymi apostrofami: `kod instrukcji` lub ``console.log(`string`);``.

Kod wielolinijkowy

Dodaj fragment kodu komendą . Fragmenty kodu zajmujące całą lub więcej linijek powinny być umieszczone w wielolinijkowym fragmencie kodu. Znaczniki ``` lub ~~~ umożliwiają kolorowanie różnych języków programowania. Możemy nadać nazwę języka programowania używając auto-uzupełnienia, kod został pokolorowany używając konkretnych ustawień kolorowania składni:

```javascript
document.write('Hello World');
```

Możesz zaznaczyć również już wklejony kod w edytorze, i użyć komendy  by zamienić go w kod. Użyj kombinacji Ctrl+`, by dodać fragment kodu bez oznaczników języka.

Tabelki

Dodaj przykładową tabelkę używając komendy . Przykładowa tabelka składa się z dwóch kolumn, nagłówka i jednego wiersza.

Wygeneruj tabelkę na podstawie szablonu. Oddziel komórki separatorem ; lub |, a następnie zaznacz szablonu.

nazwisko;dziedzina;odkrycie
Pitagoras;mathematics;Pythagorean Theorem
Albert Einstein;physics;General Relativity
Marie Curie, Pierre Curie;chemistry;Radium, Polonium

Użyj komendy by zamienić zaznaczony szablon na tabelkę Markdown.

Lista uporządkowana i nieuporządkowana

Możliwe jest tworzenie listy numerowanych oraz wypunktowanych. Wystarczy, że pierwszym znakiem linii będzie * lub - dla listy nieuporządkowanej oraz 1. dla listy uporządkowanej.

Użyj komendy by dodać listę uporządkowaną.

1. Lista numerowana
2. Lista numerowana

Użyj komendy by dodać listę nieuporządkowaną.

* Lista wypunktowana
* Lista wypunktowana
** Lista wypunktowana (drugi poziom)

Składnia Markdown

Edytor obsługuje składnię Markdown, która składa się ze znaków specjalnych. Dostępne komendy, jak formatowanie , dodanie tabelki lub fragmentu kodu są w pewnym sensie świadome otaczającej jej składni, i postarają się unikać uszkodzenia jej.

Dla przykładu, używając tylko dostępnych komend, nie możemy dodać formatowania pogrubienia do kodu wielolinijkowego, albo dodać listy do tabelki - mogłoby to doprowadzić do uszkodzenia składni.

W pewnych odosobnionych przypadkach brak nowej linii przed elementami markdown również mógłby uszkodzić składnie, dlatego edytor dodaje brakujące nowe linie. Dla przykładu, dodanie formatowania pochylenia zaraz po tabelce, mogłoby zostać błędne zinterpretowane, więc edytor doda oddzielającą nową linię pomiędzy tabelką, a pochyleniem.

Skróty klawiszowe

Skróty formatujące, kiedy w edytorze znajduje się pojedynczy kursor, wstawiają sformatowany tekst przykładowy. Jeśli w edytorze znajduje się zaznaczenie (słowo, linijka, paragraf), wtedy zaznaczenie zostaje sformatowane.

  • Ctrl+B - dodaj pogrubienie lub pogrub zaznaczenie
  • Ctrl+I - dodaj pochylenie lub pochyl zaznaczenie
  • Ctrl+U - dodaj podkreślenie lub podkreśl zaznaczenie
  • Ctrl+S - dodaj przekreślenie lub przekreśl zaznaczenie

Notacja Klawiszy

  • Alt+K - dodaj notację klawiszy

Fragment kodu bez oznacznika

  • Alt+C - dodaj pusty fragment kodu

Skróty operujące na kodzie i linijkach:

  • Alt+L - zaznaczenie całej linii
  • Alt+, Alt+ - przeniesienie linijki w której znajduje się kursor w górę/dół.
  • Tab/⌘+] - dodaj wcięcie (wcięcie w prawo)
  • Shit+Tab/⌘+[ - usunięcie wcięcia (wycięcie w lewo)

Dodawanie postów:

  • Ctrl+Enter - dodaj post
  • ⌘+Enter - dodaj post (MacOS)