Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
43 commits
Select commit Hold shift + click to select a range
a9ca503
fix: added hidden input elements for checkboxs
Haviles04 Mar 14, 2025
fe2405a
Feat: Created basic components to display team
Haviles04 Mar 18, 2025
e058ce3
config
Haviles04 Mar 18, 2025
2bcae66
chore: comments
Haviles04 Mar 18, 2025
ca32d96
feat: added switch to select team sub
Haviles04 Mar 18, 2025
4975bdf
Merge branch 'master' into Vo-Team-Dashboard
Haviles04 Mar 18, 2025
ad23726
feat: Added access
Haviles04 Mar 21, 2025
80ce9e4
feat: buildout of myTeam Dashboard in Vo
Haviles04 Mar 23, 2025
10ef7d0
feat: added remove and leave functions to oneStore
Haviles04 Mar 27, 2025
4d87369
chore: pascal case and naming
Haviles04 Mar 27, 2025
fd0a8cd
feat: added coming soon / changed position
Haviles04 Mar 27, 2025
0590e7b
feat: only showing my-team when isAdmin = true
Haviles04 Mar 27, 2025
33abc03
feat: added logic to join team from invite link
Haviles04 Mar 29, 2025
0aaa7d0
feat: started building out team invite dialog
Haviles04 Mar 29, 2025
85df77d
refactor: moved/create Team Store, and updated invite to include user…
Haviles04 Mar 30, 2025
92983be
fix: changed order
Haviles04 Mar 30, 2025
2b5ba65
Merge branch 'master' into Vo-Team-Dashboard
Haviles04 Mar 30, 2025
6f5e7fe
fix
Haviles04 Mar 30, 2025
f143817
fix: minor fixes
Haviles04 Mar 30, 2025
3407264
fix: fixed routing issue
Haviles04 Mar 30, 2025
6295dbf
fix: added finally
Haviles04 Mar 30, 2025
8bd23cb
fix: pnpm new install
Haviles04 Mar 30, 2025
96465b7
chore(VoSubscriptionDialog): rename variable, clean-up template
johnleider Mar 31, 2025
c908d1e
refactor: called forced refresh auth verify instead of setting variables
Haviles04 Mar 31, 2025
3c6ce83
chore: removed unneeded comment
Haviles04 Mar 31, 2025
281c3c2
chore: reset initial isLoading value
Haviles04 Mar 31, 2025
86b1197
chore: removed un-needed change
Haviles04 Mar 31, 2025
ea8c4a6
chore: removed console log
Haviles04 Mar 31, 2025
b379488
chore: removed unused typing
Haviles04 Mar 31, 2025
2e98e18
fix: fixed access
Haviles04 Mar 31, 2025
ec0b013
fix: fixed icons
Haviles04 Apr 1, 2025
1cc0689
refactor: returned errors a text instead of json
Haviles04 Apr 1, 2025
980a68d
fix: added function and displayed error messages
Haviles04 Apr 1, 2025
36fd512
fix: missing argument
Haviles04 Apr 1, 2025
9aff996
refactor: changed the way subscribe is handled and updated subscripti…
Haviles04 Apr 1, 2025
c260cfb
Merge branch 'master' into Vo-Team-Dashboard
Haviles04 Apr 2, 2025
fc87eb0
feat: open team dialog on successful team subscription
Haviles04 Apr 2, 2025
788d0d7
feat: moved 20% chip
Haviles04 Apr 2, 2025
9548a71
refactor: tweaks from review
johnleider Apr 2, 2025
99770b4
lint: optional chainer
Haviles04 Apr 2, 2025
1c6ec3f
separate interval and type, select interval with tabs
KaelWD Apr 7, 2025
c0f86c9
fix: disable buying team access if you're not the owner
Haviles04 Apr 8, 2025
a5ff683
fix: called is team owner in subscribe
Haviles04 Apr 8, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
@@ -1 +1,6 @@
VITE_API_SERVER_URL=https://dev-api.vuetifyjs.com

