20 Ağustos 2014 Çarşamba

PyQt Akıllı Diyaloglar

     Akıllı diyalogların akılsız diyaloglardan oluşturulma yönünde bir farkı yoktur. Sadece akılsız diyaloglara oranlara birtakım avantajları vardır. Bu avantajlar ise kullanılacak duruma göre dezavantaj da olabilir. Akıllı ve akılsız diyalogların farklılıklarına kısaca değinelim.

Akılsız diyaloglarda bir pencere açıldığında onay butonları veya çarpı işaretinden kapatılması sonucu sadece kullanıcıya görünmez olur; ama bellekte yer kaplar. Ve her yeni çağrılışında yeni bir pencere oluşturmaktadır. Bunu diyalog sonuna ekleyebileceğimiz del diyalog komutu ile çözebiliriz.
Ayrıca akılsız diyaloglar kendisini çağıran pencere ile etkileşim içinde değildir. Yani yapılan değişiklikler onaylanmadan görüntülenemez. Onaylandığında da kalıcı olarak değişiklik yapılmış olur. Bu durumda önceki duruma dönülemez.

İşte bu bahsettiğimiz durumları akıllı diyaloglar giderir. Akılsız diyaloglarda yapılan değişiklikler, kendisini çağıran pencerede gerçekleşmekte; fakat akıllı diyaloglarda yapılan değişiklikler diyaloğun kendisinde yapılır.
Diyalog kapatıldıktan sonra kendisini sildiğinden bellekte yer kaplama durumu da söz konusu değildir. Bunu da örneğimizde self.setAttribute(Qt.WA_DeleteOnClose) kodu ile sağlayacağız. Bu kodu akılsız diyaloglara koyamıyoruz; çünkü akılsız diyaloglar kendisini çağıran pencereye değişikliklere dair veri aktarmaktadır. Oysaki bu değişiklikler akıllı diyaloglarda kendi içinde halledilmiştir.

Şimdi bir metnin yazı tipini akıllı diyalog ile değiştirebileceğimiz bir örnek yapalım. Kodlarımız şu şekilde:
from PyQt4.QtCore import *
from PyQt4.QtGui import *

simgeler = 'D:/Simgeler/orange-moonlight-icons/png/64x64/'
# simgeler => http://dryicons.com/free-icons/preview/orange-moonlight-icons/

class yaziTipiDiyalogu(QDialog):
    def __init__(self, parent=None):
        super(yaziTipiDiyalogu, self).__init__(parent)
        self.parent = parent

        self.setAttribute(Qt.WA_DeleteOnClose)
        # Üst satırda yazmış olduğumuz kod pencere kapatılırken doğrudan silinmesini sağlar.
        # Böylelikle bellekte yer kaplamamış olur.

        self.yaziTipiListesi = QFontComboBox()
        self.yaziTipiListesi.setCurrentFont(QFont(self.parent.yaziTipi))

        butonKutusu = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel)
        #Butonların üstündeki yazıları Tamam ve İptal olarak değiştirelim.
        butonKutusu.button(QDialogButtonBox.Ok).setText('Tamam')
        butonKutusu.button(QDialogButtonBox.Cancel).setText('İptal')
        self.connect(butonKutusu, SIGNAL('accepted()'), self.kabul)
        self.connect(butonKutusu, SIGNAL('rejected()'), self.reject)

        pencere = QGridLayout() # Izgara pencere düzeni
        pencere.addWidget(QLabel('Yazı Tipi Seçimi: '), 0, 0)
        pencere.addWidget(self.yaziTipiListesi, 0, 1)
        pencere.addWidget(butonKutusu, 1, 0, 1, 2)
        self.setLayout(pencere)

        self.setWindowTitle("Yazı Tipini Ayarla")
        self.setWindowIcon(QIcon(simgeler + 'edit.png'))

    def kabul(self):
        self.parent.yaziTipi = self.yaziTipiListesi.currentFont().family()
        self.parent.label.setText(self.parent.metin % self.parent.yaziTipi)
        QDialog.accept(self)

