From ab1148cbc99a00ce1c5fa9be061396859c979639 Mon Sep 17 00:00:00 2001 From: Rushabh Mehta Date: Tue, 31 Jan 2012 18:01:16 +0530 Subject: [PATCH] added products, custom pages and footer --- .../home/page/event_updates/event_updates.js | 4 - erpnext/startup/event_handlers.py | 3 +- erpnext/startup/modules.js | 8 +- erpnext/startup/modules_new.js | 36 +++ erpnext/startup/startup.js | 10 +- erpnext/stock/doctype/item/item.txt | 98 +------ .../website/Module Def/Website/Website.txt | 18 +- erpnext/website/css/website.css | 42 +++ erpnext/website/doctype/blog/blog.py | 32 +-- erpnext/website/doctype/product/__init__.py | 0 erpnext/website/doctype/product/product.js | 6 + erpnext/website/doctype/product/product.py | 27 ++ erpnext/website/doctype/product/product.txt | 251 ++++++++++++++++++ .../website/doctype/product/product_page.js | 13 + erpnext/website/doctype/product/template.html | 28 ++ .../products_settings/products_settings.py | 15 ++ .../doctype/top_bar_item/top_bar_item.txt | 6 +- .../top_bar_settings/top_bar_settings.txt | 45 +++- erpnext/website/doctype/web_page/__init__.py | 0 .../website/doctype/web_page/template.html | 13 + erpnext/website/doctype/web_page/web_page.py | 30 +++ erpnext/website/doctype/web_page/web_page.txt | 110 ++++++++ erpnext/website/js/product_category.js | 22 ++ erpnext/website/js/topbar.js | 33 ++- erpnext/website/page/products/products.html | 3 +- erpnext/website/page/products/products.js | 83 +++++- erpnext/website/utils.py | 51 +++- index.html | 2 +- version.num | 2 +- 29 files changed, 835 insertions(+), 156 deletions(-) create mode 100644 erpnext/startup/modules_new.js create mode 100644 erpnext/website/doctype/product/__init__.py create mode 100644 erpnext/website/doctype/product/product.js create mode 100644 erpnext/website/doctype/product/product.py create mode 100644 erpnext/website/doctype/product/product.txt create mode 100644 erpnext/website/doctype/product/product_page.js create mode 100644 erpnext/website/doctype/product/template.html create mode 100644 erpnext/website/doctype/products_settings/products_settings.py create mode 100644 erpnext/website/doctype/web_page/__init__.py create mode 100644 erpnext/website/doctype/web_page/template.html create mode 100644 erpnext/website/doctype/web_page/web_page.py create mode 100644 erpnext/website/doctype/web_page/web_page.txt create mode 100644 erpnext/website/js/product_category.js diff --git a/erpnext/home/page/event_updates/event_updates.js b/erpnext/home/page/event_updates/event_updates.js index faf9a75e5c..1ce83dfceb 100644 --- a/erpnext/home/page/event_updates/event_updates.js +++ b/erpnext/home/page/event_updates/event_updates.js @@ -477,10 +477,6 @@ FeedList.prototype.make_list = function() { }); } -FeedList.prototype.after_run = function() { - this.list.has_data() ? $dh(this.no_result) : $ds(this.no_result) -} - FeedList.prototype.render_feed = function(parent, data) { new FeedItem(parent, data, this); } diff --git a/erpnext/startup/event_handlers.py b/erpnext/startup/event_handlers.py index 603d8f33f8..1bdbcb4b09 100644 --- a/erpnext/startup/event_handlers.py +++ b/erpnext/startup/event_handlers.py @@ -41,7 +41,8 @@ def boot_session(bootinfo): if webnotes.session['user']=='Guest': bootinfo['topbar'] = webnotes.model.doc.getsingle('Top Bar Settings') - bootinfo['topbaritems'] = webnotes.conn.sql("""select label, std_page, custom_page, parent_label + bootinfo['topbaritems'] = webnotes.conn.sql("""select label, std_page, custom_page, + parent_label, parentfield from `tabTop Bar Item` where parent='Top Bar Settings' order by idx asc""", as_dict=1) else: bootinfo['letter_heads'] = get_letter_heads() diff --git a/erpnext/startup/modules.js b/erpnext/startup/modules.js index b5356d9713..9503dbe70d 100644 --- a/erpnext/startup/modules.js +++ b/erpnext/startup/modules.js @@ -266,11 +266,14 @@ SidebarItem.prototype.show_items = function() { SidebarItem.prototype.show_section = function(sec_type) { var me = this; var label = this.det.module_label + ' ' + sec_type; - var type_map = {'Reports':'Reports', 'Custom Reports':'Custom Reports', 'Pages':'Tools', 'Single DocType':'Tools', 'Setup Forms':'Tools'} + var type_map = {'Reports':'Reports', 'Custom Reports':'Custom Reports', + 'Pages':'Tools', 'Single DocType':'Tools', 'Setup Forms':'Tools'} + if(page_body.pages[label]) { loadpage(label, null, 1); } else { + // make the reports page var page = page_body.add_page(label); this.wrapper = $a(page,'div','layout_wrapper'); @@ -373,3 +376,6 @@ pscript.startup_set_module_order = function() { $c_obj('Home Control', 'get_module_order', '', callback) } + + + diff --git a/erpnext/startup/modules_new.js b/erpnext/startup/modules_new.js new file mode 100644 index 0000000000..5f912b0191 --- /dev/null +++ b/erpnext/startup/modules_new.js @@ -0,0 +1,36 @@ +// Tools Page +erpnext.ListPage = Class.extend({ + init: function(opts) { + var me = this; + this.opts = opts; + this.page = page_body.add_page[opts.title]; + this.page.wrapper = $a(this.page, 'div', 'layout_wrapper'); + this.page.head = new PageHeading(this.wrapper, this.title) + this.page.list = new wn.widgets.Listing({ + parent: this.page.wrapper, + query: opts.query, + render:row: opts.render_row + }); + }, + show: function() { + if(this.first) { + this.page.list.run(); + this.first = false; + } + page_body.change_to(this.opts.title); + } +}); + +erpnext.ToolsPage = erpnext.ListPage.extend({ + init: function(opts) { + this._super({ + title: opts.module + ' Settings', + query: repl('select name, description from tabDocType where \ + module=%(module)s and ifnull(issingle,0)=1 order by name asc', opts), + render_row: function(parent, data) { + parent.innerHTML = repl('%(name)s\ +
%(description)s
', data) + } + }) + } +}); \ No newline at end of file diff --git a/erpnext/startup/startup.js b/erpnext/startup/startup.js index f97eb39bc1..70dcfc44f5 100644 --- a/erpnext/startup/startup.js +++ b/erpnext/startup/startup.js @@ -28,13 +28,13 @@ erpnext.startup.start = function() { wn.require('erpnext/startup/toolbar.js'); erpnext.toolbar.setup(); wn.require('erpnext/startup/feature_setup.js'); + + // border to the body + // ------------------ + $('footer').html(''); } - // border to the body - // ------------------ - $('footer').html(''); - $('#startup_div').toggle(false); } diff --git a/erpnext/stock/doctype/item/item.txt b/erpnext/stock/doctype/item/item.txt index 28d0c7a7cf..ec3b160680 100644 --- a/erpnext/stock/doctype/item/item.txt +++ b/erpnext/stock/doctype/item/item.txt @@ -5,14 +5,14 @@ { 'creation': '2010-08-08 17:09:05', 'docstatus': 0, - 'modified': '2012-01-30 12:10:37', + 'modified': '2012-01-30 16:46:37', 'modified_by': 'Administrator', 'owner': 'Administrator' }, # These values are common for all DocType { - '_last_update': '1327904359', + '_last_update': '1327905637', 'allow_attach': 1, 'allow_trash': 1, 'autoname': 'field:item_code', @@ -29,7 +29,7 @@ 'show_in_menu': 0, 'subject': '%(item_name)s', 'tag_fields': 'item_group', - 'version': 164 + 'version': 165 }, # These values are common for all DocField @@ -493,98 +493,6 @@ 'permlevel': 0 }, - # DocField - { - 'doctype': 'DocField', - 'fieldtype': 'Section Break', - 'label': 'Website Details', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Check here to show this item on your website under "Products"', - 'doctype': 'DocField', - 'fieldname': 'show_in_website', - 'fieldtype': 'Check', - 'label': 'Show in website', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Small image shown in listings (100px width) (Attach first)', - 'doctype': 'DocField', - 'fieldname': 'thumbnail_image', - 'fieldtype': 'Select', - 'label': 'Thumbnail Image', - 'options': 'attach_files:', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Small image shown product page (300px width) (Attach first)', - 'doctype': 'DocField', - 'fieldname': 'full_image', - 'fieldtype': 'Select', - 'label': 'Full Image', - 'options': 'attach_files:', - 'permlevel': 0 - }, - - # DocField - { - 'doctype': 'DocField', - 'fieldtype': 'Column Break', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Price list for your website (leave blank if you do not want to show the price)', - 'doctype': 'DocField', - 'fieldname': 'website_price_list', - 'fieldtype': 'Link', - 'label': 'Website Price List', - 'options': 'Price List', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Enter your shipping warehouse if you want "In Stock" or "Out of Stock" to appear on your website', - 'doctype': 'DocField', - 'fieldname': 'website_warehouse', - 'fieldtype': 'Link', - 'label': 'Website Warehouse', - 'options': 'Warehouse', - 'permlevel': 0 - }, - - # DocField - { - 'doctype': 'DocField', - 'fieldtype': 'Section Break', - 'permlevel': 0 - }, - - # DocField - { - 'colour': 'White:FFF', - 'description': 'Detailed description of your product for your website. Formatted in html/markdown format.', - 'doctype': 'DocField', - 'fieldname': 'website_description', - 'fieldtype': 'Code', - 'label': 'Website Description', - 'permlevel': 0 - }, - # DocField { 'colour': 'White:FFF', diff --git a/erpnext/website/Module Def/Website/Website.txt b/erpnext/website/Module Def/Website/Website.txt index fa35cde969..8ac31c7361 100644 --- a/erpnext/website/Module Def/Website/Website.txt +++ b/erpnext/website/Module Def/Website/Website.txt @@ -5,7 +5,7 @@ { 'creation': '2012-01-23 17:05:32', 'docstatus': 0, - 'modified': '2012-01-30 12:19:11', + 'modified': '2012-01-31 15:19:28', 'modified_by': 'Administrator', 'owner': 'Administrator' }, @@ -52,6 +52,22 @@ 'doctype': 'Module Def Item' }, + # Module Def Item + { + 'display_name': 'Web Page', + 'doc_name': 'Web Page', + 'doc_type': 'Forms', + 'doctype': 'Module Def Item' + }, + + # Module Def Item + { + 'display_name': 'Product', + 'doc_name': 'Product', + 'doc_type': 'Forms', + 'doctype': 'Module Def Item' + }, + # Module Def Item { 'display_name': 'Blog', diff --git a/erpnext/website/css/website.css b/erpnext/website/css/website.css index 5afb47d85b..c653c3be4f 100644 --- a/erpnext/website/css/website.css +++ b/erpnext/website/css/website.css @@ -3,6 +3,10 @@ margin: auto; } +footer { + width: 900px; + margin: auto; +} header .topbar .container { width: 900px; margin: auto; @@ -25,4 +29,42 @@ header .topbar .container { margin-right: 15px; color: #606060; overflow-x: hidden; +} + +.web-footer { + text-align: center; + color: #777; + margin: 10px; + line-height: 1.7; +} + +.web-footer div, .web-footer a { + font-size: 11px; +} + +.web-footer-menu { + margin-bottom: 7px; +} +.web-footer a, .web-footer a:visited { + color: #777; +} + +.web-footer a:hover { + background-color: #777; + color: #fff; +} + +.web-footer-menu ul { + list-style: none; + margin: 0px; +} + +.web-footer-menu ul li { + display: inline; + padding: 2px 15px; + border-right: 1px solid #999; +} + +.web-footer-menu ul li:last-child { + border-right: 0px solid #777; } \ No newline at end of file diff --git a/erpnext/website/doctype/blog/blog.py b/erpnext/website/doctype/blog/blog.py index 15457412a3..e9c0d74448 100644 --- a/erpnext/website/doctype/blog/blog.py +++ b/erpnext/website/doctype/blog/blog.py @@ -5,6 +5,7 @@ naming for same name files: file.gif, file-1.gif, file-2.gif etc """ import webnotes +import website.utils class DocType(): def __init__(self, d, dl): @@ -12,27 +13,11 @@ class DocType(): def autoname(self): """save file by its name""" - import re - self.doc.name = re.sub('[~!@#$%^&*()<>,."\']', '', self.doc.title.lower()) - self.doc.name = '-'.join(self.doc.name.split()[:4]) - if webnotes.conn.sql("""select name from tabBlog where name=%s""", self.doc.name) or \ - webnotes.conn.sql("""select name from tabPage where name=%s""", self.doc.name): - webnotes.msgprint("Another page with similar title exists, please change the title",\ - raise_exception=1) + self.doc.name = website.utils.page_name(self.doc.title) def on_update(self): - """write/update 'Page' with the blog""" - from webnotes.model.doc import Document - - if webnotes.conn.sql("""select name from tabPage where name=%s""", self.doc.name): - p = Document('Page', self.doc.name) - else: - p = Document('Page') - - p.title = self.doc.title - p.name = p.page_name = self.doc.name - p.module = 'Website' - p.standard = 'No' + """write/update 'Page' with the blog""" + p = website.utils.add_page(self.doc.title) from jinja2 import Template import markdown2 @@ -48,11 +33,6 @@ class DocType(): p.save() - # add guest access - if not webnotes.conn.sql("""select parent from `tabPage Role` - where role='Guest' and parent=%s""", self.doc.name): - d = Document('Page Role') - d.parent = self.doc.name - d.role = 'Guest' - d.save() + website.utils.add_guest_access_to_page(p.name) + \ No newline at end of file diff --git a/erpnext/website/doctype/product/__init__.py b/erpnext/website/doctype/product/__init__.py new file mode 100644 index 0000000000..e69de29bb2 diff --git a/erpnext/website/doctype/product/product.js b/erpnext/website/doctype/product/product.js new file mode 100644 index 0000000000..c0b507e4d0 --- /dev/null +++ b/erpnext/website/doctype/product/product.js @@ -0,0 +1,6 @@ +$.extend(cur_frm.cscript, { + onload: function() { + cur_frm.add_fetch('item', 'description', 'short_description'); + cur_frm.add_fetch('item', 'item_name', 'title'); + } +}); \ No newline at end of file diff --git a/erpnext/website/doctype/product/product.py b/erpnext/website/doctype/product/product.py new file mode 100644 index 0000000000..935d762010 --- /dev/null +++ b/erpnext/website/doctype/product/product.py @@ -0,0 +1,27 @@ +class DocType: + def __init__(self, d, dl): + self.doc, self.doclist = d, dl + + def validate(self): + """make page for this product""" + import website.utils + + p = website.utils.add_page("Product " + self.doc.title) + + from jinja2 import Template + import markdown2 + import os + + self.doc.long_description_html = markdown2.markdown(self.doc.long_description or '') + + with open(os.path.join(os.path.dirname(__file__), 'template.html'), 'r') as f: + p.content = Template(f.read()).render(doc=self.doc) + + with open(os.path.join(os.path.dirname(__file__), 'product_page.js'), 'r') as f: + p.script = Template(f.read()).render(doc=self.doc) + + p.save() + + website.utils.add_guest_access_to_page(p.name) + self.doc.page_name = p.name + del self.doc.fields['long_description_html'] \ No newline at end of file diff --git a/erpnext/website/doctype/product/product.txt b/erpnext/website/doctype/product/product.txt new file mode 100644 index 0000000000..fac4cfbda4 --- /dev/null +++ b/erpnext/website/doctype/product/product.txt @@ -0,0 +1,251 @@ +# DocType, Product +[ + + # These values are common in all dictionaries + { + 'creation': '2012-01-30 16:21:29', + 'docstatus': 0, + 'modified': '2012-01-31 13:46:23', + 'modified_by': 'Administrator', + 'owner': 'Administrator' + }, + + # These values are common for all DocType + { + '_last_update': '1327995660', + 'allow_attach': 1, + 'autoname': 'field:item', + 'colour': 'White:FFF', + 'description': 'A Product is shown on the website and is linked to an item.', + 'doctype': 'DocType', + 'max_attachments': 5, + 'module': 'Website', + 'name': '__common__', + 'section_style': 'Simple', + 'show_in_menu': 0, + 'version': 10 + }, + + # These values are common for all DocField + { + 'doctype': 'DocField', + 'name': '__common__', + 'parent': 'Product', + 'parentfield': 'fields', + 'parenttype': 'DocType' + }, + + # These values are common for all DocPerm + { + 'doctype': 'DocPerm', + 'name': '__common__', + 'parent': 'Product', + 'parentfield': 'permissions', + 'parenttype': 'DocType', + 'read': 1, + 'role': 'Website Manager' + }, + + # DocType, Product + { + 'doctype': 'DocType', + 'name': 'Product' + }, + + # DocPerm + { + 'create': 1, + 'doctype': 'DocPerm', + 'permlevel': 0, + 'write': 1 + }, + + # DocPerm + { + 'doctype': 'DocPerm', + 'permlevel': 1 + }, + + # DocField + { + 'colour': 'White:FFF', + 'doctype': 'DocField', + 'fieldname': 'item', + 'fieldtype': 'Link', + 'label': 'Item', + 'options': 'Item', + 'permlevel': 0, + 'reqd': 1 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'title', + 'fieldtype': 'Link', + 'label': 'Title', + 'permlevel': 0 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'published', + 'fieldtype': 'Check', + 'label': 'Published', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Select Price List for the web. Leave blank to hide price.', + 'doctype': 'DocField', + 'fieldname': 'price_list', + 'fieldtype': 'Link', + 'label': 'Price List', + 'options': 'Price List', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Select shipping warehouse to show "In Stock" or "Out of Stock". To hide, leave blank', + 'doctype': 'DocField', + 'fieldname': 'warehouse', + 'fieldtype': 'Link', + 'label': 'Warehouse', + 'options': 'Warehouse', + 'permlevel': 0 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldtype': 'Column Break', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Image for listing (Width: 100px) (Attach First)', + 'doctype': 'DocField', + 'fieldname': 'thumbnail_image', + 'fieldtype': 'Select', + 'label': 'Thumbnail Image', + 'options': 'attach_files:', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Image for listing (Width: 300px) (Attach First)', + 'doctype': 'DocField', + 'fieldname': 'full_image', + 'fieldtype': 'Select', + 'label': 'Full Image', + 'options': 'attach_files:', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'doctype': 'DocField', + 'fieldname': 'short_description', + 'fieldtype': 'Text', + 'label': 'Short Description', + 'permlevel': 0, + 'reqd': 1 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldtype': 'Section Break', + 'permlevel': 0 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Full description (formatted as markdown)', + 'doctype': 'DocField', + 'fieldname': 'long_description', + 'fieldtype': 'Code', + 'label': 'Long Description', + 'permlevel': 0, + 'reqd': 0 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldtype': 'Section Break', + 'permlevel': 0 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'page_name', + 'fieldtype': 'Data', + 'label': 'Page Name', + 'permlevel': 1 + }, + + # DocField + { + 'colour': 'White:FFF', + 'doctype': 'DocField', + 'fieldname': 'price', + 'fieldtype': 'Currency', + 'hidden': 0, + 'label': 'Price', + 'permlevel': 1 + }, + + # DocField + { + 'colour': 'White:FFF', + 'doctype': 'DocField', + 'fieldname': 'sales', + 'fieldtype': 'Currency', + 'label': 'Sales', + 'permlevel': 1 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'stock', + 'fieldtype': 'Currency', + 'label': 'Stock', + 'permlevel': 1 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'currency', + 'fieldtype': 'Link', + 'label': 'Currency', + 'options': 'Currency', + 'permlevel': 1 + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'file_list', + 'fieldtype': 'Text', + 'hidden': 1, + 'label': 'File List', + 'no_copy': 1, + 'permlevel': 0, + 'print_hide': 1 + } +] \ No newline at end of file diff --git a/erpnext/website/doctype/product/product_page.js b/erpnext/website/doctype/product/product_page.js new file mode 100644 index 0000000000..7d031ef94b --- /dev/null +++ b/erpnext/website/doctype/product/product_page.js @@ -0,0 +1,13 @@ +wn.require('erpnext/website/js/product_category.js'); + +pscript["onload_{{ doc.page_name }}"] = function(wrapper) { + erpnext.make_product_categories(wrapper); + $(wrapper).find('.product-inquiry').click(function() { + loadpage('contact', function() { + $('#content-contact-us [name="contact-message"]').val("Hello,\n\n\ + Please send me more information on {{ doc.title }} (Item Code:{{ doc.item }})\n\n\ + My contact details are:\n\nThank you!\ + "); + }) + }) +} \ No newline at end of file diff --git a/erpnext/website/doctype/product/template.html b/erpnext/website/doctype/product/template.html new file mode 100644 index 0000000000..8c7f918ef1 --- /dev/null +++ b/erpnext/website/doctype/product/template.html @@ -0,0 +1,28 @@ +
+
+

{{ doc.title }}

+
+
+ + {{ doc.long_description_html }} + +
+
+
+
+

Item Code: {{ doc.item }}

+

{{ doc.short_description }}

+

+

+
+
+

More Categories

+
+
+
+
\ No newline at end of file diff --git a/erpnext/website/doctype/products_settings/products_settings.py b/erpnext/website/doctype/products_settings/products_settings.py new file mode 100644 index 0000000000..195f37f8ac --- /dev/null +++ b/erpnext/website/doctype/products_settings/products_settings.py @@ -0,0 +1,15 @@ +import webnotes + +class DocType: + def __init__(self, d, dl): + self.doc, self.doclist = d, dl + + def on_update(self): + tmp = None + for d in self.doclist: + if d.doctype=="Product Group": + import json + tmp = json.dumps({"item_group": d.item_group, "label":d.label}) + break + + webnotes.conn.set_default("default_product_category", tmp) \ No newline at end of file diff --git a/erpnext/website/doctype/top_bar_item/top_bar_item.txt b/erpnext/website/doctype/top_bar_item/top_bar_item.txt index e352ef550f..410352c235 100644 --- a/erpnext/website/doctype/top_bar_item/top_bar_item.txt +++ b/erpnext/website/doctype/top_bar_item/top_bar_item.txt @@ -5,7 +5,7 @@ { 'creation': '2012-01-24 10:24:19', 'docstatus': 0, - 'modified': '2012-01-24 10:24:19', + 'modified': '2012-01-30 14:14:48', 'modified_by': 'Administrator', 'owner': 'Administrator' }, @@ -19,7 +19,7 @@ 'name': '__common__', 'section_style': 'Simple', 'show_in_menu': 0, - 'version': 1 + 'version': 2 }, # These values are common for all DocField @@ -52,7 +52,7 @@ 'fieldname': 'std_page', 'fieldtype': 'Select', 'label': 'Std Page', - 'options': 'Home\nAbout\nContact\nProduct\nCustomer\nBlog\nPartner\nCareer\nCustom' + 'options': 'Home\nAbout\nContact\nProducts\nBlog\nCustom' }, # DocField diff --git a/erpnext/website/doctype/top_bar_settings/top_bar_settings.txt b/erpnext/website/doctype/top_bar_settings/top_bar_settings.txt index d65146106a..ad9a158cc5 100644 --- a/erpnext/website/doctype/top_bar_settings/top_bar_settings.txt +++ b/erpnext/website/doctype/top_bar_settings/top_bar_settings.txt @@ -5,14 +5,14 @@ { 'creation': '2012-01-24 10:21:41', 'docstatus': 0, - 'modified': '2012-01-24 10:45:02', + 'modified': '2012-01-31 15:55:34', 'modified_by': 'Administrator', 'owner': 'Administrator' }, # These values are common for all DocType { - '_last_update': '1327380941', + '_last_update': '1327382102', 'allow_attach': 1, 'colour': 'White:FFF', 'doctype': 'DocType', @@ -23,7 +23,7 @@ 'name': '__common__', 'section_style': 'Simple', 'show_in_menu': 0, - 'version': 3 + 'version': 4 }, # These values are common for all DocField @@ -67,6 +67,13 @@ 'role': 'Website Manager' }, + # DocField + { + 'doctype': 'DocField', + 'fieldtype': 'Section Break', + 'label': 'Top Bar' + }, + # DocField { 'colour': 'White:FFF', @@ -86,6 +93,38 @@ 'options': 'Top Bar Item' }, + # DocField + { + 'doctype': 'DocField', + 'fieldtype': 'Section Break', + 'label': 'Footer' + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'address', + 'fieldtype': 'Text', + 'label': 'Address' + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'copyright', + 'fieldtype': 'Data', + 'label': 'Copyright' + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'footer_items', + 'fieldtype': 'Table', + 'label': 'Footer Items', + 'options': 'Top Bar Item' + }, + # DocField { 'doctype': 'DocField', diff --git a/erpnext/website/doctype/web_page/__init__.py b/erpnext/website/doctype/web_page/__init__.py new file mode 100644 index 0000000000..e69de29bb2 diff --git a/erpnext/website/doctype/web_page/template.html b/erpnext/website/doctype/web_page/template.html new file mode 100644 index 0000000000..8b0049beda --- /dev/null +++ b/erpnext/website/doctype/web_page/template.html @@ -0,0 +1,13 @@ +
+
+

