Russian Qt Forum

Qt => Общие вопросы => Тема начата: Гурман от Май 06, 2010, 09:26



Название: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: Гурман от Май 06, 2010, 09:26
есть некий суперкласс, который сам наследует QGraphicsItem, и от которого наследуют несколько классов, реализующих изображаемые на сцене объекты, в инстансе суперкласса, в поле QString содержатся наименования этих объектов, и там все пучком работает

но появилась необходимость добавить комментарии, есть смысл наследовать тот же суперкласс, поскольку в остальном комментарии по поведению очень похожи на реализованные объекты, а в суперклассе уже есть поле класса QString, то есть соблазн в него же уложить комментарии

но! комментарии должны быть многострочные, поэтому прежде чем браться за их реализацию таким способом, хочу выяснить для себя несколько вопросов, поскольку с таким использованием QString пока не сталкивался

- как в QString хранятся esc-символы, особенно перевод строки? достаточно ли просто уложить туда строку с '\n' и оно там будет нормально лежать? а что насчет `\t`?
- как подсчитать размер boundingRect для такой строки? есть ли уже готовое средство для такого подсчета, учитывающее `\t` и `\n`, или надо самому лазить по строке и считать количество видимых строк, табуляции etc?
- как будет выполняться отрисовка такой строки при вызове ((QPainter*)painter)->drawText(...); с установленными метриками и заданным прямоугольником? будет ли `\n` распознаваться как полный перевод строки с возвратом каретки? или как пробел? или только как перевод строки, без возврата каретки? будет ли распознаваться `\t`? на какой шаг табуляции?

просто хочу это все выяснить, чтобы четко понять, что надо делать, и куда-нибудь не вляпаться, и не пришлось потом переделывать


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: voronElf от Май 06, 2010, 10:45
в QString esc-символы лежат нормально, а вот насчет отображения сказать не могу, глубоко не копал


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: Гурман от Май 06, 2010, 11:10
у варианта

Код:
void QPainter::drawText ( const QRectF & rectangle, int flags, const QString & text, QRectF * boundingRect = 0 )

есть примерчик

Код:
QPainter painter(this);
 painter.drawText(rect, Qt::AlignCenter, tr("Qt by\nNokia"));

текст выводится в 2 строки, и flags может содержать Qt::TextExpandTabs то есть, табуляции расширяются - вроде все то, что надо, но не понятно с rectangle - судя по описанию вызова QRectF QPainter::boundingRect ( const QRectF & rectangle, int flags, const QString & text ) это прямоугольник, от угла которого будет рисоваться текст, но не ясно, надо ли самому считать размеры этого прямоугольника, или достаточно указать размеры 0,0 и в flags передать Qt::TextDontClip

в общем, никто похоже не делал, придется самому экспериментировать  :(


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: kuzulis от Май 06, 2010, 12:15
Цитировать
можно ли хранить и как отображать многострочный текст в QString?

Нет, в чистом виде нельзя (т.е. если строка нуль-терминированная), но можно "выкрутится" используя вместо '\0' сплиттеры.

Для хранения списка строк используется QStringList !


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: Гурман от Май 06, 2010, 13:53
'\0' там только в самом конце текста, в середине строки разделены '\n'

но тут другой вопрос... храниться и редактироваться строки будут в QString вместе с графическими айтемами, вроде нормально

однако необходима возможность в любой момент получать их в виде C-строк, поскольку с ними будут работать и библиотечные функции на C, причем они работают с другим представлением данных, в котором можно сохранить указатели на С-строки, однако просто сделать С-копии - громадное дублирование, накладно и муторно

можно написать переходники, которые при необходимости доступа к C-строкам будут возвращать ((QString)str).toLocal8bit().constData() но тут не понятно, как это работает по скорости

выгоднее всего было бы, если бы вызов constData() возвращал указатель на буфер не внутри QByteArray, а прямо внутри QString, если она уже закодирована в Local8bit - тогда можно было бы просто для всех комментариев эти указатели сохранить в структурах, с которыми работают С-функции, и получилось бы просто замечательно

кто знает? как на самом деле устроены взаимоотношения QString и QByteArray, с учетом возможного преобразования кодировки? что если QString заведомо содержит символы в правильной кодировке? приведенный выше запрос все равно вернет указатель на временный буфер, находящийся не в QString?


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: Гурман от Май 06, 2010, 15:48
блин, не понятно, как работает

Код:
QRect QFontMetrics::boundingRect ( int x, int y, int width, int height, int flags, const QString & text, int tabStops = 0, int * tabArray = 0 ) const

что если x=y=width=height=0? вернет прямоугольник 0-го размера, или подгонит его под получающуюся ширину текста?

почему у вызова

Код:
void QPainter::drawText ( const QRectF & rectangle, int flags, const QString & text, QRectF * boundingRect = 0 )

указана опция Qt::TextDontClip а у совершенно аналогичного

Код:
void QPainter::drawText ( int x, int y, int width, int height, int flags, const QString & text, QRect * boundingRect = 0 )

нет! (а он, по идее, использует упомянутый выше вызов класса QFontMetrics, да и все они по идее его используют)

или может ее просто забыли указать?

не хочется делать код, потом его перепахивать, поскольку получается относительно сложно

неужели никто с этим не сталкивался??


Название: Re: можно ли хранить и как отображать многострочный текст в QString?
Отправлено: zenden от Май 06, 2010, 19:36


выгоднее всего было бы, если бы вызов constData() возвращал указатель на буфер не внутри QByteArray, а прямо внутри QString, если она уже закодирована в Local8bit - тогда можно было бы просто для всех комментариев эти указатели сохранить в структурах, с которыми работают С-функции, и получилось бы просто замечательно

кто знает? как на самом деле устроены взаимоотношения QString и QByteArray, с учетом возможного преобразования кодировки? что если QString заведомо содержит символы в правильной кодировке? приведенный выше запрос все равно вернет указатель на временный буфер, находящийся не в QString?


QString хранит строку всегда в кодировке UTF-16