class akilliDiyaloglar(QDialog):
    def __init__(self, parent=None):
        super(akilliDiyaloglar, self).__init__(parent)
        self.yaziTipi = 'Comic Sans MS'
        self.metin = '
PythonDersleri.com
' self.label = QLabel(self.metin % self.yaziTipi) yatayKutu = QVBoxLayout() yatayKutu.addWidget(self.label) yaziTipiDugme = QPushButton('Yazı Tipini Değiştir') self.connect(yaziTipiDugme, SIGNAL('pressed()'), self.yaziTipiDegistir) yatayKutu.addWidget(yaziTipiDugme) self.setLayout(yatayKutu) self.setWindowTitle("Akıllı Diyaloglar") self.setWindowIcon(QIcon(simgeler + 'page.png')) def yaziTipiDegistir(self): diyalog = yaziTipiDiyalogu(self) diyalog.show() uygulama = QApplication([]) anaPencere = akilliDiyaloglar() anaPencere.show() uygulama.exec_()
Kodlarımızı çalıştırdığımızda karşımıza şöyle bir pencere gelecektir:
"Yazı Tipini Değiştir" butonuna tıkladığımızda ise pencere şu şekle gelecektir:
Buradaki kodlarımızda "Tamam" butonuna tıkladığımızda oluşan kabul durumunu kabul metodu ile bu diyalog içinde gerçekleştirdik. Bu sayede pencereyi kapattıktan sonra bellekten silebiliyoruz. İptal denildiğinde ise hiç bir değişiklik olmadan pencereyi kapatıp bellekten silebiliyoruz.

Akıllı diyaloglarla ilgili dikkatinizi çekmek istediğim bir nokta daha var. "Yazı Tipini Ayarla" penceremizi sürükleyip ana pencere üzerinden başka bir yere çektikten sonra ana pencere üzerinde "Yazı Tipini Değiştir" butonuna tekrar tıklamanıza yani ana pencere üzerinde işlem yapmanıza izin verir, bu durum akılsız diyaloglarda yoktur. Bu durum yapacağınız uygulamalara göre avantaj ya da dezavantaj oluşturabilir. Buna dikkat etmekte fayda var.

Akıllı diyaloglarda bir de kullanıcının yaptığı değişikliklerin kalıcı olmadığından bahsettik. Peki bu durum nasıl oluyor? Penceremize bazı uygulamalarda görmüş olabileceğiniz "Uygula" ve "Sıfırla" isminde iki buton daha eklememiz gerekiyor. Bu butonları da ekledikten sonra bütün butonları metotlara bağlamamız gerekiyor.
# Butonların eklenmiş hali
butonKutusu = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel | QDialogButtonBox.Apply | QDialogButtonBox.Reset)
butonKutusu.button(QDialogButtonBox.Apply).setText('Uygula')
# Butonun üzerindeki yazıyı "Uygula" yaptık
butonKutusu.button(QDialogButtonBox.Reset).setText('Sıfırla')
# Butonun üzerindeki yazıyı "Sıfırla" yaptık 


# Eklediğimiz butonların sinyallerini metotlara bağlıyoruz
self.connect(butonKutusu.button(QDialogButtonBox.Apply), SIGNAL('clicked()'), self.uygula)
self.connect(butonKutusu.button(QDialogButtonBox.Reset), SIGNAL('clicked()'), self.sifirla)


# Tüm butonlara ait metotların son hali de bu şekilde olmalı
def kabul(self):
        self.parent.yaziTipi = self.yaziTipiListesi.currentFont().family()
        self.parent.label.setText(self.parent.metin % self.parent.yaziTipi)
        QDialog.accept(self)

def uygula(self):
        self.parent.label.setText(self.parent.metin % self.yaziTipiListesi.currentFont().family())

def sifirla(self):
        self.parent.label.setText(self.parent.metin % self.parent.yaziTipi)
        self.yaziTipiListesi.setCurrentFont(QFont(self.parent.yaziTipi))

def reject(self):
        self.parent.label.setText(self.parent.metin % self.parent.yaziTipi)
        QDialog.reject(self)
