Merge branch 'develop' into release

This commit is contained in:
Sabe Jones
2019-04-25 13:55:17 -05:00
7 changed files with 70 additions and 42 deletions

View File

@@ -1,41 +1,41 @@
.tier1 { .tier1 {
color: #c42870 !important; color: #c42870;
} }
.tier2 { .tier2 {
color: #b01515 !important; color: #b01515;
} }
.tier3 { .tier3 {
color: #d70e14 !important; color: #d70e14;
} }
.tier4 { .tier4 {
color: #c24d00 !important; color: #c24d00;
} }
.tier5 { .tier5 {
color: #9e650f !important; color: #9e650f;
} }
.tier6 { .tier6 {
color: #2b8363 !important; color: #2b8363;
} }
.tier7 { .tier7 {
color: #167e87 !important; color: #167e87;
} }
.tier8 { .tier8 {
color: #277eab !important; color: #277eab;
} }
.tier9 { .tier9 {
color: #6133b4 !important; color: #6133b4;
} }
.tierNPC, .npc { .tierNPC, .npc {
color: #77f4c7 !important; color: #77f4c7;
fill: #77f4c7; fill: #77f4c7;
stroke: #005737; stroke: #005737;
} }

View File

@@ -21,13 +21,13 @@
.row .row
.col-12.col-md-6(v-for='challenge in filteredChallenges') .col-12.col-md-6(v-for='challenge in filteredChallenges')
challenge-item(:challenge='challenge') challenge-item(:challenge='challenge')
mugen-scroll(
.row :handler="infiniteScrollTrigger",
h2.col-12.loading(v-if='loading') {{ $t('loading') }} :should-handle="!loading && canLoadMore",
:threshold="1",
.row v-show="loading",
.col-12.text-center(v-if='showLoadMore && !loading && filteredChallenges.length > 0') )
button.btn.btn-flat.btn-show-more(@click='loadMore()') {{ $t('loadMore') }} h2.col-12.loading(v-once) {{ $t('loading') }}
</template> </template>
<style lang='scss' scoped> <style lang='scss' scoped>
@@ -75,17 +75,22 @@ import challengeUtilities from 'client/mixins/challengeUtilities';
import positiveIcon from 'assets/svg/positive.svg'; import positiveIcon from 'assets/svg/positive.svg';
import MugenScroll from 'vue-mugen-scroll';
import debounce from 'lodash/debounce';
export default { export default {
mixins: [challengeUtilities], mixins: [challengeUtilities],
components: { components: {
Sidebar, Sidebar,
ChallengeItem, ChallengeItem,
challengeModal, challengeModal,
MugenScroll,
}, },
data () { data () {
return { return {
loading: true, loading: true,
showLoadMore: true, canLoadMore: true,
icons: Object.freeze({ icons: Object.freeze({
positiveIcon, positiveIcon,
}), }),
@@ -169,17 +174,26 @@ export default {
} }
// only show the load more Button if the max count was returned // only show the load more Button if the max count was returned
this.showLoadMore = challenges.length === 10; this.canLoadMore = challenges.length === 10;
this.loading = false; this.loading = false;
}, },
challengeCreated (challenge) { challengeCreated (challenge) {
this.challenges.push(challenge); this.challenges.push(challenge);
}, },
async loadMore () { infiniteScrollTrigger () {
// show loading and wait until the loadMore debounced
// or else it would trigger on every scrolling-pixel (while not loading)
if (this.canLoadMore) {
this.loading = true;
}
this.loadMore();
},
loadMore: debounce(function loadMoreDebounce () {
this.page += 1; this.page += 1;
this.loadChallenges(); this.loadChallenges();
}, }, 1000),
}, },
}; };
</script> </script>

View File

@@ -29,13 +29,13 @@
.row .row
.col-12.col-md-6(v-for='challenge in filteredChallenges') .col-12.col-md-6(v-for='challenge in filteredChallenges')
challenge-item(:challenge='challenge') challenge-item(:challenge='challenge')
mugen-scroll(
.row :handler="infiniteScrollTrigger",
h2.col-12.loading(v-if='loading') {{ $t('loading') }} :should-handle="!loading && canLoadMore",
:threshold="1",
.row v-show="loading",
.col-12.text-center(v-if='showLoadMore && !loading && filteredChallenges.length > 0') )
button.btn.btn-flat.btn-show-more(@click='loadMore()') {{ $t('loadMore') }} h2.col-12.loading(v-once) {{ $t('loading') }}
</template> </template>
<style lang='scss' scoped> <style lang='scss' scoped>
@@ -88,6 +88,9 @@ import challengeUtilities from 'client/mixins/challengeUtilities';
import challengeIcon from 'assets/svg/challenge.svg'; import challengeIcon from 'assets/svg/challenge.svg';
import positiveIcon from 'assets/svg/positive.svg'; import positiveIcon from 'assets/svg/positive.svg';
import MugenScroll from 'vue-mugen-scroll';
import debounce from 'lodash/debounce';
export default { export default {
mixins: [challengeUtilities], mixins: [challengeUtilities],
@@ -95,6 +98,7 @@ export default {
Sidebar, Sidebar,
ChallengeItem, ChallengeItem,
challengeModal, challengeModal,
MugenScroll,
}, },
data () { data () {
return { return {
@@ -103,7 +107,7 @@ export default {
positiveIcon, positiveIcon,
}), }),
loading: false, loading: false,
showLoadMore: true, canLoadMore: true,
challenges: [], challenges: [],
sort: 'none', sort: 'none',
sortOptions: [ sortOptions: [
@@ -202,17 +206,26 @@ export default {
} }
// only show the load more Button if the max count was returned // only show the load more Button if the max count was returned
this.showLoadMore = challenges.length === 10; this.canLoadMore = challenges.length === 10;
this.loading = false; this.loading = false;
}, },
challengeCreated (challenge) { challengeCreated (challenge) {
this.challenges.push(challenge); this.challenges.push(challenge);
}, },
async loadMore () { infiniteScrollTrigger () {
// show loading and wait until the loadMore debounced
// or else it would trigger on every scrolling-pixel (while not loading)
if (this.canLoadMore) {
this.loading = true;
}
this.loadMore();
},
loadMore: debounce(function loadMoreDebounce () {
this.page += 1; this.page += 1;
this.loadChallenges(); this.loadChallenges();
}, }, 1000),
}, },
}; };
</script> </script>

