working on Autocomplete field for member addition to projects
This commit is contained in:
47
frontend/src/Components/Autocomplete.svelte
Normal file
47
frontend/src/Components/Autocomplete.svelte
Normal file
@@ -0,0 +1,47 @@
|
||||
<script>
|
||||
import { t } from '../translations.svelte.js'
|
||||
import { tick } from "svelte";
|
||||
|
||||
let { getOptionsFor = text => [], onSelect = text => [] } = $props();
|
||||
|
||||
let text = $state('')
|
||||
let options = $state([]);
|
||||
|
||||
async function onkeyup(evt){
|
||||
var select = evt.target;
|
||||
var key = evt.key;
|
||||
var ignore = ['Escape','Tab','ArrowUp','ArrowLeft','ArrowRight']
|
||||
if (ignore.includes(key)) return;
|
||||
if (key == 'ArrowDown'){
|
||||
if (select.selectedIndex == 0) select.selectedIndex=1;
|
||||
return;
|
||||
}
|
||||
if (key == 'Enter'){
|
||||
text = select.value;
|
||||
onSelect(text);
|
||||
options=[];
|
||||
return;
|
||||
}
|
||||
if (key == 'Backspace'){
|
||||
text = text.substring(0,text.length-1)
|
||||
} else if (key.length<2){
|
||||
text += evt.key
|
||||
}
|
||||
options = await getOptionsFor(text);
|
||||
await tick();
|
||||
for (let o of select.getElementsByTagName('option')) o.selected = false;
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
select{
|
||||
min-width: 200px;
|
||||
}
|
||||
</style>
|
||||
<select size={options.length<2?2:options.length+1} {onkeyup} autofocus width="40">
|
||||
<option>{text}</option>
|
||||
{#each options as option,i}
|
||||
<option>{option}</option>
|
||||
{/each}
|
||||
</select>
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
<script>
|
||||
import { onMount } from 'svelte';
|
||||
import { t } from '../translations.svelte.js';
|
||||
import Autocomplete from './Autocomplete.svelte';
|
||||
import PermissionSelector from './PermissionSelector.svelte';
|
||||
let { members, updatePermission = (uid,perm) => console.log({user:uid,perm:perm}) } = $props();
|
||||
let error = $state(null);
|
||||
@@ -18,6 +19,32 @@
|
||||
}
|
||||
}
|
||||
|
||||
async function getOptionsFor(text){
|
||||
const url = `${location.protocol}//${location.host.replace('5173','8080')}/api/user/search`;
|
||||
var resp = await fetch(url,{
|
||||
credentials: 'include',
|
||||
method: 'POST',
|
||||
body: text
|
||||
});
|
||||
if (resp.ok){
|
||||
var json = await resp.json();
|
||||
if (Array.isArray(json)) return json;
|
||||
if (typeof json == 'object'){
|
||||
let names = Object.values(json).map(user => user.name);
|
||||
if (names.length > 10) names.length = 10;
|
||||
return names;
|
||||
}
|
||||
console.warn('not an array:',json);
|
||||
return [];
|
||||
} else {
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
function onSelect(name){
|
||||
console.log({selected_user:name})
|
||||
}
|
||||
|
||||
onMount(loadPermissions);
|
||||
|
||||
</script>
|
||||
@@ -41,7 +68,9 @@
|
||||
<tr>
|
||||
<td></td>
|
||||
<td>{t('add_member')}</td>
|
||||
<td><input type="text" /></td>
|
||||
<td>
|
||||
<Autocomplete {getOptionsFor} {onSelect} />
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
Reference in New Issue
Block a user