Uygulamamıza yukarıdaki kodları da ekleyip çalıştırdığımızda bahsetmiş olduğumuz durumları gerçekleştirebilir hale gelmekteyiz. Pencerelere ait ekran görüntüsü de şu şekilde olacaktır:
Burada listeden yazı tipini seçtikten sonra Uygula diyerek kalıcı değişiklik yapmadan ve pencere kapanmadan yaptığımız değişiklikleri görebiliriz. Sıfırla diyerek de pencereyi açtığımızdaki ilk haline döndürebiliriz.


Kaynaklar:
http://zetcode.com/gui/pyqt4/dialogs/
Mustafa Başer - Python Kitabı

14 Ağustos 2014 Perşembe

PyQt Akılsız Diyaloglar

Akılsız diyaloglara neden akılsız diyalog denildiğinden çok bu diyalogların çalışma şekline değinelim. Akılsız diyaloglarda parçacıkların değerleri çağırıcı işlev tarafından ayarlanır ve yapılan değişiklikler de çağırıcı işlev tarafından yakalanır. Bu diyaloglar yalnızda parçacıkları ekranda görüntüleme işlevi görür. Ayrıca bu penceredeki işlem tamamlanmadan bu pencereyi çağıran ana pencerede başka bir işlem yapılamaz. Öncelikle açılan akılsız diyalog kapatılmalıdır.

Şimdi ana penceremiz üzerinde var olan bir label'ımızın içindeki yazının rengini bir alt pencere ile seçebileceğimiz bir örnek kod yazalım:
from PyQt4.QtGui import *
from PyQt4.QtCore import *

simgeler = 'D:/Simgeler/orange-moonlight-icons/png/64x64/'
# simgeler => http://dryicons.com/free-icons/preview/orange-moonlight-icons/

class yaziRengiDlg(QDialog):
    def __init__(self, parent=None):
        super(yaziRengiDlg, self).__init__(parent)
        izgara = QGridLayout()
        izgara.addWidget(QLabel('Yazı Rengi: '), 0, 0)
        self.yaziRengiListe = QComboBox()
        self.yaziRengiListe.addItems(('Red', 'Blue', 'Green', 'Yellow', 'Brown'))
        izgara.addWidget(self.yaziRengiListe, 0, 1)

        onayButonu = QPushButton('Tamam')
        redButonu = QPushButton('İptal')
        onayButonu.setDefault(True)

        butonKutusu = QHBoxLayout()
        butonKutusu.addWidget(onayButonu)
        butonKutusu.addWidget(redButonu)
        izgara.addLayout(butonKutusu, 1, 0, 1, 2)

        self.connect(onayButonu, SIGNAL('pressed()'), self.accept)
        self.connect(redButonu, SIGNAL('pressed()'), self.reject)

        self.setLayout(izgara)
        self.setWindowTitle('Yazı Rengini Seç')
        self.setWindowIcon(QIcon(simgeler + 'paint_brush.png'))

class akilsizDiyaloglar(QDialog):
    def __init__(self, parent=None):
        super(akilsizDiyaloglar, self).__init__(parent)
        self.yaziRengi = 'Blue'
        self.metin = 'PythonDersleri.com'
        self.label = QLabel(self.metin % self.yaziRengi)
        kutu = QVBoxLayout()
        kutu.addWidget(self.label)
        yaziRengiButonu = QPushButton('Yazı Rengini Değiştir')
        self.connect(yaziRengiButonu, SIGNAL('pressed()'), self.yaziRengiDegistir)
        kutu.addWidget(yaziRengiButonu)

        self.setLayout(kutu)
        self.setWindowTitle('Akılsız Diyaloglar')
        self.setWindowIcon(QIcon(simgeler + 'page.png'))

    def yaziRengiDegistir(self):
        diyalog = yaziRengiDlg()
        yaziRengiIndis = diyalog.yaziRengiListe.findText(self.yaziRengi)
        diyalog.yaziRengiListe.setCurrentIndex(yaziRengiIndis)
        if diyalog.exec_():
            self.yaziRengi = diyalog.yaziRengiListe.currentText()
            self.label.setText(self.metin % self.yaziRengi)

