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

QPrint - znika mi alignment

Object Storage Arubacloud
0 głosów
378 wizyt
pytanie zadane 16 listopada 2017 w C i C++ przez Eliro Stary wyjadacz (12,160 p.)
edycja 19 listopada 2017 przez Eliro
void NotepadWindow::on_actionPrint_triggered()
{
    QString text = ui->textEdit->document()->toPlainText();

    QPrinter printer;

    QPrintDialog *dialog = new QPrintDialog(&printer);
    dialog->setWindowTitle("Print Document");

    QPainter painter;
    painter.begin(&printer);
    painter.drawText(100, 100, 500, 500, Qt::AlignLeft|Qt::AlignTop, text);

    painter.end();
}

 

Problem w tym, że mój notatnik ma funkcję wyśrodkowania tekstu za pomocą 

ui->textEdit->setAlignment(Qt::AlignCenter);

 

i niestety plik xps, który się generuje w wyniku powyższego kodu (wersja do wydrukowania), wszystko wyrównuje od lewej i align:center jest całkowicie pominięty. Jakieś pomysły?

1 odpowiedź

0 głosów
odpowiedź 17 listopada 2017 przez obl Maniak (51,280 p.)
wybrane 26 listopada 2017 przez Eliro
 
Najlepsza

W tym kawałku kodu:

painter.drawText(100, 100, 500, 500, Qt::AlignLeft|Qt::AlignTop, text);

wyraźnie jest zapisane, że wyrównywanie jest do lewej (AlignLeft) i do góry (AlignTop) zmienna text, której przypisałeś wartość wyciągniętą z textEdit nie zawiera formatowania tylko czysty tekst. W kontrolce typu QTextEdit sformatowany kod jest kodem HTML-4, można go uzyskać za pomocą metody toHtml, ale wątpię, żeby metoda drawText brała takie formatowanie pod uwagę przy rysowaniu. Znalazłem taki przykład, który ponoć umożliwia poprawną interpretację takiego kodu:

    QPainter painter(this);
    QTextDocument td;
    td.setHtml("K<sub>max</sub>=K<sub>2</sub> &middot; 3");
    td.drawContents(&painter);

https://stackoverflow.com/questions/29892203/draw-rich-text-with-qpainter

komentarz 17 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)
QWidget::paintEngine: Should no longer be called
QPainter::begin: Paint device returned engine == 0, type: 1
QPainter::save: Painter not active
QPainter::pen: Painter not active
QPainter::setPen: Painter not active
QPainter::pen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::pen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::setPen: Painter not active
QPainter::restore: Unbalanced save/restore
QPainter::end: Painter not active, aborted

 

komentarz 17 listopada 2017 przez obl Maniak (51,280 p.)
Ten kod co podałem on nie jest dosłownie do skopiuj i wklej (znaczy się powinieneś go dostosować do swoich potrzeb), więc może daj kawałek kodu :)
komentarz 19 listopada 2017 przez obl Maniak (51,280 p.)
    QPainter painter;
    painter.begin(&printer);

    QTextDocument td;
    td.setHtml(ui->textEdit->toHtml());
    td.drawContents(&painter);

Takie coś powinno zadziałać

komentarz 19 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)
Wielkość tekstu, porgubienie, pochylenie itd działa, ale wciąż nie ma aligmentu. Jak coś wyśrodkuję, to i tak w pliku xps zaczyna się od lewej. Da się coś z tym zrobić?

Analogicznie z zapisem do pliku - również ten sam problem, co z drukowaniem.
komentarz 19 listopada 2017 przez obl Maniak (51,280 p.)

Ja też napisałem swój programik w stylu notatnika i mi zapisuje wyrównywanie do pliku. A zrobiłem to tak:

    QTextCursor cursor = ui->edit->textCursor();

    QTextBlockFormat textBlockFormat = cursor.blockFormat();
    textBlockFormat.setAlignment(alignment);
    cursor.mergeBlockFormat(textBlockFormat);
    ui->edit->setTextCursor(cursor);

Wyciągasz z twojego edita QTextCursor, z niego wyciągasz QTextBlockFormat gdzie masz ustawienia formatowania dla bieżącej pozycji karetki klawiatury (to ten mrugający znacznik | ) i ustawiasz wyrównanie i zastosowujesz to do kursora i na końcu ustawiasz kursor dla twojej kontrolki QTextEdit.

