From 110f3dd9102167b76d235c33f9aa1b9c991efc1b Mon Sep 17 00:00:00 2001 From: Christophe Matthieu Date: Thu, 30 Jan 2014 22:00:01 +0100 Subject: [PATCH] [IMP] website tour: refactoring: Check dom insead of trigger bzr revid: chm@openerp.com-20140130210001-kiecx5nde2um3ni1 --- .../website/static/src/js/website.editor.js | 1 + .../static/src/js/website.tour.banner.js | 49 +- addons/website/static/src/js/website.tour.js | 920 ++++++++---------- .../website/tests/ui_suite/homepage_test.js | 7 +- .../static/src/js/website.tour.blog.js | 55 +- .../website_blog/tests/ui_suite/post_test.js | 6 +- .../static/src/js/website.tour.event.js | 76 +- .../tests/ui_suite/event_test.js | 6 +- .../static/src/js/website.tour.shop.js | 312 +++--- addons/website_sale/tests/test_ui.py | 4 +- .../website_sale-sale_process-test-2.js | 6 +- .../website_sale-sale_process-test.js | 6 +- 12 files changed, 575 insertions(+), 873 deletions(-) diff --git a/addons/website/static/src/js/website.editor.js b/addons/website/static/src/js/website.editor.js index 55ab6e8fcad..ab97ee2bcf9 100644 --- a/addons/website/static/src/js/website.editor.js +++ b/addons/website/static/src/js/website.editor.js @@ -488,6 +488,7 @@ $('.css_non_editable_mode_hidden').removeClass("css_non_editable_mode_hidden"); this.rte.start_edition().then(this.check_height.bind(this)); + this.trigger('rte:called'); }, rte_changed: function () { this.$buttons.save.prop('disabled', false); diff --git a/addons/website/static/src/js/website.tour.banner.js b/addons/website/static/src/js/website.tour.banner.js index d01d66b6514..2c26ae34e98 100644 --- a/addons/website/static/src/js/website.tour.banner.js +++ b/addons/website/static/src/js/website.tour.banner.js @@ -18,53 +18,43 @@ var self = this; self.steps = [ { - stepId: 'welcome', title: "Welcome to your website!", content: "This tutorial will guide you to build your home page. We will start by adding a banner.", template: self.popover({ next: "Start Tutorial", end: "Skip It" }), backdrop: true, }, { - stepId: 'edit-page', + waitNot: '.popover.tour', element: 'button[data-action=edit]', placement: 'bottom', title: "Edit this page", content: "Every page of your website can be modified through the Edit button.", template: self.popover({ fixed: true }), - trigger: { - id: 'rte:ready', - type: 'openerp', - emitter: editor, - }, }, { - stepId: 'add-banner', element: 'button[data-action=snippet]', placement: 'bottom', title: "Insert building blocks", content: "To add content in a page, you can insert building blocks.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-banner', snippet: 'carousel', placement: 'bottom', title: "Drag & Drop a Banner", content: "Drag the Banner block and drop it in your page.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'edit-title', + waitFor: '.oe_overlay_options .oe_options:visible', element: '#wrap [data-snippet-id=carousel]:first .carousel-caption', + sampleText: 'My Title', placement: 'top', title: "Customize banner's text", content: "Click in the text and start editing it. Click continue once it's done.", - template: self.popover({ next: "Continue" }), }, { - stepId: 'customize-banner', + waitNot: '#wrap [data-snippet-id=carousel]:first .carousel-caption:contains("Your Banner Title")', element: '.oe_overlay_options .oe_options', placement: 'left', title: "Customize the banner", @@ -72,67 +62,54 @@ template: self.popover({ next: "Continue" }), }, { - stepId: 'add-three-cols', + waitNot: '.popover.tour', element: 'button[data-action=snippet]', placement: 'bottom', title: "Add Another Block", content: "Let's add another building block to your page.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-three-columns', snippet: 'three-columns', placement: 'bottom', title: "Drag & Drop a Block", content: "Drag the '3 Columns' block and drop it below the banner.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'save-changes', + waitFor: '.oe_overlay_options .oe_options:visible', element: 'button[data-action=save]', placement: 'right', title: "Save your modifications", content: "Publish your page by clicking on the 'Save' button.", template: self.popover({ fixed: true }), - trigger: 'reload', }, { - stepId: 'part-2', + waitFor: 'button[data-action=edit]:visible', title: "Congratulation!", content: "Your homepage has been updated.", template: self.popover({ next: "Continue" }), }, { - stepId: 'show-mobile', + waitNot: '.popover.tour', element: 'a[data-action=show-mobile-preview]', placement: 'bottom', title: "Test Your Mobile Version", content: "Let's check how your homepage looks like on mobile devices.", template: self.popover({ fixed: true }), - trigger: { - id: 'shown.bs.modal', - emitter: $(document), - }, }, { - stepId: 'show-mobile-close', element: 'button[data-dismiss=modal]', placement: 'right', title: "Close Mobile Preview", content: "Scroll in the mobile preview to test the rendering. Once it's ok, close this dialog.", - trigger: 'click', }, { - stepId: 'show-tutorials', - element: '#help-menu-button', - placement: 'left', - title: "More Tutorials", - content: "Get more tutorials through this 'Help' menu or click on the left 'Edit' button to continue modifying this page.", - template: self.popover({ fixed: true, end: "Close Tutorial" }), - trigger: 'click', - } + waitNot: '.modal', + title: "Congrats", + content: "Congratulation. This tour is finished.", + template: self.popover({ fixed: true, next: "Close Tutorial" }), + }, ]; return this._super(); }, diff --git a/addons/website/static/src/js/website.tour.js b/addons/website/static/src/js/website.tour.js index 322bcc1545c..03a3cedfb75 100644 --- a/addons/website/static/src/js/website.tour.js +++ b/addons/website/static/src/js/website.tour.js @@ -1,531 +1,435 @@ (function () { 'use strict'; - var website = openerp.website; - website.add_template_file('/website/static/src/xml/website.tour.xml'); +var website = openerp.website; +website.add_template_file('/website/static/src/xml/website.tour.xml'); - website.Tour = openerp.Class.extend({ - steps: [], // Override - tourStorage: window.localStorage, // FIXME: will break on iPad in private mode - init: function () { - this.tour = new Tour({ - name: this.id, - storage: this.tourStorage, - keyboard: false, - template: this.popover(), - onHide: function () { - window.scrollTo(0, 0); - } +website.EditorBar.include({ + tours: [], + start: function () { + // $('.tour-backdrop').click(function (e) { + // e.stopImmediatePropagation(); + // e.preventDefault(); + // }); + var self = this; + var menu = $('#help-menu'); + _.each(this.tours, function (tour) { + var $menuItem = $($.parseHTML('
  • '+tour.name+'
  • ')); + $menuItem.click(function () { + tour.reset(); + tour.trigger(); }); - this.registerSteps(); - }, - registerStep: function (step) { - var self = this; - step.tour = self; - step.title = openerp.qweb.render('website.tour_popover_title', { title: step.title }); - if (!step.element) { - step.orphan = true; + menu.append($menuItem); + }); + + this.waitRTEReady = false; + this.on('rte:called', this, function () {self.waitRTEReady = true; }); + this.on('rte:ready', this, function () {self.waitRTEReady = false;}); + + var res = this._super(); + website.Tour.waitReady.call(this, this.testRunning); + return res; + }, + registerTour: function (tour) { + website.Tour.add(tour); + this.tours.push(tour); + }, + testRunning: function () { + if (this.waitRTEReady) { + this.on('rte:ready', this, function () { + website.Tour.each(function () { + this.running(); + }); + }); + } else { + website.Tour.each(function () { + this.running(); + }); + } + } +}); + + +///////////////////////////////////////////////// + + +/* jQuery selector to match exact text inside an element + * :containsExact() - case insensitive + * :containsExactCase() - case sensitive + * :containsRegex() - set by user ( use: $(el).find(':containsRegex(/(red|blue|yellow)/gi)') ) + */ +$.extend($.expr[':'],{ + containsExact: function(a,i,m){ + return $.trim(a.innerHTML.toLowerCase()) === m[3].toLowerCase(); + }, + containsExactCase: function(a,i,m){ + return $.trim(a.innerHTML) === m[3]; + }, + // Note all escaped characters need to be double escaped + // inside of the containsRegex, so "\(" needs to be "\\(" + containsRegex: function(a,i,m){ + var regreg = /^\/((?:\\\/|[^\/])+)\/([mig]{0,3})$/, + reg = regreg.exec(m[3]); + return reg ? new RegExp(reg[1], reg[2]).test($.trim(a.innerHTML)) : false; + } +}); +$.ajaxSetup({ + beforeSend:function(){ + $.ajaxBusy = ($.ajaxBusy|0) + 1; + }, + complete:function(){ + $.ajaxBusy--; + } +}); + + +website.Tour = openerp.Class.extend({ + steps: [], + defaultDelay: 50, //ms + localStorage: window.localStorage, + init: function (url) { + this.tour = new Tour({ + name: this.id, + storage: this.tourStorage, + keyboard: false, + template: this.popover(), + onHide: function () { + window.scrollTo(0, 0); } + }); + this.registerSteps(); + }, + + run: function (automatic, force) { + if (force) this.reset(); + + for (var k in this.localStorage) { + if (!k.indexOf("tour-") && k.indexOf("-test") > -1) return; + } + + // only one test running + if (website.Tour.busy) return; + + website.Tour.busy = true; + this.localStorage.setItem("tour-"+this.id+"-test", 0); + + website.Tour.waitReady.call(this, function () {this._run(automatic, force);}); + }, + running: function () { + if (+this.localStorage.getItem("tour-"+this.id+"-test") >= this.steps.length) { + this.endTour(); + return; + } + + if (website.Tour.busy || !this.testUrl()) return; + + var self = this; + website.Tour.waitReady.call(this, function () { + self._running(); + }, 500); + }, + + _run: function (automatic, force) { + this.reset(); + this.localStorage.setItem("tour-"+this.id+"-test", 0); + if (automatic) { + this.localStorage.setItem("tour-"+this.id+"-test-automatic", true); + } + this.nextStep(null, automatic ? this.autoNextStep : null, automatic ? 5000 : null); + }, + _running: function () { + var stepId = this.localStorage.getItem("tour-"+this.id+"-test"); + var automatic = !!this.localStorage.getItem("tour-"+this.id+"-test-automatic"); + + if (stepId || this.checkRuningUrl()) { + + if (!this.check(this.step(stepId))) { + var step = this.next(stepId); + stepId = step ? step.stepId : stepId; + } + website.Tour.busy = true; + this.nextStep(stepId, automatic ? this.autoNextStep : null, automatic ? 5000 : null); + } + }, + + reset: function () { + website.Tour.busy = false; + for (var k in this.steps) { + this.steps[k].busy = false; + } + clearTimeout(self.timer); + clearTimeout(self.testtimer); + + for (var k in this.localStorage) { + if (!k.indexOf("tour-") || !k.indexOf(this.id)) { + this.localStorage.removeItem(k); + } + } + + $('.popover.tour').remove(); + }, + trigger: function (automatic) { + if (this.path) { + this.localStorage.setItem("tour-"+this.id+"-test", 0); + if (automatic) this.localStorage.setItem("tour-"+this.id+"-test-automatic", true); + var path = this.path.split('?'); + window.location.href = path[0] + "?tutorial."+this.id+"=true" + path.slice(1, path.length).join("?"); + } else { + this.run(automatic); + } + }, + testUrl: function () { + return !this.testPath || this.testPath.test(window.location.href); + }, + checkRuningUrl: function () { + return window.location.search.indexOf("tutorial."+this.id+"=true") > -1; + }, + + registerSteps: function () { + for (var index=0, len=this.steps.length; index 0 && $(this.steps[index-1].template).has("button[data-role='next']").size()) { + step.waitNot = '.popover.tour'; + } + if (!step.waitFor && index > 0 && this.steps[index-1].snippet) { + step.waitFor = '.oe_overlay_options .oe_options:visible'; + } + + step._title = step.title; + step.title = openerp.qweb.render('website.tour_popover_title', { title: step.title }); + if (!step.element) step.orphan = true; if (step.snippet) { step.element = '#oe_snippets div.oe_snippet[data-snippet-id="'+step.snippet+'"] .oe_snippet_thumbnail'; } - if (step.trigger) { - if (step.trigger === 'click') { - step.triggers = function (callback) { - $(step.element).one('click', function () { - (callback || self.moveToNextStep).apply(self); - }); - }; - } else if (step.trigger === 'reload') { - step.triggers = function (callback) { - var stack = JSON.parse(step.tour.tourStorage.getItem("website-reloads")) || []; - var index = stack.indexOf(step.stepId); - if (index !== -1) { - setTimeout(function () { - $(step.element).popover("destroy"); - setTimeout(function () { - stack.splice(index,1); - (callback || self.moveToNextStep).apply(self); - step.tour.tourStorage.setItem("website-reloads", JSON.stringify(stack)); - },10); - },0); - } else { - stack.push(step.stepId); - step.tour.tourStorage.setItem("website-reloads", JSON.stringify(stack)); - } - }; - } else if (step.trigger === 'drag') { - step.triggers = function (callback) { - self.onSnippetDragged(callback || self.moveToNextStep); - }; - } else if (step.trigger.id) { - if (step.trigger.emitter && step.trigger.type === 'openerp') { - step.triggers = function (callback) { - step.trigger.emitter.on(step.trigger.id, self, function customHandler () { - step.trigger.emitter.off(step.trigger.id, customHandler); - (callback || self.moveToNextStep).apply(self, arguments); - }); - }; - } else { - step.triggers = function (callback) { - var emitter = _.isString(step.trigger.emitter) ? $(step.trigger.emitter) : (step.trigger.emitter || $(step.element)); - if (!emitter.size()) throw "Emitter is undefined"; - emitter.on(step.trigger.id, function () { - (callback || self.moveToNextStep).apply(self, arguments); - }); - }; - } - } else if (step.trigger.url) { - step.triggers = function (callback) { - var stack = JSON.parse(step.tour.tourStorage.getItem("website-geturls")) || []; - var id = step.trigger.url.toString(); - var index = stack.indexOf(id); - if (index !== -1) { - var url = new website.UrlParser(window.location.href); - var test = typeof step.trigger.url === "string" ? - step.trigger.url == url.pathname+url.search : - step.trigger.url.test(url.pathname+url.search); - if (!test) return; - setTimeout(function () { - $(step.element).popover("destroy"); - setTimeout(function () { - stack.splice(index,1); - (callback || self.moveToNextStep).apply(self); - step.tour.tourStorage.setItem("website-geturls", JSON.stringify(stack)); - },10); - },0); - } else { - stack.push(id); - step.tour.tourStorage.setItem("website-geturls", JSON.stringify(stack)); - } - return index !== -1; - }; - } else if (step.trigger.modal) { - step.triggers = function (callback, auto) { - var $doc = $(document); - function onStop () { - if (step.trigger.modal.stopOnClose) { - self.stop(); - } - } - $doc.on('hide.bs.modal', onStop); - $doc.one('shown.bs.modal', function () { - $('.modal button.btn-primary').one('click', function () { - $doc.off('hide.bs.modal', onStop); - if (!callback) { - self.moveToStep(step.trigger.modal.afterSubmit); - } - }); - (callback || self.moveToNextStep).apply(self); - }); - }; - } else if (step.trigger === 'ajax') { - step.triggers = function (callback) { - $( document ).ajaxSuccess(function(event, xhr, settings) { - $( document ).unbind('ajaxSuccess'); - xhr.then(function () { - setTimeout(function () { - $(step.element).popover("destroy"); - setTimeout(function () { - (callback || self.moveToNextStep).apply(self); - },10); - },0); - }); - }); - }; - } else { - step.triggers = function (callback) { - var emitter = $(step.element); - if (!emitter.size()) throw "Emitter is undefined"; - var trigger = function () { - emitter.off(step.trigger, trigger); - (callback || self.moveToNextStep).apply(self, arguments); - }; - emitter.on(step.trigger, trigger); - }; - } - } - step.onShow = (function () { - var executed = false; - return function () { - if (!executed) { - _.isFunction(step.onStart) && step.onStart(); - _.isFunction(step.triggers) && step.triggers(); - executed = true; - } - }; - }()); - return step; - }, - registerSteps: function () { - var self = this; - this.tour.addSteps(_.map(this.steps, function (step) { - return self.registerStep(step); - })); - }, - reset: function () { - this.tourStorage.removeItem(this.id+'_current_step'); - this.tourStorage.removeItem(this.id+'_end'); - this.tourStorage.removeItem("website-reloads"); - this.tourStorage.removeItem("website-geturls"); - this.tour._current = 0; - $('.popover.tour').remove(); - }, - start: function () { - window.Tour.prototype._isOrphan = function(step) { - return (step.element == null) || !$(step.element).length; - }; - if (this.resume() || ((this.currentStepIndex() === 0) && !this.tour.ended())) { - this.tour.start(); - } - }, - currentStepIndex: function () { - var index = this.tourStorage.getItem(this.id+'_current_step') || 0; - return parseInt(index, 10); - }, - indexOfStep: function (stepId) { - var index = -1; - _.each(this.steps, function (step, i) { - if (step.stepId === stepId) { - index = i; - } - }); - return index; - }, - isCurrentStep: function (stepId) { - return this.currentStepIndex() === this.indexOfStep(stepId); - }, - moveToStep: function (step) { - var index = _.isNumber(step) ? step : this.indexOfStep(step); - if (index >= this.steps.length) { - this.stop(); - } else if (index >= 0) { - var self = this; - $('.popover.tour').remove(); - self.tour.goto(index); - } - }, - moveToNextStep: function () { - var nextStepIndex = this.currentStepIndex() + 1; - this.moveToStep(nextStepIndex); - }, - stop: function () { - this.tour.end(); - }, - redirect: function (url) { - url = url || new website.UrlParser(window.location.href); - var path = (this.path && url.pathname !== this.path) ? this.path : url.pathname; - var search = url.activateTutorial(this.id); - var newUrl = path + search; - window.location.replace(newUrl); - }, - ended: function () { - return this.tourStorage.getItem(this.id+'_end') === "yes"; - }, - resume: function () { - // Override if necessary - return this.tourStorage.getItem(this.id+'_current_step') && !this.ended(); - }, - trigger: function (url) { - // Override if necessary - url = url || new website.UrlParser(window.location.href); - return url.isActive(this.id); - }, - testUrl: function (pattern) { - var url = new website.UrlParser(window.location.href); - return pattern.test(url.pathname+url.search); - }, - popover: function (options) { - return openerp.qweb.render('website.tour_popover', options); - }, - onSnippetDragged: function (callback) { - var self = this; - var selector = '#website-top-navbar [data-snippet-id].ui-draggable'; - var beginDrag = function beginDrag () { - $('.popover.tour').remove(); - var advance = function advance () { - if (_.isFunction(callback)) { - callback.apply(self); - } - $(selector).off('mouseup', advance); - }; - $(document.body).one('mouseup', advance); - $(selector).off('mousedown', beginDrag); - }; - $(selector).one('mousedown', beginDrag); - }, - onSnippetDraggedAdvance: function () { - onSnippetDragged(self.moveToNextStep); - }, - }); - website.UrlParser = openerp.Class.extend({ - init: function (url) { - var a = document.createElement('a'); - a.href = url; - this.href = a.href; - this.host = a.host; - this.protocol = a.protocol; - this.port = a.port; - this.hostname = a.hostname; - this.pathname = a.pathname; - this.origin = a.origin; - this.search = a.search; - this.hash = a.hash; - function generateTrigger (id) { - return "tutorial."+id+"=true"; - } - this.activateTutorial = function (id) { - var urlTrigger = generateTrigger(id); - var querystring = _.filter(this.search.split('?'), function (str) { - return str; - }); - if (querystring.length > 0) { - var queries = _.filter(querystring[0].split("&"), function (query) { - return query.indexOf("tutorial.") < 0 - }); - queries.push(urlTrigger); - return "?"+_.uniq(queries).join("&"); - } else { - return "?"+urlTrigger; - } - }; - this.isActive = function (id) { - var urlTrigger = generateTrigger(id); - return this.search.indexOf(urlTrigger) >= 0; - }; - }, - }); + } - var TestConsole = openerp.Class.extend({ - tests: [], - editor: null, - init: function (editor) { - if (!editor) { - throw new Error("Editor cannot be null or undefined"); - } - this.editor = editor; - }, - test: function (id) { - return _.find(this.tests, function (tour) { - return tour.id === id; + if ($(this.steps[index-1].template).has("button[data-role='next']")) { + var step = { + stepId: index, + waitNot: '.popover.tour:visible' + }; + this.steps.push(step); + } + + this.tour.addSteps(this.steps); + }, + + popover: function (options) { + return openerp.qweb.render('website.tour_popover', options); + }, + + timer: null, + testtimer: null, + check: function (step) { + return (step && + (!step.element || ($(step.element).size() && $(step.element).is(":visible") && !$(step.element).is(":hidden"))) && + (!step.waitNot || !$(step.waitNot).size()) && + (!step.waitFor || $(step.waitFor).size())); + }, + waitNextStep: function (step, callback, overlaps) { + var self = this; + var time = new Date().getTime(); + var timer; + + window.onbeforeunload = function () { + clearTimeout(self.timer); + clearTimeout(self.testtimer); + }; + + // check popover activity + $(".popover.tour button") + .off() + .on("click", function () { + $(".popover.tour").remove(); + if (step.busy) return; + if (!$(this).is("[data-role='next']")) { + clearTimeout(self.timer); + step.busy = true; + self.tour.end(); + self.endTour(callback); + } }); - }, - snippetSelector: function (snippetId) { - return '#oe_snippets div.oe_snippet[data-snippet-id="'+snippetId+'"] .oe_snippet_thumbnail'; - }, - snippetThumbnail: function (snippetId) { - return $(this.snippetSelector(snippetId)).first(); - }, - snippetThumbnailExists: function (snippetId) { - return this.snippetThumbnail(snippetId).length > 0; - }, - dragAndDropSnippet: function (snippetId) { - function actualDragAndDrop ($thumbnail) { - var thumbnailPosition = $thumbnail.position(); - $thumbnail.trigger($.Event("mousedown", { which: 1, pageX: thumbnailPosition.left, pageY: thumbnailPosition.top })); - $thumbnail.trigger($.Event("mousemove", { which: 1, pageX: document.body.scrollWidth/2, pageY: document.body.scrollHeight/2 })); - var $dropZone = $(".oe_drop_zone").first(); - var dropPosition = $dropZone.position(); - $dropZone.trigger($.Event("mouseup", { which: 1, pageX: dropPosition.left, pageY: dropPosition.top })); - } - if (this.snippetThumbnailExists(snippetId)) { - actualDragAndDrop(this.snippetThumbnail(snippetId)); + + function checkNext () { + clearTimeout(self.timer); + if (step.busy) return; + if (self.check(step)) { + step.busy = true; + // use an other timeout for cke dom loading + setTimeout(function () { + self.nextStep(step.stepId, callback, overlaps); + }, self.defaultDelay); + } else if (!overlaps || new Date().getTime() - time < overlaps) { + self.timer = setTimeout(checkNext, self.defaultDelay); } else { - this.editor.on('rte:ready', this, function () { - actualDragAndDrop(this.snippetThumbnail(snippetId)); - }); + self.reset(); + throw new Error("Time overlaps to arrive to step " + step.stepId + ": '" + step._title + "'"); } - }, - }); + } + checkNext(); + }, + step: function (stepId) { + var steps = this.steps.slice(0,this.steps.length), + step; + while (step = steps.shift()) { + if (!stepId || step.stepId === stepId) + return step; + } + return null; + }, + next: function (stepId) { + var steps = this.steps.slice(0,this.steps.length), + step, next, index=0; + while (step = steps.shift()) { + if (!stepId || step.stepId === stepId) { + // clear popover (fix for boostrap tour if the element is removed before destroy popover) + $(".popover.tour").remove(); + // go to step in bootstrap tour + this.tour.goto(index); + if (step.callback) step.callback(); + next = steps.shift(); + break; + } + index++; + } + return next; + }, + nextStep: function (stepId, callback, overlaps) { + var self = this; + if (!this.localStorage.getItem("tour-"+this.id+"-test")) return; + this.localStorage.setItem("tour-"+this.id+"-test", stepId || 0); - website.EditorBar.include({ - tours: [], - init: function () { - var result = this._super(); - website.TestConsole = new TestConsole(this); - return result; - }, - start: function () { - $('.tour-backdrop').click(function (e) { - e.stopImmediatePropagation(); - e.preventDefault(); - }); - var menu = $('#help-menu'); - _.each(this.tours, function (tour) { - var $menuItem = $($.parseHTML('
  • '+tour.name+'
  • ')); - $menuItem.click(function () { - tour.reset(); - tour.redirect(new website.UrlParser(window.location.href)); - }); - menu.append($menuItem); - if (tour.trigger()) { - setTimeout(function () { - setTimeout(function () { - tour.start(); - },100); - },0); + this.current = this.step(stepId); + var next = this.next(stepId); + + if (next) { + setTimeout(function () { + self.waitNextStep(next, callback, overlaps); + if (callback) setTimeout(function(){callback.call(self, next);}, self.defaultDelay); + }, next && next.wait || 0); + } else { + this.endTour(); + } + }, + endTour: function () { + console.log('{ "event": "success" }'); + this.reset(); + }, + autoNextStep: function () { + var self = this; + clearTimeout(self.testtimer); + + function autoStep () { + var step = self.current; + if (!step) return; + + if (step.autoComplete) { + step.autoComplete(tour); + } + + var $popover = $(".popover.tour"); + if ($popover.find("button[data-role='next']:visible").size()) { + $popover.find("button[data-role='next']:visible").click(); + $popover.remove(); + } + + var $element = $(step.element); + if (!$element.size()) return; + + if (step.snippet) { + + var selector = '#oe_snippets div.oe_snippet[data-snippet-id="'+step.snippet+'"] .oe_snippet_thumbnail'; + self.autoDragAndDropSnippet(selector); + + } else if (step.element.match(/#oe_snippets .* \.oe_snippet_thumbnail/)) { + + self.autoDragAndDropSnippet($element); + + } else if (step.sampleText) { + + $element.trigger($.Event("keydown", { srcElement: $element })); + if ($element.is("select") || $element.is("input") ) { + $element.val(step.sampleText); + } else { + $element.html(step.sampleText); } - }); - return this._super(); - }, - registerTour: function (tour) { - var self = this; - var testId = 'test_'+tour.id+'_tour'; - this.tours.push(tour); - var defaultDelay = 250; //ms - var overlapsCrash; - var test = { - id: tour.id, - run: function (force) { - if (force === true) { - this.reset(); - tour.reset(); - } - var actionSteps = _.filter(tour.steps, function (step) { - return step.trigger || step.triggers || step.sampleText; - }); - window.onbeforeunload = function () { - clearTimeout(overlapsCrash); - }; - function throwError (message) { - console.log(tour.tourStorage.getItem("test-report")); - test.reset(); - tour.reset(); - throw message; - } - function initReport () { - // set last time for report - if (!tour.tourStorage.getItem("test-last-time")) { - tour.tourStorage.setItem("test-last-time", new Date().getTime()); - } - } - function setReport (step) { - var report = JSON.parse(tour.tourStorage.getItem("test-report")) || {}; - report[step.stepId] = (new Date().getTime() - tour.tourStorage.getItem("test-last-time")) + " ms"; - tour.tourStorage.setItem("test-report", JSON.stringify(report)); - } - function testCycling (step) { - var lastStep = tour.tourStorage.getItem(testId); - var tryStep = lastStep != step.stepId ? 0 : (+(tour.tourStorage.getItem("test-last-"+testId) || 0) + 1); - tour.tourStorage.setItem("test-last-"+testId, tryStep); - if (tryStep > 2) { - throwError("Test: '" + testId + "' cycling step: '" + step.stepId + "'"); - } - return tryStep; - } - function getDelay (step) { - return step.delay || defaultDelay; - } - function executeStep (step) { - if (testCycling(step) === 0) initReport(); + setTimeout(function () { + $element.trigger($.Event("keyup", { srcElement: $element })); + $element.trigger($.Event("change", { srcElement: $element })); + }, self.defaultDelay<<1); + + } else if ($element.is(":visible")) { - tour.tourStorage.setItem(testId, step.stepId); + $element.trigger($.Event("mouseenter", { srcElement: $element[0] })); + $element.trigger($.Event("mousedown", { srcElement: $element[0] })); + + var evt = document.createEvent("MouseEvents"); + evt.initMouseEvent("click", true, true, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null); + $element[0].dispatchEvent(evt); - var delay = getDelay (step); - - overlapsCrash = setTimeout(function () { - throwError("Test: '" + testId + "' can't resolve step: '" + step.stepId + "'"); - }, delay + 3000); - - - var _next = false; - tour.tourStorage.setItem(testId, step.stepId); - function next () { - _next = true; - clearTimeout(overlapsCrash); - - setReport(step); - - var nextStep = actionSteps.shift(); - - if (nextStep) { - executeStep(nextStep); - } else { - tour.tourStorage.removeItem(testId); - } - } - - setTimeout(function () { - var $element = $(step.element); - - var flag = step.triggers && (!step.trigger || !step.trigger.modal); - if (flag) { - try { - step.triggers(next, true); - } catch (e) { - throwError(e); - } - } - if ((step.trigger === 'reload' || (step.trigger && step.trigger.url)) && _next) return; - - if (step.snippet && step.trigger === 'drag') { - website.TestConsole.dragAndDropSnippet(step.snippet); - } else if (step.trigger && step.trigger.id === 'change') { - $element.trigger($.Event("change", { srcElement: $element })); - } else if (step.sampleText) { - $element.trigger($.Event("keydown", { srcElement: $element })); - if ($element.is("select") || $element.is("input") ) { - $element.val(step.sampleText); - } else { - $element.html(step.sampleText); - } - $element.trigger($.Event("change", { srcElement: $element })); - $element.trigger($.Event("keyup", { srcElement: $element })); - } else if ($element.is(":visible")) { // Click by default - $element.trigger($.Event("mouseenter", { srcElement: $element })); - $element.trigger($.Event("mousedown", { srcElement: $element })); - var evt = document.createEvent("MouseEvents"); - evt.initMouseEvent("click", true, true, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null); - $element[0].dispatchEvent(evt); - $element.trigger($.Event("mouseup", { srcElement: $element })); - $element.trigger($.Event("mouseleave", { srcElement: $element })); - - // trigger after for step like: mouseenter, next step click on button display with mouseenter - $element.trigger($.Event("mouseenter", { srcElement: $element })); - } - if (!flag) next(); - },delay); - } - var url = new website.UrlParser(window.location.href); - if (tour.path && url.pathname !== tour.path && !tour.tourStorage.getItem(testId)) { - tour.tourStorage.setItem(testId, actionSteps[0].stepId); - window.location.href = tour.path; - } else { - var lastStepId = tour.tourStorage.getItem(testId); - var currentStep = actionSteps.shift(); - if (lastStepId) { - while (currentStep && lastStepId !== currentStep.stepId) { - currentStep = actionSteps.shift(); - } - } - if (currentStep.snippet && $(currentStep.element).length === 0) { - self.on('rte:ready', this, function () { - executeStep(currentStep); - }); - } else { - setTimeout(function () { - executeStep(currentStep); - }, 500); - } - } - }, - reset: function () { - tour.tourStorage.removeItem(testId); - tour.tourStorage.removeItem("test-report"); - for (var k in tour.tourStorage) { - if (tour.tourStorage[k].indexOf("test-last")) { - tour.tourStorage.removeItem(k); - } - } - }, - }; - website.TestConsole.tests.push(test); - if (window.localStorage.getItem(testId)) { - test.run(); + // trigger after for step like: mouseenter, next step click on button display with mouseenter + setTimeout(function () { + $element.trigger($.Event("mouseup", { srcElement: $element[0] })); + $element.trigger($.Event("mouseleave", { srcElement: $element[0] })); + }, 1000); } - }, + } + self.testtimer = setTimeout(autoStep, 100); + }, + autoDragAndDropSnippet: function (selector) { + var $thumbnail = $(selector).first(); + var thumbnailPosition = $thumbnail.position(); + $thumbnail.trigger($.Event("mousedown", { which: 1, pageX: thumbnailPosition.left, pageY: thumbnailPosition.top })); + $thumbnail.trigger($.Event("mousemove", { which: 1, pageX: document.body.scrollWidth/2, pageY: document.body.scrollHeight/2 })); + var $dropZone = $(".oe_drop_zone").first(); + var dropPosition = $dropZone.position(); + $dropZone.trigger($.Event("mouseup", { which: 1, pageX: dropPosition.left, pageY: dropPosition.top })); + }, + +}); + + +website.Tour.tours = {}; +website.Tour.busy = false; +website.Tour.add = function (tour) { + website.Tour.waitReady(function () { + tour = tour.id ? tour : new tour(); + website.Tour.tours[tour.id] = tour; }); +}; +website.Tour.get = function (id) { + return website.Tour.tours[id]; +}; +website.Tour.each = function (callback) { + website.Tour.waitReady(function () { + for (var k in website.Tour.tours) { + callback.call(website.Tour.tours[k]); + } + }); +}; +website.Tour.waitReady = function (callback) { + var self = this; + $(document).ready(function () { + if ($.ajaxBusy == null || $.ajaxBusy) { + $(document).ajaxStop(function() { + setTimeout(function () { + callback.call(self); + },0); + }); + } + else { + setTimeout(function () { + callback.call(self); + },0); + } + }); +}; + + + }()); diff --git a/addons/website/tests/ui_suite/homepage_test.js b/addons/website/tests/ui_suite/homepage_test.js index c83ab12ce2f..16634c80d8c 100644 --- a/addons/website/tests/ui_suite/homepage_test.js +++ b/addons/website/tests/ui_suite/homepage_test.js @@ -7,9 +7,8 @@ testRunner.run(function homepageTest (page, timeout) { waitFor(function clientReady () { return page.evaluate(function () { return window.$ && window.openerp && window.openerp.website - && window.openerp.website.TestConsole - && window.openerp.website.TestConsole.test - && window.openerp.website.TestConsole.test('banner'); + && window.openerp.website.Tour + && window.openerp.website.Tour.get('banner'); }); }, function executeTest () { var before = page.evaluate(function () { @@ -17,7 +16,7 @@ testRunner.run(function homepageTest (page, timeout) { carousel: $('#wrap [data-snippet-id=carousel]').length, columns: $('#wrap [data-snippet-id=three-columns]').length, }; - window.openerp.website.TestConsole.test('banner').run(true); + window.openerp.website.Tour.get('banner').run(true, true); return result; }); waitFor(function testExecuted () { diff --git a/addons/website_blog/static/src/js/website.tour.blog.js b/addons/website_blog/static/src/js/website.tour.blog.js index 2f9d3b5cde0..5e7a7888b89 100644 --- a/addons/website_blog/static/src/js/website.tour.blog.js +++ b/addons/website_blog/static/src/js/website.tour.blog.js @@ -13,148 +13,107 @@ website.BlogTour = website.Tour.extend({ id: 'blog', name: "Create a blog post", + testPath: /\/blogpost\/[0-9]+\//, init: function (editor) { var self = this; self.steps = [ { - stepId: 'welcome-blog', title: "New Blog Post", content: "Let's go through the first steps to write beautiful blog posts.", template: self.popover({ next: "Start Tutorial", end: "Skip" }), - backdrop: true, }, { - stepId: 'content-menu', element: '#content-menu-button', placement: 'left', title: "Add Content", content: "Create new pages, blogs, menu items and products through the 'Content' menu.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'new-post-entry', element: 'a[data-action=new_blog_post]', placement: 'left', title: "New Blog Post", content: "Select this menu item to create a new blog post.", template: self.popover({ fixed: true }), - trigger: { - modal: { - stopOnClose: true, - afterSubmit: 'post-page', - }, - }, }, { - stepId: 'continue-blog', element: '.modal button.btn-primary', placement: 'bottom', title: "Create Blog Post", content: "Click Continue to create the blog post.", - trigger: { - url: /blogpost\/[0-9]+\/.*/, - }, }, { - stepId: 'post-page', + waitNot: '.modal', title: "Blog Post Created", content: "This is your new blog post. Let's edit it.", template: self.popover({ next: "Continue" }), }, { - stepId: 'post-title', element: 'h1[data-oe-expression="blog_post.name"]', placement: 'bottom', + sampleText: 'New Blog', title: "Set a Title", content: "Click on this area and set a catchy title for your blog post.", - template: self.popover({ next: "Continue" }), }, { - stepId: 'add-image-text', + waitNot: '#wrap h1[data-oe-model="blog.post"]:contains("Blog Post Title")', element: 'button[data-action=snippet]', placement: 'bottom', title: "Layout Your Blog Post", content: "Use well designed building blocks to structure the content of your blog. Click 'Insert Blocks' to add new content.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-image-text', snippet: 'image-text', placement: 'bottom', title: "Drag & Drop a Block", content: "Drag the 'Image-Text' block and drop it in your page.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'add-text-block', element: 'button[data-action=snippet]', placement: 'bottom', title: "Add Another Block", content: "Let's add another block to your post.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-text-block', snippet: 'text-block', placement: 'bottom', title: "Drag & Drop a block", content: "Drag the 'Text Block' block and drop it below the image block.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'activate-text-block-title', - element: '#wrap [data-snippet-id=text-block] .text-center[data-snippet-id=colmd]', - placement: 'top', - title: "Edit an Area", - content: "Select any area of the page to modify it. Click on this subtitle.", - trigger: { - id: 'snippet-activated', - } - }, - { - stepId: 'remove-text-block-title', element: '.oe_active .oe_snippet_remove', placement: 'top', title: "Delete the Title", content: "From this toolbar you can move, duplicate or delete the selected zone. Click on the garbage can image to delete the title.", - trigger: 'click', }, { - stepId: 'save-changes', + waitNot: '.oe_active .oe_snippet_remove:visible', element: 'button[data-action=save]', placement: 'right', title: "Save Your Blog", content: "Click the Save button to record changes on the page.", template: self.popover({ fixed: true }), - trigger: 'reload', }, { - stepId: 'publish-post', + waitFor: 'button[data-action=edit]:visible', element: 'button.btn-danger.js_publish_btn', placement: 'top', title: "Publish Your Post", content: "Your blog post is not yet published. You can update this draft version and publish it once you are ready.", - trigger: 'click', - delay: 5000, }, { - stepId: 'end-tutorial', + waitFor: '.js_publish_management button.js_publish_btn.btn-success:visible', title: "Thanks!", content: "This tutorial is finished. To discover more features, improve the content of this page and try the Promote button in the top right menu.", template: self.popover({ end: "Close Tutorial" }), - backdrop: true, }, ]; return this._super(); }, - trigger: function () { - return (this.resume() && this.testUrl(/^\/blogpost\/[0-9]+\//)) || this._super(); - }, }); }()); diff --git a/addons/website_blog/tests/ui_suite/post_test.js b/addons/website_blog/tests/ui_suite/post_test.js index a3677bfa974..b8cd8aa03da 100644 --- a/addons/website_blog/tests/ui_suite/post_test.js +++ b/addons/website_blog/tests/ui_suite/post_test.js @@ -7,12 +7,12 @@ testRunner.run(function blogTest (page, timeout) { waitFor(function clientReady () { return page.evaluate(function () { return window.$ && window.openerp && window.openerp.website - && window.openerp.website.TestConsole - && window.openerp.website.TestConsole.test('blog'); + && window.openerp.website.Tour + && window.openerp.website.Tour.get('blog'); }); }, function executeTest () { page.evaluate(function () { - window.openerp.website.TestConsole.test('blog').run(true); + window.openerp.website.Tour.test('blog').run(true, true); }); waitFor(function testExecuted () { var after = page.evaluate(function () { diff --git a/addons/website_event/static/src/js/website.tour.event.js b/addons/website_event/static/src/js/website.tour.event.js index 29f14cc2d7a..c449c4209d1 100644 --- a/addons/website_event/static/src/js/website.tour.event.js +++ b/addons/website_event/static/src/js/website.tour.event.js @@ -13,161 +13,105 @@ website.EventTour = website.Tour.extend({ id: 'event', name: "Create an event", + testPath: /\/event\/[0-9]+\/register/, init: function (editor) { var self = this; self.steps = [ { - stepId: 'welcome-event', title: "Create an Event", content: "Let's go through the first steps to publish a new event.", template: self.popover({ next: "Start Tutorial", end: "Skip It" }), - backdrop: true, }, { - stepId: 'content-menu', element: '#content-menu-button', placement: 'left', title: "Add Content", content: "The Content menu allows you to create new pages, events, menus, etc.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'new-post-entry', element: 'a[data-action=new_event]', placement: 'left', title: "New Event", content: "Click here to create a new event.", template: self.popover({ fixed: true }), - trigger: { - modal: { - stopOnClose: true, - }, - }, }, { - stepId: 'choose-name', - element: '.modal input', + element: '.modal:contains("New Event") input[type=text]', sampleText: 'Advanced Technical Training', placement: 'right', title: "Create an Event Name", content: "Create a name for your new event and click 'Continue'. e.g: Technical Training", - trigger: 'keyup', }, { - stepId: 'continue-name', + waitNot: '.modal input[type=text]:not([value!=""])', element: '.modal button.btn-primary', placement: 'right', title: "Create Event", content: "Click Continue to create the event.", - trigger: 'reload', }, { - stepId: 'event-page', + waitFor: '#website-top-navbar button[data-action="save"]:visible', title: "New Event Created", content: "This is your new event page. We will edit the event presentation page.", - template: self.popover({ next: "OK" }), + template: self.popover({ next: "Continue" }), }, { - stepId: 'add-banner', element: 'button[data-action=snippet]', placement: 'bottom', title: "Layout your event", content: "Insert blocks to layout the body of your event.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-banner', snippet: 'image-text', placement: 'bottom', title: "Drag & Drop a block", content: "Drag the 'Image-Text' block and drop it in your page.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'add-text-block', + element: 'button[data-action=snippet]', placement: 'bottom', title: "Layout your event", content: "Insert another block to your event.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-text-block', snippet: 'text-block', placement: 'bottom', title: "Drag & Drop a block", content: "Drag the 'Text Block' in your event page.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'add-three-columns', - element: 'button[data-action=snippet]', - placement: 'bottom', - title: "Layout your event", - content: "Insert a last block to your event.", - template: self.popover({ fixed: true }), - trigger: 'click', - }, - { - stepId: 'drag-three-columns', - snippet: 'three-columns', - placement: 'bottom', - title: "Drag & Drop a block", - content: "Drag the 'Three Columns' block at the bottom.", - template: self.popover({ fixed: true }), - trigger: 'drag', - }, - { - stepId: 'save-changes', element: 'button[data-action=save]', placement: 'right', title: "Save your modifications", content: "Once you click on save, your event is updated.", template: self.popover({ fixed: true }), - trigger: 'reload', }, { - stepId: 'publish-event', + waitFor: 'button[data-action=edit]:visible', element: 'button.btn-danger.js_publish_btn', placement: 'top', title: "Publish your event", content: "Click to publish your event.", - trigger: 'ajax' }, { - stepId: 'customize-event', + waitFor: '.js_publish_management button.js_publish_btn.btn-success:visible', element: '.js_publish_management button[data-toggle="dropdown"]', placement: 'left', title: "Customize your event", content: "Click here to customize your event further.", - trigger: 'click', }, { - stepId: 'edit-event-backend', - element: '.js_publish_management ul>li>a:last', - placement: 'left', - title: "Customize your event", - content: "Click here to edit your event in the backend.", - trigger: 'click', - }, - { - stepId: 'end-tutorial', - title: "Thanks!", - content: "This tutorial is finished. Congratulations on creating your first event.", - template: self.popover({ end: "Close Tutorial" }), - backdrop: true, + element: '.js_publish_management ul>li>a:last:visible', }, ]; return this._super(); - }, - trigger: function () { - return (this.resume() && this.testUrl(/^\/event\/[0-9]+\/register/)) || this._super(); - }, + } }); }()); diff --git a/addons/website_event/tests/ui_suite/event_test.js b/addons/website_event/tests/ui_suite/event_test.js index e8022c764ec..0ec8a2783bb 100644 --- a/addons/website_event/tests/ui_suite/event_test.js +++ b/addons/website_event/tests/ui_suite/event_test.js @@ -7,12 +7,12 @@ testRunner.run(function eventTest (page, timeout) { waitFor(function clientReady () { return page.evaluate(function () { return window.$ && window.openerp && window.openerp.website - && window.openerp.website.TestConsole - && window.openerp.website.TestConsole.test('event'); + && window.openerp.website.Tour + && window.openerp.website.Tour.get('event'); }); }, function executeTest () { page.evaluate(function () { - window.openerp.website.TestConsole.test('event').run(true); + window.openerp.website.Tour.get('event').run(true, true) }); waitFor(function testExecuted () { var after = page.evaluate(function () { diff --git a/addons/website_sale/static/src/js/website.tour.shop.js b/addons/website_sale/static/src/js/website.tour.shop.js index 1104f40ad4f..340fe19c798 100644 --- a/addons/website_sale/static/src/js/website.tour.shop.js +++ b/addons/website_sale/static/src/js/website.tour.shop.js @@ -7,7 +7,6 @@ start: function () { this.registerTour(new website.EditorShopTour(this)); var res = this._super(); - this.registerTour(new website.EditorShopTest(this)); return res; }, }); @@ -15,314 +14,233 @@ website.EditorShopTour = website.Tour.extend({ id: 'shop', name: "Create a product", + testPath: /\/shop\/.*/, init: function (editor) { var self = this; self.steps = [ { - stepId: 'welcome-shop', title: "Welcome to your shop", content: "You successfully installed the e-commerce. This guide will help you to create your product and promote your sales.", template: self.popover({ next: "Start Tutorial", end: "Skip It" }), - backdrop: true, }, { - stepId: 'content-menu', element: '#content-menu-button', placement: 'left', title: "Create your first product", content: "Click here to add a new product.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'edit-entry', - element: '#create-new-product', + element: 'a[data-action=new_product]', placement: 'left', title: "Create a new product", content: "Select 'New Product' to create it and manage its properties to boost your sales.", template: self.popover({ fixed: true }), - trigger: { - modal: { - stopOnClose: true, - }, - }, }, { - stepId: 'enter-name', - element: '.modal input[type=text]', + element: '.modal:contains("New Product") input[type=text]', sampleText: 'New Product', placement: 'right', title: "Choose name", content: "Enter a name for your new product then click 'Continue'.", - trigger: 'keyup', }, { - stepId: 'continue-name', + waitNot: '.modal input[type=text]:not([value!=""])', element: '.modal button.btn-primary', placement: 'right', title: "Create Product", content: "Click Continue to create the product.", - trigger: 'reload', }, { - stepId: 'product-page', + waitFor: '#website-top-navbar button[data-action="save"]:visible', title: "New product created", content: "This page contains all the information related to the new product.", - template: self.popover({ next: "OK" }), + template: self.popover({ next: "Continue" }), }, { - stepId: 'edit-price-cke', element: '.product_price .oe_currency_value', sampleText: '20.50', placement: 'left', title: "Change the price", content: "Edit the price of this product by clicking on the amount.", - template: self.popover({ next: "OK" }), }, { - stepId: 'update-image', + waitNot: '.product_price .oe_currency_value:containsExact(1.00)', element: '#wrap img.img:first', placement: 'top', title: "Update image", content: "Click here to set an image describing your product.", - triggers: function (callback) { - var self = this; - $(self.element).on('mouseenter', function () { - $(this).off('mouseenter'); - setTimeout(function () { - (callback || self.tour.moveToNextStep).apply(self.tour); - },0); - }); - }, }, { - stepId: 'update-image-button', element: 'button.hover-edition-button:visible', placement: 'top', title: "Update image", content: "Click here to set an image describing your product.", - trigger: 'click', }, { - stepId: 'upload-image', + wait: 500, element: '.well a.pull-right', placement: 'bottom', title: "Select an Image", content: "Let's select an existing image.", template: self.popover({ fixed: true }), - trigger: 'ajax' }, { - stepId: 'select-image', element: 'img[alt=imac]', placement: 'bottom', title: "Select an Image", content: "Let's select an imac image.", template: self.popover({ fixed: true }), - triggers: function (callback) { - var self = this; - var click = function () { - $('.modal-dialog.select-image img').off('click', click); - setTimeout(function () { - (callback || self.tour.moveToNextStep).apply(self.tour); - },0); - }; - $('.modal-dialog.select-image img').on('click', click); - }, }, { - stepId: 'save-image', - element: 'button.save', + waitNot: 'img[alt=imac]', + element: '.modal-content button.save', placement: 'bottom', title: "Select this Image", content: "Click to add the image to the product decsription.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'add-block', + waitNot: '.modal-content:visible', element: 'button[data-action=snippet]', placement: 'bottom', title: "Describe the Product", content: "Insert blocks like text-image, or gallery to fully describe the product.", template: self.popover({ fixed: true }), - trigger: 'click', }, { - stepId: 'drag-big-picture', snippet: 'big-picture', placement: 'bottom', title: "Drag & Drop a block", content: "Drag the 'Big Picture' block and drop it in your page.", template: self.popover({ fixed: true }), - trigger: 'drag', }, { - stepId: 'save-changes', element: 'button[data-action=save]', placement: 'right', title: "Save your modifications", content: "Once you click on save, your product is updated.", template: self.popover({ fixed: true }), - trigger: 'reload', }, { - stepId: 'publish-product', + waitFor: '#website-top-navbar button[data-action="edit"]:visible', element: '.js_publish_management button.js_publish_btn.btn-danger', placement: 'top', title: "Publish your product", content: "Click to publish your product so your customers can see it.", - trigger: 'ajax' }, { - stepId: 'congratulations', + waitFor: '.js_publish_management button.js_publish_btn.btn-success:visible', title: "Congratulations", content: "Congratulations! You just created and published your first product.", - template: self.popover({ end: "Close Tutorial" }), - backdrop: true, + template: self.popover({ next: "Close Tutorial" }), }, ]; return this._super(); - }, - trigger: function () { - return (this.resume() && this.testUrl(/^\/shop\/product\/[0-9]+\//)) || this._super(); - }, - }); - - - website.Test = website.Tour.extend({ - registerStep: function (step) { - var self = this; - var step = this._super(step); - if (step.beforeTrigger || step.afterTrigger) { - var fn = step.triggers; - step.triggers = function (callback) { - if (step.beforeTrigger) step.beforeTrigger(self); - if (!step.afterTrigger) { - fn.call(step, callback); - } else { - fn.call(step, function () { - (callback || self.moveToNextStep).apply(self); - step.afterTrigger(self); - }); - } - }; - } - return step; } }); - - website.EditorShopTest = website.Test.extend({ - id: 'shop_buy_product', - name: "Try to buy products", - path: '/shop', - init: function (editor) { - var self = this; - self.steps = [ - { - stepId: 'begin-test', - title: 'begin-test', - template: self.popover({ next: "Start Test"}), - backdrop: true, - }, - { - stepId: 'display-ipod', - element: '.oe_product_cart a:contains("iPod")', - trigger: { - url: /shop\/product\/.*/, - }, - }, - { - stepId: 'choose-ipod', - element: 'input[name="product_id"]:not([checked])', - trigger: 'mouseup', - }, - { - stepId: 'add-ipod', - element: 'form[action="/shop/add_cart/"] button', - trigger: { - url: '/shop/mycart/', - }, - }, - { - stepId: 'add-suggested-product', - element: 'form[action="/shop/add_cart/"] button:contains("Add to Cart")', - trigger: 'reload', - }, - { - stepId: 'more-product', - element: '.oe_mycart a.js_add_cart_json:eq(1)', - trigger: 'ajax', - }, - { - stepId: 'less-product', - element: '.oe_mycart a.js_add_cart_json:eq(2)', - trigger: 'reload', - }, - { - stepId: 'number-product', - element: '.oe_mycart input.js_quantity', - sampleText: '1', - trigger: 'reload', - }, - { - stepId: 'go-checkout-product', - element: 'a[href="/shop/checkout/"]', - trigger: { - url: '/shop/checkout/', - }, - }, - { - stepId: 'confirm-false-checkout-product', - element: 'form[action="/shop/confirm_order/"] button', - trigger: { - url: '/shop/confirm_order/', - }, - beforeTrigger: function (tour) { - $("input[name='phone']").val(""); - }, - }, - { - stepId: 'confirm-checkout-product', - element: 'form[action="/shop/confirm_order/"] button', - trigger: { - url: '/shop/payment/', - }, - beforeTrigger: function (tour) { - if ($("input[name='name']").val() === "") - $("input[name='name']").val("website_sale-test-shoptest"); - if ($("input[name='email']").val() === "") - $("input[name='email']").val("website_sale-test-shoptest@website_sale-test-shoptest.optenerp.com"); - $("input[name='phone']").val("123"); - $("input[name='street']").val("123"); - $("input[name='city']").val("123"); - $("input[name='zip']").val("123"); - $("select[name='country_id']").val("21"); - }, - }, - { - stepId: 'acquirer-checkout-product', - element: 'input[name="acquirer"]', - trigger: 'mouseup', - }, - { - stepId: 'pay-checkout-product', - element: 'button:contains("Pay Now")', - trigger: { - url: /shop\/confirmation\//, - }, - afterTrigger: function (tour) { - console.log('{ "event": "success" }'); - }, - } - ]; - return this._super(); - }, - trigger: function () { - return (this.resume() && this.testUrl(/\/shop\//)) || this._super(); - }, - }); + // website.EditorShopTest = website.Tour.extend({ + // id: 'shop_buy_product', + // name: "Try to buy products", + // path: '/shop', + // init: function (editor) { + // var self = this; + // self.steps = [ + // { + // title: 'begin-test', + // template: self.popover({ next: "Start Test"}), + // backdrop: true, + // }, + // { + // element: '.oe_product_cart a:contains("iPod")', + // trigger: { + // url: /shop\/product\/.*/, + // }, + // }, + // { + // element: 'input[name="product_id"]:not([checked])', + // trigger: 'mouseup', + // }, + // { + // element: 'form[action="/shop/add_cart/"] button', + // trigger: { + // url: '/shop/mycart/', + // }, + // }, + // { + // element: 'form[action="/shop/add_cart/"] button:contains("Add to Cart")', + // trigger: 'reload', + // }, + // { + // element: '.oe_mycart a.js_add_cart_json:eq(1)', + // trigger: 'ajax', + // }, + // { + // element: '.oe_mycart a.js_add_cart_json:eq(2)', + // trigger: 'reload', + // }, + // { + // element: '.oe_mycart input.js_quantity', + // sampleText: '1', + // trigger: 'reload', + // }, + // { + // element: 'a[href="/shop/checkout/"]', + // trigger: { + // url: '/shop/checkout/', + // }, + // }, + // { + // element: 'form[action="/shop/confirm_order/"] button', + // trigger: { + // url: '/shop/confirm_order/', + // }, + // beforeTrigger: function (tour) { + // $("input[name='phone']").val(""); + // }, + // }, + // { + // element: 'form[action="/shop/confirm_order/"] button', + // trigger: { + // url: '/shop/payment/', + // }, + // beforeTrigger: function (tour) { + // if ($("input[name='name']").val() === "") + // $("input[name='name']").val("website_sale-test-shoptest"); + // if ($("input[name='email']").val() === "") + // $("input[name='email']").val("website_sale-test-shoptest@website_sale-test-shoptest.optenerp.com"); + // $("input[name='phone']").val("123"); + // $("input[name='street']").val("123"); + // $("input[name='city']").val("123"); + // $("input[name='zip']").val("123"); + // $("select[name='country_id']").val("21"); + // }, + // }, + // { + // element: 'input[name="acquirer"]', + // trigger: 'mouseup', + // }, + // { + // element: 'button:contains("Pay Now")', + // trigger: { + // url: /shop\/confirmation\//, + // }, + // afterTrigger: function (tour) { + // console.log('{ "event": "success" }'); + // }, + // } + // ]; + // return this._super(); + // }, + // trigger: function () { + // return (this.resume() && this.testUrl(/\/shop\//)) || this._super(); + // }, + // }); + // // for test without editor bar + // $(document).ready(function () { + // website.Tour.add(website.EditorShopTest); + // }); }()); diff --git a/addons/website_sale/tests/test_ui.py b/addons/website_sale/tests/test_ui.py index ec852bdfa3b..f3ad5aeef1e 100644 --- a/addons/website_sale/tests/test_ui.py +++ b/addons/website_sale/tests/test_ui.py @@ -3,6 +3,6 @@ import openerp.addons.website.tests.test_ui as test_ui def load_tests(loader, base, _): base.addTest(test_ui.WebsiteUiSuite(test_ui.full_path(__file__,'website_sale-sale_process-test.js'), { 'action': 'website.action_website_homepage' }, 120.0)) - base.addTest(test_ui.WebsiteUiSuite(test_ui.full_path(__file__,'website_sale-sale_process-test-2.js'), - { 'action': 'website.action_website_homepage' }, 120.0)) + # base.addTest(test_ui.WebsiteUiSuite(test_ui.full_path(__file__,'website_sale-sale_process-test-2.js'), + # { 'action': 'website.action_website_homepage' }, 120.0)) return base \ No newline at end of file diff --git a/addons/website_sale/tests/ui_suite/website_sale-sale_process-test-2.js b/addons/website_sale/tests/ui_suite/website_sale-sale_process-test-2.js index 35e1ba6edd3..b8385f74408 100644 --- a/addons/website_sale/tests/ui_suite/website_sale-sale_process-test-2.js +++ b/addons/website_sale/tests/ui_suite/website_sale-sale_process-test-2.js @@ -7,12 +7,12 @@ testRunner.run(function websiteSaleTest (page, timeout) { waitFor(function clientReady () { return page.evaluate(function () { return window.$ && window.openerp && window.openerp.website - && window.openerp.website.TestConsole - && window.openerp.website.TestConsole.test('shop'); + && window.openerp.website.Tour + && window.openerp.website.Tour.get('shop'); }); }, function executeTest () { page.evaluate(function () { - window.openerp.website.TestConsole.test('shop').run(true); + window.openerp.website.Tour.get('shop').run(true, true); }); waitFor(function testExecuted () { var after = page.evaluate(function () { diff --git a/addons/website_sale/tests/ui_suite/website_sale-sale_process-test.js b/addons/website_sale/tests/ui_suite/website_sale-sale_process-test.js index 5e6b8279306..41dc4f5ea67 100644 --- a/addons/website_sale/tests/ui_suite/website_sale-sale_process-test.js +++ b/addons/website_sale/tests/ui_suite/website_sale-sale_process-test.js @@ -7,12 +7,12 @@ testRunner.run(function websiteSaleTest (page, timeout) { waitFor(function clientReady () { return page.evaluate(function () { return window.$ && window.openerp && window.openerp.website - && window.openerp.website.TestConsole - && window.openerp.website.TestConsole.test('shop_buy_product'); + && window.openerp.website.Tour + && window.openerp.website.Tour.get('shop_buy_product'); }); }, function executeTest () { page.evaluate(function () { - window.openerp.website.TestConsole.test('shop_buy_product').run(true); + window.openerp.website.TestConsole.test('shop_buy_product').run(true, true); }); }, timeout); }); \ No newline at end of file