uygulama = QApplication([])
anaPencere = akilsizDiyaloglar()
anaPencere.show()
uygulama.exec_()
Bu programı çalıştırdığımızda ve "Yazı Rengini Değiştir" butonuna tıkladığımızda şu şekilde bir pencere gelecektir.

Burada da farklı olarak yazmış olduğumuz kodlardan bahsedelim.

4. Satır = Bu satırda simge dosyalarımın bulunduğu dizinin yolunu bir değişkene atadık. Programımızda kullandığımız simgeleri 5. satırda belirtmiş olduğumuz linkten ücretsiz temin edebilirsiniz.
30 ve 46. Satır = Bu satırlarda belirtilen QIcon nesneleri ile pencerelerin sol üst köşesinde görünen simgeleri belirledik.
51. Satır = Bu satır ile alt pencere açıldığında ana penceredeki yazının renginin seçili olarak alt pencerede gelmesini istedik.
18. Satır = Izgara pencerenin en altına yerleştirdiğimiz yatay buton kutumuzda "Tamam" butonunu ön tanımlı olarak belirledik. Bu tarz butonlar genellikle programların sağ alt köşesine yerleştirilir. Aynı hizanın sol tarafı boş kalmaktadır. Bunu sağlamak için 20. satırdan sonra butonKutusu.addStretch() kodunun eklenmesi yeterli olacaktır. Değişikliği farkedebilmek için pencerenin boyutunu artırmanız yeterli.
25 ve 26. Satır = Diyalog pencereleri kapatıldığında geri değer döndürürler. Bu değerler 0 ve 1'dir (accept ve reject). Biz buradan dönen 1 değerini "Tamam" butonuna atadık. Bunun anlamı o pencerede yapılan değişikliklerin uygulanacağı anlamına gelmektedir.


Kaynaklar:
-Mustafa Başer - Python Kitabı

10 Ağustos 2014 Pazar

PyQt Diyaloglar

      Şu ana kadar PyQt'ye ait temel elemanlardan bir kaçını kullanarak değişik uygulamalar yaptık. Ancak grafiksel arayüze sahip programlar bunlardan daha fazlasını içerir. Kullanıcılarla etkileşimi artırmak ve kullanıcıyı daha iyi yönlendirebilmek için Diyaloglar kullanılır. Peki nedir bu diyaloglar? Diyaloglar ana pencerenin üzerine açılan ve üzerinde Qt elemanları olan pencerelerdir. Yani bir başka deyişle alt pencerelerdir.
Örneğin ana pencereniz üzerinde bulunan bir yazının rengini veya yazı tipini seçmek için açılabilecek yeni bir pencere bir diyalogdur. Diyaloglar çeşitli gruplara ayrılmaktalar. Referans olarak aldığım bir kaynakta diyaloglar üç grupta incelenmiş ben de bu şekilde ele alıp ifade etmeye çalışacağım. Bu gruplar akıllı, akılsız ve canlı diyaloglar.

İlerleyen bölümlerde kullanacağımız simgeleri http://dryicons.com/free-icons/preview/orange-moonlight-icons/ adresinden ücretsiz temin edebilirsiniz. Ben bu simgeleri kullanacağım siz başka simgeleri de tercih edebilirsiniz.


8 Ağustos 2014 Cuma