{{ doc.title }}

+
+
+ {{ doc.main_section_html }} +
+
+ {{ doc.side_section_html }} +
+
+
+
\ No newline at end of file diff --git a/erpnext/website/doctype/web_page/web_page.py b/erpnext/website/doctype/web_page/web_page.py new file mode 100644 index 0000000000..d2ad6d34a5 --- /dev/null +++ b/erpnext/website/doctype/web_page/web_page.py @@ -0,0 +1,30 @@ +import webnotes +import website.utils + +class DocType: + def __init__(self, d, dl): + self.doc, self.doclist = d, dl + + def autoname(self): + """name from title""" + self.doc.name = website.utils.page_name(self.doc.title) + + def validate(self): + """make page for this product""" + p = website.utils.add_page(self.doc.title) + + from jinja2 import Template + import os + + website.utils.markdown(self.doc, ['main_section', 'side_section']) + + with open(os.path.join(os.path.dirname(__file__), 'template.html'), 'r') as f: + p.content = Template(f.read()).render(doc=self.doc) + + p.save() + + website.utils.add_guest_access_to_page(p.name) + + del self.doc.fields['main_section_html'] + del self.doc.fields['side_section_html'] + \ No newline at end of file diff --git a/erpnext/website/doctype/web_page/web_page.txt b/erpnext/website/doctype/web_page/web_page.txt new file mode 100644 index 0000000000..aa08a8eb9f --- /dev/null +++ b/erpnext/website/doctype/web_page/web_page.txt @@ -0,0 +1,110 @@ +# DocType, Web Page +[ + + # These values are common in all dictionaries + { + 'creation': '2012-01-31 15:18:49', + 'docstatus': 0, + 'modified': '2012-01-31 15:48:50', + 'modified_by': 'Administrator', + 'owner': 'Administrator' + }, + + # These values are common for all DocType + { + '_last_update': '1328003330', + 'allow_attach': 1, + 'colour': 'White:FFF', + 'description': 'A custom page is a simple page with the layout - headline, main section, side section\n\nEditing:\n\n- Editing is in [markdown format](http://daringfireball.net/projects/markdown/syntax)\n- You can also add images and embed html code\n\nAccessing the page:\n\n- The page can be accessed as #![page-name] after the main url\n\nIdeal for pages like FAQ, Terms, Help etc.\n\n', + 'doctype': 'DocType', + 'max_attachments': 5, + 'module': 'Website', + 'name': '__common__', + 'section_style': 'Simple', + 'show_in_menu': 0, + 'version': 3 + }, + + # These values are common for all DocField + { + 'doctype': 'DocField', + 'name': '__common__', + 'parent': 'Web Page', + 'parentfield': 'fields', + 'parenttype': 'DocType', + 'permlevel': 0 + }, + + # These values are common for all DocPerm + { + 'doctype': 'DocPerm', + 'name': '__common__', + 'parent': 'Web Page', + 'parentfield': 'permissions', + 'parenttype': 'DocType', + 'read': 1, + 'role': 'Website Manager' + }, + + # DocType, Web Page + { + 'doctype': 'DocType', + 'name': 'Web Page' + }, + + # DocPerm + { + 'create': 1, + 'doctype': 'DocPerm', + 'permlevel': 0, + 'write': 1 + }, + + # DocPerm + { + 'doctype': 'DocPerm', + 'permlevel': 1 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Title / headline of your page', + 'doctype': 'DocField', + 'fieldname': 'title', + 'fieldtype': 'Data', + 'label': 'Title', + 'reqd': 1 + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Content in markdown format that appears on the main side of your page', + 'doctype': 'DocField', + 'fieldname': 'main_section', + 'fieldtype': 'Code', + 'label': 'Main Section' + }, + + # DocField + { + 'colour': 'White:FFF', + 'description': 'Content in markdown format that appears on the right side', + 'doctype': 'DocField', + 'fieldname': 'side_section', + 'fieldtype': 'Code', + 'label': 'Side Section' + }, + + # DocField + { + 'doctype': 'DocField', + 'fieldname': 'file_list', + 'fieldtype': 'Text', + 'hidden': 1, + 'label': 'File List', + 'no_copy': 1, + 'print_hide': 1 + } +] \ No newline at end of file diff --git a/erpnext/website/js/product_category.js b/erpnext/website/js/product_category.js new file mode 100644 index 0000000000..04b7e71862 --- /dev/null +++ b/erpnext/website/js/product_category.js @@ -0,0 +1,22 @@ +// make sidelisting of categories +erpnext.product_item_group = {} + +erpnext.make_product_categories = function(wrapper) { + wrapper.category_list = new wn.widgets.Listing({ + parent: $(wrapper).find('.web-side-section').get(0), + query: 'select label, count(t2.name) as items, t1.item_group \ + from `tabProduct Group` t1, `tabItem` t2\ + where t1.parent="Products Settings" \ + and t2.item_group = t1.item_group \ + and ifnull(t2.show_in_website, 0)=1 \ + group by t2.item_group \ + order by t1.idx desc', + hide_refresh: true, + render_row: function(parent, data) { + parent.innerHTML = repl('%(label)s (%(items)s)', + data); + erpnext.product_item_group[data.label] = data.item_group; + } + }); + wrapper.category_list.run(); +} diff --git a/erpnext/website/js/topbar.js b/erpnext/website/js/topbar.js index 788ed62f6c..d7cba89554 100644 --- a/erpnext/website/js/topbar.js +++ b/erpnext/website/js/topbar.js @@ -35,8 +35,8 @@ erpnext.topbar.TopBar = Class.extend({ var items = wn.boot.topbaritems for(var i=0;i%(label)s', item)) } @@ -44,4 +44,31 @@ erpnext.topbar.TopBar = Class.extend({ } }); -erpnext.topbar.topbar = new erpnext.topbar.TopBar(); \ No newline at end of file +erpnext.topbar.topbar = new erpnext.topbar.TopBar(); + +// footer +erpnext.Footer = Class.extend({ + init: function() { + $('footer').html(repl('', wn.boot.topbar)); + this.make_items(); + }, + make_items: function() { + var items = wn.boot.topbaritems + for(var i=0;i%(label)s', item)) + } + } + } +}); + +erpnext.footer = new erpnext.Footer(); \ No newline at end of file diff --git a/erpnext/website/page/products/products.html b/erpnext/website/page/products/products.html index 57f1354575..4ef5bf49fc 100644 --- a/erpnext/website/page/products/products.html +++ b/erpnext/website/page/products/products.html @@ -1,6 +1,6 @@
-

