فى هذه الجزئية سنناقش بعض الويدجات المتقدمة
يستخدم الويدجت IconView لعرض مجموعة من الأيكونات فى صورة شبكة
iconview.py #!/usr/bin/python # ZetCode PyGTK tutorial # # This example demonstrates the IconView widget. # It shows the contents of the currently selected # directory on the disk. # # author: jan bodnar # website: zetcode.com # last edited: February 2009 import gtk import os COL_PATH = 0 COL_PIXBUF = 1 COL_IS_DIRECTORY = 2 class PyApp(gtk.Window): def __init__(self): super(PyApp, self).__init__() self.set_size_request(650, 400) self.set_position(gtk.WIN_POS_CENTER) self.connect("destroy", gtk.main_quit) self.set_title("IconView") self.current_directory = '/' vbox = gtk.VBox(False, 0); toolbar = gtk.Toolbar() vbox.pack_start(toolbar, False, False, 0) self.upButton = gtk.ToolButton(gtk.STOCK_GO_UP); self.upButton.set_is_important(True) self.upButton.set_sensitive(False) toolbar.insert(self.upButton, -1) homeButton = gtk.ToolButton(gtk.STOCK_HOME) homeButton.set_is_important(True) toolbar.insert(homeButton, -1) self.fileIcon = self.get_icon(gtk.STOCK_FILE) self.dirIcon = self.get_icon(gtk.STOCK_OPEN) sw = gtk.ScrolledWindow() sw.set_shadow_type(gtk.SHADOW_ETCHED_IN) sw.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC) vbox.pack_start(sw, True, True, 0) self.store = self.create_store() self.fill_store() iconView = gtk.IconView(self.store) iconView.set_selection_mode(gtk.SELECTION_MULTIPLE) self.upButton.connect("clicked", self.on_up_clicked) homeButton.connect("clicked", self.on_home_clicked) iconView.set_text_column(COL_PATH) iconView.set_pixbuf_column(COL_PIXBUF) iconView.connect("item-activated", self.on_item_activated) sw.add(iconView) iconView.grab_focus() self.add(vbox) self.show_all() def get_icon(self, name): theme = gtk.icon_theme_get_default() return theme.load_icon(name, 48, 0) def create_store(self): store = gtk.ListStore(str, gtk.gdk.Pixbuf, bool) store.set_sort_column_id(COL_PATH, gtk.SORT_ASCENDING) return store def fill_store(self): self.store.clear() if self.current_directory == None: return for fl in os.listdir(self.current_directory): if not fl[0] == '.': if os.path.isdir(os.path.join(self.current_directory, fl)): self.store.append([fl, self.dirIcon, True]) else: self.store.append([fl, self.fileIcon, False]) def on_home_clicked(self, widget): self.current_directory = os.path.realpath(os.path.expanduser('~')) self.fill_store() self.upButton.set_sensitive(True) def on_item_activated(self, widget, item): model = widget.get_model() path = model[item][COL_PATH] isDir = model[item][COL_IS_DIRECTORY] if not isDir: return self.current_directory = self.current_directory + os.path.sep + path self.fill_store() self.upButton.set_sensitive(True) def on_up_clicked(self, widget): self.current_directory = os.path.dirname(self.current_directory) self.fill_store() sensitive = True if self.current_directory == "/": sensitive = False self.upButton.set_sensitive(sensitive) PyApp() gtk.main()
فى هذا المثال، نعرض الأيكونات للمجلد المختار الحالى، ولديه شريط ادوات وزرين up و home ونستخدمهم لتصفح النظام
self.current_directory = '/'current_directory هو المجلد اللذى سيتم عرض محتواه فى ال IconView
def create_store(self): store = gtk.ListStore(str, gtk.gdk.Pixbuf, bool) store.set_sort_column_id(COL_PATH, gtk.SORT_ASCENDING) return store
ال ListStore هو مخزن لعنصر (ويمثل بياناته بأعمدة) وهنا نستخدمه لتخزين بيانات ال IconView فتقوم الطريقة create_store بإنشاء المخزن بثلاث معاملات (اسم المجلدو كائن pixbuf و قيمة منطقية لتحدد ماذا كان مجلد او ملف-
if not fl[0] == '.': if os.path.isdir(os.path.join(self.current_directory, fl)): self.store.append([fl, self.dirIcon, True]) else: self.store.append([fl, self.fileIcon, False])
فى الطريقة fill_store .. ننشئ مخزن البيانات مكون من المجلدات عدا المخفية -تبدأ ب " . “
def on_home_clicked(self, widget): self.current_directory = os.path.realpath(os.path.expanduser('~')) self.fill_store() self.upButton.set_sensitive(True)
اذا ضغطنا على الزر Home، نحصل على مسار المنزل ونعيد ملء مخزن البيانات وننشط الزر up
فى الطريقة on_item_activated نتفاعل مع حدث -يحدث عند الضغط على عنصر من عناصر ال icon view -
model = widget.get_model() path = model[item][COL_PATH] isDir = model[item][COL_IS_DIRECTORY] if not isDir: return
نحصل على مسار العنصر المنشط، ثم نقرر ماإذا كان مجلد او ملف -نقوم بالخروج فورا-
self.current_directory = self.current_directory + os.path.sep + path self.fill_store() self.upButton.set_sensitive(True)
فى حال انه مجلد، نستبدل الجذر بالمسار الحالى ونعيد ملء مخزن البيانات وننشط حساسية الزر up
def on_up_clicked(self, widget): self.current_directory = os.path.dirname(self.current_directory) self.fill_store() sensitive = True if self.current_directory == "/": sensitive = False self.upButton.set_sensitive(sensitive)
عند الضغط على الزر up ، نستبدل مجلد الجذر بأبيه ونعيد ملء المخزن، لاحظ انه سيكون منشط فقط عند وجودنا فى اى مجلد اقل من /
Figure: IconView
فى المثال التالى، نعرض ويدجت الشجرة ليمثل list view، مرة اخرى سنستخدم ال ListStore ليمثل البيانات
listview.py #!/usr/bin/python # ZetCode PyGTK tutorial # # This example shows a TreeView widget # in a list view mode # # author: jan bodnar # website: zetcode.com # last edited: February 2009 import gtk actresses = [('jessica alba', 'pomona', '1981'), ('sigourney weaver', 'new york', '1949'), ('angelina jolie', 'los angeles', '1975'), ('natalie portman', 'jerusalem', '1981'), ('rachel weiss', 'london', '1971'), ('scarlett johansson', 'new york', '1984' )] class PyApp(gtk.Window): def __init__(self): super(PyApp, self).__init__() self.set_size_request(350, 250) self.set_position(gtk.WIN_POS_CENTER) self.connect("destroy", gtk.main_quit) self.set_title("ListView") vbox = gtk.VBox(False, 8) sw = gtk.ScrolledWindow() sw.set_shadow_type(gtk.SHADOW_ETCHED_IN) sw.set_policy(gtk.POLICY_AUTOMATIC, gtk.POLICY_AUTOMATIC) vbox.pack_start(sw, True, True, 0) store = self.create_model() treeView = gtk.TreeView(store) treeView.connect("row-activated", self.on_activated) treeView.set_rules_hint(True) sw.add(treeView) self.create_columns(treeView) self.statusbar = gtk.Statusbar() vbox.pack_start(self.statusbar, False, False, 0) self.add(vbox) self.show_all() def create_model(self): store = gtk.ListStore(str, str, str) for act in actresses: store.append([act[0], act[1], act[2]]) return store def create_columns(self, treeView): rendererText = gtk.CellRendererText() column = gtk.TreeViewColumn("Name", rendererText, text=0) column.set_sort_column_id(0) treeView.append_column(column) rendererText = gtk.CellRendererText() column = gtk.TreeViewColumn("Place", rendererText, text=1) column.set_sort_column_id(1) treeView.append_column(column) rendererText = gtk.CellRendererText() column = gtk.TreeViewColumn("Year", rendererText, text=2) column.set_sort_column_id(2) treeView.append_column(column) def on_activated(self, widget, row, col): model = widget.get_model() text = model[row][0] + ", " + model[row][1] + ", " + model[row][2] self.statusbar.push(0, text) PyApp() gtk.main()
فى مثالنا، سنعرض قائمة من 6 ممثلات "تمثل فى 6 صفوف" فى ويدجت الشجرة، كل صف يشمل اسم ومحل الميلاد وتاريخه
def create_model(self): store = gtk.ListStore(str, str, str) for act in actresses: store.append([act[0], act[1], act[2]]) return store
ننشئ المودل (البيانات اللتى سيتم تمثيلها)، هنا ننشئ List Store، ولها 3 معاملات، اسم الممثلة، تاريخ ميلادها، ومحل الميلاد
treeView = gtk.TreeView(store) treeView.connect("row-activated", self.on_activated) treeView.set_rules_hint(True)
هنا ننشئ ويدجت الشجرة، لاحظ انه يأخذ (ListStore) ليحدد البيانات اللتى سيعرضها. الطريقة set_rules_hint تغير لون الخلفية بين كل صفين -كما بالصورة-
rendererText = gtk.CellRendererText() column = gtk.TreeViewColumn("Name", rendererText, text=0) column.set_sort_column_id(0) treeView.append_column(column)
فى الطريقة create_columns ، نضيف 3 اعمدة لعارض الشجرة. الكود بالأعلى ينشئ عمود لعرض اسماء الممثلات. ال CellRendererText يحصل على التكست من العمود الأول من المودل -0-
def on_activated(self, widget, row, col): model = widget.get_model() text = model[row][0] + ", " + model[row][1] + ", " + model[row][2] self.statusbar.push(0, text)
عند الضغط على العنصر، نعرض الصف كله على شريط الحالة
Figure: ListView
فى هذه الجزئية سنتعرض لويدجت الشجرة TreeView ليمثل هيكلية البيانات
tree.py #!/usr/bin/python # ZetCode PyGTK tutorial # # This example shows a TreeView widget # in a tree view mode # # author: jan bodnar # website: zetcode.com # last edited: February 2009 import gtk class PyApp(gtk.Window): def __init__(self): super(PyApp, self).__init__() self.set_size_request(400, 300) self.set_position(gtk.WIN_POS_CENTER) self.connect("destroy", gtk.main_quit) self.set_title("Tree") tree = gtk.TreeView() languages = gtk.TreeViewColumn() languages.set_title("Programming languages") cell = gtk.CellRendererText() languages.pack_start(cell, True) languages.add_attribute(cell, "text", 0) treestore = gtk.TreeStore(str) it = treestore.append(None, ["Scripting languages"]) treestore.append(it, ["Python"]) treestore.append(it, ["PHP"]) treestore.append(it, ["Perl"]) treestore.append(it, ["Ruby"]) it = treestore.append(None, ["Compiling languages"]) treestore.append(it, ["C#"]) treestore.append(it, ["C++"]) treestore.append(it, ["C"]) treestore.append(it, ["Java"]) tree.append_column(languages) tree.set_model(treestore) self.add(tree) self.show_all() PyApp() gtk.main()
فى هذه المرة سنستخدم ويدجت ال TreeView لعرض بيانات هيكلية
tree = gtk.TreeView()انشاء ويدجت الشجرة TreeView
languages = gtk.TreeViewColumn() languages.set_title("Programming languages")
لديها عمود واحد عنوانه Programming Languages
cell = gtk.CellRendererText() languages.pack_start(cell, True) languages.add_attribute(cell, "text", 0)
نعرض بعض البيانات النصية
treestore = gtk.TreeStore(str)نخزن البيانات وهنا نستخدم نوع جديد من المخازن وهو ال TreeStore
it = treestore.append(None, ["Scripting languages"]) treestore.append(it, ["Python"]) treestore.append(it, ["PHP"])
نضيف البيانات للشجرة، الكائن TreeIter يستخدم للوصول للبيانات فى كل صف
tree.append_column(languages)اضافة العمود
tree.set_model(treestore)اضافة المودل
Figure: Tree
فى هذا الفصل تحدثنا عن ويدجات متقدمة
Home Contents Top of Page