PyQt Birbiriyle Bağımlı Parçacıklar

       Grafiksel kullanıcı arayüzüne sahip programlarda; kullanıcı tarafından fare tıklanması, klavyeden bir tuşa basılması gibi durumlar program tarafından dinlenilerek parçacıklarla ilgili tepkilerde belirli sinyaller için belirlediğimiz metotları çağırıyorduk. Biz bu oluşan sinyalleri bir başka parçacığa ait herhangi bir özellikle ilişkilendirebiliriz. Bu durumda ilk parçacıktaki değişim diğerinde de bir etki oluşturacaktır. Üstüne bir de ikinci parçacık için oluşacak bir sinyali de ilk parçacığın bir özelliğine bağlarsak, bu parçacıklar birbirlerini etkiler duruma gelecektir.

       Şöyle bir örnek ile açıklamaya devam edeyim. Örneğin ses seviyesini belirlediğimizi düşünelim. Seviye belirlediğimiz bir parçacıkla (QSlider) aynı seçimi sayıyla gösterir halde seçmemizi sağlayan bir döner kutu (QSpinBox) olabilir. Bu durumda ikisi de aynı değer üzerinde değişiklik yapmamızı sağlamaktadır. Bunun için bu parçacıkların birindeki değişim diğerini de değiştirmelidir.
       Bizim bu iki parçacığın aynı özelliklerini ortak bir değer için birbiriyle ilişkilendirebilmemiz için her iki parçacıkta da bu özelliklerin mevcut olması gerekir. Bizim burada QSlider ile QSpinBox parçacıklarını ilişkilendirmemizi sağlayan, ikisinin de valueChanged(int) sinyali ile setValue() metoduna sahip olmalarıdır. Parçacıklar ilişkilendirilirken bu duruma dikkat edilmelidir.

Yapacağımız örneğe şöyle bir görsellik daha katalım; biri yatay biri dikey iki tane QSlider ve bir tane QSpinBox kullanalım. Ve bu üç parçacıktan herhangi birinin valueChange(int) sinyalini diğerlerinin setValue() özelliklerine bağlayalım.
Kodlarımız şu şekilde:
# !/usr/bin/env python
# -*- coding: cp1254 -*-

from PyQt4.QtGui import *
from PyQt4.QtCore import *

class BirbiriyleBagimliParcaciklar(QDialog):
    def __init__(self, parent=None):
        super(BirbiriyleBagimliParcaciklar, self).__init__(parent)

        yataySlider = QSlider()
        yataySlider.setRange(0, 10)
        yataySlider.setOrientation(Qt.Horizontal) #Slider'ın yatay olması için

        dikeySlider = QSlider()
        dikeySlider.setRange(0, 10)
        dikeySlider.setOrientation(Qt.Vertical) #Slider'ın dikey olması için

        dKutu = QSpinBox()
        dKutu.setRange(0, 10)

        self.connect(dikeySlider, SIGNAL('valueChanged(int)'), yataySlider.setValue)
        self.connect(yataySlider, SIGNAL('valueChanged(int)'), dKutu.setValue)
        self.connect(dKutu, SIGNAL('valueChanged(int)'), dikeySlider.setValue)
        
        grid = QGridLayout()
        grid.addWidget(dikeySlider, 0, 0, 2, 1)
        grid.addWidget(yataySlider, 0, 1)
        grid.addWidget(dKutu, 1, 1)


        self.setLayout(grid)
        self.setFixedSize(300, 150)
        self.setWindowTitle('PyQt QSlider & QSpinBox')

uygulama = QApplication([])
pencere = BirbiriyleBagimliParcaciklar()
pencere.show()
uygulama.exec_()

Programımızı çalıştırdığımızda karşımıza şu şekilde bir pencere gelecektir.
Burada parçacıklar üzerinde herhangi bir değişiklik yaptığımızda diğer parçacıkların değiştiğini de göreceksiniz. Şimdi de koddaki  bir kaç noktaya değinelim.
13-17. Satırlar = Bu iki satırda yorumda da belirttiğimiz gibi Slider'ımızın yatay konumda mı yoksa dikey konumda mı olması gerektiğini belirtiyoruz. Bu satırı yazmazsak varsayılan olarak dikey konumlandırılıyor.
22-23-24. Satırlar = Bu satırlarda üç parçacığa ait sinyaller birbirlerini etkileyecek şekilde birbirlerine bağlanmışlardır. Halka gibi düşünülebilir. Böylelikle bir tanesinde oluşan değer değişikliği sonucu o değer diğer parçacıklara gönderilmektedir.