U mnie kontrolka inaczej się nazywa niż u ciebie więc musisz sobie to poprawić. Najlepiej zrób sobie metodę, która będzie ci ustawiała to wyrównanie tekstu żeby później nie kopiować niepotrzebnie kodu.

komentarz 19 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)

Coś zrobiłem źle

void NotepadWindow::on_actionCenter_triggered(bool checked)
{
    if(checked)
    {
        QTextCursor cursor = ui->textEdit->textCursor();

        QTextBlockFormat textBlockFormat = cursor.blockFormat();
        textBlockFormat.setAlignment(Qt::AlignCenter);
        cursor.mergeBlockFormat(textBlockFormat);
        ui->textEdit->setTextCursor(cursor);

        ui->actionLeft->setChecked(false);
        ui->actionRight->setChecked(false);
        ui->actionJustify->setChecked(false);
    }
    if(!checked)
    {
        ui->textEdit->setAlignment(Qt::AlignLeft);
    }
}

 

komentarz 19 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)
edycja 19 listopada 2017 przez Eliro

Mam też problem ogólnie z aligmentem. Gdy napiszę jakiś tekst i dopiero potem kliknę w "align center", to tekst normalnie się wyśrodkowuje. Natomiast gdy zrobię to w odwrotnej kolejności - najpierw align center, a potem zacznę pisać, to czcionka się zmniejsza.

 

Zmodyfikowałem również zapis i odczyt

void NotepadWindow::on_actionOpen_triggered()
{
    QString file = QFileDialog::getOpenFileName(this, "open"); // Otwórz okienko wyboru plików
    if(!file.isEmpty())        // Jeśli plik nie jest pusty
    {
        QFile sFile(file);
        if(sFile.open(QFile::ReadOnly | QFile::Text)) // Jeśli plik jest otwarty
        {
            mFilename = file;
            QTextStream in(&sFile);
            in.setCodec("UTF-8"); // Ustaw kodowania znaków na UTF-8
            QString text = in.readAll();
            QTextDocument doc;
            doc.setHtml(text);

            sFile.close();
            ui->textEdit->setPlainText(doc.toPlainText());
        }
    }
}

void NotepadWindow::on_actionSave_triggered()
{
    QFile sFile(mFilename);
    if(sFile.open(QFile::WriteOnly | QFile::Text)) // Jeśli plik jest otwarty
    {
        QTextStream out(&sFile);
        out << ui->textEdit->toHtml();
        out.setCodec("UTF-8"); // Ustaw kodowania znaków na UTF-8
        sFile.flush();
        sFile.close();

    }
    else if(!sFile.open(QFile::WriteOnly | QFile::Text)) on_actionSave_as_triggered();
}

 

 

I mam wrażenie, że

ui->textEdit->setFontPointSize(11);

if(!checked)
    {
        ui->textEdit->setAlignment(Qt::AlignLeft);
    }
}

    if(!checked)
    {
        ui->textEdit->setFontUnderline(0);
    }

 

 

itd. psują mi formatowanie. Po wczytaniu z pliku automatycznie ustawia się wielkość czcionki całego tekstu na taką, jaka jest domyślnie ustawiona na początku, czyli 11. Również grubość, pochylenie i aligment ustawia się na wartość if(!checked), bo w końcu przyciski nie są naciśnięte.

komentarz 19 listopada 2017 przez obl Maniak (51,280 p.)

Przy odczycie nie wykorzystuj QTextDocument:

void NotepadWindow::on_actionOpen_triggered()
{
    QString file = QFileDialog::getOpenFileName(this, "open"); // Otwórz okienko wyboru plików
    if(!file.isEmpty())        // Jeśli plik nie jest pusty
    {
        QFile sFile(file);
        if(sFile.open(QFile::ReadOnly | QFile::Text)) // Jeśli plik jest otwarty
        {
            mFilename = file;
            QTextStream in(&sFile);
            in.setCodec("UTF-8"); // Ustaw kodowania znaków na UTF-8
            QString text = in.readAll();
            sFile.close();
            ui->textEdit->setHTML(text);
        }
    }
}

QTextDocument jest potrzebny, gdy chcesz rysować sformatowany tekst (np. do wydruku).

Jeżeli chodzi o wyrównywanie to zobacz jak działają np. na tym forum przyciski wyrównywania. Niezależnie ile razy kliknę przycisk wyrównania do środka zawsze ten przycisk jest ustawiony jako aktywny, natomiast u ciebie to jest zrobione na przemian (raz klikniesz to się zaznacza, drugi raz to się odznacza). Przyciski powinny się odznaczać, gdy zostanie kliknięty np przycisk wyrównania do środka, a był wybrany przycisk wyrównania do lewej.

