diff --git a/web/src/css/header.less b/web/src/css/header.less index 4813b9333..90907ec78 100644 --- a/web/src/css/header.less +++ b/web/src/css/header.less @@ -1,24 +1,66 @@ @import (reference) '../../node_modules/bootstrap/less/variables.less'; @import (reference) '../../node_modules/bootstrap/less/mixins/grid.less'; +@menu-height: 85px; + + header { - padding-top: 0.5em; + padding-top: 6px; background-color: white; @separator-color: lighten(grey, 15%); - .menu { - padding: 10px; + menu { + display: block; + margin: 0; + padding: 0; border-bottom: solid @separator-color 1px; + height: @menu-height; + overflow: visible; // search help context laps over. } } -@menu-row-gutter-width: 5px; -.menu-row { - .make-row(@menu-row-gutter-width); +.menu-group { + @description-height: 16px; + display: inline-block; + height: @menu-height; + vertical-align: top; + + .entry { + height: (@menu-height - @description-height)/3; + line-height: 1; + padding: 0.5rem 1rem; + + label { + font-size: 1.2rem; + font-weight: normal; + margin: 0; + } + input[type=checkbox] { + margin: 0 2px; + vertical-align: middle; + } + } + .description { + height: @description-height; + text-align: center; + font-size: 0.9rem; + } +} +.menu-group + .menu-group:before { + @space: 10px; + content: " "; + border-left: solid 1px lighten(grey, 40%); + margin-top: @space; + height: @menu-height - @space*2; + position: absolute; +} + +@menu-main-gutter-width: 5px; +.menu-main { + .make-row(@menu-main-gutter-width); } .filter-input { - .make-sm-column(3, @menu-row-gutter-width); - margin-bottom:5px; + .make-sm-column(4, @menu-main-gutter-width); } .filter-input .popover { diff --git a/web/src/js/components/FlowView/ToggleEdit.jsx b/web/src/js/components/FlowView/ToggleEdit.jsx index 9016348e4..6a691a3d3 100644 --- a/web/src/js/components/FlowView/ToggleEdit.jsx +++ b/web/src/js/components/FlowView/ToggleEdit.jsx @@ -14,11 +14,11 @@ function ToggleEdit({ isEdit, startEdit, stopEdit, flow, modifiedFlow }) { return (
{isEdit ? - stopEdit(flow, modifiedFlow)}> + stopEdit(flow, modifiedFlow)}> : - startEdit(flow)}> + startEdit(flow)}> } diff --git a/web/src/js/components/Header.jsx b/web/src/js/components/Header.jsx index 702786e6b..1500db1ba 100644 --- a/web/src/js/components/Header.jsx +++ b/web/src/js/components/Header.jsx @@ -2,14 +2,13 @@ import React, { Component, PropTypes } from 'react' import { connect } from 'react-redux' import classnames from 'classnames' import MainMenu from './Header/MainMenu' -import ViewMenu from './Header/ViewMenu' import OptionMenu from './Header/OptionMenu' import FileMenu from './Header/FileMenu' import FlowMenu from './Header/FlowMenu' import {setActiveMenu} from '../ducks/ui/header' class Header extends Component { - static entries = [MainMenu, ViewMenu, OptionMenu] + static entries = [MainMenu, OptionMenu] handleClick(active, e) { e.preventDefault() @@ -38,9 +37,9 @@ class Header extends Component { ))} -
+ -
+ ) } diff --git a/web/src/js/components/Header/FlowMenu.jsx b/web/src/js/components/Header/FlowMenu.jsx index e78a49aa8..e0c59afeb 100644 --- a/web/src/js/components/Header/FlowMenu.jsx +++ b/web/src/js/components/Header/FlowMenu.jsx @@ -18,15 +18,12 @@ FlowMenu.propTypes = { function FlowMenu({ flow, acceptFlow, replayFlow, duplicateFlow, removeFlow, revertFlow }) { return (
-
-
-
+
) } diff --git a/web/src/js/components/Header/MainMenu.jsx b/web/src/js/components/Header/MainMenu.jsx index 5ab3fa9d9..6a4e12bff 100644 --- a/web/src/js/components/Header/MainMenu.jsx +++ b/web/src/js/components/Header/MainMenu.jsx @@ -1,20 +1,17 @@ -import React, { Component, PropTypes } from 'react' -import { connect } from 'react-redux' -import FilterInput from './FilterInput' -import { update as updateSettings } from '../../ducks/settings' -import { setFilter, setHighlight } from '../../ducks/flows' +import React, { Component, PropTypes } from "react" +import { connect } from "react-redux" +import FilterInput from "./FilterInput" +import { update as updateSettings } from "../../ducks/settings" +import { setFilter, setHighlight } from "../../ducks/flows" MainMenu.title = "Start" export default function MainMenu() { return ( -
-
- - - -
-
+
+ + +
) } diff --git a/web/src/js/components/Header/MenuToggle.jsx b/web/src/js/components/Header/MenuToggle.jsx new file mode 100644 index 000000000..726db7bd1 --- /dev/null +++ b/web/src/js/components/Header/MenuToggle.jsx @@ -0,0 +1,69 @@ +import { PropTypes } from "react" +import { connect } from "react-redux" +import { update as updateSettings } from "../../ducks/settings" +import { toggleVisibility } from "../../ducks/eventLog" + +MenuToggle.propTypes = { + value: PropTypes.bool.isRequired, + onChange: PropTypes.func.isRequired, + children: PropTypes.node.isRequired, +} + +export function MenuToggle({ value, onChange, children }) { + return ( +
+ +
+ ) +} + + +SettingsToggle.propTypes = { + setting: PropTypes.string.isRequired, + children: PropTypes.node.isRequired, +} + +export function SettingsToggle({ setting, children, settings, updateSettings }) { + return ( + updateSettings({ [setting]: !settings[setting] })} + > + {children} + + ) +} +SettingsToggle = connect( + state => ({ + settings: state.settings, + }), + { + updateSettings, + } +)(SettingsToggle) + + +export function EventlogToggle({ toggleVisibility, eventLogVisible }) { + return ( + + Display Event Log + + ) +} +EventlogToggle = connect( + state => ({ + eventLogVisible: state.eventLog.visible, + }), + { + toggleVisibility, + } +)(EventlogToggle) + diff --git a/web/src/js/components/Header/OptionMenu.jsx b/web/src/js/components/Header/OptionMenu.jsx index f1d19f48f..4fb5dc1f9 100644 --- a/web/src/js/components/Header/OptionMenu.jsx +++ b/web/src/js/components/Header/OptionMenu.jsx @@ -1,75 +1,59 @@ import React, { PropTypes } from 'react' import { connect } from 'react-redux' -import ToggleButton from '../common/ToggleButton' -import ToggleInputButton from '../common/ToggleInputButton' -import { update as updateSettings } from '../../ducks/settings' +import {SettingsToggle, EventlogToggle} from './MenuToggle' +import DocsLink from '../common/DocsLink' OptionMenu.title = 'Options' -OptionMenu.propTypes = { - settings: PropTypes.object.isRequired, - updateSettings: PropTypes.func.isRequired, -} - -function OptionMenu({ settings, updateSettings }) { +export default function OptionMenu() { return (
-
- updateSettings({ showhost: !settings.showhost })} - /> - updateSettings({ no_upstream_cert: !settings.no_upstream_cert })} - /> - updateSettings({ rawtcp: !settings.rawtcp })} - /> - updateSettings({ http2: !settings.http2 })} - /> - updateSettings({ websocket: !settings.websocket })} - /> - updateSettings({ anticache: !settings.anticache })} - /> - updateSettings({ anticomp: !settings.anticomp })} - /> - updateSettings({ stickyauth: !settings.stickyauth ? txt : null })} - /> - updateSettings({ stickycookie: !settings.stickycookie ? txt : null })} - /> - updateSettings({ stream_large_bodies: !settings.stream_large_bodies ? txt : null })} - /> +
+ HTTP/2.0 + WebSockets + Raw TCP +
Protocol Support
-
+
+ + Disable Caching + + + Disable Compression + +
+
HTTP Options
+
+
+ + Use Host Header + + +
+
View Options
+
+ { /* + updateSettings({ no_upstream_cert: !settings.no_upstream_cert })} + /> + updateSettings({ stickyauth: !settings.stickyauth ? txt : null })} + /> + updateSettings({ stickycookie: !settings.stickycookie ? txt : null })} + /> + updateSettings({ stream_large_bodies: !settings.stream_large_bodies ? txt : null })} + /> + */}
) } - -export default connect( - state => ({ - settings: state.settings, - }), - { - updateSettings, - } -)(OptionMenu) diff --git a/web/src/js/components/Header/ViewMenu.jsx b/web/src/js/components/Header/ViewMenu.jsx deleted file mode 100644 index 22b370d15..000000000 --- a/web/src/js/components/Header/ViewMenu.jsx +++ /dev/null @@ -1,32 +0,0 @@ -import React, { PropTypes } from 'react' -import { connect } from 'react-redux' -import ToggleButton from '../common/ToggleButton' -import { toggleVisibility } from '../../ducks/eventLog' - -ViewMenu.title = 'View' -ViewMenu.route = 'flows' - -ViewMenu.propTypes = { - eventLogVisible: PropTypes.bool.isRequired, - toggleEventLog: PropTypes.func.isRequired, -} - -function ViewMenu({ eventLogVisible, toggleEventLog }) { - return ( -
-
- -
-
-
- ) -} - -export default connect( - state => ({ - eventLogVisible: state.eventLog.visible, - }), - { - toggleEventLog: toggleVisibility, - } -)(ViewMenu) diff --git a/web/src/js/components/common/DocsLink.jsx b/web/src/js/components/common/DocsLink.jsx new file mode 100644 index 000000000..182811a30 --- /dev/null +++ b/web/src/js/components/common/DocsLink.jsx @@ -0,0 +1,14 @@ +import { PropTypes } from 'react' + +DocsLink.propTypes = { + resource: PropTypes.string.isRequired, +} + +export default function DocsLink({ children, resource }) { + let url = `http://docs.mitmproxy.org/en/stable/${resource}` + return ( + + {children || } + + ) +} diff --git a/web/src/js/ducks/ui/header.js b/web/src/js/ducks/ui/header.js index 25dfe6027..1eff3ef6d 100644 --- a/web/src/js/ducks/ui/header.js +++ b/web/src/js/ducks/ui/header.js @@ -4,7 +4,7 @@ export const SET_ACTIVE_MENU = 'UI_SET_ACTIVE_MENU' const defaultState = { - activeMenu: 'Start', + activeMenu: 'Options', isFlowSelected: false, } @@ -22,7 +22,7 @@ export default function reducer(state = defaultState, action) { if (action.flowIds.length && !state.isFlowSelected) { return { ...state, - activeMenu: 'Flow', + activeMenu: 'Options', isFlowSelected: true, } }