Qt Lezione3: un visualizzatore di immagini
Click here to load reader
-
Upload
paolo-sereno -
Category
Technology
-
view
4.706 -
download
3
description
Transcript of Qt Lezione3: un visualizzatore di immagini
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Creare un’applicazione di visualizzazioneimmagini
Premessa
Questa presentazione è rilasciata sotto Licenza Creative Commons: Attribution-NonCommercial-NoDerivativeWorks (http://creativecommons.org/licenses/by-nc-nd/3.0/deed.it).
Questo documento può quindi essere riprodotto senza violare nessuna legge, sia in versione elettronica, sia in versione cartacea, purché sia riprodotto integralmente in tutte le sue parti, compresa la pagina che contiene queste informazioni:
Versione originale scaricabile dal sitohttp://www.sereno-online.com/site/
Tutti i marchi riportati in questa pubblicazione appartengono ai rispettivi proprietari.
Link Utili
Qui di seguito riporto alcuni link utili per chi usa quotidianamente l’ambiente di sviluppo Qt e vuole confrontarsi con altri sviluppatore, utenti e semplici appassionati di questo toolkit gratuito ed open source.
Gruppo Programmatori Italiani Qt Software (GPIQt)
http://www.facebook.com/inbox/?ref=mb#/group.php?gid=81561439535
qt in Italy
http://qt-apps.org/groups/?id=17
qtitaliantranslators
http://gitorious.org/+qtitaliantranslators
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Scopo
Scopo di questa terza lezione è arricchire l’applicazione creata nella seconda lezione con alcune utili funzionalità. Il codice sorgente della terza lezione è reperibile sul sito http://www.sereno-online.com/sitealla pagina di downloads.
Questo esempio non vuole essere un’applicazione completa e con molte funzionalità, si vuole cioè evitare di sommare troppi concetti per un’unica lezione e si vuol lasciare al lettore la curiosità di scoprire nuove funzioni del Qt application framework.
I fondamenti di quest’applicazione sono presi da un progetto open source (QPhoton) il cui obiettivo è quello di realizzare un programma di fotoritocco semplice da usare e poco pesante.
Buon lavoro!
Passo 1
Per prima cosa partiamo dalla main window della seconda lezione (in altre parole, possiamo recuperare il codice sorgente della lezione numero 2), rappresentata nella figura qui sotto
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Passo 2
Aggiungiamo ora (in Qt Creator) una MDIArea alla nostra main window (MdiArea si trova nella toolbar a sinistra, subito dopo la lista files, alla voce Containers), il risultato dovrà essere più o meno così:
come si può osservare, l’area centrale della nostra main window è ora grigio scuro, questo perché è stata inserita la MDIArea.
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Passo 3
Scriviamo ora nel file mainwindow.cpp il codice seguente:
#include "ui_mainwindow.h"#include "mainwindow.h"#include <QAction>#include <QFileDialog>#include <QImageReader>#include <QList>#include <QString>#include <QLabel>#include <QPixmap>
MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow){
ui->setupUi(this);connect(ui->actionOpen,SIGNAL(triggered()),this, SLOT(openFile()));
}
MainWindow::~MainWindow(){
delete ui;}
int MainWindow::openFile(){
QString fileName,currentPath;// set filters = all supported file formats. New plugins will automatically add new image formatsQList <QByteArray> supportedFilters;QString filters;QString defaultFilter;QImageReader reader;supportedFilters = reader.supportedImageFormats();defaultFilter.append(tr("Images ( "));
for (int i = 0; i < supportedFilters.size(); ++i) {
defaultFilter.append("*.");defaultFilter.append(supportedFilters[i].toUpper());defaultFilter.append(" ");filters.append(supportedFilters[i].toUpper());filters.append(" (*.");filters.append(supportedFilters[i]);filters.append(" );;");
}
defaultFilter.append(");;");filters.append(tr("Any File( * )"));filters.prepend(defaultFilter);fileName=QFileDialog::getOpenFileName(this,tr("Open"),currentPath,filters);
if (!fileName.isEmpty()) // if fileName is not empty{
child = new QLabel(0);child->setPixmap(fileName);ui->mdiArea->addSubWindow(child);child->show();
}
return 0;}
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Passo 4
Analizziamo nel dettaglio ogni singolo metodo.
Il costruttore:
MainWindow::MainWindow(QWidget *parent): QMainWindow(parent), ui(new Ui::MainWindow){
ui->setupUi(this);connect(ui->actionOpen,SIGNAL(triggered()),this, SLOT(openFile()));
}
Fin qui nulla di nuovo rispetto la seconda lezione.
setupUI è il metodo incaricato di inizializzare l’intera interfaccia utente creata da Qt Creator.
connect realizza la connessione con la QAction di nome actionOpen del menu (File->Open) che abbiamo
creato da Qt Creator. Nella lezione 2 avevamo fatto una cosa analoga per la actionExit, ovvero il menu responsabile di chiudere l’aplicazione; ora abbiamo creato un altro menu (File->Open) per l’apertura di un file. Scopo della connect è “chiamare” un metodo in corrispondenza di un segnale generato dalla QAction; questo metodo lo chiameremo openFile e sarà responsabile di aprire il nostro file immagine che andremo a visualizzare.
Il distruttore:
MainWindow::~MainWindow(){
delete ui;}
Anche qui nulla di nuovo rispetto la lezione 2. Il distruttore si occupa di cancellare tutto ciò che era stato creato in precedenza.
Il metodo int MainWindow::openFile():
Per prima cosa analizziamo le seguenti righe di codice:
QList <QByteArray> supportedFilters;QString filters;QString defaultFilter;QImageReader reader;supportedFilters = reader.supportedImageFormats();
Si tratta delle dichiarazioni necessarie per permettere successivamente alla nostra applicazione di riconoscere quali sono i file immagine supportati (ad es PNG, JPG, BMP, etc...). Tutto si realizza attraverso la
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
classe QImageReader che restituisce nella lista di ByteArray (cioè QList <QByteArray>) tutte le estensioni dei files immagine riconosciuti. In altre parole, con la linea di codice
supportedFilters = reader.supportedImageFormats();
Andiamo a riempire la lista “supportedfilters” con tutte quelle estensioni di file che il nostro sistema può leggere (cioè che le Qt sanno riconoscere grazie ai “decoder” di immagine installati).
Per approfondire questo argomento si può consultare la documentazione sul sito qtsoftware o il Qt Assistant.
A questo punto, consideriamo il codice seguente:
for (int i = 0; i < supportedFilters.size(); ++i) {
defaultFilter.append("*.");defaultFilter.append(supportedFilters[i].toUpper());defaultFilter.append(" ");filters.append(supportedFilters[i].toUpper());filters.append(" (*.");filters.append(supportedFilters[i]);filters.append(" );;");
}
si tratta di un ciclo for che itera sulla dimensione della lista “supportedfilters”. Questa lista infatti mette a disposizione un elevato numero di metodi, tutti molto utili, tra cui il metodo size() che ci informa sul numero di elementi contenuti nella lista.
Obiettivo del ciclo for è quello di creare una stringa (QString) contenente qualcosa del tipo: “*.PNG *.BMP *.JPG” e così via. Questa strana stringa ci servirà nel resto del codice per filtrare (da qui il nome filter…) quali files vogliamo andare ad aprire con la openFile.
Nota: le linee di codice di questo ciclo loop non devono essere considerate superficialmente, proviamo a cambiare qualcosa (ad esempio a rimuovere l’istruzione filters.append(" );;"); e osservate cosa succede.
Dopo il ciclo for concentriamoci ora su:
defaultFilter.append(");;");filters.append(tr("Any File( * )"));filters.prepend(defaultFilter);fileName=QFileDialog::getOpenFileName(this,tr("Open"),currentPath,filters);
le prime 3 linee di codice servono per preparare la stringa filters da passare come parametro a QFileDialog per selezionare solamente i files che ci interessa aprire (e cioè i files immagine supportati, ad esempio JPG, BMP, PNG etc.)
Fermiamoci ora su:
fileName=QFileDialog::getOpenFileName(this,tr("Open"),currentPath,filters);
questa linea di codice è molto importante! Essa infatti ci permette di far comparire la dialog box standard di apertura files illustrato in figura seguente:
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
come si può osservare il campo Tipo File mostra l’indicazione
Images (*. BMP *.GIF *.ICO…
Questa è appunto la sequenza di filtri che abbiamo identificato grazie alle linee di codice che abbiamo visto precedentemente.
Vediamo ora i parametri passati alla QFileDialog::getOpenFileName
tr("Open")
è il titolo della dialog box. Non si è scelto di scrivere direttamente la stringa (è cioè “Open”) ma si è voluto passare attraverso il meccanismo della tr() per consentire la traduzione in lingue diverse dell’applicazione.
Può sembrare prematuro parlare subito di localizzazione, ma se ci abituiamo sin da subito a NON scrivere direttamente le nostre stringhe nel codice ma le mettiamo sempre dentro ad una tr(), ci toveremo poi pronti ad eseguire Qt Linguist (con lrelease/lupdate) per tradurre la nostra interfaccia utente. Per ora non ci addentriamo nei dettagli della localizzazione, ma ricordiamoci di scrivere tutte le nostre stringhe dentro ad
una tr(). SEMPRE!
currentPath
questo parametro serve ad indicare quale path usare alla getOpenFileName per visualizzare i files.
Per questo esempio currentPath è stato dichiarato ma non usato. Lascio al lettore il compito di
inizializzarlo.
filters
è la nostra lista di filtri per la selezione del tipo di file da aprire
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Arriviamo ora all’ultimo blocco di istruzioni:
if (!fileName.isEmpty()) // if fileName is not empty{
child = new QLabel(0);child->setPixmap(fileName);ui->mdiArea->addSubWindow(child);child->show();
}
quando viene selezionato un file, la getOpenFileName restituisce in fileName una stringa (vuota nel caso di nessun file selezionato).
L’istruzione:
if (!fileName.isEmpty())
serve appunto a verificare se un file è stato selezionato ed in tal caso si procede con il resto del codice, altrimenti il metodo openFile termina senza caricare alcun file.
isEmpty() è uno dei tanti metodi della classe QString (i metodi sono molti e tutti utilissimi!) e serve per sapere se la stringa è vuota.
Nel caso sia stato selezionato un file immagine verrà eseguito il codice seguente:
child = new QLabel(0);child->setPixmap(fileName);ui->mdiArea->addSubWindow(child);child->show();
e qui dobbiamo soffermarci un po’ per capire.
child è una istanza di QLabel, classe molto utile per visualizzare qualsiasi cosa: da una semplice stringa ad un’ immagine (che è proprio il nostro caso!)
La classe QLabel può visualizzare le immagini Pixmap; infatti il metodo setPixmap() ci consente proprio di caricare un’immagine il cui “fileName” (cioè il path) è il parametro passato come argomento (child->setPixmap(fileName);).A questo punto dobbiamo indicare alla mdiArea che c’è una nuova subwindow da visualizzare e questro viene fatto tramite la
ui->mdiArea->addSubWindow(child);
e per ultimo chiamiamo il metodo show() della QLabel ( child->show() ) per visualizzare la finestra child ed il gioco è fatto.
Mini Guide Qt
Autore P. Sereno http://www.sereno-online.com/site
Considerazioni finali
Questa è la terza lezione di un ciclo che verrà reso disponibile gratuitamente in Internet sul sito
http://www.sereno-online.com/site
A partire da questa lezione le cose si fanno più complicate, servirà quindi più tempo per capirle e per fare sul codice diverse prove.
Ogni vostro commento o richiesta di informazioni rappresenta un utile punto di partenza per nuove lezioni o miglioramenti.
Buon divertimento!
Paolo