From 1c0b5d7c47dc0ebfe8d445cfe81ff35dfbaf560f Mon Sep 17 00:00:00 2001 From: Charlie Date: Thu, 05 Nov 2009 15:55:20 +0000 Subject: Workshop activity My tutorials --- (limited to 'Workshop.activity/Workshop.py') diff --git a/Workshop.activity/Workshop.py b/Workshop.activity/Workshop.py new file mode 100644 index 0000000..6958d2c --- /dev/null +++ b/Workshop.activity/Workshop.py @@ -0,0 +1,455 @@ +import gtk +import gobject + +from WorkshopListItem import WorkshopListItem +from Rating import Rating +from WorkshopModel import WorkshopModel +from WorkshopController import WorkshopController +from dialogs import InfoDialog +import operator + +class WorkshopView(gtk.Alignment): + """ + Main container for the Workshop Mytutorial Part + """ + def __init__(self): + """ + Constructor + """ + gtk.Alignment.__init__(self,0.0,0.0,1.0,1.0) + + #Register Rating as a gobject + gobject.type_register(Rating) + + #create the model and the controller + self.model = WorkshopModel(self) + self.controller = WorkshopController(self,self.model) + + #Create the main view + self.mainView = WorkshopMain(self.controller) + self.detailView = None + + #display the main view + self.add(self.mainView) + self.mainView.show() + + #display all tutorials + self.controller.tutorial_query(None,None) + + def set_tutorial_list(self,tutorial_list): + """ + Set the list of tutorial to display in the main View + Refresh the View + + @param tutorial_list the list of tutorial + """ + self.mainView.set_tutorial_list(tutorial_list) + + + def change_sorting(self,sorting_key): + """ + Sort the list of tutorial base on the sorting_key + + @param sorting_key the tutorial metadata to use to sort the tutorials + """ + self.mainView.change_sorting(sorting_key) + + def display_detail(self,tutorial): + """ + Displays the detail view of a tutorial + + @param tutorial the tutorial to display + """ + #hide the main view + self.mainView.hide() + self.remove(self.mainView) + + #create the detail view and show it + self.detailView = WorkshopDetail(tutorial,self.controller) + self.add(self.detailView) + self.detailView.show() + + def display_main_view(self): + """ + Displays the main view of the Workshop + """ + #hide the detail view + self.detailView.hide() + self.remove(self.detailView) + + #display the main view + self.add(self.mainView) + self.mainView.show() + + def display_info_dialog(self,tutorial): + """ + Displays the infos dialog on a tutorial + + @param tutorial the tutorial to edit + """ + infoDialog = InfoDialog(tutorial,self.controller) + infoDialog.run() + infoDialog.destroy() + + @staticmethod + def display_login(): + loginDialog = LoginDialog() + loginDialog.run() + loginDialog.destroy() + + def refresh_content(self): + """ + Refresh the data displayed + """ + #refresh the tutorial list + self.mainView.refresh_tutorial_display() + + #refresh the detail view + self.detailView.refresh_content() + +class WorkshopMain(gtk.VBox): + """ + Contains the main view for the Workshop My tutorial + """ + def __init__(self,controller): + """Constructor + + @param controller The controller to attach the view to + """ + gtk.VBox.__init__(self,False,10) + + self.controller = controller + self.tutorial_list = [] + + #by default tutorials are sorted by name + self.sorting_key = 'Name' + + self.set_border_width(10) + + #The searchbar is displayed at the top + self.search_bar = SearchBar(self.controller) + self.pack_start(self.search_bar,False,False) + + #Add a separator after the search bar + sep = gtk.HSeparator() + self.pack_start(sep,False,False) + + #create the list item container with a scroll bar if necessary + self.main_container = gtk.ScrolledWindow() + self.main_container.set_policy(gtk.POLICY_AUTOMATIC,gtk.POLICY_AUTOMATIC) + + self.list_container= gtk.VBox() + + self.main_container.add_with_viewport(self.list_container) + self.pack_start(self.main_container) + + #Show the components + self.search_bar.show() + self.list_container.show() + self.main_container.show() + sep.show() + + + def change_sorting(self,sorting): + """ + Changes the property by which tutorial are sorted + + @param sorting The property by which tutorials will be sorted + """ + + self.sorting_key = sorting + self.sort_tutorial() + + def sort_tutorial(self): + """ + Sorts the tutorials + """ + + #if tutorials are sorted by rating they are in the reverse order + self.tutorial_list.sort(key=operator.attrgetter(self.sorting_key.lower())) + self.refresh_tutorial_display() + + def set_tutorial_list(self,tutorial_list): + """ + Set the list of tutorial to display + + @param tutorial_list the tutorial list + """ + self.tutorial_list = tutorial_list + self.sort_tutorial() + + def refresh_tutorial_display(self): + """ + Refresh the tutorial content by deleting every item and recreating them + """ + #delete every tutorial list item + for child in self.list_container.get_children(): + self.list_container.remove(child) + + #Creates and add a new item for every tutorial + for tuto in self.tutorial_list: + item = WorkshopListItem(tuto,self.controller) + self.list_container.pack_start(item) + item.show() + +class SearchBar(gtk.HBox): + """ + The search bar control for the Workshop My tutorial + """ + def __init__(self,controller): + """ + Constructor + + @param controller The controller to link the view to + """ + gtk.HBox.__init__(self,False,10) + + self.set_border_width(5) + self.controller = controller + + #creating and configuring the controls + self.search_entry = gtk.Entry(400) + + self.search_button = gtk.Button("Go") + + self.separator = gtk.VSeparator() + + self.sort_label = gtk.Label("Sort by") + self.sort_combo = gtk.combo_box_new_text() + self.sort_combo.insert_text(0,"Name") + self.sort_combo.insert_text(1,"Rating") + self.sort_combo.set_active(0) + + self.selected_sorting = self.sort_combo.get_active_text() + + #Adding the controls to the view + self.pack_start(self.search_entry,padding=5) + self.pack_start(self.search_button,False,False,padding=10) + self.pack_start(self.separator,False,False,padding=10) + self.pack_start(self.sort_label,False,False,padding=5) + self.pack_start(self.sort_combo,) + + #showing the controls + self.search_entry.show() + self.search_button.show() + self.separator.show() + self.sort_label.show() + self.sort_combo.show() + + #connecting the events + self.search_button.connect("clicked",self.controller.tutorial_query,self.search_entry.get_text()) + self.sort_combo.connect("changed",self.controller.sort_selection_changed,None) + +class WorkshopDetail(gtk.VBox): + def __init__(self,tutorial,controller): + """ + Constructor + + @param tutorial The tutorial to display + @param controller The controller to link the view with + """ + + #Used for string formatting + self.title_text = '%(title)s' + self.author_text = 'by %(author)s' + self.desc_text = 'Description: %(description)s' + + self.controller = controller + self.tutorial = tutorial + + gtk.VBox.__init__(self,False,10) + self.set_border_width(10) + + #The first row contains the back button + first_row = gtk.HBox(False) + back_image = gtk.Image() + back_image.set_from_file('arrow_back.png') + self.back_button = gtk.Button("Back") + self.back_button.set_image(back_image) + + first_row.pack_start(self.back_button,False,False) + + #The second row contains the activity icon, the title label, + #the author label and the star rating + icon = gtk.Image() + icon.set_from_file('icon.svg') + + label_holder = gtk.VBox(False,10) + + self.title_label = gtk.Label("") + self.author_label = gtk.Label("") + + #Add a small offsert for author's label alignement because it's cute + self.author_label.set_alignment(0.05,0.5) + self.title_label.set_alignment(0.0,0.5) + + label_holder.pack_start(self.title_label) + label_holder.pack_start(self.author_label) + + self.rating = Rating(tutorial,controller,rating = tutorial.rating) + + second_row = gtk.HBox(False) + second_row.pack_start(icon,False,False) + second_row.pack_start(label_holder) + second_row.pack_end(self.rating,False,False) + + #The middle of the screen contains an area for the description + self.desc_view = gtk.TextView() + self.desc_buff = gtk.TextBuffer() + self.desc_buff.set_text(tutorial.description) + self.desc_view.set_buffer(self.desc_buff) + self.desc_view.set_editable(False) + self.desc_view.set_wrap_mode(gtk.WRAP_WORD) + self.desc_view.set_cursor_visible(False) + self.desc_view.connect("realize",self.realize_cb,None) + self.desc_view.modify_base(gtk.STATE_NORMAL, gtk.gdk.color_parse("gray") ) + + #The bottom of the screen contains the button(fourth and fifth row + self.launch_button = gtk.Button('Launch') + self.launch_button.get_child().set_markup(self.title_text %{"title":"Launch"}) + self.edit_button = gtk.Button('Edit') + self.edit_button.get_child().set_markup(self.title_text %{"title":"Edit"}) + self.update_button = gtk.Button('Update') + self.update_button.get_child().set_markup(self.title_text %{"title":"Update"}) + self.info_button = gtk.Button('Infos') + self.info_button.get_child().set_markup(self.title_text %{"title":"Infos"}) + self.delete_button = gtk.Button('Delete') + self.delete_button.get_child().set_markup(self.title_text %{"title":"Delete"}) + + fourth_row = gtk.HBox(False,15) + fourth_row.pack_start(self.launch_button,False,False) + fourth_row.pack_start(self.edit_button,False,False) + fourth_row.pack_start(self.update_button,False,False) + fourth_row.pack_start(self.info_button,False,False) + fourth_row.pack_end(self.delete_button,False,False) + + + self.publish_button = gtk.Button('') + self.publish_button.get_child().set_markup(self.title_text %{"title":"Publish"}) + self.unpublish_button = gtk.Button('') + self.unpublish_button.get_child().set_markup(self.title_text %{"title":"Unpublish"}) + + fifth_row = gtk.HBox(False,15) + fifth_row.pack_start(self.publish_button,False,False) + fifth_row.pack_start(self.unpublish_button,False,False) + + #The description view contains all the extra space + self.pack_start(first_row,False,False) + self.pack_start(second_row,False,False) + self.pack_start(self.desc_view) + self.pack_end(fifth_row,False,False) + self.pack_end(fourth_row,False,False) + + #show everything + self.back_button.show() + first_row.show() + self.title_label.show() + self.author_label.show() + self.rating.show() + label_holder.show() + second_row.show() + icon.show() + self.desc_view.show() + self.launch_button.show() + self.edit_button.show() + self.update_button.show() + self.info_button.show() + self.delete_button.show() + fourth_row.show() + + self.publish_button.show() + self.unpublish_button.show() + fifth_row.show() + + #set some text with markup + self.title_label.set_markup(self.title_text % {"title":tutorial.name}) + self.author_label.set_markup(self.author_text % {"author":tutorial.author}) + + #connect the clicked events of the buttons + self.back_button.connect("clicked",self.controller.back_pressed,None) + self.publish_button.connect("clicked",self.controller.publish_tutorial,self.tutorial) + self.unpublish_button.connect("clicked",self.controller.unpublish_tutorial,self.tutorial) + self.launch_button.connect("clicked",self.controller.launch_tutorial,self.tutorial) + self.edit_button.connect("clicked",self.controller.edit_tutorial,self.tutorial) + self.update_button.connect("clicked",self.controller.update_tutorial,self.tutorial) + self.info_button.connect("clicked",self.controller.info_tutorial,self.tutorial) + self.delete_button.connect("clicked",self.controller.delete_tutorial,self.tutorial) + + def realize_cb(self,widget,data=None): + """ + This fucntion changes the cursor over the description view + So we see an arrow and not the insert text cursor + """ + widget.get_window(gtk.TEXT_WINDOW_TEXT).set_cursor(gtk.gdk.Cursor(gtk.gdk.LEFT_PTR)) + + def refresh_content(self): + """ + Refresh the labels' text based on the tutorial object + """ + self.title_label.set_markup(self.title_text % {"title":self.tutorial.name}) + self.author_label.set_markup(self.author_text % {"author":self.tutorial.author}) + self.desc_buff.set_text(self.tutorial.description) + +class WorkshopListItem(gtk.Alignment): + """ + A list item containing the details of a tutorial + """ + def __init__(self,tutorial,controller): + """ + Constructor + + @param controller The controller to link the view to + """ + gtk.Alignment.__init__(self,0.0,0.0,1.0,1.0) + self.tutorial = tutorial + self.controller = controller + + #The table will contain everything else + self.table = gtk.Table(3,3,False) + self.table.set_row_spacing(1,10) + + #Create the controls + self.lbl_title = gtk.Label('') + self.lbl_title.set_alignment(0.0,0.5) + self.title_text = '%(title)s' + self.lbl_title.set_markup(self.title_text % {'title':tutorial.name}) + + self.lbl_desc = gtk.Label(tutorial.description) + self.lbl_desc.set_line_wrap(True) + self.lbl_desc.set_alignment(0.0,0.5) + + self.btn_launch = gtk.Button('Launch') + + launch_align= gtk.Alignment(0.0,1.0,0.0,0.0) + launch_align.add(self.btn_launch) + + self.btn_details = gtk.Button('Details') + + self.icon = gtk.Image() + self.icon.set_from_file('icon.svg') + + self.rating = Rating(tutorial,controller,tutorial.rating, True) + + #Add the controls to the table + self.table.attach(self.icon,0,1,0,1,0,0) + self.table.attach(self.lbl_title,1,2,0,1,yoptions=0) + self.table.attach(self.lbl_desc,1,2,1,2,xoptions=gtk.FILL,yoptions=gtk.EXPAND) + self.table.attach(launch_align,1,2,2,3,gtk.FILL) + self.table.attach(self.btn_details,2,3,2,3,0,0) + self.table.attach(self.rating,2,3,0,2,0,0) + + #show everything + self.table.show() + self.icon.show() + self.lbl_title.show() + launch_align.show() + self.lbl_desc.show() + self.btn_launch.show() + self.btn_details.show() + self.rating.show() + + self.add(self.table) + + #connect the buttons + self.btn_details.connect("clicked",self.controller.show_details,self.tutorial) + self.btn_launch.connect("clicked",self.controller.launch_tutorial,self.tutorial) -- cgit v0.9.1