void NotepadWindow::on_actionCenter_triggered(bool checked)
{
        QTextCursor cursor = ui->textEdit->textCursor();
 
        QTextBlockFormat textBlockFormat = cursor.blockFormat();
        textBlockFormat.setAlignment(Qt::AlignCenter);
        cursor.mergeBlockFormat(textBlockFormat);
        ui->textEdit->setTextCursor(cursor);
 
        ui->actionCenter->setChecked(true);
        ui->actionLeft->setChecked(false);
        ui->actionRight->setChecked(false);
        ui->actionJustify->setChecked(false);
}

 

komentarz 19 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)
Dzięki wielkie! Niemal wszystko już działa! Jesteś wielki! :D

 

Tylko jest jedno ale - wersja do wydruku nadal ustawia wszystko od lewej :/
komentarz 20 listopada 2017 przez obl Maniak (51,280 p.)

Bo żeby wyrównywało do środka, lewej czy wyjustowało tekst musisz określić wymiary strony:

printer.setPageSizeMM(QSize(210, 297));

 

komentarz 25 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)
void NotepadWindow::on_actionPrint_triggered()
{

    QPrinter printer;
    printer.setPageSizeMM(QSize(210, 297));

    QPrintDialog *dialog = new QPrintDialog(&printer);
    dialog->setWindowTitle("Print Document");

    QPainter painter;
    painter.begin(&printer);

    QTextDocument td;
    td.setHtml(ui->textEdit->toHtml());
    td.drawContents(&painter);
    //painter.drawText(printer.pageRect(), ui->textEdit->toPlainText());

    painter.end();
}

 

 

???

komentarz 26 listopada 2017 przez obl Maniak (51,280 p.)

Tak, to powinno pomóc, chociaż pewności 100% nie mam bo nie mam jak to sprawdzić. Jeżeli ci nie działa to jeszcze można spróbować ustawić rozmiar dokumentu w QTextDocument:

QSize size(2100, 2970);
textDocument.setPageSize(size);

problem polega na tym, że tutaj podajesz rozmiar w px a drukarka używa mm aby to przeliczyć trzeba znać ustawienia dpi (rozdzielczości drukowania). Generalnie jak używam QTextDocument do wyświetlania tekstu z ustawionym rozmiarem strony to wyśrodkowanie i wyrównanie do prawej działa. Nie działa mi tylko wyjustowanie.

komentarz 26 listopada 2017 przez Eliro Stary wyjadacz (12,160 p.)

Po przeliczeniu ustawiłem tak:

    QSize size(793.7007874016, 1122.519685039);
    td.setPageSize(size);

i działa. Dzięki Wielkie! :D

Podobne pytania

0 głosów
1 odpowiedź 220 wizyt
pytanie zadane 10 czerwca 2015 w C i C++ przez gnx Dyskutant (7,720 p.)
0 głosów
1 odpowiedź 171 wizyt
pytanie zadane 20 września 2021 w C i C++ przez tonn204 Mądrala (7,440 p.)
0 głosów
1 odpowiedź 300 wizyt

92,579 zapytań

141,432 odpowiedzi

319,662 komentarzy

61,964 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.

Akademia Sekuraka

Kolejna edycja największej imprezy hakerskiej w Polsce, czyli Mega Sekurak Hacking Party odbędzie się już 20 maja 2024r. Z tej okazji mamy dla Was kod: pasjamshp - jeżeli wpiszecie go w koszyku, to wówczas otrzymacie 40% zniżki na bilet w wersji standard!

Więcej informacji na temat imprezy znajdziecie tutaj. Dziękujemy ekipie Sekuraka za taką fajną zniżkę dla wszystkich Pasjonatów!

Akademia Sekuraka

Niedawno wystartował dodruk tej świetnej, rozchwytywanej książki (około 940 stron). Mamy dla Was kod: pasja (wpiszcie go w koszyku), dzięki któremu otrzymujemy 10% zniżki - dziękujemy zaprzyjaźnionej ekipie Sekuraka za taki bonus dla Pasjonatów! Książka to pierwszy tom z serii o ITsec, który łagodnie wprowadzi w świat bezpieczeństwa IT każdą osobę - warto, polecamy!

...