Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Some drop down fixes #10337

Merged
merged 5 commits into from
Jun 21, 2024
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,10 @@
For example, `locale` parameter of `Equal_Ignore_Case` kind in join component.
- [Node previews][10310]: Node may be previewed by hovering output port while
pressing <kbd>Ctrl</kbd> key (<kbd>Cmd</kbd> on macOS).
- [Fixed issue with two arrows being visible at once in drop-down
widget.][10337]
- [Fixed issue where picking "<Numeric literal>" variant in some ports
disallowed changing it again.][10337]

[10064]: https://github.com/enso-org/enso/pull/10064
[10179]: https://github.com/enso-org/enso/pull/10179
Expand All @@ -21,6 +25,7 @@
[10205]: https://github.com/enso-org/enso/pull/10205
[10297]: https://github.com/enso-org/enso/pull/10297
[10310]: https://github.com/enso-org/enso/pull/10310
[10337]: https://github.com/enso-org/enso/pull/10337

#### Enso Standard Library

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ import NumericInputWidget from '@/components/widgets/NumericInputWidget.vue'
import { Score, WidgetInput, defineWidget, widgetProps } from '@/providers/widgetRegistry'
import { WidgetEditHandler } from '@/providers/widgetRegistry/editHandler'
import { Ast } from '@/util/ast'
import { targetIsOutside } from '@/util/autoBlur'
import { unrefElement } from '@vueuse/core'
import { computed, ref, type ComponentInstance } from 'vue'

