flush to develop (#380)

Signed-off-by: Alexander Platov <sas_lord@mail.ru>
Co-authored-by: Denis Bykhov <80476319+BykhovDenis@users.noreply.github.com>
Co-authored-by: Andrey Sobolev <haiodo@gmail.com>
This commit is contained in:
Andrey Platov
2021-11-26 12:28:15 +01:00
committed by GitHub
co-authored by Denis Bykhov Andrey Sobolev
parent cd0e7da28e
commit 68ae2f2e31
23 changed files with 312 additions and 347 deletions
@@ -14,7 +14,7 @@
-->
<script lang="ts">
import { CircleButton, IconAdd, showPopup, Spinner } from '@anticrm/ui'
import { CircleButton, IconAdd, showPopup, Spinner, Link } from '@anticrm/ui'
import type { Doc, Ref, Space, Class, Bag } from '@anticrm/core'
import { setPlatformStatus, unknownError } from '@anticrm/platform'
@@ -24,6 +24,7 @@
import { Table } from '@anticrm/view-resources'
import { uploadFile } from '../utils'
import Upload from './icons/Upload.svelte'
import chunter from '@anticrm/chunter'
@@ -37,12 +38,12 @@
$: query.query(chunter.class.Attachment, { attachedTo: objectId }, result => { attachments = result })
let inputFile: HTMLInputElement
let loading = false
let loading = 0
const client = getClient()
async function createAttachment(file: File) {
loading = true
loading++
try {
const uuid = await uploadFile(space, file, objectId)
console.log('uploaded file uuid', uuid)
@@ -56,16 +57,30 @@
} catch (err: any) {
setPlatformStatus(unknownError(err))
} finally {
loading = false
loading--
}
}
function fileSelected() {
function fileSelected () {
console.log(inputFile.files)
const file = inputFile.files?.[0]
if (file !== undefined) { createAttachment(file) }
const list = inputFile.files
if (list === null || list.length === 0) return
for (let index = 0; index < list.length; index++) {
const file = list.item(index)
if (file !== null) createAttachment(file)
}
}
function fileDrop (e: DragEvent) {
const list = e.dataTransfer?.files
if (list === undefined || list.length === 0) return
for (let index = 0; index < list.length; index++) {
const file = list.item(index)
if (file !== null) createAttachment(file)
}
}
let dragover = false
</script>
<div class="attachments-container">
@@ -76,14 +91,30 @@
{:else}
<CircleButton icon={IconAdd} size={'small'} on:click={ () => { inputFile.click() } } />
{/if}
<input bind:this={inputFile} type="file" name="file" id="file" style="display: none" on:change={fileSelected}/>
<input bind:this={inputFile} multiple type="file" name="file" id="file" style="display: none" on:change={fileSelected}/>
</div>
<Table
_class={chunter.class.Attachment}
config={['', 'lastModified']}
options={ {} }
query={ { attachedTo: objectId } }
/>
{#if attachments.length === 0 && !loading}
<div class="flex-col-center mt-5 resume" class:solid={dragover}
on:dragover|preventDefault={ () => { dragover = true } }
on:dragleave={ () => { dragover = false } }
on:drop|preventDefault|stopPropagation={fileDrop}
on:click={ () => { inputFile.click() } }
>
<Upload size={'large'} />
<div class="small-text content-dark-color mt-2">There are no attachments for this candidate.</div>
<div class="small-text">
Upload or drop files here
</div>
</div>
{:else}
<Table
_class={chunter.class.Attachment}
config={['', 'lastModified']}
options={ {} }
query={ { attachedTo: objectId } }
/>
{/if}
</div>
<style lang="scss">
@@ -99,44 +130,12 @@
}
}
.table-body {
margin-top: .75rem;
th, td {
padding: .75rem 0;
text-align: left;
}
th {
font-weight: 500;
font-size: .75rem;
color: var(--theme-content-dark-color);
}
td {
color: var(--theme-caption-color);
}
.tr-body { border-top: 1px solid var(--theme-button-border-hovered); }
}
.item {
display: flex;
align-items: center;
padding: .75rem 1rem;
}
.file-icon {
margin-right: 1.25rem;
width: 2rem;
height: 2rem;
font-weight: 500;
font-size: 0.625rem;
line-height: 150%;
text-transform: uppercase;
color: #fff;
background-color: var(--primary-button-enabled);
border: 1px solid rgba(0, 0, 0, .1);
border-radius: .5rem;
}
.file-desc {
font-size: 0.75rem;
color: var(--theme-content-dark-color);
.resume {
cursor: pointer;
padding: 1rem;
color: var(--theme-caption-color);
background: rgba(255, 255, 255, .03);
border: 1px dashed rgba(255, 255, 255, .16);
border-radius: .75rem;
}
</style>
@@ -151,7 +151,9 @@
<span><Label label={'Add social links'} /></span>
{:else}
<Channels value={object.channels} size={'small'} />
<CircleButton icon={Edit} size={'small'} transparent on:click={(ev) => showPopup(SocialEditor, { values: object.channels ?? [] }, ev.target, (result) => { object.channels = result })} />
<div class="ml-1">
<CircleButton icon={Edit} size={'small'} transparent on:click={(ev) => showPopup(SocialEditor, { values: object.channels ?? [] }, ev.target, (result) => { object.channels = result })} />
</div>
{/if}
</div>
@@ -73,18 +73,6 @@
</div>
</svelte:fragment> -->
<!-- <div class="flex-row-center">
<div class="avatar">
<div class="border"/>
<Avatar />
</div>
<div class="flex-col">
<div class="name">{formatName(candidate.name)}</div>
<div class="title">For {getVacancyName()}</div>
<div class="city">at Cisco</div>
</div>
</div> -->
<div class="grid-cards">
<CandidateCard {candidate}/>
<VacancyCard {vacancy}/>
@@ -98,57 +86,6 @@
{/if}
<style lang="scss">
@import '../../../../packages/theme/styles/mixins.scss';
.avatar {
flex-shrink: 0;
overflow: hidden;
position: relative;
display: flex;
justify-content: center;
align-items: center;
margin-right: 1.5rem;
width: 6rem;
height: 6rem;
border-radius: 50%;
filter: drop-shadow(0px 14px 44px rgba(28, 23, 22, .8));
cursor: pointer;
&::after {
content: '';
@include bg-layer(var(--theme-avatar-hover), .5);
z-index: -1;
}
&::before {
content: '';
@include bg-layer(var(--theme-avatar-bg), .1);
backdrop-filter: blur(25px);
z-index: -2;
}
.border {
@include bg-fullsize;
border: 2px solid var(--theme-avatar-border);
border-radius: 50%;
}
}
.name {
font-weight: 500;
font-size: 1.25rem;
color: var(--theme-caption-color);
}
.title, .city {
font-weight: 500;
font-size: .75rem;
color: var(--theme-content-color);
}
.title { margin-top: .75rem; }
.resume a {
font-size: .75rem;
color: var(--theme-content-dark-color);
&:hover { color: var(--theme-content-color); }
}
.attachments {
margin-top: 3.5rem;
}
@@ -158,21 +95,4 @@
grid-template-columns: 1fr 1fr;
column-gap: 1.5rem;
}
// .container {
// display: flex;
// flex-direction: column;
// height: 100%;
// background-color: var(--theme-bg-color);
// border-radius: 1.25rem;
// box-shadow: 0px 3.125rem 7.5rem rgba(0, 0, 0, .4);
// .tabs-container {
// flex-grow: 1;
// display: flex;
// flex-direction: column;
// height: fit-content;
// padding: 0 2.5rem 2.5rem;
// }
// }
</style>
@@ -23,7 +23,6 @@
import { Panel } from '@anticrm/panel'
import type { Candidate } from '@anticrm/recruit'
import Contact from './icons/Contact.svelte'
import IconAvatar from './icons/Avatar.svelte'
import Attachments from './Attachments.svelte'
import Edit from './icons/Edit.svelte'
import SocialEditor from './SocialEditor.svelte'
@@ -91,7 +90,9 @@
rightSection = ev.detail.presenter
}
}} />
<CircleButton icon={Edit} size={'small'} selected on:click={(ev) => showPopup(SocialEditor, { values: object.channels ?? [] }, ev.target, (result) => { saveChannels(result) })} />
<div class="ml-1">
<CircleButton icon={Edit} size={'small'} selected on:click={(ev) => showPopup(SocialEditor, { values: object.channels ?? [] }, ev.target, (result) => { saveChannels(result) })} />
</div>
{/if}
</div>
</div>
@@ -106,6 +106,6 @@
align-items: center;
margin-top: 1rem;
.btn { flex-grow: 1; }
.btn + .btn { margin-left: .75rem; }
// .btn + .btn { margin-left: .75rem; }
}
</style>
@@ -0,0 +1,28 @@
<!--
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
export let size: 'small' | 'medium' | 'large'
const fill: string = 'currentColor'
</script>
<svg class="svg-{size}" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24">
<path fill="var(--duotone-color)" d="M18,6.4c-0.1,0-0.2,0-0.3,0c-0.1,0-0.1,0-0.1,0c-0.1,0-0.1,0-0.1,0c0,0,0,0-0.1-0.1c0,0,0,0-0.1-0.1 c0-0.1-0.1-0.2-0.2-0.4c-0.9-1.9-2.8-3.3-5.1-3.3c-2.3,0-4.2,1.4-5.1,3.3C6.8,5.9,6.7,6,6.7,6.1c0,0.1-0.1,0.1-0.1,0.1 C6.6,6.3,6.6,6.3,6.5,6.3c0,0,0,0-0.1,0c0,0,0,0-0.1,0c-0.1,0-0.2,0-0.3,0C4,6.4,2.4,8,2.4,10S4,13.6,6,13.6h6h6 c2,0,3.6-1.6,3.6-3.6S20,6.4,18,6.4z"/>
<g {fill}>
<path d="M18,6.4c-0.1,0-0.2,0-0.3,0c-0.1,0-0.1,0-0.1,0c-0.1,0-0.1,0-0.1,0c0,0,0,0-0.1-0.1c0,0,0,0,0,0c0,0,0,0,0,0 c0,0,0,0,0,0c0,0,0,0,0,0c0,0,0,0-0.1-0.1c0-0.1-0.1-0.2-0.2-0.4c-0.9-1.9-2.8-3.3-5.1-3.3c-2.3,0-4.2,1.4-5.1,3.3 C6.8,5.9,6.7,6,6.7,6.1c0,0.1-0.1,0.1-0.1,0.1c0,0,0,0,0,0C6.6,6.3,6.6,6.3,6.5,6.3c0,0,0,0-0.1,0c0,0,0,0-0.1,0 c-0.1,0-0.2,0-0.3,0C4,6.4,2.4,8,2.4,10S4,13.6,6,13.6h0.6l1.2-1.2H6c-1.3,0-2.4-1.1-2.4-2.4c0-1.3,1.1-2.4,2.4-2.4h0.1 c0.2,0,0.4,0,0.6,0c0.2,0,0.4-0.1,0.6-0.2c0.2-0.1,0.3-0.3,0.4-0.4c0.1-0.1,0.1-0.2,0.2-0.3C7.8,6.5,7.9,6.4,8,6.2l0,0 c0.7-1.5,2.2-2.6,4-2.6s3.3,1.1,4,2.6l0,0c0.1,0.2,0.1,0.3,0.2,0.4c0,0.1,0.1,0.2,0.2,0.3c0.1,0.2,0.2,0.3,0.4,0.4 c0.2,0.1,0.4,0.2,0.6,0.2c0.2,0,0.4,0,0.6,0H18c1.3,0,2.4,1.1,2.4,2.4c0,1.3-1.1,2.4-2.4,2.4h-1.8l1.2,1.2H18c2,0,3.6-1.6,3.6-3.6 S20,6.4,18,6.4z"/>
<path d="M12,11.2l-4.4,4.4l0.8,0.8l3-3V21c0,0.3,0.3,0.6,0.6,0.6s0.6-0.3,0.6-0.6v-7.6l3,3l0.8-0.8L12,11.2z"/>
</g>
</svg>
@@ -15,15 +15,11 @@
-->
<script lang="ts">
import type { IntlString } from '@anticrm/platform'
// import type { IntlString } from '@anticrm/platform'
import { Label } from '@anticrm/ui'
export let label: IntlString
export let placeholder: IntlString
export let value: any
export let focus: boolean
export let maxWidth: string
export let maxWidth: string | undefined = undefined
export let onChange: (value: any) => void
function getLabel(value: boolean | undefined) {
@@ -31,15 +27,21 @@
if (value === false) return 'No'
return 'N/A'
}
</script>
<div class="flex-row-center yesno-container" class:yes={value === true} class:no={value === false} class:unknown={value === undefined} on:click={() => {
if (value === true) value = false
else if (value === false) value = undefined
else value = true
onChange(value)
<div
class="flex-row-center yesno-container"
class:yes={value === true}
class:no={value === false}
class:unknown={value === undefined}
style={(maxWidth) ? `max-width: ${maxWidth};` : ''}
on:click={() => {
if (value === true) value = false
else if (value === false) value = undefined
else value = true
onChange(value)
}}
>
<svg class="svg-small" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
<circle class:yes={value === true} class:no={value === false} cx="8" cy="8" r="6"/>
{#if value === true}
@@ -19,7 +19,7 @@
export let label: IntlString
export let color: string
export let counter: number
// export let counter: number
export let addAction: () => void | undefined
</script>
@@ -71,10 +71,10 @@
height: 100%;
font-weight: 500;
color: var(--theme-caption-color);
span {
font-weight: 400;
color: var(--theme-content-dark-color);
}
// span {
// font-weight: 400;
// color: var(--theme-content-dark-color);
// }
}
.tool {
opacity: .4;
@@ -19,7 +19,7 @@
import type { IntlString } from '@anticrm/platform'
import { EditBox } from '@anticrm/ui'
export let label: IntlString
// export let label: IntlString
export let placeholder: IntlString
export let value: any
export let focus: boolean
@@ -158,6 +158,7 @@
color: var(--theme-caption-color);
border-bottom: 1px solid var(--theme-button-border-hovered);
&:hover .firstCell .menuRow { visibility: visible; }
&:last-child { border-bottom: none; }
}
.fixed .menuRow { visibility: visible; }
</style>
@@ -200,6 +200,7 @@
.checkCell { visibility: visible; }
}
&:hover .firstCell .menuRow { visibility: visible; }
&:last-child { border-bottom: none; }
}
.fixed {