Kaynaklar:
-Mustafa Başer - Python Kitabı

5 Ağustos 2014 Salı

PyQT Klavye Kısayolları ve QRadioButton

Kes, kopyala, yapıştır, kaydet gibi bazı işlemler için klavyedeki kısayolları kullanmak birçok kullanıcı için vazgeçilmezdir. Grafiksel arayüze sahip programlarda da genellikle fareyi kullanırız; ancak bazı kullanıcılar klavyeyi kullanmak isteyebilirler. Bu durumda programımızı klavyedeki tuşlar ile ilişkilendirmemiz gerekecektir.

Bir örnek ile bunu nasıl yapabileceğimize bakalım. Pencere üzerine bir yazı koyalım ve bu yazının rengini değiştirebileceğimiz seçenekler ekleyelim.  Aynı zamanda kullanıcı bu renk seçeneklerini klavyeden de seçebilsin.

Kodlarımız şu şekilde:
# !/usr/bin/env python
# -*- coding: cp1254 -*-

from PyQt4.QtGui import *
from PyQt4.QtCore import *

class Klavye_Kisayollari(QDialog):
    def __init__(self, parent=None):
        super(Klavye_Kisayollari, self).__init__(parent)

        self.renk = 'blue'
        self.yazi = '''PythonDersleri.com'''

        self.metin = QLabel(self.yazi % self.renk)

        aciklamaLabeli = QLabel('Yazı rengi:')

        self.maviButon = QRadioButton('&Mavi')
        self.maviButon.setChecked(True)
        self.yesilButon = QRadioButton('&Yeşil')
        self.kirmiziButon = QRadioButton('&Kırmızı')

        self.butonGrubu = QButtonGroup()
        self.butonGrubu.addButton(self.maviButon)
        self.butonGrubu.addButton(self.kirmiziButon)
        self.butonGrubu.addButton(self.yesilButon)
        self.connect(self.butonGrubu, SIGNAL('buttonClicked(int)'), self.metniGuncelle)

        izgara = QGridLayout()
        izgara.addWidget(self.metin, 0, 1, 4, 1)
        izgara.addWidget(aciklamaLabeli, 0, 0)
        izgara.addWidget(self.maviButon, 1, 0)
        izgara.addWidget(self.yesilButon, 2, 0)
        izgara.addWidget(self.kirmiziButon, 3, 0)

        self.setLayout(izgara)
        self.setWindowTitle('PyQt Klavye Kısayolları')
        self.setFixedSize(300, 100)

    def metniGuncelle(self):
        if self.maviButon.isChecked():
            self.renk = 'blue'
        elif self.kirmiziButon.isChecked():
            self.renk = 'red'
        elif self.yesilButon.isChecked():
            self.renk = 'green'

        self.metin.setText(self.yazi % self.renk)

uygulama = QApplication([])
pencere = Klavye_Kisayollari()
pencere.show()
uygulama.exec_()
Bu kodu çalıştırdığımızda karşımıza şu şekilde bir pencere gelecektir.
Windows işletim sisteminde renklerin baş harflerinin altı çizili olması için çalıştıktan sonra ALT tuşuna basılması gerekiyor.

Şimdi biz burada renkler için klavye kısayolları atamış olduk. Bu kısa yollar Qt'de & işareti ile belirtiliyor. & işaretinden sonra gelen karakteri kısayol olarak atamış oluyoruz. Pencerede de kısayol olarak belirlenmiş olan karakter altı çizili olarak gösteriliyor. Örneğin uygulamamızda yazımızın rengini kırmızı yapmak için klavyeden ALT + K tuşlarına basmamız yeterlidir.

Parçacıklar içinde QRadioButton, QPushButton gibi kısayol olarak atayabileceğimiz bir metin geçmiyorsa ne yapacağımız düşünüyor olabilirsiniz. Bunun çözümü de çok basit. İçinde metin geçmeyen bu parçacıklar için kullanıcıya o parçacığın ne işlev gördüğünü belirtmek amacıyla genellikle bir QLabel kullanılmaktadır. Yapmak istediğimiz kısayolu o labelde belirtip, label ile de o parçacığı ilişkilendirmemiz gerekir. Bunu da labelIsmi.setBuddy(parcacikIsmi) şeklinde belirtmemiz yeterlidir.