const props = defineProps(widgetProps(widgetDefinition))
Expand Down Expand Up @@ -38,6 +40,10 @@ const limits = computed(() => {
const editHandler = WidgetEditHandler.New('WidgetNumber', props.input, {
cancel: () => inputComponent.value?.cancel(),
start: () => inputComponent.value?.focus(),
pointerdown(event) {
if (targetIsOutside(event, unrefElement(inputComponent))) editHandler.end()
return false
},
end: () => inputComponent.value?.blur(),
})
</script>
Expand Down Expand Up @@ -78,7 +84,6 @@ export const widgetDefinition = defineWidget(
@update:modelValue="setValue"
@click.stop
@focus="editHandler.start()"
@blur="editHandler.end()"
@input="editHandler.edit($event)"
/>
</template>
Expand Down
35 changes: 29 additions & 6 deletions app/gui2/src/components/GraphEditor/widgets/WidgetSelection.vue
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@ import SizeTransition from '@/components/SizeTransition.vue'
import SvgIcon from '@/components/SvgIcon.vue'
import DropdownWidget, { type DropdownEntry } from '@/components/widgets/DropdownWidget.vue'
import { unrefElement } from '@/composables/events'
import { provideSelectionArrow } from '@/providers/selectionArrow.ts'
import { defineWidget, Score, WidgetInput, widgetProps } from '@/providers/widgetRegistry'
import { injectSelectionArrow, provideSelectionArrow } from '@/providers/selectionArrow.ts'
import { Score, WidgetInput, defineWidget, widgetProps } from '@/providers/widgetRegistry'
import {
multipleChoiceConfiguration,
singleChoiceConfiguration,
Expand All @@ -27,7 +27,7 @@ import { arrayEquals } from '@/util/data/array'
import type { Opt } from '@/util/data/opt'
import { qnLastSegment, tryQualifiedName } from '@/util/qualifiedName'
import { autoUpdate, offset, shift, size, useFloating } from '@floating-ui/vue'
import { computed, proxyRefs, ref, type ComponentInstance, type RendererNode } from 'vue'
import { computed, proxyRefs, ref, watch, type ComponentInstance, type RendererNode } from 'vue'

const props = defineProps(widgetProps(widgetDefinition))
const suggestions = useSuggestionDbStore()
Expand Down Expand Up @@ -221,6 +221,8 @@ const innerWidgetInput = computed<WidgetInput>(() => {
}
})

const parentSelectionArrow = injectSelectionArrow(true)
const suppressArrow = ref(false)
provideSelectionArrow(
proxyRefs({
id: computed(() => {
Expand All @@ -231,17 +233,36 @@ provideSelectionArrow(
if (node instanceof Ast.AutoscopedIdentifier) return node.identifier.id
if (node instanceof Ast.PropertyAccess) return node.rhs.id
if (node instanceof Ast.App) node = node.function
else break
else {
const wrapped = node.wrappedExpression()
if (wrapped != null) node = wrapped
else break
}
}
return null
}),
requestArrow: (target: RendererNode) => {
arrowLocation.value = target
},
handled: false,
get suppressArrow() {
return suppressArrow.value
},
set suppressArrow(value) {
suppressArrow.value = value
},
}),
)

watch(
() => isHovered.value && !suppressArrow.value,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Putting this in a computed showArrow to use here and in the v-if/v-else-if would ensure that if our logic for when to show the arrow changes, it is still consistent with when we inhibit a parent arrow.

(suppressParentsArrow) => {
if (parentSelectionArrow) {
parentSelectionArrow.suppressArrow = suppressParentsArrow
}
},
)

const isMulti = computed(() => props.input.dynamicConfig?.kind === 'Multiple_Choice')
const dropDownInteraction = WidgetEditHandler.New('WidgetSelection', props.input, {
cancel: () => {},
Expand Down Expand Up @@ -318,6 +339,7 @@ function toggleVectorValue(vector: Ast.MutableVector, value: string, previousSta
function expressionTagClicked(tag: ExpressionTag, previousState: boolean) {
const edit = graph.startEdit()
const tagValue = resolveTagExpression(edit, tag)
console.log('expressionTagClicked', tagValue)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Debug logging (here and 1 below)

if (isMulti.value) {
const inputValue = props.input.value
if (inputValue instanceof Ast.Vector) {
Expand All @@ -332,6 +354,7 @@ function expressionTagClicked(tag: ExpressionTag, previousState: boolean) {
props.onUpdate({ edit, portUpdate: { value: vector, origin: props.input.portId } })
}
} else {
console.log('Updating widget', tagValue)
props.onUpdate({ edit, portUpdate: { value: tagValue, origin: props.input.portId } })
}
}
Expand Down Expand Up @@ -399,9 +422,9 @@ declare module '@/providers/widgetRegistry' {
must be already in the DOM when the <Teleport> component is mounted.
So the Teleport itself can be instantiated only when `arrowLocation` is already available. -->
<Teleport v-if="arrowLocation" :to="arrowLocation">
<SvgIcon v-if="isHovered" name="arrow_right_head_only" class="arrow" />
<SvgIcon v-if="isHovered && !suppressArrow" name="arrow_right_head_only" class="arrow" />
</Teleport>
<SvgIcon v-else-if="isHovered" name="arrow_right_head_only" class="arrow" />
<SvgIcon v-else-if="isHovered && !suppressArrow" name="arrow_right_head_only" class="arrow" />
<Teleport v-if="tree.nodeElement" :to="tree.nodeElement">
<SizeTransition height :duration="100">
<DropdownWidget
Expand Down
6 changes: 5 additions & 1 deletion app/gui2/src/providers/selectionArrow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { createContextStore } from '@/providers'
import type { PortId } from '@/providers/portInfo.ts'
import type { AstId, TokenId } from '@/util/ast/abstract.ts'
import { identity } from '@vueuse/core'
import type { RendererElement } from 'vue'
import type { Ref, RendererElement } from 'vue'

interface SelectionArrowInfo {
/** Id of the subexpression that should display arrow underneath. */
Expand All @@ -12,6 +12,10 @@ interface SelectionArrowInfo {
/** Whether or not the arrow provided by this context instance was already requested.
* Do not request the arrow twice, it will be stolen from other elements! */
handled: boolean
/**
*
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing docs

*/
suppressArrow: boolean
}

export { injectFn as injectSelectionArrow, provideFn as provideSelectionArrow }
Expand Down
Loading