diff --git a/package-lock.json b/package-lock.json index 34fba602b5..cdf26d5341 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "habitica", - "version": "4.28.0", + "version": "4.28.1", "lockfileVersion": 1, "requires": true, "dependencies": { diff --git a/package.json b/package.json index bed67e00ce..e6068ace2d 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "habitica", "description": "A habit tracker app which treats your goals like a Role Playing Game.", - "version": "4.28.0", + "version": "4.28.1", "main": "./website/server/index.js", "greenkeeper": { "ignore": [ diff --git a/test/common/ops/sell.js b/test/common/ops/sell.js index 11c9676c03..9631fb9650 100644 --- a/test/common/ops/sell.js +++ b/test/common/ops/sell.js @@ -75,6 +75,16 @@ describe('shared.ops.sell', () => { } }); + it('returns an error when the requested amount is negative', (done) => { + try { + sell(user, {params: { type, key }, query: {amount: -42} }); + } catch (err) { + expect(err).to.be.an.instanceof(BadRequest); + expect(err.message).to.equal(i18n.t('positiveAmountRequired', {type})); + done(); + } + }); + it('reduces item count from user', () => { sell(user, {params: { type, key } }); diff --git a/website/client/assets/images/npc/broken/market_broken_background.png b/website/client/assets/images/npc/broken/market_broken_background.png new file mode 100644 index 0000000000..a1000472c6 Binary files /dev/null and b/website/client/assets/images/npc/broken/market_broken_background.png differ diff --git a/website/client/assets/images/npc/broken/market_broken_layer.png b/website/client/assets/images/npc/broken/market_broken_layer.png new file mode 100644 index 0000000000..a9f310ee09 Binary files /dev/null and b/website/client/assets/images/npc/broken/market_broken_layer.png differ diff --git a/website/client/assets/images/npc/broken/market_broken_npc.png b/website/client/assets/images/npc/broken/market_broken_npc.png new file mode 100644 index 0000000000..62d7fe69b9 Binary files /dev/null and b/website/client/assets/images/npc/broken/market_broken_npc.png differ diff --git a/website/client/assets/images/npc/broken/rage-strike-market-scaled@2x.png b/website/client/assets/images/npc/broken/rage-strike-market-scaled@2x.png new file mode 100644 index 0000000000..56fac8fe2b Binary files /dev/null and b/website/client/assets/images/npc/broken/rage-strike-market-scaled@2x.png differ diff --git a/website/client/components/groups/tavern.vue b/website/client/components/groups/tavern.vue index 7ed00400dd..71224e012d 100644 --- a/website/client/components/groups/tavern.vue +++ b/website/client/components/groups/tavern.vue @@ -76,7 +76,7 @@ .m-auto(@click="showWorldBossRage('seasonalShop')") img.rage-strike(src="~assets/images/world-boss/rage_strike@2x.png", v-if="!group.quest.extra.worldDmg.seasonalShop") img.rage-strike-active(src="~assets/images/world-boss/rage_strike-seasonalShop@2x.png", v-if="group.quest.extra.worldDmg.seasonalShop") - .m-auto + .m-auto(@click="showWorldBossRage('market')") img.rage-strike(src="~assets/images/world-boss/rage_strike@2x.png", v-if="!group.quest.extra.worldDmg.market") img.rage-strike-active(src="~assets/images/world-boss/rage_strike-market@2x.png", v-if="group.quest.extra.worldDmg.market") .m-auto @@ -760,6 +760,7 @@ export default { }, showWorldBossRage (npc) { if (this.group.quest.extra.worldDmg[npc]) { + this.$store.state.rageModalOptions.npc = npc; this.$root.$emit('bv::show::modal', 'world-boss-rage'); } }, diff --git a/website/client/components/shops/market/index.vue b/website/client/components/shops/market/index.vue index 3952ab31d6..db3da6abda 100644 --- a/website/client/components/shops/market/index.vue +++ b/website/client/components/shops/market/index.vue @@ -27,7 +27,8 @@ ) .standard-page div.featuredItems - .background + .background(:class="{broken: broken}") + .background(:class="{cracked: broken, broken: broken}") div.npc div.featured-label span.rectangle @@ -312,8 +313,24 @@ left: 80px; } } - } + .background.broken { + background: url('~assets/images/npc/broken/market_broken_background.png'); + + background-repeat: repeat-x; + } + + .background.cracked { + background: url('~assets/images/npc/broken/market_broken_layer.png'); + + background-repeat: repeat-x; + } + + .broken .npc { + background: url('~assets/images/npc/broken/market_broken_npc.png'); + background-repeat: no-repeat; + } + } } .market .gems-left { @@ -443,8 +460,14 @@ export default { hideLocked: false, hidePinned: false, + + broken: false, }; }, + async mounted () { + const worldState = await this.$store.dispatch('worldState:getWorldState'); + this.broken = worldState.worldBoss.extra.worldDmg.market; + }, computed: { ...mapState({ content: 'content', diff --git a/website/client/components/shops/market/sellModal.vue b/website/client/components/shops/market/sellModal.vue index cfeaef7b48..b22bd3fb74 100644 --- a/website/client/components/shops/market/sellModal.vue +++ b/website/client/components/shops/market/sellModal.vue @@ -26,7 +26,7 @@ b.how-many-to-sell {{ $t('howManyToSell') }} div - b-input.itemsToSell(type="number", v-model="selectedAmountToSell", :max="itemCount", min="1") + b-input.itemsToSell(type="number", v-model="selectedAmountToSell", :max="itemCount", min="1", @keyup.native="preventNegative($event)") span.svg-icon.inline.icon-32(aria-hidden="true", v-html="icons.gold") span.value {{ item.value }} @@ -141,6 +141,13 @@ this.selectedAmountToSell = 1; }, + preventNegative ($event) { + let value = $event.target.value; + + if (isNaN($event.target.valueAsNumber) || Number(value) < 0) { + this.selectedAmountToSell = 0; + } + }, sellItems () { this.$store.dispatch('shops:sellItems', { type: this.itemType, diff --git a/website/client/components/world-boss/worldBossRageModal.vue b/website/client/components/world-boss/worldBossRageModal.vue index bcae7a5a0d..73e8c1be27 100644 --- a/website/client/components/world-boss/worldBossRageModal.vue +++ b/website/client/components/world-boss/worldBossRageModal.vue @@ -1,13 +1,23 @@