lots of style stuff, can delete guild intros
parent
b8e65797de
commit
a464e48287
|
@ -51,7 +51,7 @@
|
|||
|
||||
{#if canDownloadAny}
|
||||
<div id="cardContent">
|
||||
<div id="uploader">
|
||||
<div id="nestedCardContent">
|
||||
<h3>Download New Intro</h3>
|
||||
{#if !!downloadPromise}
|
||||
{#await downloadPromise}
|
||||
|
@ -76,7 +76,7 @@
|
|||
<button on:click={download}>Download</button>
|
||||
{/if}
|
||||
</div>
|
||||
<div id="uploader">
|
||||
<div id="nestedCardContent">
|
||||
<h3>Upload New Intro</h3>
|
||||
{#if !!uploadPromise}
|
||||
{#await uploadPromise}
|
||||
|
|
|
@ -11,6 +11,7 @@
|
|||
export let exclude = null;
|
||||
export let include = null;
|
||||
export let btnLabel = 'Add';
|
||||
export let btnDanger = false;
|
||||
export let emptyMsg = null;
|
||||
|
||||
let filteredIntroList = [];
|
||||
|
@ -82,16 +83,35 @@
|
|||
let selectedIntros = [];
|
||||
</script>
|
||||
|
||||
<div id="list">
|
||||
{#if !!filteredIntroList && filteredIntroList.length > 0}
|
||||
{#each filteredIntroList as intro (intro.index)}
|
||||
<label out:send={{ key: intro.index }} in:receive={{ key: intro.index }} animate:flip={{ duration: 200 }} id="list-item">
|
||||
<input type="checkbox" bind:group={selectedIntros} name="selectedIntros" value={intro.index}>
|
||||
{intro.name}
|
||||
</label>
|
||||
{/each}
|
||||
{:else}
|
||||
<p style="color: red">{emptyMsg}</p>
|
||||
{/if}
|
||||
<button on:click={onConfirm}>{btnLabel}</button>
|
||||
<div id="nestedCardContent" class="cardLight cardNoShadow">
|
||||
<div id="list">
|
||||
{#if !!filteredIntroList && filteredIntroList.length > 0}
|
||||
{#each filteredIntroList as intro (intro.index)}
|
||||
<label out:send={{ key: intro.index }} in:receive={{ key: intro.index }} animate:flip={{ duration: 200 }} id="list-item">
|
||||
<input type="checkbox" bind:group={selectedIntros} name="selectedIntros" value={intro.index}>
|
||||
{intro.name}
|
||||
</label>
|
||||
{/each}
|
||||
{:else}
|
||||
<p style="color: red">{emptyMsg}</p>
|
||||
{/if}
|
||||
</div>
|
||||
<button style="background-image: linear-gradient(0deg, {btnDanger ? '#a81111' : '#1f1f36'}, {btnDanger ? '#db1616' : '#23233d'});"on:click={onConfirm}>{btnLabel}</button>
|
||||
</div>
|
||||
|
||||
<style>
|
||||
div#list {
|
||||
display: flex;
|
||||
width: 85%;
|
||||
border-radius: 4px;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
background-color: #323259;
|
||||
padding: 1em;
|
||||
overflow-x: hidden;
|
||||
overflow-y: auto;
|
||||
margin: 16px;
|
||||
height: 256px;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { env } from '$env/dynamic/public';
|
||||
|
||||
export const apiCall = async (method, endpoint, token, body) => {
|
||||
export const apiCall = async (method, endpoint, token, body, contentType) => {
|
||||
const headers = (() => {
|
||||
if (!!token) {
|
||||
return { 'token': token };
|
||||
|
@ -12,7 +12,7 @@ export const apiCall = async (method, endpoint, token, body) => {
|
|||
return (await
|
||||
fetch(
|
||||
`${env.PUBLIC_API_URL}/${endpoint}`,
|
||||
{ method: method, headers: headers, body: body })
|
||||
{ method: method, headers: { 'Content-Type': contentType, ...headers }, body: body })
|
||||
|
||||
);
|
||||
};
|
||||
|
@ -48,3 +48,7 @@ export const removeIntro = async (guild, channel, selectedIntros, token) => {
|
|||
export const uploadIntro = async (guild, name, file, token) => {
|
||||
await apiCall('POST', `intros/${guild}/upload?name=${encodeURIComponent(name)}`, token, file);
|
||||
}
|
||||
|
||||
export const deleteIntro = async (guild, selectedIntros, token) => {
|
||||
await apiCall('DELETE', `intros/${guild}/delete`, token, JSON.stringify(selectedIntros), 'application/json');
|
||||
}
|
||||
|
|
20
src/app.html
20
src/app.html
|
@ -23,7 +23,7 @@
|
|||
div#cardContent {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(auto-fit, minmax(500px, 1fr));
|
||||
align-items: center;
|
||||
align-items: stretch;
|
||||
justify-items: center;
|
||||
justify-content: center;
|
||||
background-color: #323259;
|
||||
|
@ -33,14 +33,24 @@
|
|||
gap: 1em;
|
||||
}
|
||||
|
||||
div#list {
|
||||
div#nestedCardContent {
|
||||
display: flex;
|
||||
position: relative;
|
||||
width: 85%;
|
||||
border-radius: 4px;
|
||||
height: fit-content;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
background-color: #2a2a4a;
|
||||
padding: 16px;
|
||||
box-shadow: 1px 3px 4px 1px #1f1f36;
|
||||
}
|
||||
|
||||
div#nestedCardContent.cardNoShadow{
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
div#nestedCardContent.cardLight{
|
||||
background-color: #323259;
|
||||
padding: 1em;
|
||||
}
|
||||
|
||||
button, #list-item {
|
||||
|
@ -68,5 +78,5 @@
|
|||
background-image: linear-gradient(0deg, #40406e, #444475);
|
||||
}
|
||||
</style>
|
||||
<body data-sveltekit-preload-data="hover" style="display: block; margin: 0; width: 100%; overflow-x: hidden; overflow-y: scroll;">%sveltekit.body%</body>
|
||||
<body data-sveltekit-preload-data="hover" style="display: block; margin: 0; width: 100%; overflow-x: hidden; overflow-y: scroll;"><div>%sveltekit.body%</div></body>
|
||||
</html>
|
||||
|
|
|
@ -0,0 +1,61 @@
|
|||
<script>
|
||||
import { member, intros } from '../store.ts';
|
||||
import IntroSelector from '../IntroSelector.svelte';
|
||||
import { slide } from 'svelte/transition';
|
||||
import { deleteIntro } from '../api.js';
|
||||
|
||||
let deletePromise = null;
|
||||
let dashboardVisible = false;
|
||||
|
||||
const apiDeleteIntro = async (guild, selectedIntros) => {
|
||||
await deleteIntro(guild, selectedIntros, $member.token);
|
||||
await member.pullData($member.token);
|
||||
await intros.fetchIntros($member.guilds);
|
||||
};
|
||||
const deleteIntros = (event) => {
|
||||
deletePromise = apiDeleteIntro(event.detail.guild, event.detail.intros);
|
||||
};
|
||||
</script>
|
||||
|
||||
<h3>Wow you're a moderator, here is a cool dashboard for you to use</h3>
|
||||
<div id="cardContent" class="noGrid">
|
||||
<div id="nestedCardContent" class="cardLight cardNoShadow">
|
||||
{#if dashboardVisible}
|
||||
<div id="nestedCardContent" class="cardLight cardNoShadow" transition:slide>
|
||||
<button on:click={() => dashboardVisible = false}>
|
||||
Hide dashboard ^
|
||||
</button>
|
||||
{#if !!deletePromise}
|
||||
{#await deletePromise}
|
||||
{:catch err}
|
||||
<p style="color: red">{err}</p>
|
||||
{/await}
|
||||
{/if}
|
||||
<div id="nestedCardContent">
|
||||
{#each $member.guilds as guild}
|
||||
<h4>{guild.name}</h4>
|
||||
<IntroSelector
|
||||
guild={guild.id}
|
||||
exclude={[]}
|
||||
on:confirm={deleteIntros}
|
||||
btnLabel="Delete Intro From Guild"
|
||||
btnDanger={true}
|
||||
emptyMsg="Your guild doesn't have any intros, try adding some below"
|
||||
/>
|
||||
{/each}
|
||||
</div>
|
||||
</div>
|
||||
{:else}
|
||||
<button on:click={() => dashboardVisible = true}>
|
||||
Show dashboard v
|
||||
</button>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<style>
|
||||
h3 {
|
||||
text-align: center;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -6,6 +6,7 @@
|
|||
import Login from '../Login.svelte';
|
||||
import IntroSelector from '../IntroSelector.svelte';
|
||||
import IntroDownloader from '../IntroDownloader.svelte';
|
||||
import ModDashboard from '../components/ModDashboard.svelte';
|
||||
|
||||
let addIntroPromise = null;
|
||||
let removeIntroPromise = null;
|
||||
|
@ -33,14 +34,16 @@
|
|||
<h1>MemeJoin - A bot for user intros</h1>
|
||||
<p style='text-align:center;'>{$member.username}</p>
|
||||
|
||||
<ModDashboard />
|
||||
<IntroDownloader />
|
||||
<h3>Guild Settings</h3>
|
||||
<div id="cardContent">
|
||||
{#each $member.guilds as guild}
|
||||
<div id="guild">
|
||||
<div id="nestedCardContent" class="cardLight cardNoShadow">
|
||||
<h4>{guild.name}</h4>
|
||||
<div id="guild-settings">
|
||||
<div id="nestedCardContent">
|
||||
{#each guild.channels as channel}
|
||||
<div id="channel-settings">
|
||||
<div id="nestedCardContent" class="cardNoShadow">
|
||||
<h4>{channel.name}</h4>
|
||||
{#await addIntroPromise then result}
|
||||
{:catch err}
|
||||
|
@ -81,7 +84,7 @@
|
|||
{/if}
|
||||
|
||||
<style>
|
||||
h1 {
|
||||
h1, h2, h3 {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
|
@ -110,6 +113,7 @@
|
|||
div#channel-settings {
|
||||
display: flex;
|
||||
width: 85%;
|
||||
height: 95%;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
background-color: #2a2a4a;
|
||||
|
|
Reference in New Issue