Bu programda yeni görmüş olduğumuz bir de Radio Butonların gruplandırılması var. Bu butonları gruplandırmamızın sebebi, çoklu seçimi önleyip, sadece bir tanesinin seçili olmasını sağlamaktır. Eğer penceremizde başka fonksiyonlar için oluşturduğumuz başka radio butonlar yoksa gruplandırmaya gerek yoktur; ancak varsa birbirlerinden ayırt edilmeleri için gruplandırmamız gerekmektedir.

Not: Programınızda kısayolları belirlerken aynı karaktere birden fazla atama yapmamaya dikkat ediniz.


Kaynaklar:
-Mustafa Başer - Python Kitabı

1 Ağustos 2014 Cuma

PyQt QLineEdit Kullanımı

       Bu yazımızda sizlere QLineEdit yani kullanıcıdan veri almamızı sağlayan kutucuklardan bahsedeceğiz. Kullanıcıdan bu kutucuklar ile bilgilerini alıp, aldığımız bu verileri de bir dosyaya kaydedeceğimiz örnek bir uygulama yapalım. Bu sayede anlaşılması kolay olur hem de dosya işlemlerini kısaca bir tekrar etmiş oluruz.
       Izgara pencere düzeni kullanarak kullanıcıdan adını, soyadını, yaşını ve bölümünü alacağımız alanları belirtelim, aldığımız bu verileri dosyaya kaydetmek için bir de buton oluşturalım ve bunları penceremize yerleştirelim.
Hazırlamış olduğumuz örnek kodlarımız şu şekilde:
# !/usr/bin/env python
# -*- coding: cp1254 -*-
 
from PyQt4.QtGui import *
from PyQt4.QtCore import *

class QLineEdit_Kullanimi(QDialog):
    def __init__(self, parent=None):
        super(QLineEdit_Kullanimi, self).__init__(parent)

        self.ad = QLabel('Ad:')
        self.soyad = QLabel('Soyad:')
        self.yas = QLabel('Yaş:')
        self.bolum = QLabel('Bölüm:')

        self.adi = QLineEdit()
        self.soyadi = QLineEdit()
        self.yasi = QLineEdit()
        self.yasi.setInputMask('99')
        self.bolumu = QLineEdit()
        
        self.kaydet = QPushButton('Kaydet')
        self.connect(self.kaydet, SIGNAL('pressed()'), self.dosyayaYaz)

        izgara = QGridLayout()
        izgara.addWidget(self.ad, 0, 0,)
        izgara.addWidget(self.soyad, 1, 0,)
        izgara.addWidget(self.yas, 2, 0,)
        izgara.addWidget(self.bolum, 3, 0,)
        
        izgara.addWidget(self.adi, 0, 1,)
        izgara.addWidget(self.soyadi, 1, 1,)
        izgara.addWidget(self.yasi, 2, 1,)
        izgara.addWidget(self.bolumu, 3, 1,)

        izgara.addWidget(self.kaydet, 4, 1,)

        self.setLayout(izgara)
        self.setWindowTitle('PyQt QLineEdit')
        

    def dosyayaYaz(self):
        dosya = open('Çıktı.txt', 'w')
        dosya.write(self.adi.text() + '\n' + self.soyadi.text() + '\n' + self.yasi.text() + '\n' + self.bolumu.text())
        dosya.close()        
        self.adi.setText('')
        self.soyadi.setText('')
        self.yasi.setText('')
        self.bolumu.setText('')

uygulama = QApplication([])
pencere = QLineEdit_Kullanimi()
pencere.show()
uygulama.exec_()

Bu programımızı çalıştırdığımızda şekildeki gibi bir ekran bizi karşılayacaktır.

