mirror of
https://github.com/IT4Change/ohmyform-ui.git
synced 2025-12-13 09:45:50 +00:00
add checkbox field type
fixes https://github.com/ohmyform/ohmyform/issues/138
This commit is contained in:
parent
831e0d7779
commit
5bcaedb556
@ -18,6 +18,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
|
||||
- field logic
|
||||
- add enviroment config
|
||||
- anonymous form submissions (fixes https://github.com/ohmyform/ohmyform/issues/108)
|
||||
- checkbox field type (fixed https://github.com/ohmyform/ohmyform/issues/138)
|
||||
|
||||
### Changed
|
||||
|
||||
|
||||
@ -30,9 +30,20 @@ export const SubmissionValues: React.FC<Props> = (props) => {
|
||||
{
|
||||
title: t('submission:value'),
|
||||
render(_, row) {
|
||||
console.log('row.value', row.value)
|
||||
|
||||
try {
|
||||
const data = JSON.parse(row.value) as { value: string }
|
||||
|
||||
if (Array.isArray(data.value)) {
|
||||
return (
|
||||
<ul>
|
||||
{data.value.map(r => (
|
||||
<li key={r}>{JSON.stringify(r)}</li>
|
||||
))}
|
||||
</ul>
|
||||
)
|
||||
}
|
||||
return data.value
|
||||
} catch (e) {
|
||||
return row.value
|
||||
|
||||
77
components/form/admin/types/checkbox.type.tsx
Normal file
77
components/form/admin/types/checkbox.type.tsx
Normal file
@ -0,0 +1,77 @@
|
||||
import { Button, Col, Form, Input, Row } from 'antd'
|
||||
import React from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import { AdminFieldTypeProps } from './type.props'
|
||||
|
||||
export const CheckboxType: React.FC<AdminFieldTypeProps> = (props) => {
|
||||
const { t } = useTranslation()
|
||||
|
||||
return (
|
||||
<div>
|
||||
<Form.Item
|
||||
label={t('type:checkbox:default')}
|
||||
name={[props.field.name as string, 'value']}
|
||||
labelCol={{ span: 6 }}
|
||||
>
|
||||
<Input />
|
||||
</Form.Item>
|
||||
|
||||
<Form.List name={[props.field.name as string, 'options']}>
|
||||
{(fields, { add, remove }) => {
|
||||
return (
|
||||
<div>
|
||||
{fields.map((field, index) => (
|
||||
<Form.Item
|
||||
wrapperCol={{
|
||||
sm: { offset: index === 0 ? 0 : 6 },
|
||||
}}
|
||||
labelCol={{ span: 6 }}
|
||||
label={index === 0 ? t('type:checkbox:options') : ''}
|
||||
key={field.key}
|
||||
>
|
||||
<Row gutter={16}>
|
||||
<Col span={12}>
|
||||
<Form.Item
|
||||
wrapperCol={{ span: 24 }}
|
||||
name={[field.name, 'title']}
|
||||
style={{ marginBottom: 0 }}
|
||||
>
|
||||
<Input placeholder={t('type:checkbox:titlePlaceholder')} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col span={8}>
|
||||
<Form.Item
|
||||
wrapperCol={{ span: 24 }}
|
||||
name={[field.name, 'value']}
|
||||
style={{ marginBottom: 0 }}
|
||||
rules={[{ required: true, message: t('validation:valueRequired') }]}
|
||||
>
|
||||
<Input placeholder={t('type:checkbox:valuePlaceholder')} />
|
||||
</Form.Item>
|
||||
</Col>
|
||||
<Col span={4}>
|
||||
<Button danger onClick={() => remove(index)}>
|
||||
{t('type:checkbox:removeOption')}
|
||||
</Button>
|
||||
</Col>
|
||||
</Row>
|
||||
</Form.Item>
|
||||
))}
|
||||
|
||||
<Form.Item
|
||||
wrapperCol={{
|
||||
sm: { offset: 6 },
|
||||
}}
|
||||
labelCol={{ span: 6 }}
|
||||
>
|
||||
<Button type={'dashed'} onClick={() => add()}>
|
||||
{t('type:checkbox:addOption')}
|
||||
</Button>
|
||||
</Form.Item>
|
||||
</div>
|
||||
)
|
||||
}}
|
||||
</Form.List>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@ -1,4 +1,5 @@
|
||||
import React from 'react'
|
||||
import { CheckboxType } from './checkbox.type'
|
||||
import { DateType } from './date.type'
|
||||
import { DropdownType } from './dropdown.type'
|
||||
import { EmailType } from './email.type'
|
||||
@ -18,6 +19,7 @@ export const adminTypes: {
|
||||
} = {
|
||||
date: DateType,
|
||||
dropdown: DropdownType,
|
||||
checkbox: CheckboxType,
|
||||
email: EmailType,
|
||||
hidden: HiddenType,
|
||||
link: LinkType,
|
||||
|
||||
41
components/form/types/checkbox.type.tsx
Normal file
41
components/form/types/checkbox.type.tsx
Normal file
@ -0,0 +1,41 @@
|
||||
import { Checkbox, Form } from 'antd'
|
||||
import React from 'react'
|
||||
import { useTranslation } from 'react-i18next'
|
||||
import { StyledCheckbox } from '../../styled/checkbox'
|
||||
import { FieldTypeProps } from './type.props'
|
||||
|
||||
export const CheckboxType: React.FC<FieldTypeProps> = ({ field, design, urlValue }) => {
|
||||
const { t } = useTranslation()
|
||||
|
||||
let initialValue: string = undefined
|
||||
|
||||
if (field.value) {
|
||||
initialValue = field.value
|
||||
}
|
||||
|
||||
if (urlValue) {
|
||||
initialValue = urlValue
|
||||
}
|
||||
|
||||
return (
|
||||
<div>
|
||||
<Form.Item
|
||||
name={[field.id, 'value']}
|
||||
rules={[{ required: field.required, message: t('validation:valueRequired') }]}
|
||||
initialValue={field.options
|
||||
.map((option) => option.value)
|
||||
.find((value) => value === initialValue)}
|
||||
>
|
||||
<Checkbox.Group>
|
||||
{field.options
|
||||
.filter((option) => option.key === null)
|
||||
.map((option) => (
|
||||
<StyledCheckbox design={design} value={option.value} key={option.value}>
|
||||
{option.title || option.value}
|
||||
</StyledCheckbox>
|
||||
))}
|
||||
</Checkbox.Group>
|
||||
</Form.Item>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
@ -1,4 +1,5 @@
|
||||
import React from 'react'
|
||||
import { CheckboxType } from './checkbox.type'
|
||||
import { DateType } from './date.type'
|
||||
import { DropdownType } from './dropdown.type'
|
||||
import { EmailType } from './email.type'
|
||||
@ -17,6 +18,7 @@ export const fieldTypes: {
|
||||
} = {
|
||||
date: DateType,
|
||||
dropdown: DropdownType,
|
||||
checkbox: CheckboxType,
|
||||
email: EmailType,
|
||||
link: LinkType,
|
||||
number: NumberType,
|
||||
|
||||
38
components/styled/checkbox.tsx
Normal file
38
components/styled/checkbox.tsx
Normal file
@ -0,0 +1,38 @@
|
||||
import { Checkbox } from 'antd'
|
||||
import { RadioProps } from 'antd/lib/radio/interface'
|
||||
import React from 'react'
|
||||
import styled from 'styled-components'
|
||||
import { FormPublicDesignFragment } from '../../graphql/fragment/form.public.fragment'
|
||||
|
||||
interface Props extends RadioProps {
|
||||
design: FormPublicDesignFragment
|
||||
}
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-call,@typescript-eslint/no-unsafe-assignment
|
||||
const Field = styled(Checkbox)`
|
||||
color: ${(props: Props) => props.design.colors.answer};
|
||||
border-color: ${(props: Props) => props.design.colors.answer};
|
||||
background: none;
|
||||
|
||||
.ant-radio {
|
||||
.ant-radio-inner {
|
||||
border-color: ${(props: Props) => props.design.colors.answer};
|
||||
|
||||
&::after {
|
||||
background: ${(props: Props) => props.design.colors.answer};
|
||||
}
|
||||
}
|
||||
|
||||
&::after {
|
||||
border-color: ${(props: Props) => props.design.colors.answer};
|
||||
}
|
||||
}
|
||||
|
||||
.anticon {
|
||||
color: ${(props: Props) => props.design.colors.answer};
|
||||
}
|
||||
`
|
||||
|
||||
export const StyledCheckbox: React.FC<Props> = ({ children, ...props }) => {
|
||||
return <Field {...props}>{children}</Field>
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user