Unverified Commit c752f571 authored by Andrey Azov's avatar Andrey Azov Committed by GitHub
Browse files

Close z-menu upon clicking anywhere outside it (#154)

parent 939f7a74
Pipeline #34478 passed with stages
in 5 minutes and 6 seconds
......@@ -20,6 +20,7 @@ pub enum Action {
SetStick(String),
SetState(String,bool),
Settled,
ActivityOutsideZMenu,
ZMenuClickCheck(CPixel),
ShowZMenu(String,String,Dot<i32,i32>,JSONValue),
SetFocus(String),
......@@ -47,6 +48,7 @@ impl Action {
Action::ZoomTo(_) => 10,
Action::Move(_) => 10,
Action::Zoom(_) => 10,
Action::ActivityOutsideZMenu => 20,
Action::ZMenuClickCheck(_) => 25,
Action::ShowZMenu(_,_,_,_) => 25,
Action::SetFocus(_) => 20,
......@@ -212,6 +214,7 @@ pub fn actions_run(cg: &mut App, evs: &Vec<Action>, currency: Option<f64>) {
Action::ZMenuClickCheck(pos) => exe_zmenu_click_check(cg,&pos,currency),
Action::ShowZMenu(id,track_id,pos,payload) => exe_zmenu_show(cg,&id,&track_id,pos,payload),
Action::Reset => exe_reset(cg),
Action::ActivityOutsideZMenu => exe_deactivate(cg),
Action::Noop => ()
}
}
......
......@@ -100,6 +100,10 @@ fn custom_reset_event() -> Vec<Action> {
vec![Action::Reset]
}
fn custom_activity_outside_event() -> Vec<Action> {
vec![Action::ActivityOutsideZMenu]
}
fn every<F>(v: &JSONValue, cb: F) -> Vec<Action> where F: Fn(&JSONValue) -> Action {
if let JSONValue::Array(vv) = v {
vv.iter().map(|x| cb(x)).collect()
......@@ -135,9 +139,16 @@ fn custom_make_one_event_key(k: &String, v: &JSONValue, keys: &Vec<String>) -> V
fn custom_make_events(j: &JSONValue) -> Vec<Action> {
let mut out = Vec::<Action>::new();
if let JSONValue::Object(map) = j {
let keys : Vec<String> = map.keys().cloned().collect();
for (k,v) in map {
out.append(&mut custom_make_one_event_key(k,v,&keys));
if let Some(action) = j.get("action") {
match unwrap!(action.as_str()) {
"zmenu-activity-outside" => out.append(&mut custom_activity_outside_event()),
_ => {}
}
} else {
let keys : Vec<String> = map.keys().cloned().collect();
for (k,v) in map {
out.append(&mut custom_make_one_event_key(k,v,&keys));
}
}
}
out.push(Action::Settled);
......
import React from 'react';
import React, { useRef } from 'react';
import browserMessagingService from 'src/content/app/browser/browser-messaging-service';
import useOutsideClick from 'src/shared/hooks/useOutsideClick';
import ZmenuContent from './ZmenuContent';
import styles from './Zmenu.scss';
import { ZmenuData, AnchorCoordinates } from './zmenu-types';
import { ZmenuData, ZmenuAction, AnchorCoordinates } from './zmenu-types';
const TIP_WIDTH = 18;
const TIP_HEIGHT = 13;
......@@ -35,6 +38,15 @@ type GetInlineStylesParams = {
};
const Zmenu = (props: Props) => {
const onOutsideClick = () =>
browserMessagingService.send('bpane', {
id: props.id,
action: ZmenuAction.ACTIVITY_OUTSIDE
});
const zmenuRef = useRef<HTMLDivElement>(null);
useOutsideClick(zmenuRef, onOutsideClick);
const direction = chooseDirection(props);
const inlineStyles = getInlineStyles({
direction,
......@@ -45,6 +57,7 @@ const Zmenu = (props: Props) => {
<div
className={styles.zmenuWrapper}
style={inlineStyles.body}
ref={zmenuRef}
onMouseEnter={() => props.onEnter(props.id)}
onMouseLeave={() => props.onLeave(props.id)}
>
......
......@@ -86,7 +86,7 @@ const ZmenuController = (props: Props) => {
id,
action: ZmenuAction.ENTER
};
browserMessagingService.send('bpane-zmenu', payload);
browserMessagingService.send('bpane', payload);
};
const handleZmenuLeave = (id: string) => {
......@@ -94,7 +94,7 @@ const ZmenuController = (props: Props) => {
id,
action: ZmenuAction.LEAVE
};
browserMessagingService.send('bpane-zmenu', payload);
browserMessagingService.send('bpane', payload);
};
const zmenuElements = Object.keys(zmenus).map((id) => (
......
......@@ -25,6 +25,7 @@ export enum Markup {
export enum ZmenuAction {
CREATE = 'create_zmenu',
DESTROY = 'destroy_zmenu',
ACTIVITY_OUTSIDE = 'zmenu-activity-outside', // TODO: sometime later, unify underscores vs hyphens (together with Genome Browser)
REPOSITION = 'update_zmenu_position',
ENTER = 'zmenu-enter',
LEAVE = 'zmenu-leave'
......@@ -73,6 +74,13 @@ export type ZmenuEnterPayload = {
action: ZmenuAction.ENTER;
};
// Sent from React to Genome browser
// (on mouseleave, or on click outside)
export type ZmenuOutsideActivityPayload = {
id: string;
action: ZmenuAction.ACTIVITY_OUTSIDE;
};
// Sent from React to Genome browser
// (on mouseleave, or on click outside)
export type ZmenuLeavePayload = {
......
......@@ -19,13 +19,13 @@ if( typeof Rust === "undefined" ) {
if( typeof process === "object" && typeof process.versions === "object" && typeof process.versions.node === "string" ) {
var fs = require( "fs" );
var path = require( "path" );
var wasm_path = path.join( __dirname, "/static/browser/browser-aa6bec24b5f094a89a38389a9e2aec50.wasm" );
var wasm_path = path.join( __dirname, "/static/browser/browser-e704a92ee84b1fefe12604ddc0291b07.wasm" );
var buffer = fs.readFileSync( wasm_path );
var mod = new WebAssembly.Module( buffer );
var wasm_instance = new WebAssembly.Instance( mod, instance.imports );
return instance.initialize( wasm_instance );
} else {
var file = fetch( "/static/browser/browser-aa6bec24b5f094a89a38389a9e2aec50.wasm", {credentials: "same-origin"} );
var file = fetch( "/static/browser/browser-e704a92ee84b1fefe12604ddc0291b07.wasm", {credentials: "same-origin"} );
var wasm_instance = ( typeof WebAssembly.instantiateStreaming === "function"
? WebAssembly.instantiateStreaming( file, instance.imports )
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment