Today I posted the third chapter of the GLModel article series. You can find a link to the article on the sidebar of the blog.
Archive for the ‘Qt’ Category
QUiViewer
I have written a small application today which aims at viewing UI files from Qt4. Nothing special, but can be very usefull. I based the idea on KUIViewer program which allows the user to view Qt3 UI files (unfortunately it crashes when fed with an UI from Qt4).
You can get the app tarball here.
Syntax highlighter
Today my thoughts about making syntax highlighting for my blog came back to me. As my blog is based on bash scripts, I needed an application that would do the actual highlighting. I know there exists a plugin for nanoblogger that enables syntax highlighting, but it’s fair from being mature. So I sat down and implemented
my own generic syntax highlighter. It’s not complete yet, but it already does some highlighting and it only took about an hour to implement. Qt was very helpful, as usual
Testing the highlighter should include trying to parse the code of the highlighter itself and so I did. You can see the result below.
- #include
- #include
- #include
- #include
- #include
- #include
- #include
- class�QHighlighter{
- public:
- ��QHighlighter(QIODevice�*indevice);
- ��void�readConfig(QIODevice�*configdevice);
- ��QString�parse();
- protected:
- ��QString�isKeyword(const�QString�&);
- ��QString�parseNumber();
- ��QString�parseIdentifier();
- ��QString�parseString();
- ��QString�parseComment();
- ��QString�parsePreproc();
- ��QString�parseSLComment();
- ��void�makeLines(bool�count=false);
- ��QIODevice�*_indevice;
- ��bool�_perror;
- ��QString�output;
- ��QMap<QString,�QStringList>�keywords;
- ��
- };
- void�QHighlighter::readConfig(QIODevice�*configdevice){
- ����QDomDocument�doc;
- ����if(!doc.setContent(configdevice)){
- ��������qDebug(“CONFIG ERROR”);
- ��������return;
- ����}
- ����QDomElement�root�=�doc.documentElement();
- ����for(QDomElement�keywselem�=�root.firstChildElement(“keywords”);�
- ��������!keywselem.isNull();�
- ��������keywselem�=�keywselem.nextSiblingElement(“keywords”))
- ����{
- ��������QStringList�kw;
- ��������for(QDomElement�key�=�keywselem.firstChildElement(“keyword”);�
- ������������!key.isNull();
- ������������key�=�key.nextSiblingElement(“keyword”))
- ��������{
- ������������kw�<<�key.text().trimmed();
- ��������}
- ��������QDomElement�keystyle�=�keywselem.firstChildElement(“style”);
- ��������QString�kstyle�=�keystyle.text().replace(“$”,�“%”).replace(“[“,�“<").replace(“]–>,�“>”);
- ��������keywords[kstyle]�=�kw;
- ����}
- }
- QString�QHighlighter::isKeyword(const�QString�&s){
- ��foreach(QString�k,�keywords.keys()){
- ����const�QStringList�&slist�=�keywords[k];
- ����foreach(QString�el,�slist){
- ������if(QRegExp(el).exactMatch(s))�return�k.arg(s);
- ����}
- �}
- �return�s;
- }
- QHighlighter::QHighlighter(QIODevice�*indevice){
- ��_indevice�=�indevice;
- ��_perror�=�false;
- }
- void�QHighlighter::makeLines(bool�countLines){
- ��if(!countLines)�output�=�output.replace(“\n”,�“
“);- ��else�{
- ����QString�n�=�”
- “;
- ����foreach(QString�line,�output.split(“\n”)){
- ������n+=QString(”
- %1
- ����}
- ����n+=“
\n”).arg(line);
“
;- ����output�=�n;
- ��}
- }
- QString�QHighlighter::parse(){
- ��QString�current;
- ��while(!_indevice->atEnd()){
- ����char�c�=�_indevice->peek(1).at(0);
- ����QChar�ch(c);
- ����if(ch.isNumber())�{
- ������current�=�parseNumber();
- ������output�+=QString(“%1“).arg(current);
- ����}�else�if(ch.isLetter()�||�ch==‘_’)�{
- ������current�=�parseIdentifier();
- ������output�+=�isKeyword(current);
- ����}�else�if(c==‘”‘||�c==‘\”�)�{
- ������current�=�parseString().replace(“<“,�“<“);
- ������output�+=QString(“%1“).arg(current);
- ����}�else�if(c==‘/’�&&�_indevice->peek(2)==“/*”)�{
- ������current�=�parseComment().replace(“<“,�“<“);
- ������output�+=QString(“%1“).arg(current);
- ����}�else�if(c==‘/’�&&�_indevice->peek(2)==“//”){
- ������current�=�parseSLComment().replace(“<“,�“<“);
- ������output�+=�QString(“%1“).arg(current);
- ����}�else�if(c==‘#’){
- ������current�=�parsePreproc().replace(“<“,�“<“);
- ������output�+=�QString(“%1“).arg(current);
- ����}�else�if(c==‘<‘){
- ����_indevice->getChar(&c);
- ������output�+=�“<“;
- ����}�else�{
- ������_indevice->getChar(&c);
- ������if(c!=‘ ‘)
- ������output�+=�c;
- ������else�output�+=“�”;
- ����}
- ��}
- ��makeLines(true);
- ��return�output;
- }
- QString�QHighlighter::parsePreproc(){
- ��return�_indevice->readLine();
- }
- QString�QHighlighter::parseSLComment(){
- ��return�_indevice->readLine();
- }
- QString�QHighlighter::parseNumber(){
- ��QString�result;
- ��char�c;
- ��while(!_indevice->atEnd()){
- ����if(!_indevice->getChar(&c)){
- ������_perror�=�true;
- ������return�result;
- ����}
- ����QChar�ch(c);
- ����if(ch.isNumber()�||�c==‘.’){
- ������result+=c;
- ����}�else�{
- ������_indevice->ungetChar(c);
- ������return�result;
- ����}
- ��}
- ��return�result;
- }
- QString�QHighlighter::parseComment(){
- ��QString�result;
- ��char�c=‘\0′;
- ��char�prev=‘\0′;
- ��while(!_indevice->atEnd()){
- ����if(!_indevice->getChar(&c)){
- ������_perror�=�true;
- ������return�result;
- ����}
- ����// match */
- ����if(c==‘/’�&&�prev==‘*’){
- ��������result�+=c;
- ��������return�result;
- ����}
- ����prev�=�c;
- ����result+=c;
- ��}
- ���_perror�=�true;
- ��return�result;
- }
- QString�QHighlighter::parseIdentifier(){
- ��QString�result;
- ��char�c;
- ��while(!_indevice->atEnd()){
- ����if(!_indevice->getChar(&c)){
- ������_perror�=�true;
- ������return�result;
- ����}
- ����QChar�ch(c);
- ����if(ch.isLetter()�||�ch.isDigit()�||�c==‘_’�||�c==‘:’){
- ������result+=c;
- ����}�else�{
- ������_indevice->ungetChar(c);
- ������return�result;
- ����}
- ��}
- ��return�result;
- }
- QString�QHighlighter::parseString(){
- ��QString�result;
- ��char�c;
- ��char�sep;
- ��_indevice->getChar(&sep);
- ��result+=sep;
- ��while(!_indevice->atEnd()){
- ����if(!_indevice->getChar(&c)){
- ������_perror�=�true;
- ������return�result;
- ����}
- ����if(c==‘\\’){
- ������if(!_indevice->getChar(&c)){
- ��������_perror�=�true;
- ��������return�result;
- ������}
- ������result+=‘\\’;
- ������result+=c;
- ����}�else�if(c!=sep)�
- ������result+=c;
- �����else�{
- ������// _indevice->ungetChar(c);
- ��������result+=c;
- �������return�result;
- �����}
- ��}
- ��_perror�=�true;
- ��return�result;
- }
- int�main(int�argc,�char�**argv){
- ��QFile�infile(argv[1]);
- ��if(!infile.open(QFile::ReadOnly))�return�2;
- ��QHighlighter�h(&infile);
- ��QFile�config(“h.config”);
- ��if(!config.open(QFile::ReadOnly))�return�2;
- ��h.readConfig(&config);
- ��QString�result�=�h.parse();
- ��QFile�outfile(“hh.html”);
- ��outfile.open(QFile::WriteOnly);
- // outfile.write(”
");
- ��outfile.write(result.toLocal8Bit());
- // outfile.write(“”);
- ��return�0;
- }
]]>
Mandriva and Qt4.2 font problems
Yes! I finally managed to solve my font problems with Mandriva and Qt 4.2. What was happening was that font antialiasing was not working for any of the Qt4.2 applications. What was funny was that for Qt4.1.4 everything was (and still is) working fine.
I was trying to find a solution since the very beginning of Qt4.2 public snapshots. At first I thought that this was caused by the fact that Qt4.2 was still unstable but when 4.2.0 came out and the problem persisted, I became worried. I even talked to Trolltech support during DevDays in Munich about the issue, but without any result.
Today I finally managed to get my fonts antialiased in Mandriva. The problem is caused by a configuration file from Mandriva’s fontconfig package, which disables antialiasing for some fonts. I don’t know why, but although it shouldn’t, Qt4.2 triggers one of the sections in the file that disables antialiasing. What is strange is that changing font faces in qtconfig doesn’t solve anything – the section is still triggered,
so the problem might be within Qt or fontconfig.
The workaround is to remove the file (or comment out the section) – it is situated in /etc/fonts/conf.d/ and is called 02-mdk-disable-antialias.conf.
I just sent a bug report to Trolltech about it, let’s see if they can do anything about it.
Finally I can start playing around with a fully working Qt4.2 installation…
Designer Tutorial
Some time ago I created and published a video tutorial for Qt4 Designer. Nothing funky, some small speaking problems, but hopefully next tutorial will be better.
I received a good feedback from people who have seen the tutorial before I published it, so hopefully someone will find my work useful.
You can download the tutorial from my webpage.
Impressions from DevDays 2006
I came back from Munich (Germany) where I attended Trolltech Developer Days and after a week I’d like to describe the trip and my impressions.
One of the main goals of going to that conference was to meet other admins of QtCentre.org. Unfortunately Johan and Axel couldn’t come, but the rest of (more or less) active admins were there – I went to Munich together with Jacek and Daniel lives in Munich so it was easy for him to come.
The conference took place in Hilton Hotel in Munich and consisted of two days with each day divided into sessions (called “Breakouts”). In each session one could choose from three different lectures on various topics.
I noticed that the biggest effort was put on the model-view framework.
The Trolls themselves were really kind. They were wearing T-shirts with “I’m a Troll” writing on the front side and “Ask me” on the back (see pictures below). You could ask them any question and really expect it to be
answered (although my question remained unanswered :P).
The quality of sessions was very high. All the Trolls were speaking fluent and plain English. The lectures included examples (like during the “Advanced Item-Views” session, see the picture on the left) and (at least to me) were easy to understand. Some of the lectures were so popular, that people had problems squeezing into the room, but that’s because the three rooms used for Breakouts had different sizes and obviously Trolls made some errors estimating which course will be the most popular in each session.
As I mentioned before, one of the main goals of attending DevDays was to finally meet other administrators in person. I’ve met Daniel Kish (“theLSB” on QtCentre aka “hatulflezet” on QtForum) and together with Jacek (I’ve
known Jacek for 10 years now) we talked a lot and discussed the future of QtCentre.
We’ve also met Knuth Yrwin, the Qt Community Manager in Trolltech. He’s the person responsible for contact with the community, so I expect more contacts between him and QtCentre team. Knut held a “BOF: Open Source” talk which aimed to give goals to Trolltech on how to more support Free Software.
Unfortunately, only a few people attended (one of them was Karin “kyrah”
Kosina). The discussion was live, loud and firm, but unfortunately didn’t lead to some binding statements on the Trolltech side. Let’s see how the situation develops – the Trolls were notified of Open Source
expectations (although I don’t consider myself a person who might speak on behalf of “Open Source”, but surely consider myself a person who might speak on behalf of Qt community) and we’re in contact with Knut, so
hopefully that’s not the end of this story.
Harald Fernengel (Trolltech Release Manager) demonstrating the penalty for not using QTestLib for developing Qt. |
Benoit Schillings (Trolltech CTO) conducting the trivia question contest: “Remember, multiple inheritance is a beautiful thing!” |
One of API additions planned for Qt 4.3 – QWidget::setWidowIcon(). |
Eirik Chambe-Eng (Trolltech Co-CEO) welcomes people to the conference. |
GLModel part 2
Today, motivated by a comment on my blog and Johan’s blog post, I have published the next article about making a custom Qt model that holds information about objects in a 3D scene. This article aims to show how to create an internal representation of data used by the model.
Charts 0.2
I’ve been sick for a few days now and I don’t feel like doing anything serious, so I have a lot free time to do “other things”.
I started thinking and finally decided that I should release an update to my MVC charts. I wrote the updated class some time ago but never put it on the Web. Now it’s time to do that. Nothing funky, I added some stuff for manipulating the chart title and axis descriptions. Unfortunately something weird causes charts to eat up all my cpu cycles and I can’t find the reason. I even tried profiling the code but without success. Oh well… maybe I’ll go back to the application and try to trace what’s going on. Better that than lying in bed whole day.
You can download the bundle from my website.
OpenGL Model articles
I decided to write a series of articles about implementing a complete data model based on Qt4 model-view framework called Interview which will hold object data from 3D scenes for use with OpenGL (a series of articles about implementing an OpenGL view in Qt4 will follow).
First two articles are ready:
If you have any commments or requests about those or future articles, drop me a line here or on QtCentre.
New Year — new forum, farewell QtForum!
First of all, Happy New Year everyone!
Phew… it’s been some time now since my last note here, but that time wasn’t wasted. I was busy putting up QtCentre, a new community site dedicated to Qt. The reason for that? Well, simply put, QtForum was sold to a 3rd party, who already owns some other linux-related forums like kde-forum.org, kde-forum.de, ubuntu-forum, gentoo-forum and probably others. We (the moderators of QtForum) tried contacting him both by other people — Christian (previous owner of the board) or directly (via e-mail), but with no success. After that we decided to open our own site and so we did
24 hours of QtCentre activity passed an hour ago and we already have about 30 threads, more than 100 posts and about 100 members. That’s not a bad result, isn’t it?
It wasn’t easy for me to give up on QtForum. I spent a lot of time there. It was my first place in the Internet which I could consider “my own”. I posted more than 4200 times there within 20 months. I remember my first days there. Actually it was quite of funny — me, with almost no Qt experience at all, answering complex Qt related questions just by reading the docs. Well, to be honest that’s how I answer most of Qt questions, as Trolltech made a really good job with the reference…
I hope QtForum community spirit will follow us to QtCentre, although I know it’ll not be the same — I’m not just a simple user (or a moderator, as for last months), but an admin now! Whoaa!
Ok, enough for today, I have to get up in 6 hours…
And read the docs, Luke! Read the docs… *)
*) That used to be my QtForum signature 😉