VITE_YEARLY_TEAM_PRICE=299.99
VITE_YEARLY_SOLO_PRICE=29.99
VITE_MONTHLY_TEAM_PRICE=29.99
VITE_MONTHLY_SOLO_PRICE=2.99
4 changes: 3 additions & 1 deletion .eslintrc-auto-import.json
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,7 @@
"useQueueStore": true,
"aliases": true,
"trackEvent": true,
"useTeamStore": true,
"Banner": true,
"Bin": true,
"DirectiveBinding": true,
Expand Down Expand Up @@ -138,6 +139,7 @@
"SettingsState": true,
"SiteState": true,
"SnackbarQueueState": true,
"SponsorState": true
"SponsorState": true,
"Team": true
}
}
5 changes: 5 additions & 0 deletions auto-imports.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,7 @@ declare global {
const useSlots: typeof import('vue')['useSlots']
const useSponsorsStore: typeof import('./lib/stores/sponsors')['useSponsorsStore']
const useSpotsStore: typeof import('./lib/stores/spots')['useSpotsStore']
const useTeamStore: typeof import('./lib/stores/team')['useTeamStore']
const useTemplateRef: typeof import('vue')['useTemplateRef']
const useTheme: typeof import('vuetify')['useTheme']
const useUserStore: typeof import('./lib/stores/user')['useUserStore']
Expand Down Expand Up @@ -152,6 +153,9 @@ declare global {
export type { Spot } from './lib/stores/spots'
import('./lib/stores/spots')
// @ts-ignore
export type { Team } from './lib/stores/team'
import('./lib/stores/team')
// @ts-ignore
export type { RootState, SavedState } from './lib/stores/user'
import('./lib/stores/user')
}
Expand Down Expand Up @@ -256,6 +260,7 @@ declare module 'vue' {
readonly useSlots: UnwrapRef<typeof import('vue')['useSlots']>
readonly useSponsorsStore: UnwrapRef<typeof import('./lib/stores/sponsors')['useSponsorsStore']>
readonly useSpotsStore: UnwrapRef<typeof import('./lib/stores/spots')['useSpotsStore']>
readonly useTeamStore: UnwrapRef<typeof import('./lib/stores/team')['useTeamStore']>
readonly useTemplateRef: UnwrapRef<typeof import('vue')['useTemplateRef']>
readonly useTheme: UnwrapRef<typeof import('vuetify')['useTheme']>
readonly useUserStore: UnwrapRef<typeof import('./lib/stores/user')['useUserStore']>
Expand Down
3 changes: 3 additions & 0 deletions components.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,9 @@ declare module 'vue' {
VoSubscriptionStatus: typeof import('./lib/components/subscription/VoSubscriptionStatus.vue')['default']
VoSubscriptionSubscribe: typeof import('./lib/components/subscription/VoSubscriptionSubscribe.vue')['default']
VoSwitch: typeof import('./lib/components/app/VoSwitch.vue')['default']
VoTeamDialog: typeof import('./lib/components/team/VoTeamDialog.vue')['default']
VoTeamInvite: typeof import('./lib/components/team/VoTeamInvite.vue')['default']
VoTeamListItem: typeof import('./lib/components/team/VoTeamListItem.vue')['default']
VoUserAvatar: typeof import('./lib/components/user/VoUserAvatar.vue')['default']
VoUserBadges: typeof import('./lib/components/user/VoUserBadges.vue')['default']
VoUserColors: typeof import('./lib/components/user/VoUserColors.vue')['default']
Expand Down
1 change: 1 addition & 0 deletions lib/components/app/VoAppBar.vue
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
vertical
/>

<!-- Leads to one dropdown dialog -->
<VoAuthBtn />
</template>
</v-app-bar>
Expand Down
2 changes: 2 additions & 0 deletions lib/components/auth/VoAuthBtn.vue
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,15 @@
</VoNotificationsTotalBadge>

<VoAuthDialog />
<VoTeamInvite />

<VoSnackbarQueue />
</template>

<script lang="ts" setup>
// Icons
import { mdiLogin } from '@mdi/js'
import VoTeamInvite from '../team/VoTeamInvite.vue'

defineProps({
external: Boolean,
Expand Down
29 changes: 16 additions & 13 deletions lib/components/subscription/VoSubscriptionDialog.vue
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,8 @@

<v-window :model-value="window">
<v-window-item value="subscribe">
<VoSubscriptionSubscribe v-model="subscription" />

<VoSubscriptionSubscribe v-model:interval="interval" v-model:type="type" />
<br>

<VoSubscriptionPerks />
</v-window-item>

Expand Down Expand Up @@ -50,13 +48,13 @@
<VoBtn
v-else-if="!one.one"
block
:color="!subscription ? 'disabled' : 'primary'"
:disabled="!subscription"
:color="!(interval && type) ? 'disabled' : 'primary'"
:disabled="!(interval && type)"
:loading="one.isLoading"
prepend-icon="$vuetify"
size="default"
text="Activate Subscription"
@click="one.subscribe(subscription!)"
@click="one.subscribe(interval!, type!)"
/>

<VoBtn
Expand All @@ -83,15 +81,20 @@
const dialog = defineModel('modelValue', { type: Boolean })

const one = useOneStore()
const query = useQuery<{ one: string }>()
const subscription = shallowRef(one.interval)
const query = useQuery<{ one: string, team: string}>()
const interval = shallowRef(one.interval)
const type = shallowRef(one.subscriptionType)
const window = shallowRef(one.hasBilling ? 'status' : 'subscribe')
const isUpdatingSubscription = shallowRef<boolean | null>(false)

watch(subscription, val => {
if (!one.isSubscriber || !one.interval) return
watch([interval, type], ([interval, type]) => {
if (!one.isSubscriber || !one.interval || !one.subscriptionType) return

isUpdatingSubscription.value = val !== one.interval
isUpdatingSubscription.value = interval !== one.interval || type !== one.subscriptionType
})
watchEffect(() => {
interval.value = one.interval
type.value = one.subscriptionType
})

watch(dialog, async val => {
Expand All @@ -106,7 +109,7 @@

watch(query, async () => {
if (!one.sessionId && !['subscribe', 'status'].includes(query.value.one)) return

if (query.value.team) return
window.value = one.sessionId || query.value.one === 'status' ? 'status' : 'subscribe'

one.isOpen = true
Expand All @@ -117,7 +120,7 @@
}, { immediate: true })

async function onClickModify () {
await one.modify(subscription.value!)
await one.modify(interval.value!, type.value!)
await one.subscriptionInfo()

isUpdatingSubscription.value = null
Expand Down
69 changes: 44 additions & 25 deletions lib/components/subscription/VoSubscriptionSubscribe.vue
Original file line number Diff line number Diff line change
@@ -1,16 +1,30 @@
<template>
<v-item-group v-model="subscription" mandatory>
<v-tabs v-model="interval" color="primary" mandatory>
<v-tab value="month">Monthly billing</v-tab>
<v-tab value="year">
Yearly billing
<v-chip
class="ml-2"
color="success"
size="small"
text="Save 2 months"
variant="flat"
/>
</v-tab>
</v-tabs>

<v-item-group v-model="type" class="mb-4" mandatory>
<v-row>
<v-col cols="12" md="6">
<v-item value="month">
<v-item value="solo">
<template #default="{ toggle, isSelected }">
<v-card
:border="isSelected ? 'sm primary opacity-100' : 'sm'"
:color="isSelected ? 'primary' : undefined"
:prepend-icon="isSelected ? `svg:${mdiCheckCircleOutline}` : '$radioOff'"
rounded="lg"
subtitle="$2.99/month"
title="Monthly"
:subtitle="prices.solo[interval]"
title="Solo Developer"
:variant="isSelected ? 'tonal' : 'text'"
@click="toggle"
>
Expand All @@ -23,31 +37,22 @@
</v-col>

<v-col cols="12" md="6">
<v-item value="year">
<v-item value="team">
<template #default="{ toggle, isSelected }">
<v-card
:border="isSelected ? 'sm primary opacity-100' : 'sm'"
:color="isSelected ? 'primary' : undefined"
:disabled="disableTeam"
:prepend-icon="isSelected ? `svg:${mdiCheckCircleOutline}` : '$radioOff'"
rounded="lg"
subtitle="$29.99/year"
title="Yearly"
:subtitle="prices.team[interval]"
title="Team Access"
:variant="isSelected ? 'tonal' : 'text'"
@click="toggle"
>
<template #prepend>
<v-icon class="mt-n6" />
</template>

<template #append>
<v-chip
class="mt-n6"
color="success"
size="small"
text="Save 20%"
variant="flat"
/>
</template>
</v-card>
</template>
</v-item>
Expand All @@ -57,21 +62,35 @@
</template>

<script lang="ts" setup>
// Icons
// Icons
import { mdiCheckCircleOutline } from '@mdi/js'

const dialog = shallowRef(false)
const subscription = defineModel({
type: String as PropType<'month' | 'year' | undefined>,
const interval = defineModel('interval', {
type: String as PropType<'month' | 'year'>,
default: 'month',
})
const type = defineModel('type', {
type: String as PropType<'solo' | 'team'>,
default: 'solo',
})

const one = useOneStore()
const team = useTeamStore()

const disableTeam = computed(() => team.hasTeamAccess && !team.isTeamOwner)

const prices = {
solo: {
month: import.meta.env.VITE_MONTHLY_SOLO_PRICE + ' / Month',
year: import.meta.env.VITE_YEARLY_SOLO_PRICE + ' / Year',
},
team: {
month: import.meta.env.VITE_MONTHLY_TEAM_PRICE + ' / Month',
year: import.meta.env.VITE_YEARLY_TEAM_PRICE + ' / Year',
},
}

watch(dialog, async val => {
if (val) one.subscriptionInfo()
})

watch(() => one.interval, val => {
subscription.value = val
}, { immediate: true })
</script>
Loading