فبراير 09، 2009

سلسلة البرمجة الرسومية بواسطة باي كيوت PyQt4 للمبتدئين 04

اليوم تنتهي رحلتنا مع الآلة الحاسبة حيث سنضيف اللمسات الأخيرة على الواجهة و الشفرة المصدرية.

بخصوص الواجهة الرسومية سنقوم بحدف الحقلين الأول و الثاني و ستصبح الواجهة كالتالي:



و الشفرة المصدرية أصبحت كالتالي:



import sys

from PyQt4 import QtGui, QtCore, uic

from functools import partial



class CalcDialog(QtGui.QDialog):



    iMathOp = 0

    fstValue = 0

    MathOps = " + ", " - ", " * ", " / "



    def __init__(self, *args):

        QtGui.QWidget.__init__(self, *args)

        uic.loadUi("PyCalc.ui", self)



        NumButtonsList = self.c0, self.c1, self.c2, self.c3, self.c4, self.c5, self.c6, self.c7, self.c8, self.c9

        for x in range(0, len(NumButtonsList)) :

            self.connect(NumButtonsList[x], QtCore.SIGNAL("clicked()"), partial(self.fAddNbr, str(x)))



        MathOpButtonsList = self.opplus, self.opminus, self.opmulti, self.opdiv

        for x in range(0, len(MathOpButtonsList)) :

            self.connect(MathOpButtonsList[x], QtCore.SIGNAL("clicked()"), partial(self.fEntrySwitch, x+1 ))



        self.connect(self.opequal, QtCore.SIGNAL("clicked()"), self.fCalculate)

        self.connect(self.opdot, QtCore.SIGNAL("clicked()"), self.fDecimal)

        self.connect(self.opclear, QtCore.SIGNAL("clicked()"), self.fClear)



    def fAddNbr(self, x):

        self.valresult.setText(self.valresult.text() + x)



    def fEntrySwitch(self, iMathOp):

        self.iMathOp = iMathOp

        self.fstValue = float(self.valresult.text())

        self.valresult.setText('')



    def fDecimal(self):

        x = str(self.valresult.text())

        if x.find('.') == -1:

            self.valresult.setText(self.valresult.text() + '.')



    def fCalculate(self):

        if self.iMathOp >0:

            rCalc = eval("self.fstValue" + self.MathOps[self.iMathOp-1] +  "float(self.valresult.text())")

            self.valresult.setText(str(rCalc))



        self.iMathOp = 0



    def fClear(self):

        self.iMathOp = 0

        self.fstValue = 0

        self.valresult.setText('')



if __name__ == '__main__':

    app = QtGui.QApplication(sys.argv)



    widget = CalcDialog()

    widget.show()

    sys.exit(app.exec_())




الآن سأشرح التغييرات التي طرأت على الشفرة المصدرية:

أولا، لاحظنا في الشفرة المصدرية السابقة (التدوينة الثالثة) أن هنالك عشرة أسطر متعلقة بربط الأزرار بالدالة fAddNbr متشابهة في كل شيء إلا العدد الذي نمرره فكل مرة للدالة.

للتخلص من تلك الأسطر يمكن وضع كل أسماء الأزرار في قائمة، ثم المرور على كل واحد منها بإستخدام حلقة و تنفيد أمر ربط الزر بدالة fAddNbr

 نفس الشيء فعلناه بالنسبة لأزرار العمليات الحسابية.

ثانيا، أصبحت الدالة fAddNbr تقوم بشيء واحد وهو إضافة العدد الجديد إلى العدد المتواجد في الحقل.

ثالثا، قمنا بتعديل دالة fEntrySwitch بحيث إستغنينا عن المتغيرة bSwitch و أضفنا سطر جديد يسمح بالإحتفاض بالعدد الأول في المتغيرة fstValue

رابعا، قمنا بتحديث دالة fDecimal حتى تتمشى مع الوضع الجديد و هو وجود حقل واحد بدلا من إثنين.

خامسا، وقع لدالة fCalculate تغيير مهم و هو كل العمليات الحسابية يتم معالجتها بسطر واحد فقط. بحيث إستخدمنا دالة eval التي تقوم بتقيم العمليات الحسابية من نص إلى قيمة عددية.
فمثلا إن كتبنا "6 * 3" محتفظين بعلامتي "" فنقصد من ذلك أن هذا نصا و ليس عددا، لكن بايثون يتوفر على دالة إسمها eval تستطيع فهم و تقييم ما كتب في ذلك النص و إظهار النتيجة الحسابية.

سادسا تم تحديث دالة fClear حتى تقوم بمسح كل القيم. يضا تمت إعادة تسمية القسم من CalcApp إلى CalcDialog

و بهذا إنتهت هذه السلسلة. من السهل أن نستمر في تطوير هذه الآلة الحاسبة حتى تصبح جد متقدمة لكن هذا ليس من هدف هذه السلسلة. بايثون و كيوت جد متطورين و يوفرين إمكانات ضخمة.

بالنسبة للمبرمجين الذين إعتادوا على VB أو غيره قد يجدون صعوبة في التأقلم مع بايثون و كيوت، لكن الإستفادة التي ستحصلون عليها بعد خوض هذه المغامرة ستكون كبيرة.

و إن كنت تعتقد أنك لن تستطيع البرمجة ببايثون و كيوت يمكن تجربة KBasic أو Gambas إن كانت لك خلفية في VB أو Lazarus إن كنت من مبرمجي Delphi/Pascal. المهم هو أن لينوكس غني بلغات البرمجة و أدواتها.


بالنسبة للمتقدمين في البرمجة في PyQt4 هل هنالك أية ملاحظات أو تحسينات يمكن إضافتها على الشفرة المصدرية؟

تحديث 1 (14-04-2009): يمكن تحميل الشفرة المصدرية من هنا.

هناك تعليق واحد:

  1. كدا احسن بكتير
    بالمناسبة انت ممكن تستخدم in بدل من find فى اختبار وجود قيمة فى ال string

    >>> "H" in "Hello, World"
    True
    >>> "h" in "Hello, World"
    False

    وبردو يتسحسن تحذف ال f اللى بتسبق اسامى ال slots زى fClear , fDecimal وكدا

    وبس كدا على البركة

    ردحذف