Skip to content

Commit

Permalink
New Insights query UI, Option B (#4233)
Browse files Browse the repository at this point in the history
Co-authored-by: Paolo D'Amico <[email protected]>
  • Loading branch information
samwinslow and paolodamico authored May 7, 2021
1 parent d71e52c commit 2c78919
Show file tree
Hide file tree
Showing 19 changed files with 526 additions and 124 deletions.
89 changes: 6 additions & 83 deletions frontend/src/lib/components/PropertyFilters/PropertyFilters.js
Original file line number Diff line number Diff line change
@@ -1,94 +1,16 @@
import React, { useState } from 'react'
import { PropertyFilter } from './PropertyFilter'
import { Button } from 'antd'
import { useValues, useActions } from 'kea'
import React from 'react'
import { useValues } from 'kea'
import { propertyFilterLogic } from './propertyFilterLogic'
import { Popover, Row } from 'antd'
import { CloseButton } from 'lib/components/CloseButton'
import PropertyFilterButton from './PropertyFilterButton'
import '../../../scenes/actions/Actions.scss'

const FilterRow = React.memo(function FilterRow({
item,
index,
filters,
logic,
pageKey,
showConditionBadge,
totalCount,
popoverPlacement,
}) {
const { remove } = useActions(logic)
let [open, setOpen] = useState(false)
const { key } = item

let handleVisibleChange = (visible) => {
if (!visible && Object.keys(item).length >= 0 && !item[Object.keys(item)[0]]) {
remove(index)
}
setOpen(visible)
}

return (
<Row
align="middle"
className="mt-05 mb-05"
data-attr={'property-filter-' + index}
style={{
maxWidth: '90vw',
}}
>
<Popover
trigger="click"
onVisibleChange={handleVisibleChange}
destroyTooltipOnHide={true}
defaultVisible={false}
visible={open}
placement={popoverPlacement || 'bottomLeft'}
content={
<PropertyFilter
key={index}
index={index}
onComplete={() => setOpen(false)}
logic={logic}
selectProps={{
delayBeforeAutoOpen: 150,
}}
/>
}
>
{key ? (
<PropertyFilterButton onClick={() => setOpen(!open)} item={item} />
) : (
<Button type="default" shape="round" data-attr={'new-prop-filter-' + pageKey}>
Add filter
</Button>
)}
</Popover>
{!!Object.keys(filters[index]).length && (
<CloseButton
className="ml-1"
onClick={() => {
remove(index)
}}
style={{ cursor: 'pointer', float: 'none', marginLeft: 5 }}
/>
)}
{key && showConditionBadge && index + 1 < totalCount && (
<span style={{ marginLeft: 16, right: 16, position: 'absolute' }} className="stateful-badge and">
AND
</span>
)}
</Row>
)
})
import { FilterRow } from './components/FilterRow'
import 'scenes/actions/Actions.scss'

export function PropertyFilters({
endpoint = null,
propertyFilters = null,
onChange = null,
pageKey,
showConditionBadge = false,
disablePopover = false,
popoverPlacement = null,
style = {},
}) {
Expand All @@ -109,6 +31,7 @@ export function PropertyFilters({
filters={filters}
pageKey={pageKey}
showConditionBadge={showConditionBadge}
disablePopover={disablePopover}
popoverPlacement={popoverPlacement}
/>
)
Expand Down
105 changes: 105 additions & 0 deletions frontend/src/lib/components/PropertyFilters/components/FilterRow.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
import React, { useState } from 'react'
import { PropertyFilter } from './PropertyFilter'
import { Button } from 'antd'
import { useActions } from 'kea'
import { Popover, Row } from 'antd'
import { CloseButton } from 'lib/components/CloseButton'
import { DeleteOutlined } from '@ant-design/icons'
import PropertyFilterButton from './PropertyFilterButton'
import 'scenes/actions/Actions.scss'

export const FilterRow = React.memo(function FilterRow({
item,
index,
filters,
logic,
pageKey,
showConditionBadge,
totalCount,
disablePopover = false, // use bare PropertyFilter without popover
popoverPlacement,
}) {
const { remove } = useActions(logic)
let [open, setOpen] = useState(false)
const { key } = item

let handleVisibleChange = (visible) => {
if (!visible && Object.keys(item).length >= 0 && !item[Object.keys(item)[0]]) {
remove(index)
}
setOpen(visible)
}

const propertyFilterCommonProps = {
key: index,
index,
onComplete: () => setOpen(false),
logic,
selectProps: {
delayBeforeAutoOpen: 150,
},
}

return (
<Row
align="middle"
className="mt-05 mb-05"
data-attr={'property-filter-' + index}
style={{
maxWidth: '90vw',
}}
>
{disablePopover ? (
<>
<PropertyFilter {...propertyFilterCommonProps} variant="unified" />
{!!Object.keys(filters[index]).length && (
<Button
type="link"
onClick={() => remove(index)}
style={{
padding: 0,
paddingLeft: 5,
}}
>
<DeleteOutlined />
</Button>
)}
</>
) : (
<>
<Popover
trigger="click"
onVisibleChange={handleVisibleChange}
destroyTooltipOnHide={true}
defaultVisible={false}
visible={open}
placement={popoverPlacement || 'bottomLeft'}
content={<PropertyFilter {...propertyFilterCommonProps} variant="tabs" />}
>
{key ? (
<PropertyFilterButton onClick={() => setOpen(!open)} item={item} />
) : (
<Button type="default" shape="round" data-attr={'new-prop-filter-' + pageKey}>
Add filter
</Button>
)}
</Popover>
{!!Object.keys(filters[index]).length && (
<CloseButton
className="ml-1"
onClick={() => {
remove(index)
}}
style={{ cursor: 'pointer', float: 'none', marginLeft: 5 }}
/>
)}
</>
)}
{key && showConditionBadge && index + 1 < totalCount && (
<span style={{ marginLeft: 16, right: 16, position: 'absolute' }} className="stateful-badge and">
AND
</span>
)}
</Row>
)
})
Original file line number Diff line number Diff line change
@@ -1,20 +1,23 @@
import React, { useState } from 'react'
import { PropertyOperator } from '~/types'
import { Col, Select } from 'antd'
import { Col, Select, SelectProps } from 'antd'
import { isOperatorFlag, isOperatorMulti, operatorMap } from 'lib/utils'
import { PropertyValue } from 'lib/components/PropertyFilters/PropertyValue'
import { PropertyValue } from './PropertyValue'
import { ColProps } from 'antd/lib/col'

export type OperatorValueFilterType = string | number | Array<string | number> | null

interface OperatorValueSelectProps {
type: string
propkey: string
operator: PropertyOperator | undefined
value: string | number | Array<string | number> | null
columnOptions?: ColProps
onChange: (operator: PropertyOperator, value: string | number | Array<string | number> | null) => void
columnOptions?: ColProps | [ColProps, ColProps]
onChange: (operator: PropertyOperator, value: OperatorValueFilterType) => void
operatorSelectProps?: Omit<SelectProps<any>, 'onChange'>
}

interface OperatorSelectProps {
interface OperatorSelectProps extends SelectProps<any> {
operator: PropertyOperator
operators: Array<PropertyOperator>
onChange: (operator: PropertyOperator) => void
Expand All @@ -27,12 +30,13 @@ export function OperatorValueSelect({
value,
columnOptions,
onChange,
operatorSelectProps,
}: OperatorValueSelectProps): JSX.Element {
const [currentOperator, setCurrentOperator] = useState(operator)

return (
<>
<Col {...columnOptions}>
<Col {...(Array.isArray(columnOptions) ? columnOptions[0] : columnOptions)}>
<OperatorSelect
operator={currentOperator || 'exact'}
operators={Object.keys(operatorMap) as Array<PropertyOperator>}
Expand All @@ -52,10 +56,11 @@ export function OperatorValueSelect({
onChange(newOperator, value)
}
}}
{...operatorSelectProps}
/>
</Col>
{!isOperatorFlag(currentOperator || 'exact') && (
<Col {...columnOptions}>
<Col {...(Array.isArray(columnOptions) ? columnOptions[1] : columnOptions)}>
<PropertyValue
type={type}
key={propkey}
Expand All @@ -77,7 +82,7 @@ type CustomOptionsType = {
label: string
}

export function OperatorSelect({ operator, operators, onChange }: OperatorSelectProps): JSX.Element {
export function OperatorSelect({ operator, operators, onChange, ...props }: OperatorSelectProps): JSX.Element {
return (
<Select
style={{ width: '100%' }}
Expand All @@ -92,6 +97,7 @@ export function OperatorSelect({ operator, operators, onChange }: OperatorSelect
const newOperator = op as typeof op & CustomOptionsType
onChange(newOperator.value)
}}
{...props}
>
{operators.map((op) => (
<Select.Option key={op} value={op || 'exact'}>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import React from 'react'
import { SelectGradientOverflowProps } from 'lib/components/SelectGradientOverflow'
import { propertyFilterLogic } from '../propertyFilterLogic'
import { TabbedPropertyFilter } from './TabbedPropertyFilter'
import { UnifiedPropertyFilter } from './UnifiedPropertyFilter'

export interface PropertyFilterInternalProps {
index: number
onComplete: CallableFunction
logic: typeof propertyFilterLogic
selectProps: Partial<SelectGradientOverflowProps>
}

export interface PropertyFilterProps extends PropertyFilterInternalProps {
variant: 'tabs' | 'unified'
}

export function PropertyFilter({ variant = 'tabs', ...props }: PropertyFilterProps): JSX.Element {
switch (variant) {
case 'unified':
return <UnifiedPropertyFilter {...props} />
case 'tabs':
return <TabbedPropertyFilter {...props} />
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { formatPropertyLabel } from 'lib/utils'
import React from 'react'
import { cohortsModel } from '~/models'
import { PropertyFilter } from '~/types'
import { keyMapping } from '../PropertyKeyInfo'
import { keyMapping } from 'lib/components/PropertyKeyInfo'

export interface Props {
item: PropertyFilter
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,10 @@ interface Props {
placeholder: string
autoOpenIfEmpty?: boolean
delayBeforeAutoOpen?: number
dropdownMatchSelectWidth?: boolean | number
}

interface PropertyOptionGroup {
export interface PropertyOptionGroup {
type: 'event' | 'person' | 'element'
label: string
options: Array<{ value: string }>
Expand Down Expand Up @@ -55,6 +56,7 @@ export function PropertySelect({
placeholder,
autoOpenIfEmpty,
delayBeforeAutoOpen,
dropdownMatchSelectWidth = true,
}: Props): JSX.Element {
const [search, setSearch] = useState(false as string | false)
return (
Expand All @@ -78,6 +80,7 @@ export function PropertySelect({
onChange(type, val.replace(/^(event_|person_|element_)/gi, ''))
}}
style={{ width: '100%' }}
dropdownMatchSelectWidth={dropdownMatchSelectWidth}
>
{optionGroups.map(
(group) =>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React, { useState, useEffect } from 'react'
import { AutoComplete, Select } from 'antd'
import { useThrottledCallback } from 'use-debounce'
import api from '../../api'
import api from 'lib/api'
import { isMobile, isOperatorFlag, isOperatorMulti, isOperatorRegex, isValidRegex } from 'lib/utils'
import { SelectGradientOverflow } from 'lib/components/SelectGradientOverflow'

Expand Down
Loading

0 comments on commit 2c78919

Please sign in to comment.