View File

@@ -11,7 +11,7 @@
<style scoped lang="scss"> <style scoped lang="scss">
@import '~client/assets/scss/colors.scss'; @import '~client/assets/scss/colors.scss';
a { a.no-tier {
color: $gray-50; color: $gray-50;
} }

View File

@@ -10,7 +10,8 @@ export default {
userLevelStyleFromLevel (level, npc, style) { userLevelStyleFromLevel (level, npc, style) {
style = style || ''; style = style || '';
if (npc) style += ' npc'; if (npc) style += ' npc';
if (level) style += ` tier${level}`; style += level ? ` tier${level}` : ' no-tier';
return style; return style;
}, },
}, },

View File

@@ -99,7 +99,7 @@ api.loginLocal = {
let user = await User.findOne(login).exec(); let user = await User.findOne(login).exec();
// if user is using social login, then user will not have a hashed_password stored // if user is using social login, then user will not have a hashed_password stored
if (!user.auth.local.hashed_password) throw new NotAuthorized(res.t('invalidLoginCredentialsLong')); if (!user || !user.auth.local.hashed_password) throw new NotAuthorized(res.t('invalidLoginCredentialsLong'));
let isValidPassword; let isValidPassword;

View File

@@ -11,7 +11,9 @@ import {
} from '../models/group'; } from '../models/group';
import apiError from '../libs/apiError'; import apiError from '../libs/apiError';
const partyMembersFields = 'profile.name stats achievements items.special'; const partyMembersFields = 'profile.name stats achievements items.special notifications flags';
// Excluding notifications and flags from the list of public fields to return.
const partyMembersPublicFields = 'profile.name stats achievements items.special';
// @TODO: After refactoring individual spells, move quantity to the calculations // @TODO: After refactoring individual spells, move quantity to the calculations
@@ -78,8 +80,7 @@ async function castPartySpell (req, party, partyMembers, user, spell, quantity =
'party._id': party._id, 'party._id': party._id,
_id: { $ne: user._id }, // add separately _id: { $ne: user._id }, // add separately
}) })
// .select(partyMembersFields) Selecting the entire user because otherwise when saving it'll save .select(partyMembersFields)
// default values for non-selected fields and pre('save') will mess up thinking some values are missing
.exec(); .exec();
partyMembers.unshift(user); partyMembers.unshift(user);
@@ -101,8 +102,7 @@ async function castUserSpell (res, req, party, partyMembers, targetId, user, spe
if (!party) throw new NotFound(res.t('partyNotFound')); if (!party) throw new NotFound(res.t('partyNotFound'));
partyMembers = await User partyMembers = await User
.findOne({_id: targetId, 'party._id': party._id}) .findOne({_id: targetId, 'party._id': party._id})
// .select(partyMembersFields) Selecting the entire user because otherwise when saving it'll save .select(partyMembersFields)
// default values for non-selected fields and pre('save') will mess up thinking some values are missing
.exec(); .exec();
} }
@@ -183,9 +183,9 @@ async function castSpell (req, res, {isV3 = false}) {
let partyMembersRes = Array.isArray(partyMembers) ? partyMembers : [partyMembers]; let partyMembersRes = Array.isArray(partyMembers) ? partyMembers : [partyMembers];
// Only return some fields. // Only return some fields.
// See comment above on why we can't just select the necessary fields when querying // We can't just return the selected fields because they're private
partyMembersRes = partyMembersRes.map(partyMember => { partyMembersRes = partyMembersRes.map(partyMember => {
return common.pickDeep(partyMember.toJSON(), common.$w(partyMembersFields)); return common.pickDeep(partyMember.toJSON(), common.$w(partyMembersPublicFields));
}); });
let userToJson = user; let userToJson = user;