implemented easy-list
Signed-off-by: Stephan Richter <s.richter@srsoftware.de>
This commit is contained in:
@@ -13,6 +13,7 @@
|
||||
import Companies from "./routes/company/Index.svelte";
|
||||
import ContactList from "./routes/contact/Index.svelte";
|
||||
import DocList from "./routes/document/List.svelte";
|
||||
import EasyList from "./routes/task/EasyList.svelte";
|
||||
import EditService from "./routes/user/EditService.svelte";
|
||||
import EditUser from "./routes/user/EditUser.svelte";
|
||||
import FileIndex from "./routes/files/Index.svelte";
|
||||
@@ -104,6 +105,7 @@
|
||||
<Route path="/tags" component={TagList} />
|
||||
<Route path="/tags/use/:tag" component={TagUses} />
|
||||
<Route path="/task" component={TaskList} />
|
||||
<Route path="/tags/easylist/:tag" component={EasyList} />
|
||||
<Route path="/task/:parent_task_id/add_subtask" component={AddTask} />
|
||||
<Route path="/task/:id/edit" component={ViewTask} />
|
||||
<Route path="/task/:id/view" component={ViewTask} />
|
||||
|
||||
104
frontend/src/routes/task/EasyList.svelte
Normal file
104
frontend/src/routes/task/EasyList.svelte
Normal file
@@ -0,0 +1,104 @@
|
||||
<script>
|
||||
import { onMount } from 'svelte';
|
||||
import { useTinyRouter } from 'svelte-tiny-router';
|
||||
import { api, get, patch } from '../../urls.svelte';
|
||||
import { error, yikes } from '../../warn.svelte';
|
||||
import { t } from '../../translations.svelte';
|
||||
|
||||
let { tag } = $props();
|
||||
let filter = $state(null);
|
||||
let search = $derived(filter ? filter.toLowerCase() : null);
|
||||
let input;
|
||||
let tasks = $state(null);
|
||||
let router = useTinyRouter();
|
||||
let sorted = $derived(tasks ? Object.values(tasks).filter(noNoIndex).sort(byName) : null);
|
||||
|
||||
function byName(a,b){
|
||||
return a.name.localeCompare(b.name);
|
||||
}
|
||||
|
||||
|
||||
function close(e,task){
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
update(task,60);
|
||||
}
|
||||
|
||||
async function load(){
|
||||
const url = api(`task/tagged/${tag}`);
|
||||
const res = await get(url);
|
||||
if (res.ok){
|
||||
tasks = await res.json();
|
||||
console.log(Object.values(tasks).map(t => t.name));
|
||||
yikes();
|
||||
input.focus();
|
||||
} else error(res);
|
||||
}
|
||||
|
||||
function noNoIndex(task){
|
||||
return !task.no_index;
|
||||
}
|
||||
|
||||
function oncontextmenu(e){
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
console.log(e);
|
||||
var target = e.target;
|
||||
while (target && !target.href) target=target.parentNode;
|
||||
let href = target.getAttribute('href');
|
||||
if (href) router.navigate(href);
|
||||
return false;
|
||||
}
|
||||
|
||||
function open(e,task){
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
update(task,20);
|
||||
}
|
||||
|
||||
async function update(task,newState){
|
||||
const url = api(`task/${task.id}`);
|
||||
const res = await patch(url,{status:newState});
|
||||
if (res.ok){
|
||||
task.status = newState;
|
||||
yikes();
|
||||
// filter = null; // not sure what is better, resetting or keeping
|
||||
input.focus();
|
||||
|
||||
} else error(res);
|
||||
}
|
||||
|
||||
onMount(load);
|
||||
</script>
|
||||
|
||||
<div class="easylist">
|
||||
<div class="filter">
|
||||
{t('filter')}: <input type="text" bind:value={filter} bind:this={input} />
|
||||
</div>
|
||||
|
||||
<fieldset class="open">
|
||||
<legend>{t('state_open')}</legend>
|
||||
{#if sorted}
|
||||
{#each sorted as task}
|
||||
{#if task.status == 20 && (!filter || task.name.toLowerCase().includes(search))}
|
||||
<a href={`/task/${task.id}/view`} title={task.description.source} onclick={e => close(e,task)} {oncontextmenu} >
|
||||
{task.name}
|
||||
</a>
|
||||
{/if}
|
||||
{/each}
|
||||
{/if}
|
||||
</fieldset>
|
||||
|
||||
<fieldset class="closed">
|
||||
<legend>{t('state_complete')}</legend>
|
||||
{#if sorted}
|
||||
{#each sorted as task}
|
||||
{#if task.status > 20 && (!filter || task.name.toLowerCase().includes(search))}
|
||||
<a href={`/task/${task.id}/view`} title={task.description.source} onclick={e => open(e,task)} {oncontextmenu} >
|
||||
{task.name}
|
||||
</a>
|
||||
{/if}
|
||||
{/each}
|
||||
{/if}
|
||||
</fieldset>
|
||||
</div>
|
||||
Reference in New Issue
Block a user