@oasisomniverse/vue 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (117) hide show
  1. package/package.json +37 -0
  2. package/src/components/Avatar/AvatarWallet.vue +29 -0
  3. package/src/components/Avatar/EditAvatar.vue +21 -0
  4. package/src/components/Avatar/SearchAvatar.vue +24 -0
  5. package/src/components/Avatar/ViewAvatar.vue +19 -0
  6. package/src/components/AvatarConnect/AvatarConnect.vue +64 -0
  7. package/src/components/AvatarProfile/AvatarProfile.vue +123 -0
  8. package/src/components/ComingSoon/ComingSoon.vue +14 -0
  9. package/src/components/Confirmation/Confirmation.vue +18 -0
  10. package/src/components/Contact/Contact.vue +40 -0
  11. package/src/components/DataScreen/AddData.vue +26 -0
  12. package/src/components/DataScreen/CrossChainManagement.vue +14 -0
  13. package/src/components/DataScreen/LoadData.vue +24 -0
  14. package/src/components/DataScreen/ManageData.vue +14 -0
  15. package/src/components/DataScreen/OffChainManagement.vue +14 -0
  16. package/src/components/DataScreen/SearchData.vue +24 -0
  17. package/src/components/Eggs/Eggs.vue +40 -0
  18. package/src/components/Eggs/ManageEggs.vue +14 -0
  19. package/src/components/Eggs/SearchEggs.vue +24 -0
  20. package/src/components/Eggs/ViewEggs.vue +20 -0
  21. package/src/components/ForgotPassword/ForgotPassword.vue +71 -0
  22. package/src/components/Game/Game.vue +29 -0
  23. package/src/components/Game/SearchProfiles.vue +24 -0
  24. package/src/components/Game/ViewAchievements.vue +25 -0
  25. package/src/components/Game/ViewLeagues.vue +25 -0
  26. package/src/components/Game/ViewTournaments.vue +27 -0
  27. package/src/components/HyperDrive/HyperDrive.vue +46 -0
  28. package/src/components/Karma/SearchKarma.vue +24 -0
  29. package/src/components/Karma/ViewAvatarKarma.vue +20 -0
  30. package/src/components/Karma/ViewKarma.vue +30 -0
  31. package/src/components/Karma/VoteKarma.vue +26 -0
  32. package/src/components/KarmaPanel/KarmaPanel.vue +71 -0
  33. package/src/components/KarmaToast/KarmaToast.vue +29 -0
  34. package/src/components/Login/Login.vue +90 -0
  35. package/src/components/Map/Add2dObjectMap.vue +23 -0
  36. package/src/components/Map/Add3dObjectMap.vue +24 -0
  37. package/src/components/Map/AddQuestToMap.vue +22 -0
  38. package/src/components/Map/DownloadOurWorld.vue +18 -0
  39. package/src/components/Map/ManageMap.vue +14 -0
  40. package/src/components/Map/Map.vue +38 -0
  41. package/src/components/Map/PlotRouteOnMap.vue +25 -0
  42. package/src/components/Map/SearchMap.vue +24 -0
  43. package/src/components/Map/ViewGlobal3dMap.vue +14 -0
  44. package/src/components/Map/ViewHalonsOnMap.vue +27 -0
  45. package/src/components/Map/ViewOappOnMap.vue +14 -0
  46. package/src/components/Map/ViewQuestOnMap.vue +20 -0
  47. package/src/components/MenuMessage/MenuMessage.vue +72 -0
  48. package/src/components/Message/Message.vue +50 -0
  49. package/src/components/Messaging/Messaging.vue +44 -0
  50. package/src/components/Mission/ManageMission.vue +14 -0
  51. package/src/components/Mission/Mission.vue +32 -0
  52. package/src/components/Mission/SearchMission.vue +24 -0
  53. package/src/components/Mission/ViewMission.vue +21 -0
  54. package/src/components/NFT/ContactPopup.vue +36 -0
  55. package/src/components/NFT/ManageOasisNft.vue +14 -0
  56. package/src/components/NFT/NFT.vue +36 -0
  57. package/src/components/NFT/PurchaseOasisNft.vue +21 -0
  58. package/src/components/NFT/PurchaseOasisVirtualLandNft.vue +23 -0
  59. package/src/components/NFT/SearchOasisNft.vue +30 -0
  60. package/src/components/NFT/Solana.vue +27 -0
  61. package/src/components/NFT/ViewOasisNft.vue +20 -0
  62. package/src/components/NavBar/NavBar.vue +71 -0
  63. package/src/components/OApp/CreateOAPP.vue +31 -0
  64. package/src/components/OApp/DeployOAPP.vue +23 -0
  65. package/src/components/OApp/DownloadOurWorld.vue +18 -0
  66. package/src/components/OApp/EditOAPP.vue +21 -0
  67. package/src/components/OApp/InstallOAPP.vue +23 -0
  68. package/src/components/OApp/LaunchOAPP.vue +19 -0
  69. package/src/components/OApp/ManageOAPP.vue +14 -0
  70. package/src/components/OApp/OApp.vue +40 -0
  71. package/src/components/OApp/SearchOAPP.vue +30 -0
  72. package/src/components/ONET/ONET.vue +40 -0
  73. package/src/components/ONODE/ONODE.vue +42 -0
  74. package/src/components/OasisModal/OasisModal.vue +36 -0
  75. package/src/components/Provider/ActivityPub.vue +14 -0
  76. package/src/components/Provider/CompareProviderSpeeds.vue +32 -0
  77. package/src/components/Provider/Eosio.vue +14 -0
  78. package/src/components/Provider/Ethereum.vue +14 -0
  79. package/src/components/Provider/Holochain.vue +14 -0
  80. package/src/components/Provider/Ipfs.vue +14 -0
  81. package/src/components/Provider/ManageAutoFailOver.vue +14 -0
  82. package/src/components/Provider/ManageAutoReplicaton.vue +14 -0
  83. package/src/components/Provider/ManageLoadBalancing.vue +14 -0
  84. package/src/components/Provider/ManageProviders.vue +27 -0
  85. package/src/components/Provider/MongoDb.vue +14 -0
  86. package/src/components/Provider/Neo4j.vue +14 -0
  87. package/src/components/Provider/SearchProviders.vue +24 -0
  88. package/src/components/Provider/Seeds.vue +14 -0
  89. package/src/components/Provider/Solid.vue +14 -0
  90. package/src/components/Provider/SqlLite.vue +14 -0
  91. package/src/components/Provider/ThreeFold.vue +14 -0
  92. package/src/components/Provider/ViewProviderStats.vue +27 -0
  93. package/src/components/Provider/ViewProviders.vue +30 -0
  94. package/src/components/ProviderDropdown/ProviderDropdown.vue +34 -0
  95. package/src/components/Providers/Providers.vue +30 -0
  96. package/src/components/Quest/ManageQuest.vue +14 -0
  97. package/src/components/Quest/Quest.vue +35 -0
  98. package/src/components/Quest/SearchQuest.vue +30 -0
  99. package/src/components/Quest/ViewQuest.vue +23 -0
  100. package/src/components/ResetPassword/ResetPassword.vue +39 -0
  101. package/src/components/SearchAvatars/SearchAvatars.vue +42 -0
  102. package/src/components/Seeds/AcceptInvite.vue +26 -0
  103. package/src/components/Seeds/DonateSeeds.vue +34 -0
  104. package/src/components/Seeds/ManageSeeds.vue +14 -0
  105. package/src/components/Seeds/PayWithSeeds.vue +34 -0
  106. package/src/components/Seeds/RewardSeeds.vue +20 -0
  107. package/src/components/Seeds/SearchSeeds.vue +18 -0
  108. package/src/components/Seeds/Seeds.vue +37 -0
  109. package/src/components/Seeds/SendInvite.vue +34 -0
  110. package/src/components/Seeds/ViewOrganizations.vue +27 -0
  111. package/src/components/Seeds/ViewSeeds.vue +34 -0
  112. package/src/components/Settings/Settings.vue +52 -0
  113. package/src/components/Signup/Signup.vue +121 -0
  114. package/src/components/StarField/StarField.vue +55 -0
  115. package/src/components/VerifyEmail/VerifyEmail.vue +21 -0
  116. package/src/components/Wallet/Wallet.vue +41 -0
  117. package/src/index.ts +143 -0
