Skip to content

Commit

Permalink
Limit security groups selection to a maximum of 5
Browse files Browse the repository at this point in the history
Includes an update to dropdown's multiple selection that fixes a bug
(checkmark wouldn't disappear) that occurred when the maximum is reached.
  • Loading branch information
Sergiu Miclea authored and thenoizz committed Sep 24, 2019
1 parent 728c415 commit 4158401
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 9 deletions.
36 changes: 27 additions & 9 deletions src/components/molecules/Dropdown/Dropdown.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -228,6 +228,7 @@ class Dropdown extends React.Component<Props, State> {
scrollableParent: HTMLElement
buttonRect: ClientRect
itemMouseDown: boolean
checkmarkRefs: { [string]: HTMLElement } = {}

componentDidMount() {
window.addEventListener('mousedown', this.handlePageClick, false)
Expand All @@ -239,6 +240,20 @@ class Dropdown extends React.Component<Props, State> {
}
}

componentWillReceiveProps(newProps: Props) {
if (!this.props.multipleSelection) {
return
}
// Clear checkmark if items are removed in newProps
let newSelectedItems = newProps.selectedItems || []
let oldSelectedItems = this.props.selectedItems || []
let hash = item => `${this.getLabel(item)}-${this.getValue(item) || ''}`
let needsCheckmarkClear = oldSelectedItems.filter(oldItem => !newSelectedItems.find(newItem => hash(oldItem) === hash(newItem)))
needsCheckmarkClear.forEach(clearItem => {
this.toggleCheckmarkAnimation(clearItem, this.checkmarkRefs[hash(clearItem)], true)
})
}

componentWillUpdate() {
if (this.buttonRef) this.buttonRect = this.buttonRef.getBoundingClientRect()
}
Expand Down Expand Up @@ -308,11 +323,17 @@ class Dropdown extends React.Component<Props, State> {
})
}

handleItemClick(item: any, checkmarkRef: HTMLElement) {
handleItemClick(item: any) {
if (!this.props.multipleSelection) {
this.setState({ showDropdownList: false, firstItemHover: false })
} else {
this.toggleCheckmarkAnimation(item, checkmarkRef)
let selected = Boolean(this.props.selectedItems && this.props.selectedItems.find(i =>
this.getValue(i) === this.getValue(item)))
this.toggleCheckmarkAnimation(
item,
this.checkmarkRefs[`${this.getLabel(item)}-${this.getValue(item) || ''}`],
selected
)
}

if (this.props.onChange) {
Expand All @@ -332,15 +353,13 @@ class Dropdown extends React.Component<Props, State> {
}
}

toggleCheckmarkAnimation(item: any, checkmarkRef: HTMLElement) {
toggleCheckmarkAnimation(item: any, checkmarkRef: HTMLElement, selected: boolean) {
if (!item || !checkmarkRef) {
return
}
let multipleSelected = this.props.selectedItems && this.props.selectedItems.find(i =>
this.getValue(i) === this.getValue(item))
let symbol = checkmarkRef.querySelector('#symbol')
if (symbol) {
symbol.style.animationName = multipleSelected ? 'dashOff' : 'dashOn'
symbol.style.animationName = selected ? 'dashOff' : 'dashOn'
}
}

Expand Down Expand Up @@ -415,7 +434,6 @@ class Dropdown extends React.Component<Props, State> {
let duplicatedLabel = duplicatedLabels.find(l => l === label)
let multipleSelected = this.props.selectedItems && this.props.selectedItems
.find(i => this.getValue(i) === value)
let checkmarkRef
let listItem = (
<ListItem
data-test-id="dropdownListItem"
Expand All @@ -425,15 +443,15 @@ class Dropdown extends React.Component<Props, State> {
onMouseUp={() => { this.itemMouseDown = false }}
onMouseEnter={() => { this.handleItemMouseEnter(i) }}
onMouseLeave={() => { this.handleItemMouseLeave(i) }}
onClick={() => { this.handleItemClick(item, checkmarkRef) }}
onClick={() => { this.handleItemClick(item) }}
selected={!this.props.multipleSelection && value === selectedValue}
multipleSelected={this.props.multipleSelection && multipleSelected}
dim={this.props.dimFirstItem && i === 0}
paddingLeft={this.props.multipleSelection ? 8 : 16}
>
{this.props.multipleSelection ? (
<Checkmark
innerRef={ref => { checkmarkRef = ref }}
innerRef={ref => { this.checkmarkRefs[`${label}-${value || ''}`] = ref }}
dangerouslySetInnerHTML={{ __html: checkmarkImage }}
show={multipleSelected}
/>
Expand Down
4 changes: 4 additions & 0 deletions src/components/organisms/WizardNetworks/WizardNetworks.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,7 @@ class WizardNetworks extends React.Component<Props> {
}

renderSecGroupsDropdown(selectedNetwork: ?NetworkMap, nic: NicType) {
const MAX_SELECTED_GROUPS = 5
let hasSecurityGroups: boolean = Boolean(this.props.networks.find(n => n.security_groups && n.security_groups.length))
let securityGroups = selectedNetwork && selectedNetwork.targetNetwork && selectedNetwork.targetNetwork.security_groups
let selectedSecGroups: SecurityGroup[] = (selectedNetwork && selectedNetwork.targetSecurityGroups) || []
Expand All @@ -203,6 +204,9 @@ class WizardNetworks extends React.Component<Props> {
if (!selectedNetwork) {
return
}
if (selectedSecGroups.length > MAX_SELECTED_GROUPS) {
selectedSecGroups.splice(MAX_SELECTED_GROUPS - 1, 1)
}
this.props.onChange(nic, selectedNetwork.targetNetwork, selectedSecGroups)
}}
/>
Expand Down

0 comments on commit 4158401

Please sign in to comment.