+

@@ -8,4 +8,5 @@

Categories

+
\ No newline at end of file diff --git a/erpnext/website/page/products/products.js b/erpnext/website/page/products/products.js index 993397dd38..0e7dec501b 100644 --- a/erpnext/website/page/products/products.js +++ b/erpnext/website/page/products/products.js @@ -1,11 +1,84 @@ erpnext.products = {} +wn.require('erpnext/website/js/product_category.js'); + pscript.onload_products = function(wrapper) { + sys_defaults.default_product_category = JSON.parse(sys_defaults.default_product_category); + erpnext.products.wrapper = wrapper; + + // make lists + erpnext.make_product_categories(wrapper); + erpnext.products.make_product_list(wrapper); + + // button + $(wrapper).find('.products-search .btn').click(function() { + wrapper.mainlist.run(); + }); + + $(wrapper).find('.products-search input').keypress(function(ev) { + if(ev.which==13) $(wrapper).find('.products-search .btn').click(); + }); +} + +pscript.onshow_products = function(wrapper) { + // show default product category + erpnext.products.set_group(); +} + +erpnext.products.get_group = function() { + var route = window.location.hash.split('/'); + if(route.length>1) { + // from url + var grp = erpnext.product_item_group[route[1]]; + var label = route[1]; + } else { + // default + var grp = sys_defaults.default_product_category.item_group; + var label = sys_defaults.default_product_category.label; + } + erpnext.products.cur_group = grp; + return {grp:grp, label:label}; +} + +erpnext.products.make_product_list = function(wrapper) { + wrapper.mainlist = new wn.widgets.Listing({ + parent: $(wrapper).find('.web-main-section').get(0), + run_btn: $(wrapper).find('.products-search .btn').get(0), + hide_refresh: true, + get_query: function() { + args = { + searchstr: $('input[name="products-search"]').val() || '', + cat: erpnext.products.cur_group + }; + return repl('select t1.name, t1.title, t1.thumbnail_image, \ + t1.page_name, t1.short_description \ + from tabProduct t1, tabItem t2 \ + where t1.item = t2.name \ + and t2.item_group="%(cat)s" \ + and t1.short_description like "%%(searchstr)s%"', args) + }, + render_row: function(parent, data) { + parent.innerHTML = repl('
\ +
\ +
\ + %(title)s\ +

%(short_description)s

\ +
', data); + } + }); + +} + +erpnext.products.set_group = function() { + var cat = erpnext.products.get_group(); + if(!cat.grp) { + // still nothing + setTimeout('erpnext.products.set_group()', 1000); + return; + } // get erpnext.products.default_category + var wrapper = erpnext.products.wrapper; - // make search box - - // make main listing based on default category - - // make sidelisting of categories + $(wrapper).find('h1').html(cat.label); + wrapper.mainlist.run(); } \ No newline at end of file diff --git a/erpnext/website/utils.py b/erpnext/website/utils.py index e1802cb64f..330f7a39a4 100644 --- a/erpnext/website/utils.py +++ b/erpnext/website/utils.py @@ -1,14 +1,53 @@ +import webnotes +from webnotes.model.doc import Document + def make_template(doc, path, convert_fields = ['main_section', 'side_section']): """make template""" - import os, jinja2, markdown2 + import os, jinja2 - # markdown - for f in convert_fields: - doc.fields[f + '_html'] = markdown2.markdown(doc.fields[f] or '', \ - extras=["wiki-tables"]) + markdown(doc, convert_fields) # write template with open(path, 'r') as f: temp = jinja2.Template(f.read()) - return temp.render(doc = doc.fields) \ No newline at end of file + return temp.render(doc = doc.fields) + +def markdown(doc, fields): + """convert fields to markdown""" + import markdown2 + # markdown + for f in fields: + doc.fields[f + '_html'] = markdown2.markdown(doc.fields[f] or '', \ + extras=["wiki-tables"]) + + +def page_name(title): + """make page name from title, and check that there is no duplicate""" + import re + name = re.sub('[~!@#$%^&*()<>,."\']', '', title.lower()) + return '-'.join(name.split()[:4]) + +def add_page(title): + """add a custom page with title""" + name = page_name(title) + if webnotes.conn.sql("""select name from tabPage where name=%s""", name): + p = Document('Page', name) + else: + p = Document('Page') + + p.title = title + p.name = p.page_name = name + p.module = 'Website' + p.standard = 'No' + + return p + +def add_guest_access_to_page(page): + """add Guest in Page Role""" + if not webnotes.conn.sql("""select parent from `tabPage Role` + where role='Guest' and parent=%s""", page): + d = Document('Page Role') + d.parent = page + d.role = 'Guest' + d.save() \ No newline at end of file diff --git a/index.html b/index.html index d758f2f602..a75f24af93 100644 --- a/index.html +++ b/index.html @@ -3,7 +3,7 @@ ERPNext -