@@ -0,0 +1,36 @@
1
+ <script setup lang="ts">
2
+ const emit = defineEmits<{ close: [] }>()
3
+ const contacts = [
4
+ { name: 'Alice Wonderland', country: 'UK', group: 'Friends' },
5
+ { name: 'Bob Builder', country: 'USA', group: 'Colleagues' },
6
+ { name: 'Charlie Brown', country: 'Canada', group: 'Friends' },
7
+ { name: 'Diana Prince', country: 'Greece', group: 'Family' },
8
+ ]
9
+ const groups = ['Friends', 'Family', 'Colleagues', 'My List 1', 'My List 2']
10
+ </script>
11
+ <template>
12
+ <div class="p-shell">
13
+ <h2 class="p-title">👥 Contacts</h2>
14
+ <div class="p-group-bar">
15
+ <button v-for="g in groups" :key="g" class="p-group-btn">{{ g }}</button>
16
+ </div>
17
+ <div class="p-table-wrap">
18
+ <table class="p-table">
19
+ <thead><tr><th>Name</th><th>Country</th><th>Group</th></tr></thead>
20
+ <tbody>
21
+ <tr v-for="c in contacts" :key="c.name">
22
+ <td>{{ c.name }}</td><td>{{ c.country }}</td><td>{{ c.group }}</td>
23
+ </tr>
24
+ </tbody>
25
+ </table>
26
+ </div>
27
+ <div class="p-foot-btns">
28
+ <button class="p-foot-btn">Find Avatar</button>
29
+ <button class="p-foot-btn">Create List</button>
30
+ </div>
31
+ <button class="p-btn" @click="emit('close')">Close</button>
32
+ </div>
33
+ </template>
34
+ <style scoped>
35
+ .p-shell{display:flex;flex-direction:column;gap:16px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-group-bar{display:flex;gap:8px;flex-wrap:wrap}.p-group-btn{background:rgba(0,200,255,.08);border:1px solid rgba(0,200,255,.2);border-radius:6px;color:#00c8ff;font-size:12px;font-weight:600;padding:6px 14px;cursor:pointer;transition:background .2s}.p-group-btn:hover{background:rgba(0,200,255,.16)}.p-table-wrap{overflow-x:auto;border-radius:10px;border:1px solid rgba(0,200,255,.15)}.p-table{width:100%;border-collapse:collapse;font-size:13px}.p-table th{background:rgba(0,200,255,.08);color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:11px;font-weight:700;letter-spacing:.06em;padding:10px 12px;text-align:left}.p-table td{color:#c8dff0;padding:9px 12px;border-top:1px solid rgba(255,255,255,.05)}.p-table tr:hover td{background:rgba(0,200,255,.04)}.p-foot-btns{display:flex;gap:10px;justify-content:flex-end}.p-foot-btn{background:rgba(0,200,255,.08);border:1px solid rgba(0,200,255,.2);border-radius:6px;color:#00c8ff;font-size:12px;font-weight:600;padding:7px 16px;cursor:pointer}.p-btn{align-self:flex-end;background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}
36
+ </style>
@@ -0,0 +1,14 @@
1
+ <script setup lang="ts">
2
+ const emit = defineEmits<{ close: [] }>()
3
+ </script>
4
+ <template>
5
+ <div class="p-shell">
6
+ <div class="p-icon">🖼️</div>
7
+ <h2 class="p-title">Manage OASIS NFT</h2>
8
+ <p class="p-body">NFT management tools are coming soon — mint, transfer, burn and list your OASIS NFTs across multiple blockchain providers.</p>
9
+ <button class="p-btn" @click="emit('close')">OK</button>
10
+ </div>
11
+ </template>
12
+ <style scoped>
13
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:44px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-body{font-size:14px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}
14
+ </style>
@@ -0,0 +1,36 @@
1
+ <script setup lang="ts">
2
+ import { ref, computed } from 'vue'
3
+ interface NFT { id: string; name: string; rarity: string; type: string; karma: number; image: string }
4
+ const tabs = ['All', 'Avatar', 'Land', 'Item', 'Art']
5
+ const activeTab = ref('All')
6
+ const nfts = ref<NFT[]>([
7
+ { id: '1', name: 'Cosmic Warrior', rarity: 'Legendary', type: 'Avatar', karma: 500, image: '⚔️' },
8
+ { id: '2', name: 'Forest Realm', rarity: 'Epic', type: 'Land', karma: 250, image: '🌲' },
9
+ { id: '3', name: 'Quantum Blade', rarity: 'Rare', type: 'Item', karma: 100, image: '🗡️' },
10
+ { id: '4', name: 'Nebula Portrait', rarity: 'Common', type: 'Art', karma: 30, image: '🎨' },
11
+ { id: '5', name: 'Light Keeper', rarity: 'Epic', type: 'Avatar', karma: 200, image: '🌟' },
12
+ { id: '6', name: 'Sky Citadel', rarity: 'Rare', type: 'Land', karma: 120, image: '🏰' },
13
+ ])
14
+ const filtered = computed(() => activeTab.value === 'All' ? nfts.value : nfts.value.filter(n => n.type === activeTab.value))
15
+ </script>
16
+ <template>
17
+ <div class="nft-shell">
18
+ <div class="nft-header"><h2 class="nft-title">🖼️ NFTs</h2><p class="nft-sub">Your OASIS non-fungible token collection.</p></div>
19
+ <div class="nft-tabs">
20
+ <button v-for="t in tabs" :key="t" class="nft-tab" :class="{ 'nft-tab--active': activeTab === t }" @click="activeTab = t">{{ t }}</button>
21
+ </div>
22
+ <div class="nft-grid">
23
+ <div v-for="n in filtered" :key="n.id" class="nft-card">
24
+ <div class="nft-img">{{ n.image }}</div>
25
+ <div class="nft-rarity" :class="`nft-rarity--${n.rarity.toLowerCase()}`">{{ n.rarity }}</div>
26
+ <div class="nft-name">{{ n.name }}</div>
27
+ <div class="nft-type">{{ n.type }}</div>
28
+ <div class="nft-karma">+{{ n.karma }} karma</div>
29
+ </div>
30
+ <div v-if="filtered.length === 0" class="nft-empty">No NFTs in this category.</div>
31
+ </div>
32
+ </div>
33
+ </template>
34
+ <style scoped>
35
+ .nft-shell{display:flex;flex-direction:column;gap:18px}.nft-header{text-align:center}.nft-title{font-family:'Orbitron',sans-serif;font-size:20px;color:#fff;margin:0 0 6px}.nft-sub{font-size:13px;color:#7a9bbf;margin:0}.nft-tabs{display:flex;gap:8px;flex-wrap:wrap}.nft-tab{background:rgba(255,255,255,.05);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#7a9bbf;font-family:'Orbitron',sans-serif;font-size:11px;font-weight:700;letter-spacing:.06em;padding:7px 16px;cursor:pointer;transition:all .2s}.nft-tab--active{background:rgba(0,200,255,.15);border-color:#00c8ff;color:#00c8ff}.nft-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(150px,1fr));gap:14px}.nft-card{background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.12);border-radius:12px;padding:14px;display:flex;flex-direction:column;align-items:center;gap:8px;transition:border-color .2s}.nft-card:hover{border-color:rgba(0,200,255,.35)}.nft-img{font-size:44px}.nft-rarity{font-size:10px;font-weight:700;letter-spacing:.1em;text-transform:uppercase;border-radius:999px;padding:3px 10px;border:1px solid currentColor}.nft-rarity--common{color:#7a9bbf;border-color:rgba(122,155,191,.3)}.nft-rarity--rare{color:#5ba8ff;border-color:rgba(91,168,255,.3)}.nft-rarity--epic{color:#b87fff;border-color:rgba(184,127,255,.3)}.nft-rarity--legendary{color:#ffb43c;border-color:rgba(255,180,60,.3)}.nft-name{font-family:'Orbitron',sans-serif;font-size:12px;color:#fff;text-align:center}.nft-type{font-size:11px;color:#7a9bbf}.nft-karma{font-size:12px;color:#48dc82;font-weight:600}.nft-empty{grid-column:1/-1;text-align:center;color:#4a6a88;padding:32px;font-size:14px}
36
+ </style>
@@ -0,0 +1,21 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ name?: string; price?: string; imageUrl?: string; provider?: string }>()
3
+ const emit = defineEmits<{ close: []; purchase: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-nft-preview">{{ imageUrl ? '' : '🖼️' }}</div>
8
+ <h2 class="p-title">{{ name ?? 'OASIS NFT' }}</h2>
9
+ <div class="p-details">
10
+ <div class="p-detail"><span class="p-detail-label">Price</span><span class="p-detail-value">{{ price ?? '0.1 ETH' }}</span></div>
11
+ <div class="p-detail"><span class="p-detail-label">Provider</span><span class="p-detail-value">{{ provider ?? 'Ethereum' }}</span></div>
12
+ </div>
13
+ <div class="p-actions">
14
+ <button class="p-btn-cancel" @click="emit('close')">Cancel</button>
15
+ <button class="p-btn" @click="emit('purchase')">Purchase</button>
16
+ </div>
17
+ </div>
18
+ </template>
19
+ <style scoped>
20
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:18px;padding:32px 20px;text-align:center}.p-nft-preview{width:120px;height:120px;background:linear-gradient(135deg,rgba(0,200,255,.1),rgba(184,127,255,.1));border:1px solid rgba(0,200,255,.2);border-radius:12px;display:flex;align-items:center;justify-content:center;font-size:48px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-details{display:flex;gap:16px}.p-detail{background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.15);border-radius:10px;padding:12px 18px;display:flex;flex-direction:column;gap:4px}.p-detail-label{font-size:11px;color:#7a9bbf;font-weight:600;letter-spacing:.08em;text-transform:uppercase}.p-detail-value{font-family:'Orbitron',sans-serif;font-size:15px;color:#fff;font-weight:700}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
21
+ </style>
@@ -0,0 +1,23 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ parcelId?: string; size?: string; price?: string; coordinates?: string }>()
3
+ const emit = defineEmits<{ close: []; purchase: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-icon">🏝️</div>
8
+ <h2 class="p-title">Purchase Virtual Land NFT</h2>
9
+ <div class="p-details">
10
+ <div class="p-detail"><span class="p-detail-label">Parcel ID</span><span class="p-detail-value">{{ parcelId ?? '#LAND-001' }}</span></div>
11
+ <div class="p-detail"><span class="p-detail-label">Size</span><span class="p-detail-value">{{ size ?? '1 km²' }}</span></div>
12
+ <div class="p-detail"><span class="p-detail-label">Coordinates</span><span class="p-detail-value">{{ coordinates ?? '51.5, -0.1' }}</span></div>
13
+ <div class="p-detail"><span class="p-detail-label">Price</span><span class="p-detail-value p-detail-value--gold">{{ price ?? '0.5 ETH' }}</span></div>
14
+ </div>
15
+ <div class="p-actions">
16
+ <button class="p-btn-cancel" @click="emit('close')">Cancel</button>
17
+ <button class="p-btn" @click="emit('purchase')">Purchase Land</button>
18
+ </div>
19
+ </div>
20
+ </template>
21
+ <style scoped>
22
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:18px;padding:32px 20px;text-align:center}.p-icon{font-size:54px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-details{display:grid;grid-template-columns:1fr 1fr;gap:10px;width:100%;max-width:340px}.p-detail{background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.15);border-radius:10px;padding:12px 16px;display:flex;flex-direction:column;gap:4px;text-align:center}.p-detail-label{font-size:11px;color:#7a9bbf;font-weight:600;letter-spacing:.08em;text-transform:uppercase}.p-detail-value{font-family:'Orbitron',sans-serif;font-size:14px;color:#fff;font-weight:700}.p-detail-value--gold{color:#ffb43c}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
23
+ </style>
@@ -0,0 +1,30 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ const emit = defineEmits<{ close: []; submit: [{ query: string; provider: string; type: string }] }>()
4
+ const form = ref({ query: '', provider: 'All', type: 'All' })
5
+ function handleSubmit() { emit('submit', { ...form.value }) }
6
+ </script>
7
+ <template>
8
+ <div class="p-shell">
9
+ <h2 class="p-title">🔍 Search OASIS NFTs</h2>
10
+ <form class="p-form" @submit.prevent="handleSubmit">
11
+ <div class="p-row"><label class="p-label">Name / ID</label><input class="p-input" v-model="form.query" placeholder="Search NFTs..." /></div>
12
+ <div class="p-row">
13
+ <label class="p-label">Provider</label>
14
+ <select class="p-input" v-model="form.provider">
15
+ <option>All</option><option>Ethereum</option><option>Solana</option><option>Polygon</option>
16
+ </select>
17
+ </div>
18
+ <div class="p-row">
19
+ <label class="p-label">Type</label>
20
+ <select class="p-input" v-model="form.type">
21
+ <option>All</option><option>Avatar</option><option>Land</option><option>Item</option><option>Art</option>
22
+ </select>
23
+ </div>
24
+ <div class="p-actions"><button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button><button class="p-btn" type="submit">Search</button></div>
25
+ </form>
26
+ </div>
27
+ </template>
28
+ <style scoped>
29
+ .p-shell{display:flex;flex-direction:column;gap:20px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-form{display:flex;flex-direction:column;gap:14px}.p-row{display:flex;flex-direction:column;gap:6px}.p-label{font-size:12px;color:#7a9bbf;font-weight:600;letter-spacing:.05em}.p-input{background:rgba(255,255,255,.06);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#fff;font-size:14px;padding:10px 12px;width:100%;box-sizing:border-box;outline:none;transition:border-color .2s}.p-input:focus{border-color:rgba(0,200,255,.5)}.p-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:4px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer}
30
+ </style>
@@ -0,0 +1,27 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ const emit = defineEmits<{ close: []; submit: [{ solana: string; provider: string; toAvatar: string; walletAddress: string; message: string }] }>()
4
+ const form = ref({ solana: '', provider: 'Solana', toAvatar: '', walletAddress: '', message: '' })
5
+ function handleSubmit() { emit('submit', { ...form.value }) }
6
+ </script>
7
+ <template>
8
+ <div class="p-shell">
9
+ <h2 class="p-title">◎ Solana Provider</h2>
10
+ <form class="p-form" @submit.prevent="handleSubmit">
11
+ <div class="p-row"><label class="p-label">Solana</label><input class="p-input" v-model="form.solana" placeholder="Solana address or amount" /></div>
12
+ <div class="p-row">
13
+ <label class="p-label">Provider</label>
14
+ <select class="p-input" v-model="form.provider">
15
+ <option>Solana</option><option>Ethereum</option><option>Holochain</option>
16
+ </select>
17
+ </div>
18
+ <div class="p-row"><label class="p-label">To Avatar</label><input class="p-input" v-model="form.toAvatar" placeholder="Recipient avatar username" /></div>
19
+ <div class="p-row"><label class="p-label">Or Wallet Address</label><input class="p-input" v-model="form.walletAddress" placeholder="0x... or Solana address" /></div>
20
+ <div class="p-row"><label class="p-label">Message</label><textarea class="p-textarea" v-model="form.message" placeholder="Optional message..."></textarea></div>
21
+ <div class="p-actions"><button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button><button class="p-btn" type="submit">Send</button></div>
22
+ </form>
23
+ </div>
24
+ </template>
25
+ <style scoped>
26
+ .p-shell{display:flex;flex-direction:column;gap:20px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-form{display:flex;flex-direction:column;gap:14px}.p-row{display:flex;flex-direction:column;gap:6px}.p-label{font-size:12px;color:#7a9bbf;font-weight:600;letter-spacing:.05em}.p-input,.p-textarea{background:rgba(255,255,255,.06);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#fff;font-size:14px;padding:10px 12px;width:100%;box-sizing:border-box;outline:none;transition:border-color .2s}.p-input:focus,.p-textarea:focus{border-color:rgba(0,200,255,.5)}.p-textarea{min-height:80px;resize:vertical}.p-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:4px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer}
27
+ </style>
@@ -0,0 +1,20 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ name?: string; tokenId?: string; owner?: string; provider?: string; description?: string }>()
3
+ const emit = defineEmits<{ close: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-nft-preview">🖼️</div>
8
+ <h2 class="p-title">{{ name ?? 'OASIS NFT' }}</h2>
9
+ <div class="p-details">
10
+ <div class="p-detail"><span class="p-detail-label">Token ID</span><span class="p-detail-value">{{ tokenId ?? '#0001' }}</span></div>
11
+ <div class="p-detail"><span class="p-detail-label">Owner</span><span class="p-detail-value">{{ owner ?? 'Unknown' }}</span></div>
12
+ <div class="p-detail"><span class="p-detail-label">Provider</span><span class="p-detail-value">{{ provider ?? 'Ethereum' }}</span></div>
13
+ </div>
14
+ <p class="p-body">{{ description ?? 'A unique OASIS NFT existing across the decentralised web.' }}</p>
15
+ <button class="p-btn" @click="emit('close')">Close</button>
16
+ </div>
17
+ </template>
18
+ <style scoped>
19
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-nft-preview{width:100px;height:100px;background:linear-gradient(135deg,rgba(0,200,255,.1),rgba(184,127,255,.1));border:1px solid rgba(0,200,255,.2);border-radius:12px;display:flex;align-items:center;justify-content:center;font-size:40px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-details{display:flex;gap:12px;flex-wrap:wrap;justify-content:center}.p-detail{background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.15);border-radius:10px;padding:10px 14px;display:flex;flex-direction:column;gap:4px;text-align:center}.p-detail-label{font-size:11px;color:#7a9bbf;font-weight:600;letter-spacing:.08em;text-transform:uppercase}.p-detail-value{font-family:'Orbitron',sans-serif;font-size:13px;color:#fff;font-weight:700}.p-body{font-size:13px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}
20
+ </style>
@@ -0,0 +1,71 @@
1
+ <template>
2
+ <nav class="nav" :class="{ scrolled }">
3
+ <a class="nav-brand" href="#">
4
+ <span class="paw">🐾</span>
5
+ <span>NOAH'S <em>ARK</em></span>
6
+ </a>
7
+ <button class="nav-toggle" :class="{ open: menuOpen }" @click="menuOpen = !menuOpen" aria-label="Menu">
8
+ <span /><span /><span />
9
+ </button>
10
+ <ul class="nav-links" :class="{ open: menuOpen }">
11
+ <li v-for="link in links" :key="link.href">
12
+ <a :href="link.href" @click="menuOpen = false">{{ link.label }}</a>
13
+ </li>
14
+ </ul>
15
+ <div class="nav-right">
16
+ <a class="nav-cta" href="#adopt">🐾 Adopt Now</a>
17
+ <AvatarConnect />
18
+ </div>
19
+ </nav>
20
+ </template>
21
+
22
+ <script setup lang="ts">
23
+ import { ref, onMounted, onUnmounted } from 'vue'
24
+ import AvatarConnect from '../AvatarConnect/AvatarConnect.vue'
25
+
26
+ const menuOpen = ref(false)
27
+ const scrolled = ref(false)
28
+
29
+ const links = [
30
+ { href: '#mission', label: 'Mission' },
31
+ { href: '#karma', label: 'Karma' },
32
+ { href: '#profiles', label: 'Profiles' },
33
+ { href: '#network', label: 'Network' },
34
+ { href: '#strays', label: 'Report a Stray' },
35
+ { href: '#community', label: 'Community' },
36
+ { href: '#volunteer', label: 'Volunteer' },
37
+ { href: '#features', label: 'Features' },
38
+ { href: '#healing', label: 'Healing' },
39
+ { href: '#digitalpet', label: 'Digital Pet' },
40
+ { href: '#franchise', label: 'Franchise' },
41
+ ]
42
+
43
+ function onScroll() { scrolled.value = window.scrollY > 40 }
44
+ onMounted(() => window.addEventListener('scroll', onScroll))
45
+ onUnmounted(() => window.removeEventListener('scroll', onScroll))
46
+ </script>
47
+
48
+ <style scoped>
49
+ .nav { position: fixed; top: 0; left: 0; right: 0; z-index: 100; padding: 18px 40px; display: flex; align-items: center; justify-content: space-between; background: rgba(3,7,20,.88); backdrop-filter: blur(12px); border-bottom: 1px solid rgba(0,232,124,.12); transition: padding .3s; }
50
+ .nav.scrolled { padding: 12px 40px; }
51
+ .nav-brand { font-family: 'Orbitron', sans-serif; font-size: 12px; font-weight: 700; letter-spacing: .18em; color: #fff; text-decoration: none; display: flex; align-items: center; gap: 10px; white-space: nowrap; }
52
+ .nav-brand .paw { font-size: 18px; }
53
+ .nav-brand em { color: #00e87c; font-style: normal; }
54
+ .nav-links { display: flex; gap: 16px; list-style: none; padding: 0; }
55
+ .nav-links a { font-family: 'Share Tech Mono', monospace; font-size: 11px; letter-spacing: .07em; color: #a8bfd8; text-decoration: none; text-transform: uppercase; transition: color .2s; }
56
+ .nav-links a:hover { color: #00e87c; }
57
+ .nav-right { display: flex; align-items: center; gap: 10px; flex-shrink: 0; }
58
+ .nav-cta { font-family: 'Share Tech Mono', monospace; font-size: 11px; letter-spacing: .1em; color: #00e87c; border: 1px solid rgba(0,232,124,.35); border-radius: 999px; padding: 8px 18px; text-decoration: none; white-space: nowrap; transition: background .2s; }
59
+ .nav-cta:hover { background: rgba(0,232,124,.08); }
60
+ .nav-toggle { display: none; flex-direction: column; justify-content: center; gap: 5px; width: 32px; height: 32px; background: none; border: none; cursor: pointer; }
61
+ .nav-toggle span { display: block; width: 100%; height: 2px; background: #a8bfd8; transition: transform .25s, opacity .25s; }
62
+ .nav-toggle.open span:nth-child(1) { transform: translateY(7px) rotate(45deg); }
63
+ .nav-toggle.open span:nth-child(2) { opacity: 0; }
64
+ .nav-toggle.open span:nth-child(3) { transform: translateY(-7px) rotate(-45deg); }
65
+ @media (max-width: 1100px) {
66
+ .nav-toggle { display: flex; }
67
+ .nav-links { position: fixed; top: 0; right: 0; height: 100vh; width: min(78vw,320px); flex-direction: column; justify-content: flex-start; align-items: flex-start; gap: 14px; padding: 76px 32px 24px; overflow-y: auto; background: rgba(3,7,20,.97); backdrop-filter: blur(12px); border-left: 1px solid rgba(0,232,124,.12); transform: translateX(100%); transition: transform .3s ease; }
68
+ .nav-links.open { transform: translateX(0); }
69
+ .nav { padding: 14px 20px; }
70
+ }
71
+ </style>
@@ -0,0 +1,31 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ const emit = defineEmits<{ close: []; submit: [{ name: string; description: string; type: string; provider: string }] }>()
4
+ const form = ref({ name: '', description: '', type: 'Web', provider: 'Holochain' })
5
+ function handleSubmit() { emit('submit', { ...form.value }) }
6
+ </script>
7
+ <template>
8
+ <div class="p-shell">
9
+ <h2 class="p-title">✨ Create OAPP</h2>
10
+ <form class="p-form" @submit.prevent="handleSubmit">
11
+ <div class="p-row"><label class="p-label">OAPP Name</label><input class="p-input" v-model="form.name" placeholder="My OASIS Application" /></div>
12
+ <div class="p-row"><label class="p-label">Description</label><textarea class="p-textarea" v-model="form.description" placeholder="What does this OAPP do?"></textarea></div>
13
+ <div class="p-row">
14
+ <label class="p-label">Type</label>
15
+ <select class="p-input" v-model="form.type">
16
+ <option>Web</option><option>Game</option><option>AR</option><option>VR</option><option>Mobile</option>
17
+ </select>
18
+ </div>
19
+ <div class="p-row">
20
+ <label class="p-label">Provider</label>
21
+ <select class="p-input" v-model="form.provider">
22
+ <option>Holochain</option><option>Ethereum</option><option>IPFS</option><option>MongoDB</option>
23
+ </select>
24
+ </div>
25
+ <div class="p-actions"><button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button><button class="p-btn" type="submit">Create</button></div>
26
+ </form>
27
+ </div>
28
+ </template>
29
+ <style scoped>
30
+ .p-shell{display:flex;flex-direction:column;gap:20px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-form{display:flex;flex-direction:column;gap:14px}.p-row{display:flex;flex-direction:column;gap:6px}.p-label{font-size:12px;color:#7a9bbf;font-weight:600;letter-spacing:.05em}.p-input,.p-textarea{background:rgba(255,255,255,.06);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#fff;font-size:14px;padding:10px 12px;width:100%;box-sizing:border-box;outline:none;transition:border-color .2s}.p-input:focus,.p-textarea:focus{border-color:rgba(0,200,255,.5)}.p-textarea{min-height:80px;resize:vertical}.p-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:4px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer}
31
+ </style>
@@ -0,0 +1,23 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ name?: string; version?: string }>()
3
+ const emit = defineEmits<{ close: []; deploy: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-icon">🚀</div>
8
+ <h2 class="p-title">Deploy OAPP</h2>
9
+ <p class="p-body">Ready to deploy <strong>{{ name ?? 'this OAPP' }}</strong> v{{ version ?? '1.0.0' }} to the OASIS network?</p>
10
+ <div class="p-checklist">
11
+ <div class="p-check">✅ Code compiled</div>
12
+ <div class="p-check">✅ Tests passed</div>
13
+ <div class="p-check">✅ Provider configured</div>
14
+ </div>
15
+ <div class="p-actions">
16
+ <button class="p-btn-cancel" @click="emit('close')">Cancel</button>
17
+ <button class="p-btn" @click="emit('deploy')">Deploy</button>
18
+ </div>
19
+ </div>
20
+ </template>
21
+ <style scoped>
22
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:48px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-body{font-size:14px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-checklist{display:flex;flex-direction:column;gap:8px;align-self:stretch;background:rgba(0,200,255,.04);border:1px solid rgba(0,200,255,.12);border-radius:10px;padding:14px}.p-check{font-size:13px;color:#c8dff0;text-align:left}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
23
+ </style>
@@ -0,0 +1,18 @@
1
+ <script setup lang="ts">
2
+ const emit = defineEmits<{ close: []; download: [] }>()
3
+ </script>
4
+ <template>
5
+ <div class="p-shell">
6
+ <div class="p-icon">🌍</div>
7
+ <h2 class="p-title">Download Our World</h2>
8
+ <p class="p-body">Download Our World to run it locally and develop OAPPs against a local OASIS node. Includes the full OASIS API runtime and development tools.</p>
9
+ <div class="p-size">Estimated size: <strong>4.2 GB</strong></div>
10
+ <div class="p-actions">
11
+ <button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button>
12
+ <button class="p-btn" @click="emit('download')">Download</button>
13
+ </div>
14
+ </div>
15
+ </template>
16
+ <style scoped>
17
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:54px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-body{font-size:14px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-size{font-size:13px;color:#7a9bbf;background:rgba(0,200,255,.06);border:1px solid rgba(0,200,255,.15);border-radius:8px;padding:8px 16px}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
18
+ </style>
@@ -0,0 +1,21 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ defineProps<{ initialName?: string; initialDescription?: string }>()
4
+ const emit = defineEmits<{ close: []; submit: [{ name: string; description: string; version: string }] }>()
5
+ const form = ref({ name: '', description: '', version: '1.0.0' })
6
+ function handleSubmit() { emit('submit', { ...form.value }) }
7
+ </script>
8
+ <template>
9
+ <div class="p-shell">
10
+ <h2 class="p-title">✏️ Edit OAPP</h2>
11
+ <form class="p-form" @submit.prevent="handleSubmit">
12
+ <div class="p-row"><label class="p-label">OAPP Name</label><input class="p-input" v-model="form.name" :placeholder="initialName ?? 'OAPP name'" /></div>
13
+ <div class="p-row"><label class="p-label">Description</label><textarea class="p-textarea" v-model="form.description" :placeholder="initialDescription ?? 'Description'"></textarea></div>
14
+ <div class="p-row"><label class="p-label">Version</label><input class="p-input" v-model="form.version" placeholder="1.0.0" /></div>
15
+ <div class="p-actions"><button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button><button class="p-btn" type="submit">Save</button></div>
16
+ </form>
17
+ </div>
18
+ </template>
19
+ <style scoped>
20
+ .p-shell{display:flex;flex-direction:column;gap:20px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-form{display:flex;flex-direction:column;gap:14px}.p-row{display:flex;flex-direction:column;gap:6px}.p-label{font-size:12px;color:#7a9bbf;font-weight:600;letter-spacing:.05em}.p-input,.p-textarea{background:rgba(255,255,255,.06);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#fff;font-size:14px;padding:10px 12px;width:100%;box-sizing:border-box;outline:none;transition:border-color .2s}.p-input:focus,.p-textarea:focus{border-color:rgba(0,200,255,.5)}.p-textarea{min-height:80px;resize:vertical}.p-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:4px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer}
21
+ </style>
@@ -0,0 +1,23 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ name?: string; version?: string; size?: string }>()
3
+ const emit = defineEmits<{ close: []; install: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-icon">📦</div>
8
+ <h2 class="p-title">Install OAPP</h2>
9
+ <div class="p-card">
10
+ <div class="p-card-row"><span class="p-card-label">Name</span><span class="p-card-value">{{ name ?? 'OAPP' }}</span></div>
11
+ <div class="p-card-row"><span class="p-card-label">Version</span><span class="p-card-value">{{ version ?? '1.0.0' }}</span></div>
12
+ <div class="p-card-row"><span class="p-card-label">Size</span><span class="p-card-value">{{ size ?? '2.3 MB' }}</span></div>
13
+ </div>
14
+ <p class="p-body">This OAPP will be installed to your OASIS avatar and made available in Our World.</p>
15
+ <div class="p-actions">
16
+ <button class="p-btn-cancel" @click="emit('close')">Cancel</button>
17
+ <button class="p-btn" @click="emit('install')">Install</button>
18
+ </div>
19
+ </div>
20
+ </template>
21
+ <style scoped>
22
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:48px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-card{width:100%;max-width:300px;background:rgba(0,200,255,.04);border:1px solid rgba(0,200,255,.15);border-radius:10px;overflow:hidden}.p-card-row{display:flex;justify-content:space-between;align-items:center;padding:10px 14px;border-bottom:1px solid rgba(0,200,255,.08)}.p-card-row:last-child{border-bottom:none}.p-card-label{font-size:12px;color:#7a9bbf;font-weight:600}.p-card-value{font-size:13px;color:#fff;font-weight:600}.p-body{font-size:13px;color:#a8bfd8;line-height:1.6;margin:0;max-width:340px}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
23
+ </style>
@@ -0,0 +1,19 @@
1
+ <script setup lang="ts">
2
+ defineProps<{ name?: string; description?: string }>()
3
+ const emit = defineEmits<{ close: []; launch: [] }>()
4
+ </script>
5
+ <template>
6
+ <div class="p-shell">
7
+ <div class="p-icon">▶️</div>
8
+ <h2 class="p-title">Launch OAPP</h2>
9
+ <p class="p-body">You are about to launch <strong>{{ name ?? 'this OAPP' }}</strong>. It will open within the OASIS Omniverse.</p>
10
+ <p class="p-desc" v-if="description">{{ description }}</p>
11
+ <div class="p-actions">
12
+ <button class="p-btn-cancel" @click="emit('close')">Cancel</button>
13
+ <button class="p-btn" @click="emit('launch')">Launch</button>
14
+ </div>
15
+ </div>
16
+ </template>
17
+ <style scoped>
18
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:48px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-body{font-size:14px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-desc{font-size:13px;color:#7a9bbf;line-height:1.5;margin:0;max-width:360px}.p-actions{display:flex;gap:12px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer}
19
+ </style>
@@ -0,0 +1,14 @@
1
+ <script setup lang="ts">
2
+ const emit = defineEmits<{ close: [] }>()
3
+ </script>
4
+ <template>
5
+ <div class="p-shell">
6
+ <div class="p-icon">⚙️</div>
7
+ <h2 class="p-title">Manage OAPP</h2>
8
+ <p class="p-body">Advanced OAPP management tools are coming soon — configure permissions, update dependencies, manage subscriptions, and monitor usage analytics.</p>
9
+ <button class="p-btn" @click="emit('close')">OK</button>
10
+ </div>
11
+ </template>
12
+ <style scoped>
13
+ .p-shell{display:flex;flex-direction:column;align-items:center;gap:16px;padding:32px 20px;text-align:center}.p-icon{font-size:44px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-body{font-size:14px;color:#a8bfd8;line-height:1.6;margin:0;max-width:360px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:11px 28px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}
14
+ </style>
@@ -0,0 +1,40 @@
1
+ <script setup lang="ts">
2
+ import { ref, computed } from 'vue'
3
+ interface OApp { id: string; name: string; description: string; category: string; icon: string; karma: number; launched: boolean }
4
+ const search = ref('')
5
+ const oapps = ref<OApp[]>([
6
+ { id: '1', name: 'OLAND', description: 'Virtual land management and terraforming in the OASIS.', category: 'Metaverse', icon: '🌍', karma: 200, launched: false },
7
+ { id: '2', name: 'OMARKET', description: 'Decentralised marketplace for NFTs and digital goods.', category: 'Commerce', icon: '🛒', karma: 150, launched: false },
8
+ { id: '3', name: 'OCHAT', description: 'Encrypted peer-to-peer messaging on the ONET.', category: 'Social', icon: '💬', karma: 80, launched: false },
9
+ { id: '4', name: 'OQUESTS', description: 'Daily quests and challenges for karma rewards.', category: 'Gaming', icon: '⚔️', karma: 300, launched: false },
10
+ ])
11
+ const filtered = computed(() => {
12
+ const q = search.value.toLowerCase()
13
+ return oapps.value.filter(a => a.name.toLowerCase().includes(q) || a.description.toLowerCase().includes(q))
14
+ })
15
+ function toggle(a: OApp) { a.launched = !a.launched }
16
+ </script>
17
+ <template>
18
+ <div class="oapp-shell">
19
+ <div class="oapp-header"><h2 class="oapp-title">📱 OApps</h2><p class="oapp-sub">Decentralised apps built on the OASIS network.</p></div>
20
+ <input class="oasis-input" type="text" v-model="search" placeholder="Search OApps…" />
21
+ <div class="oapp-grid">
22
+ <div v-for="a in filtered" :key="a.id" class="oapp-card">
23
+ <div class="oapp-icon">{{ a.icon }}</div>
24
+ <div class="oapp-info">
25
+ <div class="oapp-name">{{ a.name }}</div>
26
+ <div class="oapp-cat">{{ a.category }}</div>
27
+ <div class="oapp-desc">{{ a.description }}</div>
28
+ </div>
29
+ <div class="oapp-footer">
30
+ <div class="oapp-karma">+{{ a.karma }} karma</div>
31
+ <button class="oapp-btn" :class="{ 'oapp-btn--launched': a.launched }" @click="toggle(a)">{{ a.launched ? 'Quit' : 'Launch' }}</button>
32
+ </div>
33
+ </div>
34
+ <div v-if="filtered.length === 0" class="oapp-empty">No OApps found.</div>
35
+ </div>
36
+ </div>
37
+ </template>
38
+ <style scoped>
39
+ .oapp-shell{display:flex;flex-direction:column;gap:18px}.oapp-header{text-align:center}.oapp-title{font-family:'Orbitron',sans-serif;font-size:20px;color:#fff;margin:0 0 6px}.oapp-sub{font-size:13px;color:#7a9bbf;margin:0}.oasis-input{width:100%;background:rgba(255,255,255,.05);border:1px solid rgba(0,200,255,.2);border-radius:8px;padding:10px 14px;color:#fff;font-size:14px;outline:none;box-sizing:border-box;transition:border-color .2s;font-family:inherit}.oasis-input:focus{border-color:rgba(0,200,255,.5)}.oapp-grid{display:flex;flex-direction:column;gap:12px}.oapp-card{display:flex;align-items:flex-start;gap:14px;background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.12);border-radius:12px;padding:16px;transition:border-color .2s}.oapp-card:hover{border-color:rgba(0,200,255,.3)}.oapp-icon{font-size:32px;flex-shrink:0}.oapp-info{flex:1}.oapp-name{font-family:'Orbitron',sans-serif;font-size:13px;color:#fff;margin-bottom:3px}.oapp-cat{font-size:11px;color:#5ba8ff;text-transform:uppercase;letter-spacing:.06em;margin-bottom:5px}.oapp-desc{font-size:12px;color:#7a9bbf;line-height:1.5}.oapp-footer{display:flex;flex-direction:column;align-items:flex-end;gap:8px;flex-shrink:0}.oapp-karma{font-size:11px;color:#48dc82;font-weight:600;white-space:nowrap}.oapp-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:7px;color:#fff;font-family:'Orbitron',sans-serif;font-size:11px;font-weight:700;letter-spacing:.08em;padding:7px 16px;cursor:pointer;transition:opacity .2s;white-space:nowrap}.oapp-btn--launched{background:rgba(255,80,80,.2);border:1px solid rgba(255,80,80,.4);color:#ff6b6b}.oapp-empty{text-align:center;color:#4a6a88;font-size:14px;padding:32px}
40
+ </style>
@@ -0,0 +1,30 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ const emit = defineEmits<{ close: []; submit: [{ query: string; type: string; provider: string }] }>()
4
+ const form = ref({ query: '', type: 'All', provider: 'All' })
5
+ function handleSubmit() { emit('submit', { ...form.value }) }
6
+ </script>
7
+ <template>
8
+ <div class="p-shell">
9
+ <h2 class="p-title">🔍 Search OAPPs</h2>
10
+ <form class="p-form" @submit.prevent="handleSubmit">
11
+ <div class="p-row"><label class="p-label">OAPP Name</label><input class="p-input" v-model="form.query" placeholder="Search OAPPs..." /></div>
12
+ <div class="p-row">
13
+ <label class="p-label">Type</label>
14
+ <select class="p-input" v-model="form.type">
15
+ <option>All</option><option>Web</option><option>Game</option><option>AR</option><option>VR</option><option>Mobile</option>
16
+ </select>
17
+ </div>
18
+ <div class="p-row">
19
+ <label class="p-label">Provider</label>
20
+ <select class="p-input" v-model="form.provider">
21
+ <option>All</option><option>Holochain</option><option>Ethereum</option><option>IPFS</option>
22
+ </select>
23
+ </div>
24
+ <div class="p-actions"><button class="p-btn-cancel" type="button" @click="emit('close')">Cancel</button><button class="p-btn" type="submit">Search</button></div>
25
+ </form>
26
+ </div>
27
+ </template>
28
+ <style scoped>
29
+ .p-shell{display:flex;flex-direction:column;gap:20px;padding:24px 20px}.p-title{font-family:'Orbitron',sans-serif;font-size:18px;color:#fff;margin:0}.p-form{display:flex;flex-direction:column;gap:14px}.p-row{display:flex;flex-direction:column;gap:6px}.p-label{font-size:12px;color:#7a9bbf;font-weight:600;letter-spacing:.05em}.p-input{background:rgba(255,255,255,.06);border:1px solid rgba(0,200,255,.2);border-radius:8px;color:#fff;font-size:14px;padding:10px 12px;width:100%;box-sizing:border-box;outline:none;transition:border-color .2s}.p-input:focus{border-color:rgba(0,200,255,.5)}.p-actions{display:flex;gap:10px;justify-content:flex-end;margin-top:4px}.p-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer;transition:opacity .2s}.p-btn:hover{opacity:.85}.p-btn-cancel{background:transparent;border:1px solid rgba(0,200,255,.3);border-radius:8px;color:#00c8ff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:10px 24px;cursor:pointer}
30
+ </style>
@@ -0,0 +1,40 @@
1
+ <script setup lang="ts">
2
+ import { ref } from 'vue'
3
+ const connected = ref(false)
4
+ const stats = [
5
+ { label: 'Peers', value: '2,847' },
6
+ { label: 'Speed', value: '1.2 Gb/s' },
7
+ { label: 'Encrypted', value: '100%' },
8
+ ]
9
+ const peers = [
10
+ { id: '1', name: 'AvatarX_7291', location: 'New York, US', ping: 14 },
11
+ { id: '2', name: 'StarKeeper_99', location: 'London, UK', ping: 32 },
12
+ { id: '3', name: 'NeonRider_404', location: 'Tokyo, JP', ping: 67 },
13
+ ]
14
+ </script>
15
+ <template>
16
+ <div class="onet-shell">
17
+ <div class="onet-header"><h2 class="onet-title">🌐 ONET</h2><p class="onet-sub">The OASIS decentralised internet layer.</p></div>
18
+ <div class="onet-status-card" :class="{ 'onet-status--active': connected }">
19
+ <div class="onet-status-dot" :class="{ 'onet-status-dot--active': connected }"></div>
20
+ <div class="onet-status-info"><div class="onet-status-label">ONET Connection</div><div class="onet-status-val">{{ connected ? 'Connected' : 'Disconnected' }}</div></div>
21
+ <button class="onet-btn" @click="connected = !connected">{{ connected ? 'Disconnect' : 'Connect' }}</button>
22
+ </div>
23
+ <template v-if="connected">
24
+ <div class="onet-stats">
25
+ <div v-for="s in stats" :key="s.label" class="onet-stat"><div class="onet-stat-val">{{ s.value }}</div><div class="onet-stat-label">{{ s.label }}</div></div>
26
+ </div>
27
+ <div class="onet-peers-header">Active Peers</div>
28
+ <div class="onet-peers">
29
+ <div v-for="p in peers" :key="p.id" class="onet-peer">
30
+ <div class="onet-peer-icon">👤</div>
31
+ <div class="onet-peer-info"><div class="onet-peer-name">{{ p.name }}</div><div class="onet-peer-location">{{ p.location }}</div></div>
32
+ <div class="onet-peer-ping">{{ p.ping }}ms</div>
33
+ </div>
34
+ </div>
35
+ </template>
36
+ </div>
37
+ </template>
38
+ <style scoped>
39
+ .onet-shell{display:flex;flex-direction:column;gap:18px}.onet-header{text-align:center}.onet-title{font-family:'Orbitron',sans-serif;font-size:20px;color:#fff;margin:0 0 6px}.onet-sub{font-size:13px;color:#7a9bbf;margin:0}.onet-status-card{display:flex;align-items:center;gap:14px;background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.12);border-radius:12px;padding:16px}.onet-status--active{border-color:rgba(72,220,130,.3)}.onet-status-dot{width:12px;height:12px;border-radius:50%;background:#4a6a88;flex-shrink:0;transition:all .3s}.onet-status-dot--active{background:#48dc82;box-shadow:0 0 10px #48dc82}.onet-status-info{flex:1}.onet-status-label{font-size:12px;color:#7a9bbf;text-transform:uppercase;letter-spacing:.06em}.onet-status-val{font-family:'Orbitron',sans-serif;font-size:14px;color:#fff;margin-top:3px}.onet-btn{background:linear-gradient(135deg,#00c8ff,#0080ff);border:none;border-radius:8px;color:#fff;font-family:'Orbitron',sans-serif;font-size:12px;font-weight:700;letter-spacing:.08em;padding:9px 18px;cursor:pointer}.onet-stats{display:grid;grid-template-columns:repeat(3,1fr);gap:12px}.onet-stat{background:rgba(255,255,255,.04);border:1px solid rgba(0,200,255,.1);border-radius:10px;padding:14px;text-align:center}.onet-stat-val{font-family:'Share Tech Mono',monospace;font-size:18px;color:#00c8ff;font-weight:600}.onet-stat-label{font-size:11px;color:#7a9bbf;margin-top:4px;text-transform:uppercase;letter-spacing:.06em}.onet-peers-header{font-family:'Orbitron',sans-serif;font-size:12px;color:#7a9bbf;letter-spacing:.06em;text-transform:uppercase}.onet-peers{display:flex;flex-direction:column;gap:8px}.onet-peer{display:flex;align-items:center;gap:12px;padding:10px 14px;background:rgba(255,255,255,.03);border:1px solid rgba(0,200,255,.07);border-radius:8px}.onet-peer-icon{font-size:20px}.onet-peer-info{flex:1}.onet-peer-name{font-size:13px;color:#e0f0ff}.onet-peer-location{font-size:11px;color:#4a6a88;margin-top:2px}.onet-peer-ping{font-family:'Share Tech Mono',monospace;font-size:12px;color:#48dc82}
40
+ </style>