// import each from 'lodash/each';
// import flattenDeep from 'lodash/flattenDeep';
import times from 'lodash/times';
import Intro from 'intro.js/';
export default {
data () {
return {
TOUR_END: -2,
tour: {},
chapters: {},
loaded: false,
};
},
watch: {
$route () {
this.routeChange();
},
},
methods: {
load () {
// @TODO: this should be called after app is loaded
// Init and show the welcome tour (only after user is pulled from server & wrapped).
if (window.env.IS_MOBILE) return; // Don't show tour immediately on mobile devices
// let alreadyShown = (before, after) => {
// return Boolean(!before && after === true);
// };
// $rootScope.$watch('user.flags.dropsEnabled', _.flow(alreadyShown, function(already) { //FIXME requires lodash@~3.2.0
},
initTour () {
if (this.loaded) return;
this.chapters = {
intro: [
[
{
// state: 'options.profile.avatar',
element: '.member-details',
intro: this.$t('tourAvatar'),
// position: 'top',
// proceed: this.$t('tourAvatarProceed'),
// backdrop: false,
// orphan: true,
// gold: 4,
// experience: 29,
},
{
// state: 'tasks',
element: '.todo',
intro: this.$t('tourToDosBrief'),
position: 'left',
// proceed: this.$t('tourOkay'),
// gold: 4,
// experience: 29,
},
{
// state: 'tasks',
element: '.daily',
intro: this.$t('tourDailiesBrief'),
position: 'right',
// proceed: this.$t('tourDailiesProceed'),
// gold: 4,
// experience: 29,
},
{
// state: 'tasks',
element: '.habit',
intro: this.$t('tourHabitsBrief'),
position: 'right',
// proceed: this.$t('tourHabitsProceed'),
// gold: 4,
// experience: 29,
},
{
// state: 'tasks',
element: '.reward',
intro: this.user.flags.armoireEnabled ? this.$t('tourRewardsArmoire') : this.$t('tourRewardsBrief'),
position: 'left',
// proceed: this.$t('tourRewardsProceed'),
// gold: 4,
// experience: 29,
// final: true,
},
],
],
classes: [
[
{
orphan: true,
intro: this.$t('classGearText'),
final: true,
state: 'options.inventory.equipment',
element: '.weapon',
title: this.$t('classGear'),
hideNavigation: true,
},
],
],
stats: [[
{
orphan: true,
intro: this.$t('tourStatsPage'),
final: true,
proceed: this.$t('tourOkay'),
hideNavigation: true,
},
]],
tavern: [[
{
orphan: true,
intro: this.$t('tourTavernPage'),
final: true,
proceed: this.$t('tourAwesome'),
hideNavigation: true,
},
]],
party: [[
{
orphan: true,
intro: this.$t('tourPartyPage'),
final: true,
proceed: this.$t('tourSplendid'),
hideNavigation: true,
},
]],
guilds: [[
{
// orphan: true,
intro: this.$t('tourGuildsPage'),
// final: true,
// proceed: this.$t('tourNifty'),
// hideNavigation: true,
},
]],
challenges: [[
{
orphan: true,
intro: this.$t('tourChallengesPage'),
final: true,
proceed: this.$t('tourOkay'),
hideNavigation: true,
},
]],
market: [[
{
orphan: true,
intro: this.$t('tourMarketPage'),
final: true,
proceed: this.$t('tourAwesome'),
hideNavigation: true,
},
]],
hall: [[
{
orphan: true,
intro: this.$t('tourHallPage'),
final: true,
proceed: this.$t('tourSplendid'),
hideNavigation: true,
},
]],
pets: [[
{
orphan: true,
intro: this.$t('tourPetsPage'),
final: true,
proceed: this.$t('tourNifty'),
hideNavigation: true,
},
]],
mounts: [[
{
orphan: true,
intro: this.$t('tourMountsPage'),
final: true,
proceed: this.$t('tourOkay'),
hideNavigation: true,
},
]],
equipment: [[
{
orphan: true,
intro: this.$t('tourEquipmentPage'),
final: true,
proceed: this.$t('tourAwesome'),
hideNavigation: true,
},
]],
};
// let chapters = this.chapters;
// each(chapters, (chapter, k) => {
// flattenDeep(chapter).forEach((step, i) => {
// // @TODO: (env.worldDmg.guide ? 'npc_justin_broken' : 'npc_justin')
// step.content = `
`;
// // @TODO: $(step.element).popover('destroy'); // destroy existing hover popovers so we can add our own
//
// step.onShow = () => {
// // @TODO: Analytics.track({'hitType':'event','eventCategory':'behavior','eventAction':'tutorial','eventLabel':k+'-web','eventValue':i+1,'complete':false});
// // @TODO: Add Router if (!step.state || $state.is(step.state)) return;
// // @TODO: Add Router $state.go(step.state);
// // @TODO: Do we need this? return $timeout(() => {});
// };
// });
// });
// let tour = this.tour;
// each(chapters, (v, k) => {
// tour[k] = new Tour({
// name: k,
// backdrop: true,
// template: (i, step) => {
// let showFinish = step.final || k === 'classes';
// let showCounter = k === 'intro' && !step.final;
// // TODO: we can probably create a component for all this
//
// let counterSpan = '';
// if (showCounter) counterSpan = `${i + 1} of ${flattenDeep(chapters[k]).length}`;
//
// let prevButton = '';
// if (!step.hideNavigation) prevButton = '';
//
// let nextButton = '';
// let stepProceedText = 'Next';
// if (step.proceed) stepProceedText = step.proceed;
// if (!step.hideNavigation) nextButton = ``;
// let stepFinishText = 'Finish Tour';
// if (step.proceed) stepFinishText = step.proceed;
// if (showFinish) nextButton = ``;
//
// return ` \
//
\
//
\
//
\
//
\
// ${counterSpan} \
//
\
// ${prevButton} \
// ${nextButton} \
// \
//
\
//
\
//
`;
// },
// storage: false,
// });
// });
this.loaded = true;
},
routeChange () {
this.initTour();
switch (this.$route.name) {
// case 'options.profile.avatar': return goto('intro', 5);
case 'stats': return this.goto('stats', 0);
case 'tavern': return this.goto('tavern', 0);
case 'party': return this.goto('party', 0);
case 'guildsDiscovery': return this.goto('guilds', 0);
case 'challenges': return this.goto('challenges', 0);
case 'patrons': return this.goto('hall', 0);
case 'items': return this.goto('market', 0);
case 'stable': return this.goto('pets', 0);
// @TODO: same page now case 'stable': return this.goto('mounts', 0);
case 'equipment': return this.goto('equipment', 0);
}
},
hoyo (user) {
// @TODO: What is was the timeout for?
window.amplitude.setUserId(user._id);
window.ga('set', {userId: user._id});
},
goto (chapter, page, force) {
if (chapter === 'intro' && this.user.flags.welcomed !== true) {
// @TODO: Add dispatch User.set({'flags.welcomed': true});
}
if (chapter === 'classes' && this.user.flags.tour.classes === -2) return;
if (page === -1) page = 0;
let curr = this.user.flags.tour[chapter];
if (page !== curr + 1 && !force) return;
// let chap = this.tour[chapter];
// if (!chap) return;
let opts = {}; // @TODO: chap._options;
opts.steps = [];
page += 1;
times(page, (p) => {
opts.steps = opts.steps.concat(this.chapters[chapter][p]);
});
// let end = opts.steps.length;
// opts.steps = opts.steps.concat(this.chapters[chapter][page]);
// chap._removeState('end');
// @TODO: Do we always need to initialize here?
let intro = Intro.introJs();
intro.setOptions({steps: opts.steps});
intro.start();
intro.oncomplete(() => {
this.markTourComplete(chapter);
});
// if (chap._inited) {
// chap.goTo(end);
// } else {
// chap.setCurrentStep(end);
// if (page > 0) {
// chap.init();
// chap.goTo(page);
// } else {
// chap.start();
// }
// }
},
markTourComplete (chapter) {
// @TODO: this is suppose to keep track of wher ethe left off. Do that later
let ups = {};
let lastKnownStep = this.user.flags.tour[chapter];
// Return early if user has already completed this tutorial
if (lastKnownStep === -2) {
return;
}
// if (i > lastKnownStep) {
// if (step.gold) ups['stats.gp'] = this.user.stats.gp + step.gold;
// if (step.experience) ups['stats.exp'] = this.user.stats.exp + step.experience;
// ups[`flags.tour.${k}`] = i;
// }
// step.final
// if (true) { // -2 indicates complete
// if (chapter === 'intro') {
// // Manually show bunny scroll reward
// // let rewardData = {
// // reward: [Shared.content.quests.dustbunnies],
// // rewardKey: ['inventory_quest_scroll_dustbunnies'],
// // rewardText: Shared.content.quests.dustbunnies.text(),
// // message: this.$t('checkinEarned'),
// // nextRewardAt: 1,
// // };
// // @TODO: Notification.showLoginIncentive(this.user, rewardData, Social.loadWidgets);
// }
// Mark tour complete
ups[`flags.tour.${chapter}`] = -2; // @TODO: Move magic numbers to enum
// @TODO: Analytics.track({'hitType':'event','eventCategory':'behavior','eventAction':'tutorial','eventLabel':k+'-web','eventValue':i+1,'complete':true})
// }
this.$store.dispatch('user:set', ups);
// User.set() doesn't include a check for level changes, so manually check here.
// @TODO:
// if (step.experience) {
// this.user.fns.updateStats(this.user.stats);
// }
},
},
};