Skip to content

Commit

Permalink
fix: conditions component autocomplete visibility
Browse files Browse the repository at this point in the history
  • Loading branch information
kevinchappell committed Nov 19, 2024
1 parent 29f8f25 commit 57a9028
Show file tree
Hide file tree
Showing 6 changed files with 52 additions and 29 deletions.
1 change: 1 addition & 0 deletions src/demo/js/options/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ export const editorOptions = {
sessionStorage: true,
editPanelOrder: ['attrs', 'options'],
// controlOnLeft: true,
// onLoad: () => {},
}

export const renderOptions = {
Expand Down
61 changes: 44 additions & 17 deletions src/lib/js/components/autocomplete.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,12 @@ export const componentOptions = selectedId => {
* Output an autocomplete form element
*/
export default class Autocomplete {
/**
* Create an Autocomplete instance
* @param {String} key - The key for the autocomplete instance
* @param {String} value - The initial value for the autocomplete input
* @param {String} i18nKey - The internationalization key for the autocomplete
*/
constructor(key, value, i18nKey) {
this.key = key
this.className = key.replace(/\./g, '-')
Expand Down Expand Up @@ -220,16 +226,16 @@ export default class Autocomplete {
})

this.dom = dom.create({
children: [this.displayField, this.hiddenField, this.list],
children: [this.displayField, this.hiddenField],
className: this.className,
action: {
onRender: () => {
onRender: element => {
this.stage = element.closest('.formeo-stage')
const component = this.value && Components.getAddress(this.value)
this.label = component && getComponentLabel(component)
if (this.label) {
this.displayField.value = this.label
}
this.updateOptions()
},
},
})
Expand All @@ -238,16 +244,17 @@ export default class Autocomplete {
}

updateOptions() {
let options = optionsCache
const now = Date.now()
if (now - lastCache > ANIMATION_SPEED_SLOW) {

if (!options || now - lastCache > ANIMATION_SPEED_SLOW * 10) {
dom.empty(this.list)
this.generateOptions()
options = this.generateOptions()
lastCache = now
}
const options = optionsCache || this.generateOptions()

for (const option of options) {
this.list.appendChild(option)
if (!this.list.children.length) {
this.list.append(...options)
}
}

Expand Down Expand Up @@ -291,13 +298,17 @@ export default class Autocomplete {
return optionsCache
}

/**
* Hides autocomplete list and deselects all the options
* @param {Object} list - list of autocomplete options
*/
hideList(list = this.list) {
animate.slideUp(list, ANIMATION_SPEED_FAST)
this.removeHighlight()
setListPosition() {
const { offsetHeight, offsetWidth } = this.displayField
const containerRect = this.displayField.closest('.formeo-stage').getBoundingClientRect()
const triggerRect = this.displayField.getBoundingClientRect()
const listStyle = {
position: 'absolute',
top: `${triggerRect.y + offsetHeight + window.scrollY - containerRect.y}px`,
left: `${triggerRect.x + window.scrollX - containerRect.x}px`,
width: `${offsetWidth + 1}px`,
}
Object.assign(this.list.style, listStyle)
}

/**
Expand All @@ -306,18 +317,34 @@ export default class Autocomplete {
* @param {Object} selectedOption - option to be selected
*/
showList(selectedOption, list = this.list) {
if (!this.stage.contains(this.list)) {
this.stage.appendChild(this.list)
}
this.setListPosition()
this.selectOption(selectedOption)
animate.slideDown(list, ANIMATION_SPEED_FAST)
}

/**
* Hides autocomplete list and deselects all the options
* @param {Object} list - list of autocomplete options
*/
hideList(list = this.list) {
animate.slideUp(list, ANIMATION_SPEED_FAST)
this.removeHighlight()
if (this.stage.contains(this.list)) {
this.stage.removeChild(this.list)
}
}

/**
* Returns first option from autocomplete list with 'active-option' class
* @param {Object} list - list of autocomplete options
* @return {Object} first list option with 'active-option' class
*/
getActiveOption(list = this.list) {
const activeOption = list.getElementsByClassName('active-option')[0]
if (activeOption && activeOption.style.display !== 'none') {
const activeOption = list.querySelector('.active-option')
if (activeOption?.style.display !== 'none') {
return activeOption
}
return null
Expand Down
1 change: 1 addition & 0 deletions src/lib/js/config.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ export const defaults = {
i18n: {
location: 'https://draggable.github.io/formeo/assets/lang/',
},
onLoad: () => {},
}
},
}
10 changes: 6 additions & 4 deletions src/lib/js/editor.js
Original file line number Diff line number Diff line change
Expand Up @@ -73,12 +73,14 @@ export class FormeoEditor {

promises.push(i18n.init({ ...this.opts.i18n, locale: window.sessionStorage?.getItem(SESSION_LOCALE_KEY) }))

const resolvedPromises = await Promise.all(promises)

if (this.opts.allowEdit) {
this.init()
promises.push(this.init())
}

const resolvedPromises = await Promise.all(promises)

this.opts.onLoad?.(this)

return resolvedPromises
}

Expand All @@ -88,7 +90,7 @@ export class FormeoEditor {
* dom elements, actions events and more.
*/
init() {
Controls.init(this.opts.controls, this.opts.stickyControls).then(controls => {
return Controls.init(this.opts.controls, this.opts.stickyControls).then(controls => {
this.controls = controls
this.load(this.userFormData, this.opts)
this.formId = Components.get('id')
Expand Down
4 changes: 0 additions & 4 deletions src/lib/sass/components/_field-edit.scss
Original file line number Diff line number Diff line change
Expand Up @@ -27,10 +27,6 @@
list-style: decimal;
}

.active-panel {
background-color: color.$white;
}

.field-prop {
display: flex;
}
Expand Down
4 changes: 0 additions & 4 deletions src/lib/sass/components/_panels.scss
Original file line number Diff line number Diff line change
Expand Up @@ -101,10 +101,6 @@
}
}

.f-panel {
background-color: color.$white;
}

.panel-labels {
div {
flex-direction: row;
Expand Down

0 comments on commit 57a9028

Please sign in to comment.