summaryrefslogtreecommitdiff
path: root/wikipedia
diff options
context:
space:
mode:
authorNick Isaacs <nick@endlessm.com>2013-08-15 14:40:09 -0700
committerNick Isaacs <nick@endlessm.com>2013-08-21 14:29:05 -0700
commit34deb37e1a26cb8817bf86ddf23d3600285a4292 (patch)
treef827b8ab8735baea17ffd0d207375baad5f1be79 /wikipedia
parent973b40e1962fa462bc3d477ca2c6ef10588c8d24 (diff)
Can add articles to the main category.
If there are articles for an app's main category, then it becomes clickable and acts like any other category. If there are no articles for a category, it isn't cilckable and has no hover animations. We no longer use the Title Label View since the main category is now a category button like any other. [endlessm/eos-sdk#259]
Diffstat (limited to 'wikipedia')
-rw-r--r--wikipedia/EndlessWikipedia.js1
-rw-r--r--wikipedia/PrebuiltFrontPage.js21
-rw-r--r--wikipedia/models/category_model.js3
-rw-r--r--wikipedia/models/domain_wiki_model.js14
-rw-r--r--wikipedia/presenters/domain_wiki_presenter.js14
-rw-r--r--wikipedia/views/domain_wiki_view.js5
-rw-r--r--wikipedia/widgets/category_button.js88
-rw-r--r--wikipedia/widgets/category_layout_manager.js41
-rw-r--r--wikipedia/widgets/category_selector_view.js12
9 files changed, 118 insertions, 81 deletions
diff --git a/wikipedia/EndlessWikipedia.js b/wikipedia/EndlessWikipedia.js
index 25df16c..2767e61 100644
--- a/wikipedia/EndlessWikipedia.js
+++ b/wikipedia/EndlessWikipedia.js
@@ -10,6 +10,7 @@ this.ArticleList = imports.wikipedia.ArticleList.ArticleList;
this.WikipediaWebView = imports.wikipedia.WikipediaWebView.WikipediaWebView;
const STYLE_CLASS_TITLE = 'title';
+const STYLE_CLASS_MAIN = 'main-element';
const STYLE_CLASS_PREBUILT = 'prebuilt';
const STYLE_CLASS_CATEGORY = 'category';
const STYLE_CLASS_ARTICLE = 'article';
diff --git a/wikipedia/PrebuiltFrontPage.js b/wikipedia/PrebuiltFrontPage.js
index 5da89f0..73f915e 100644
--- a/wikipedia/PrebuiltFrontPage.js
+++ b/wikipedia/PrebuiltFrontPage.js
@@ -4,7 +4,6 @@ const Lang = imports.lang;
const EndlessWikipedia = imports.wikipedia.EndlessWikipedia;
const CategorySelectorView = imports.wikipedia.widgets.category_selector_view;
-const TitleLabelView = imports.wikipedia.widgets.title_label_view;
const TITLE_CATEGORY_COLUMN_SPACING = 10; // pixels
@@ -13,18 +12,6 @@ GObject.ParamFlags.READWRITE = GObject.ParamFlags.READABLE | GObject.ParamFlags.
const PrebuiltFrontPage = new Lang.Class({
Name: 'PrebuiltFrontPage',
Extends: Gtk.Grid,
- Properties: {
- 'title': GObject.ParamSpec.string('title',
- 'Front page title',
- 'Name of the Wikipedia-based application',
- GObject.ParamFlags.READWRITE | GObject.ParamFlags.CONSTRUCT,
- ''),
- 'image-uri': GObject.ParamSpec.string('image-uri',
- 'Image URI',
- 'Image URI for title image',
- GObject.ParamFlags.READWRITE | GObject.ParamFlags.CONSTRUCT,
- '')
- },
Signals: {
'category-chosen': {
param_types: [GObject.TYPE_STRING, GObject.TYPE_INT]
@@ -32,14 +19,7 @@ const PrebuiltFrontPage = new Lang.Class({
},
_init: function(props) {
- this._title = null;
- this._image_uri = null;
- this._title_label = new TitleLabelView.TitleLabelView();
- let context = this._title_label.get_style_context()
- context.add_class(EndlessWikipedia.STYLE_CLASS_TITLE);
- context.add_class(EndlessWikipedia.STYLE_CLASS_PREBUILT);
- context.add_class(EndlessWikipedia.STYLE_CLASS_FRONT_PAGE);
this._category_selector = new CategorySelectorView.CategorySelectorView();
props = props || {};
@@ -47,7 +27,6 @@ const PrebuiltFrontPage = new Lang.Class({
props.column_spacing = TITLE_CATEGORY_COLUMN_SPACING;
this.parent(props);
- this.add(this._title_label);
this.add(this._category_selector);
this._category_selector.connect('category-chosen',
Lang.bind(this, this._onCategoryChosen));
diff --git a/wikipedia/models/category_model.js b/wikipedia/models/category_model.js
index 1c981bc..8a1c1ff 100644
--- a/wikipedia/models/category_model.js
+++ b/wikipedia/models/category_model.js
@@ -21,6 +21,9 @@ const CategoryModel = new Lang.Class({
'image-thumbnail-uri': GObject.ParamSpec.string('image-thumbnail-uri', 'Category Thumbnail Image URI', 'Path to thumbnail image for this category in the GResource',
GObject.ParamFlags.READABLE | GObject.ParamFlags.WRITABLE | GObject.ParamFlags.CONSTRUCT,
""),
+ 'is-main-category': GObject.ParamSpec.boolean('is-main-category', 'Is Main Category boolean', 'Flag denoting whether this category is the main category for this app',
+ GObject.ParamFlags.READABLE | GObject.ParamFlags.WRITABLE | GObject.ParamFlags.CONSTRUCT,
+ false),
},
_init: function(params) {
diff --git a/wikipedia/models/domain_wiki_model.js b/wikipedia/models/domain_wiki_model.js
index 87941ba..a387ff9 100644
--- a/wikipedia/models/domain_wiki_model.js
+++ b/wikipedia/models/domain_wiki_model.js
@@ -12,20 +12,6 @@ const DomainWikiModel = new Lang.Class({
Name: "DomainWikiModel",
Extends: GObject.Object,
- Properties: {
- 'image-uri': GObject.ParamSpec.string('image-uri',
- 'Application image URI',
- 'URI describing a path to the image for this application.',
- GObject.ParamFlags.READABLE | GObject.ParamFlags.WRITABLE | GObject.ParamFlags.CONSTRUCT_ONLY,
- ''),
-
- // Name of the Wikipedia-based application, e.g. 'Brazil', 'Math'
- 'application-name': GObject.ParamSpec.string('application-name',
- 'Application name',
- 'Name of the Wikipedia-based application',
- GObject.ParamFlags.READABLE,
- '')
- },
//params should have the image-uri for the app's image, and the application name.
_init: function(params) {
diff --git a/wikipedia/presenters/domain_wiki_presenter.js b/wikipedia/presenters/domain_wiki_presenter.js
index 15229ce..b6b432a 100644
--- a/wikipedia/presenters/domain_wiki_presenter.js
+++ b/wikipedia/presenters/domain_wiki_presenter.js
@@ -46,8 +46,6 @@ const DomainWikiPresenter = new Lang.Class({
initFromJsonFile: function(filename) {
let app_content = JSON.parse(Utils.load_file_from_resource(filename));
- this._application_name = app_content['app_name'];
- this._image_uri = app_content['app_image_uri'];
this._lang_code = filename.substring(0, 2);
let categories = app_content['categories'];
let cat_length = categories.length
@@ -56,18 +54,24 @@ const DomainWikiPresenter = new Lang.Class({
let category = categories[i];
let categoryModel = this.initCategory(category);
let articles = category['articles'];
- categoryModel.addArticles(this.initArticleModels(articles));
+ let articleModels = [];
+ if(!(articles.length == 0)) {
+ //if the category has no articles, then we cannot initialize them.
+ //This happens if the main category isn't clickable.
+ articleModels = this.initArticleModels(articles);
+ }
+ categoryModel.addArticles(articleModels);
category_models.push(categoryModel);
}
this._domain_wiki_model.addCategories(category_models);
- this._domain_wiki_view.set_front_page_info(this._application_name, this._image_uri);
},
initCategory: function(category){
let image_uri = category['image_file'];
let image_thumbnail_uri = category['image_thumb_uri'];
let params = {description:category['content_text'], image_uri:image_uri,
- image_thumbnail_uri:image_thumbnail_uri, title:category['category_name']};
+ image_thumbnail_uri:image_thumbnail_uri, title:category['category_name'],
+ is_main_category:category['is_main_category']};
return new CategoryModel.CategoryModel(params);
},
diff --git a/wikipedia/views/domain_wiki_view.js b/wikipedia/views/domain_wiki_view.js
index 9dd8358..a44eaa2 100644
--- a/wikipedia/views/domain_wiki_view.js
+++ b/wikipedia/views/domain_wiki_view.js
@@ -165,11 +165,6 @@ const DomainWikiView = new Lang.Class({
this._presenter = presenter;
},
- set_front_page_info: function(title, image_uri) {
- this._front_page.title = title;
- this._front_page.image_uri = image_uri;
- },
-
set_category_info: function(category, articles) {
this._category_view.title = category.title;
this._category_view.description = category.description;
diff --git a/wikipedia/widgets/category_button.js b/wikipedia/widgets/category_button.js
index 77812f1..4edac83 100644
--- a/wikipedia/widgets/category_button.js
+++ b/wikipedia/widgets/category_button.js
@@ -12,6 +12,7 @@ const CATEGORY_BUTTON_RIGHT_MARGIN = 20; // pixels
const CATEGORY_BUTTON_BOTTOM_MARGIN = 20; // pixels
const CATEGORY_LABEL_BENTON_SANS_CORRECTION = 0; // pixels
const _HOVER_ARROW_URI = '/com/endlessm/wikipedia-domain/assets/category_hover_arrow.png';
+const MAIN_CATEGORY_SCREEN_WIDTH_PERCENTAGE = 0.37;
GObject.ParamFlags.READWRITE = GObject.ParamFlags.READABLE | GObject.ParamFlags.WRITABLE;
@@ -31,7 +32,21 @@ const CategoryButton = new Lang.Class({
'Category title',
'Display name for the category',
GObject.ParamFlags.READWRITE | GObject.ParamFlags.CONSTRUCT,
- '')
+ ''),
+
+ // Boolean whether this button is clickable
+ 'clickable-category': GObject.ParamSpec.boolean('clickable-category',
+ 'Clickable Category',
+ 'Flag whether this category button should be clickable',
+ GObject.ParamFlags.READWRITE | GObject.ParamFlags.CONSTRUCT_ONLY,
+ true),
+
+ // Boolean whether this button is the main category
+ 'is-main-category': GObject.ParamSpec.boolean('is-main-category',
+ 'Is Main Category',
+ 'Flag whether this category button is the main category',
+ GObject.ParamFlags.READWRITE | GObject.ParamFlags.CONSTRUCT_ONLY,
+ false)
},
Signals: {
'clicked': {}
@@ -41,6 +56,8 @@ const CategoryButton = new Lang.Class({
// Get ready for property construction
this._image_uri = null;
this._category_title = null;
+ this._clickable_category = null;
+ this._is_main_category = null;
this._overlay = new Gtk.Overlay();
this._eventbox = new Gtk.EventBox({
@@ -65,19 +82,6 @@ const CategoryButton = new Lang.Class({
no_show_all: true
});
- this._eventbox.add_events(Gdk.EventMask.ENTER_NOTIFY_MASK |
- Gdk.EventMask.LEAVE_NOTIFY_MASK);
- this._eventbox.connect('enter-notify-event',
- Lang.bind(this, function(widget, event) {
- this._eventbox.set_state_flags(Gtk.StateFlags.PRELIGHT, false);
- this._arrow.show();
- }));
- this._eventbox.connect('leave-notify-event',
- Lang.bind(this, function(widget, event) {
- this._eventbox.unset_state_flags(Gtk.StateFlags.PRELIGHT);
- this._arrow.hide();
- }));
-
let context = this._label.get_style_context();
context.add_class(EndlessWikipedia.STYLE_CLASS_TITLE);
context.add_class(EndlessWikipedia.STYLE_CLASS_CATEGORY);
@@ -129,13 +133,63 @@ const CategoryButton = new Lang.Class({
this._label.set_text(value.toUpperCase());
},
+ get clickable_category() {
+ return this._clickable_category;
+ },
+
+ set clickable_category(value) {
+ this._clickable_category = value;
+ if(this._clickable_category) {
+ //Hover events/effects only trigger if the button is clickable.
+ this._eventbox.add_events(Gdk.EventMask.ENTER_NOTIFY_MASK |
+ Gdk.EventMask.LEAVE_NOTIFY_MASK);
+ this._eventbox.connect('enter-notify-event',
+ Lang.bind(this, function(widget, event) {
+ this._eventbox.set_state_flags(Gtk.StateFlags.PRELIGHT, false);
+ this._arrow.show();
+ }));
+ this._eventbox.connect('leave-notify-event',
+ Lang.bind(this, function(widget, event) {
+ this._eventbox.unset_state_flags(Gtk.StateFlags.PRELIGHT);
+ this._arrow.hide();
+ }));
+ }
+ },
+
+ get is_main_category() {
+ return this._is_main_category;
+ },
+
+ set is_main_category(value) {
+ this._is_main_category = value;
+ if(this._is_main_category) {
+ let context = this._label.get_style_context();
+ context.add_class(EndlessWikipedia.STYLE_CLASS_MAIN);
+ this._label.margin_bottom = 0;
+ }
+ },
+
// OVERRIDES
+ vfunc_get_preferred_width: function() {
+ if(this._is_main_category) {
+ let toplevel = this.get_toplevel();
+ if(toplevel == null)
+ return this.parent();
+ let width = toplevel.get_allocated_width() * MAIN_CATEGORY_SCREEN_WIDTH_PERCENTAGE;
+ return [width, width];
+ } else {
+ return this.parent();
+ }
+ },
+
vfunc_size_allocate: function(allocation) {
this.parent(allocation);
- let new_pixbuf = Utils.load_pixbuf_cover(Utils.resourceUriToPath(this._image_uri),
- allocation.width, allocation.height);
- this._image.set_from_pixbuf(new_pixbuf);
+ if(this._image_uri !== "" && this._image_uri != null) {
+ let new_pixbuf = Utils.load_pixbuf_cover(Utils.resourceUriToPath(this._image_uri),
+ allocation.width, allocation.height);
+ this._image.set_from_pixbuf(new_pixbuf);
+ }
},
// HANDLERS
diff --git a/wikipedia/widgets/category_layout_manager.js b/wikipedia/widgets/category_layout_manager.js
index a7be3bb..d49661c 100644
--- a/wikipedia/widgets/category_layout_manager.js
+++ b/wikipedia/widgets/category_layout_manager.js
@@ -7,11 +7,13 @@ const CategoryLayoutManager = new Lang.Class({
_init: function(props) {
props = props || {};
- props.column_homogeneous = true;
props.row_homogeneous = true;
+ //we don't make the columns homogenous because the 0th column
+ //needs to be 37% of the screen, according to designs.
this.parent(props);
this._childWidgets = [];
+ this._mainWidget = null;
},
// Distribute children in two columns, except for the last one if an odd
@@ -19,23 +21,41 @@ const CategoryLayoutManager = new Lang.Class({
_redistributeChildren: function() {
let numChildren = this._childWidgets.length;
let oddNumber = numChildren % 2 == 1;
+
+ let numRows = 1;
+
this._childWidgets.forEach(function(child, index) {
- let column = index % 2;
+ let column = (index % 2) + 1; //plus 1 because the mainWidget is the 0 column.
let row = Math.floor(index / 2);
+ if(numRows < row + 1)
+ numRows = row + 1; //our running count of how many rows we have, which we
+ //need when we add the main widget.
+
if(child.get_parent() === this)
Gtk.Container.prototype.remove.call(this,
this._childWidgets[index]);
if(oddNumber && index == numChildren - 1)
- this.attach(child, 0, row, 2, 1);
+ this.attach(child, 1, row, 2, 1);
else
this.attach(child, column, row, 1, 1);
}, this);
+
+ if(this._mainWidget) {
+ if(this._mainWidget.get_parent() === this) {
+ Gtk.Container.prototype.remove.call(this, this._mainWidget);
+ }
+ this.attach(this._mainWidget, 0, 0, 1, numRows);
+ }
},
add: function(child) {
- this._childWidgets.push(child);
+ if(child.is_main_category) {
+ this._mainWidget = child;
+ } else {
+ this._childWidgets.push(child);
+ }
this._redistributeChildren();
},
@@ -50,16 +70,3 @@ const CategoryLayoutManager = new Lang.Class({
this._redistributeChildren();
}
});
-
-// Gtk.init(null);
-// let w = new Gtk.Window();
-// let g = new CategoryLayoutManager();
-// let count = 7;
-// for(let i = 0; i < count; i++) {
-// let widget = new Gtk.Button({label: 'Widget ' + i});
-// g.add(widget);
-// }
-// w.add(g);
-// w.connect('destroy', Gtk.main_quit);
-// w.show_all();
-// Gtk.main();
diff --git a/wikipedia/widgets/category_selector_view.js b/wikipedia/widgets/category_selector_view.js
index 776bf52..57188ea 100644
--- a/wikipedia/widgets/category_selector_view.js
+++ b/wikipedia/widgets/category_selector_view.js
@@ -27,12 +27,20 @@ const CategorySelectorView = new Lang.Class({
// Takes an array of dictionaries with keys 'title' and 'image_uri'
setCategories: function(categories) {
categories.forEach(function(category, index, obj) {
+ let isClickable = !category.getArticles().length == 0;
let button = new CategoryButton.CategoryButton({
category_title: category.title,
- image_uri: category.image_thumbnail_uri
+ image_uri: category.image_thumbnail_uri,
+ clickable_category: isClickable,
+ is_main_category: category.is_main_category,
+ hexpand: !category.is_main_category
});
button.index = index;
- button.connect('clicked', Lang.bind(this, this._onButtonClicked));
+ //if the category has no articles, you shouldn't be able to click on it.
+ if(isClickable) {
+ button.connect('clicked', Lang.bind(this, this._onButtonClicked));
+ }
+
this.add(button);
}, this);
},