Skip to content
This repository has been archived by the owner on Dec 11, 2019. It is now read-only.

Issue 9306 related #9542

Merged
merged 1 commit into from
Jun 29, 2017
Merged
Show file tree
Hide file tree
Changes from all 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
2 changes: 1 addition & 1 deletion app/common/state/tabContentState.js
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ const tabContentState = {
const tabPageIndex = state.getIn(['ui', 'tabs', 'tabPageIndex'], 0)
const previewTabPageIndex = state.getIn(['ui', 'tabs', 'previewTabPageIndex'])

return previewTabPageIndex !== undefined ? previewTabPageIndex : tabPageIndex
return previewTabPageIndex != null ? previewTabPageIndex : tabPageIndex
},

isMediumView: (state, frameKey) => {
Expand Down
18 changes: 0 additions & 18 deletions app/renderer/components/tabs/tab.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@ const tabContentState = require('../../../common/state/tabContentState')

// Constants
const dragTypes = require('../../../../js/constants/dragTypes')
const settings = require('../../../../js/constants/settings')

// Styles
const styles = require('../styles/tab')
Expand All @@ -44,7 +43,6 @@ const frameStateUtil = require('../../../../js/state/frameStateUtil')
const {getTabBreakpoint, tabUpdateFrameRate} = require('../../lib/tabUtil')
const {isWindows} = require('../../../common/lib/platformUtil')
const {getCurrentWindowId} = require('../../currentWindow')
const {getSetting} = require('../../../../js/settings')
const UrlUtil = require('../../../../js/lib/urlutil')
const {hasBreakpoint} = require('../../lib/tabUtil')

Expand Down Expand Up @@ -131,25 +129,10 @@ class Tab extends React.Component {
}

onMouseLeave () {
if (this.props.previewTabs) {
window.clearTimeout(this.hoverTimeout)
windowActions.setPreviewFrame(null)
}
windowActions.setTabHoverState(this.props.frameKey, false)
}

onMouseEnter (e) {
// relatedTarget inside mouseenter checks which element before this event was the pointer on
// if this element has a tab-like class, then it's likely that the user was previewing
// a sequency of tabs. Called here as previewMode.
const previewMode = /tab(?!pages)/i.test(e.relatedTarget.classList)

// If user isn't in previewMode, we add a bit of delay to avoid tab from flashing out
// as reported here: https://github.com/brave/browser-laptop/issues/1434
if (this.props.previewTabs) {
this.hoverTimeout =
window.setTimeout(windowActions.setPreviewFrame.bind(null, this.props.frameKey), previewMode ? 0 : 200)
}
windowActions.setTabHoverState(this.props.frameKey, true)
}

Expand Down Expand Up @@ -270,7 +253,6 @@ class Tab extends React.Component {

// used in other functions
props.totalTabs = state.get('tabs').size
props.previewTabs = getSetting(settings.SHOW_TAB_PREVIEWS)
props.dragData = state.getIn(['dragData', 'type']) === dragTypes.TAB && state.get('dragData')
props.hasTabInFullScreen = tabContentState.hasTabInFullScreen(currentWindow)
props.tabId = frame.get('tabId')
Expand Down
13 changes: 2 additions & 11 deletions app/renderer/components/tabs/tabPage.js
Original file line number Diff line number Diff line change
Expand Up @@ -33,20 +33,11 @@ class TabPage extends React.Component {
}

onMouseLeave () {
window.clearTimeout(this.hoverTimeout)
windowActions.setPreviewTabPageIndex()
windowActions.setTabPageHoverState(this.props.index, false)
}

onMouseEnter (e) {
// relatedTarget inside mouse enter checks which element before this event was the pointer on
// if this element has a tab-like class, then it's likely that the user was previewing
// a sequence of tabs. Called here as previewMode.
const previewMode = /tab(?!pages)/i.test(e.relatedTarget.classList)

// If user isn't in previewMode, we add a bit of delay to avoid tab from flashing out
// as reported here: https://github.com/brave/browser-laptop/issues/1434
this.hoverTimeout =
window.setTimeout(windowActions.setPreviewTabPageIndex.bind(null, this.props.index), previewMode ? 0 : 200)
windowActions.setTabPageHoverState(this.props.index, true)
}

onDrop (e) {
Expand Down
2 changes: 1 addition & 1 deletion app/renderer/components/tabs/tabs.js
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ class Tabs extends React.Component {
onMouseLeave={this.onMouseLeave}>
<span className={cx({
tabStripContainer: true,
isPreview: this.props.previewTabPageIndex !== undefined,
isPreview: this.props.previewTabPageIndex != null,
allowDragging: this.props.shouldAllowWindowDrag
})}
onDragOver={this.onDragOver}
Expand Down
28 changes: 13 additions & 15 deletions app/renderer/reducers/frameReducer.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,12 @@ const config = require('../../../js/constants/config')

// Actions
const appActions = require('../../../js/actions/appActions')
const windowActions = require('../../../js/actions/windowActions')

// Utils
const frameStateUtil = require('../../../js/state/frameStateUtil')
const {getCurrentWindowId} = require('../currentWindow')
const {getSourceAboutUrl, getSourceMagnetUrl} = require('../../../js/lib/appUrlUtil')
const {isURL, isPotentialPhishingUrl, getUrlFromInput} = require('../../../js/lib/urlutil')
const settings = require('../../../js/constants/settings')
const {getSetting} = require('../../../js/settings')

const setFullScreen = (state, action) => {
const index = frameStateUtil.getFrameIndex(state, action.frameProps.get('key'))
Expand All @@ -32,15 +29,13 @@ const setFullScreen = (state, action) => {
}

const closeFrame = (state, action) => {
const activeFrameIndex = frameStateUtil.getActiveFrameIndex(state)
const index = frameStateUtil.getFrameIndex(state, action.frameKey)
if (index === -1) {
return state
}

const frameProps = frameStateUtil.getFrameByKey(state, action.frameKey)
const hoverState = state.getIn(['frames', index, 'hoverState'])
const framePreviewEnabled = getSetting(settings.SHOW_TAB_PREVIEWS)

state = state.merge(frameStateUtil.removeFrame(
state,
Expand All @@ -56,15 +51,15 @@ const closeFrame = (state, action) => {

const nextFrame = frameStateUtil.getFrameByIndex(state, index)

if (nextFrame && hoverState) {
if (nextFrame) {
// Copy the hover state if tab closed with mouse as long as we have a next frame
// This allow us to have closeTab button visible for sequential frames closing,
// until onMouseLeave event happens.
windowActions.setTabHoverState(nextFrame.get('key'), hoverState)
if (framePreviewEnabled && index !== activeFrameIndex) {
// After closing a tab, preview the next frame as long as there is one
windowActions.setPreviewFrame(nextFrame.get('key'))
if (hoverState) {
state = frameStateUtil.setTabHoverState(state, nextFrame.get('key'), hoverState)
}
} else if (hoverState && frameStateUtil.getPreviewFrameKey(state) === action.frameKey) {
state = frameStateUtil.setPreviewFrameKey(state, null)
}

return state
Expand Down Expand Up @@ -124,12 +119,15 @@ const frameReducer = (state, action, immutableAction) => {
const active = immutableAction.getIn(['tabValue', 'active'])
if (active != null) {
if (active) {
state = state.merge({
activeFrameKey: frame.get('key'),
previewFrameKey: null
})
state = state.set('activeFrameKey', frame.get('key'))
if (frame.get('hoverState')) {
state = state.set('previewFrameKey', null)
}
if (frame.getIn(['ui', 'tabs', 'hoverTabPageIndex']) == null) {
state = state.deleteIn(['ui', 'tabs', 'previewTabPageIndex'])
}
state = state.setIn(['frames', index, 'lastAccessedTime'], new Date().getTime())
state = state.deleteIn(['ui', 'tabs', 'previewTabPageIndex'])

state = frameStateUtil.updateTabPageIndex(state, frame)
}
}
Expand Down
15 changes: 14 additions & 1 deletion docs/windowActions.md
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,8 @@ Dispatches a message to the store when the frame is active and the window is foc
### setPreviewFrame(frameKey)

Dispatches a message to the store to set a preview frame.
This is done when hovering over a tab.
This should only be called internally by `WINDOW_SET_TAB_HOVER_STATE`
when we need to delay updating the preview frame value

**Parameters**

Expand Down Expand Up @@ -234,6 +235,18 @@ Dispatches a message to the store to set the current tab hover state.



### setTabPageHoverState(tabPageIndex, hoverState)

Dispatches a message to the store to set the current tab hover state.

**Parameters**

**tabPageIndex**: `Object`, the frame key for the webview in question.

**hoverState**: `boolean`, whether or not mouse is over tabPage



### setPreviewTabPageIndex(previewTabPageIndex)

Dispatches a message to the store to set the tab page index being previewed.
Expand Down
17 changes: 16 additions & 1 deletion js/actions/windowActions.js
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,8 @@ const windowActions = {

/**
* Dispatches a message to the store to set a preview frame.
* This is done when hovering over a tab.
* This should only be called internally by `WINDOW_SET_TAB_HOVER_STATE`
* when we need to delay updating the preview frame value
*
* @param {Object} frameKey - the frame key for the webview in question.
*/
Expand Down Expand Up @@ -280,6 +281,20 @@ const windowActions = {
})
},

/**
* Dispatches a message to the store to set the current tab hover state.
*
* @param {Object} tabPageIndex - the frame key for the webview in question.
* @param {boolean} hoverState - whether or not mouse is over tabPage
*/
setTabPageHoverState: function (tabPageIndex, hoverState) {
dispatch({
actionType: windowConstants.WINDOW_SET_TAB_PAGE_HOVER_STATE,
tabPageIndex,
hoverState
})
},

/**
* Dispatches a message to the store to set the tab page index being previewed.
*
Expand Down
1 change: 1 addition & 0 deletions js/constants/windowConstants.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ const windowConstants = {
WINDOW_SET_TAB_PAGE_INDEX: _,
WINDOW_SET_TAB_BREAKPOINT: _,
WINDOW_SET_TAB_HOVER_STATE: _,
WINDOW_SET_TAB_PAGE_HOVER_STATE: _,
WINDOW_TAB_MOVE: _,
WINDOW_SET_THEME_COLOR: _,
WINDOW_WEBVIEW_LOAD_END: _,
Expand Down
116 changes: 111 additions & 5 deletions js/state/frameStateUtil.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@ const {getSetting} = require('../settings')
const {isIntermediateAboutPage} = require('../lib/appUrlUtil')
const urlParse = require('../../app/common/urlParse')

let tabPageHoverTimeout
let tabHoverTimeout = null

const comparatorByKeyAsc = (a, b) => a.get('key') > b.get('key')
? 1 : b.get('key') > a.get('key') ? -1 : 0

Expand Down Expand Up @@ -391,15 +394,13 @@ function removeFrame (state, frameProps, framePropsIndex) {
}

return {
previewFrameKey: null,
closedFrames,
frames: newFrames
}
}

function getFrameTabPageIndex (state, frameProps, tabsPerTabPage) {
frameProps = makeImmutable(frameProps)
const index = findNonPinnedDisplayIndexForFrameKey(state, frameProps.get('key'))
function getFrameTabPageIndex (state, frameKey, tabsPerTabPage = getSetting(settings.TABS_PER_PAGE)) {
const index = findNonPinnedDisplayIndexForFrameKey(state, frameKey)
if (index === -1) {
return -1
}
Expand Down Expand Up @@ -451,7 +452,8 @@ function isPinned (state, frameKey) {
* @param frameProps Any frame belonging to the page
*/
function updateTabPageIndex (state, frameProps) {
const index = getFrameTabPageIndex(state, frameProps, getSetting(settings.TABS_PER_PAGE))
frameProps = makeImmutable(frameProps)
const index = getFrameTabPageIndex(state, frameProps.get('key'))

if (index === -1) {
return state
Expand Down Expand Up @@ -532,7 +534,111 @@ const getTabPageCount = (state) => {
return Math.ceil(frames.size / tabsPerPage)
}

const getPreviewFrameKey = (state) => {
return state.get('previewFrameKey')
}

const setPreviewTabPageIndex = (state, index, immediate = false) => {
clearTimeout(tabPageHoverTimeout)
const previewTabs = getSetting(settings.SHOW_TAB_PREVIEWS)
const isActive = state.getIn(['ui', 'tabs', 'tabPageIndex']) === index
let newTabPageIndex = index

if (!previewTabs || state.getIn(['ui', 'tabs', 'hoverTabPageIndex']) !== index || isActive) {
newTabPageIndex = null
}

if (!immediate) {
// if there is an existing preview tab page index then we're already in preview mode
// we use actions here because that is the only way to delay updating the state
const previewMode = state.getIn(['ui', 'tabs', 'previewTabPageIndex']) != null
if (previewMode && newTabPageIndex == null) {
// add a small delay when we are clearing the preview frame key so we don't lose
// previewMode if the user mouses over another tab - see below
tabPageHoverTimeout = setTimeout(windowActions.setPreviewTabPageIndex.bind(null, null), 200)
return state
}

if (!previewMode) {
// If user isn't in previewMode so we add a bit of delay to avoid tab from flashing out
// as reported here: https://github.com/brave/browser-laptop/issues/1434
// using an action here because that is the only way we can do a delayed state update
tabPageHoverTimeout = setTimeout(windowActions.setPreviewTabPageIndex.bind(null, newTabPageIndex), 200)
return state
}
}

return state.setIn(['ui', 'tabs', 'previewTabPageIndex'], newTabPageIndex)
}

const setPreviewFrameKey = (state, frameKey, immediate = false) => {
clearTimeout(tabHoverTimeout)
const frame = getFrameByKey(state, frameKey)
const isActive = isFrameKeyActive(state, frameKey)
const previewTabs = getSetting(settings.SHOW_TAB_PREVIEWS)
let newPreviewFrameKey = frameKey

if (!previewTabs || frame == null || !frame.get('hoverState') || isActive) {
newPreviewFrameKey = null
}

if (!immediate) {
// if there is an existing preview frame key then we're already in preview mode
// we use actions here because that is the only way to delay updating the state
const previewMode = getPreviewFrameKey(state) != null
if (previewMode && newPreviewFrameKey == null) {
// add a small delay when we are clearing the preview frame key so we don't lose
// previewMode if the user mouses over another tab - see below
tabHoverTimeout = setTimeout(windowActions.setPreviewFrame.bind(null, null), 200)
return state
}

if (!previewMode) {
// If user isn't in previewMode so we add a bit of delay to avoid tab from flashing out
// as reported here: https://github.com/brave/browser-laptop/issues/1434
// using an action here because that is the only way we can do a delayed state update
tabHoverTimeout = setTimeout(windowActions.setPreviewFrame.bind(null, newPreviewFrameKey), 200)
return state
}
}

const index = getFrameTabPageIndex(state, frame)
if (index !== -1) {
if (index !== state.getIn(['ui', 'tabs', 'tabPageIndex'])) {
state = state.setIn(['ui', 'tabs', 'previewTabPageIndex'], index)
} else {
state = state.deleteIn(['ui', 'tabs', 'previewTabPageIndex'])
}
}
return state.set('previewFrameKey', newPreviewFrameKey)
}

const setTabPageHoverState = (state, tabPageIndex, hoverState) => {
const currentHoverIndex = state.getIn(['ui', 'tabs', 'hoverTabPageIndex'])
if (!hoverState && currentHoverIndex === tabPageIndex) {
state = state.setIn(['ui', 'tabs', 'hoverTabPageIndex'], null)
} else if (hoverState) {
state = state.setIn(['ui', 'tabs', 'hoverTabPageIndex'], tabPageIndex)
}
state = setPreviewTabPageIndex(state, tabPageIndex)
return state
}

const setTabHoverState = (state, frameKey, hoverState) => {
const frameIndex = getFrameIndex(state, frameKey)
if (frameIndex !== -1) {
state = state.setIn(['frames', frameIndex, 'hoverState'], hoverState)
state = setPreviewFrameKey(state, frameKey)
}
return state
}

module.exports = {
setTabPageHoverState,
setPreviewTabPageIndex,
setTabHoverState,
setPreviewFrameKey,
getPreviewFrameKey,
deleteTabInternalIndex,
deleteFrameInternalIndex,
updateFramesInternalIndex,
Expand Down
Loading