Sonrasında bu formu doldurup "Kaydet" butonuna tıkladığımızda kodlarımızı yazdığımız dosya ile aynı dizinde "Çıktı.txt" isimli bir dosya oluşacaktır. Bu dosyayı açıp baktığımızda ise içeriği şöyledir:
Uygar
Köroğlu
22
Bilgisayar Mühendisliği

Şimdi yukarıdaki yazmış olduğumuz kodları kısaca açıklayalım. Burada da sadece farklı olarak yazdığımız kodları açıklayacağız.

11-12-13-14. Satırlar  = Bu satırlarda kutucukları anlamlandırmak için Label oluşturuyoruz.
16-17-18-20. Satırlar = Bu dört satırda kullanıcıdan veri almak için kutucuk oluşturuyoruz.
19. Satır = Bu satırda kişiye ait yaşı alırken kullanıcının gireceği veriye bir sınırlama getirdiğimizi belirtiyoruz. Buraya yazdığımız '9' sayısının kaç adet olduğu ile kaç karakter girilebileceğini ve bu sayının kendisi ise buraya [0, 9] aralığında bir rakamın girilebileceğini belirtmektedir. Yani bu şekilde kullanıcının yalnızca sayı girmesi ve bu sayının da maksimum iki basamaklı olabileceğini belirtmiş olduk.
22. Satır = Bu satırda da "Kaydet" butonumuzu oluşturduk.
23. Satır = Bu satırda da butona tıklandığında verileri dosyaya yazacak olan metodu çağırdık.
42. Satır = Buton tıklandığında çalışacak olan metodu tanımladık.
43. Satır = "Çıktı.txt" isminde bir dosyayı yazma modunda açıyoruz.
44. Satır = Kutucuklardan aldığımız verileri satır satır dosyaya yazıyoruz.
45. Satır = Dosyamızı kapatıyoruz.
46-47-48-49. Satırlar = Bu satırlarda dosyaya yazma işleminden sonra kutucukların içini temizliyoruz. Bir nevi kaydettiğimizin de farkına varabilmemiz için bunu yazdık.

       Yukarıda 19. satırda bahsetmiş olduğumuz setInputMask() metodu ile verebileceğimiz kısıtlamalar için kullanabileceğimiz parametrelerden bahsetmek istiyorum. Bu parametreler ile kullanıcının gireceği karakterlere belli kısıtlamalar getiriyoruz, bu kısıtlamalar sayesinde kullanıcıların geçersiz karakterler girmesinin önüne geçilebilir. Bu metot ile kullanabileceğimiz parametreler şu şekilde:

h       =>       Hexadecimal (onaltılık) karakterler için kullanılır, zorunluluk gerektirmez.
H      =>       Hexadecimal (onaltılık) karakterler için. a-f, A-F, 0-9
b       =>       Binary (ikilik) karakterler için kullanılır, zorunluluk gerektirmez.
B      =>       Binary (ikilik) karakterler için. 0-1
0       =>       ASCII sayılar için kullanılır, zorunluluk gerektirmez. 0-9
9       =>       ASCII sayılar için
d       =>       ASCII sayılar için kullanılır, zorunluluk gerektirmez. 1-9 (0 yok)
D      =>       ASCII sayılar için
#       =>       ASCII sayılar ve artı eksi işareti için kullanılır, zorunluluk gerektirmez.
a       =>       ASCII alfabe karakterleri için kullanılır, zorunluluk gerektirmez. a-z, A-Z
A      =>       ASCII alfabe karakterleri için
n       =>       ASCII sayısal karakterler için kullanılır, zorunluluk gerektirmez.
N      =>       ASCII alfabe karakterler için a-z, A-Z, 0-9
x       =>       Herhangi bir karakter olabilir, zorunluluk gerektirmez.
X      =>       Herhangi bir karakter olabilir
>      =>       Bu karakterden sonra gelecek olan bütün alfabe büyük harf olacak.
<      =>       Bu karakterden sonra gelecek olan bütün alfabe küçük harf olacak.
!       =>       Büyük-Küçük harf zorunluluğunu kapatır.


Kaynaklar:
-Mustafa Başer - Python Kitabı