[DE mobile] Add insert, open link handler in context menu
This commit is contained in:
parent
cb62ade641
commit
bf7f2e43f9
|
@ -106,6 +106,21 @@ class ContextMenu extends ContextMenuController {
|
|||
this.props.openOptions('edit');
|
||||
}, 0);
|
||||
break;
|
||||
case 'addlink':
|
||||
setTimeout(() => {
|
||||
this.props.openOptions('add', 'link');
|
||||
}, 400)
|
||||
break;
|
||||
case 'openlink':
|
||||
const stack = Common.EditorApi.get().getSelectedElements();
|
||||
let value;
|
||||
stack.forEach((item) => {
|
||||
if (item.get_ObjectType() == Asc.c_oAscTypeSelectElement.Hyperlink) {
|
||||
value = item.get_ObjectValue().get_Value();
|
||||
}
|
||||
});
|
||||
value && this.openLink(value);
|
||||
break;
|
||||
}
|
||||
|
||||
console.log("click context menu item: " + action);
|
||||
|
@ -185,6 +200,15 @@ class ContextMenu extends ContextMenuController {
|
|||
});
|
||||
}
|
||||
|
||||
openLink(url) {
|
||||
if (Common.EditorApi.get().asc_getUrlType(url) > 0) {
|
||||
const newDocumentPage = window.open(url, '_blank');
|
||||
if (newDocumentPage) {
|
||||
newDocumentPage.focus();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onDocumentReady() {
|
||||
super.onDocumentReady();
|
||||
|
||||
|
@ -323,12 +347,12 @@ class ContextMenu extends ContextMenuController {
|
|||
});
|
||||
}
|
||||
|
||||
// if ( !_.isEmpty(api.can_AddHyperlink()) && !lockedHeader) {
|
||||
// arrItems.push({
|
||||
// caption: _t.menuAddLink,
|
||||
// event: 'addlink'
|
||||
// });
|
||||
// }
|
||||
if ( !!api.can_AddHyperlink() && !lockedHeader) {
|
||||
itemsText.push({
|
||||
caption: _t.menuAddLink,
|
||||
event: 'addlink'
|
||||
});
|
||||
}
|
||||
|
||||
if ( canReview ) {
|
||||
if (this.inRevisionChange) {
|
||||
|
|
67
apps/documenteditor/mobile/src/controller/add/AddLink.jsx
Normal file
67
apps/documenteditor/mobile/src/controller/add/AddLink.jsx
Normal file
|
@ -0,0 +1,67 @@
|
|||
import React, {Component} from 'react';
|
||||
import { f7 } from 'framework7-react';
|
||||
import {Device} from '../../../../../common/mobile/utils/device';
|
||||
import { withTranslation} from 'react-i18next';
|
||||
|
||||
import {PageAddLink} from '../../view/add/AddLink';
|
||||
|
||||
class AddLinkController extends Component {
|
||||
constructor (props) {
|
||||
super(props);
|
||||
this.onInsertLink = this.onInsertLink.bind(this);
|
||||
}
|
||||
|
||||
closeModal () {
|
||||
if ( Device.phone ) {
|
||||
f7.sheet.close('.add-popup', true);
|
||||
} else {
|
||||
f7.popover.close('#add-popover');
|
||||
}
|
||||
}
|
||||
|
||||
getDisplayLinkText () {
|
||||
const api = Common.EditorApi.get();
|
||||
return api.can_AddHyperlink();
|
||||
}
|
||||
|
||||
onInsertLink (url, display, tip) {
|
||||
const api = Common.EditorApi.get();
|
||||
|
||||
const { t } = this.props;
|
||||
const _t = t("Add", { returnObjects: true });
|
||||
|
||||
const urltype = api.asc_getUrlType(url.trim());
|
||||
const isEmail = (urltype == 2);
|
||||
|
||||
if (urltype < 1) {
|
||||
f7.dialog.alert(_t.txtNotUrl, _t.notcriticalErrorTitle);
|
||||
return;
|
||||
}
|
||||
|
||||
let _url = url.replace(/^\s+|\s+$/g,'');
|
||||
|
||||
if (! /(((^https?)|(^ftp)):\/\/)|(^mailto:)/i.test(_url) )
|
||||
_url = (isEmail ? 'mailto:' : 'http://' ) + _url;
|
||||
|
||||
_url = _url.replace(new RegExp("%20",'g')," ");
|
||||
|
||||
const props = new Asc.CHyperlinkProperty();
|
||||
props.put_Value(_url);
|
||||
props.put_Text(!display ? _url : display);
|
||||
props.put_ToolTip(tip);
|
||||
|
||||
api.add_Hyperlink(props);
|
||||
|
||||
this.closeModal();
|
||||
}
|
||||
|
||||
render () {
|
||||
return (
|
||||
<PageAddLink closeModal={this.closeModal} onInsertLink={this.onInsertLink} getDisplayLinkText={this.getDisplayLinkText} noNavbar={this.props.noNavbar}/>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
const AddLinkWithTranslation = withTranslation()(AddLinkController);
|
||||
|
||||
export {AddLinkWithTranslation as AddLinkController};
|
|
@ -66,7 +66,6 @@ const _Rometo10 = (str) => {
|
|||
class AddOtherController extends Component {
|
||||
constructor (props) {
|
||||
super(props);
|
||||
this.onInsertLink = this.onInsertLink.bind(this);
|
||||
this.onInsertPageNumber = this.onInsertPageNumber.bind(this);
|
||||
this.onPageBreak = this.onPageBreak.bind(this);
|
||||
this.onColumnBreak = this.onColumnBreak.bind(this);
|
||||
|
@ -86,42 +85,6 @@ class AddOtherController extends Component {
|
|||
}
|
||||
}
|
||||
|
||||
getDisplayLinkText () {
|
||||
const api = Common.EditorApi.get();
|
||||
return api.can_AddHyperlink();
|
||||
}
|
||||
|
||||
onInsertLink (url, display, tip) {
|
||||
const api = Common.EditorApi.get();
|
||||
|
||||
const { t } = this.props;
|
||||
const _t = t("Add", { returnObjects: true });
|
||||
|
||||
const urltype = api.asc_getUrlType(url.trim());
|
||||
const isEmail = (urltype == 2);
|
||||
|
||||
if (urltype < 1) {
|
||||
f7.dialog.alert(_t.txtNotUrl, _t.notcriticalErrorTitle);
|
||||
return;
|
||||
}
|
||||
|
||||
let _url = url.replace(/^\s+|\s+$/g,'');
|
||||
|
||||
if (! /(((^https?)|(^ftp)):\/\/)|(^mailto:)/i.test(_url) )
|
||||
_url = (isEmail ? 'mailto:' : 'http://' ) + _url;
|
||||
|
||||
_url = _url.replace(new RegExp("%20",'g')," ");
|
||||
|
||||
const props = new Asc.CHyperlinkProperty();
|
||||
props.put_Value(_url);
|
||||
props.put_Text(!display ? _url : display);
|
||||
props.put_ToolTip(tip);
|
||||
|
||||
api.add_Hyperlink(props);
|
||||
|
||||
this.closeModal();
|
||||
}
|
||||
|
||||
onInsertPageNumber (type) {
|
||||
const api = Common.EditorApi.get();
|
||||
|
||||
|
@ -280,8 +243,6 @@ class AddOtherController extends Component {
|
|||
render () {
|
||||
return (
|
||||
<AddOther closeModal={this.closeModal}
|
||||
onInsertLink={this.onInsertLink}
|
||||
getDisplayLinkText={this.getDisplayLinkText}
|
||||
onInsertPageNumber={this.onInsertPageNumber}
|
||||
onPageBreak={this.onPageBreak}
|
||||
onColumnBreak={this.onColumnBreak}
|
||||
|
|
|
@ -18,25 +18,29 @@ export default class MainPage extends Component {
|
|||
this.state = {
|
||||
editOptionsVisible: false,
|
||||
addOptionsVisible: false,
|
||||
addShowOptions: null,
|
||||
settingsVisible: false,
|
||||
collaborationVisible: false
|
||||
};
|
||||
}
|
||||
|
||||
handleClickToOpenOptions = (opts, page) => {
|
||||
handleClickToOpenOptions = (opts, showOpts) => {
|
||||
ContextMenu.closeContextMenu();
|
||||
|
||||
this.setState(state => {
|
||||
if ( opts == 'edit' )
|
||||
return {editOptionsVisible: true};
|
||||
else if ( opts == 'add' )
|
||||
return {addOptionsVisible: true};
|
||||
return {
|
||||
addOptionsVisible: true,
|
||||
addShowOptions: showOpts
|
||||
};
|
||||
else if ( opts == 'settings' )
|
||||
return {settingsVisible: true};
|
||||
else if ( opts == 'coauth' )
|
||||
return {
|
||||
collaborationVisible: true,
|
||||
collaborationPage: page
|
||||
collaborationPage: showOpts
|
||||
};
|
||||
});
|
||||
};
|
||||
|
@ -90,7 +94,7 @@ export default class MainPage extends Component {
|
|||
}
|
||||
{
|
||||
!this.state.addOptionsVisible ? null :
|
||||
<AddOptions onclosed={this.handleOptionsViewClosed.bind(this, 'add')} />
|
||||
<AddOptions onclosed={this.handleOptionsViewClosed.bind(this, 'add')} showOptions={this.state.addShowOptions} />
|
||||
}
|
||||
{
|
||||
!this.state.settingsVisible ? null :
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
import React, {Component, useEffect} from 'react';
|
||||
import {View,Page,Navbar,NavRight,Link,Popup,Popover,Icon,Tabs,Tab} from 'framework7-react';
|
||||
import React, {Component, useEffect, Fragment} from 'react';
|
||||
import {View,Page,Navbar,NavRight, NavTitle, Link,Popup,Popover,Icon,Tabs,Tab} from 'framework7-react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import {f7} from 'framework7-react';
|
||||
import { observer, inject } from "mobx-react";
|
||||
|
@ -8,10 +8,11 @@ import {Device} from '../../../../../common/mobile/utils/device';
|
|||
import {AddTableController} from "../../controller/add/AddTable";
|
||||
import AddShapeController from "../../controller/add/AddShape";
|
||||
import {AddImageController} from "../../controller/add/AddImage";
|
||||
import {AddLinkController} from "../../controller/add/AddLink";
|
||||
import {AddOtherController} from "../../controller/add/AddOther";
|
||||
|
||||
import {PageImageLinkSettings} from "../add/AddImage";
|
||||
import {PageAddLink, PageAddNumber, PageAddBreak, PageAddSectionBreak, PageAddFootnote} from "../add/AddOther";
|
||||
import {PageAddNumber, PageAddBreak, PageAddSectionBreak, PageAddFootnote} from "../add/AddOther";
|
||||
|
||||
const routes = [
|
||||
// Image
|
||||
|
@ -22,7 +23,7 @@ const routes = [
|
|||
// Other
|
||||
{
|
||||
path: '/add-link/',
|
||||
component: PageAddLink,
|
||||
component: AddLinkController,
|
||||
},
|
||||
{
|
||||
path: '/add-page-number/',
|
||||
|
@ -44,15 +45,20 @@ const routes = [
|
|||
|
||||
const AddLayoutNavbar = ({ tabs, inPopover }) => {
|
||||
const isAndroid = Device.android;
|
||||
const { t } = useTranslation();
|
||||
const _t = t('Add', {returnObjects: true});
|
||||
return (
|
||||
<Navbar>
|
||||
<div className='tab-buttons tabbar'>
|
||||
{tabs.map((item, index) =>
|
||||
<Link key={"de-link-" + item.id} tabLink={"#" + item.id} tabLinkActive={index === 0}>
|
||||
<Icon slot="media" icon={item.icon}></Icon>
|
||||
</Link>)}
|
||||
{isAndroid && <span className='tab-link-highlight' style={{width: 100 / tabs.lenght + '%'}}></span>}
|
||||
</div>
|
||||
{tabs.length > 1 ?
|
||||
<div className='tab-buttons tabbar'>
|
||||
{tabs.map((item, index) =>
|
||||
<Link key={"de-link-" + item.id} tabLink={"#" + item.id} tabLinkActive={index === 0}>
|
||||
<Icon slot="media" icon={item.icon}></Icon>
|
||||
</Link>)}
|
||||
{isAndroid && <span className='tab-link-highlight' style={{width: 100 / tabs.lenght + '%'}}></span>}
|
||||
</div> :
|
||||
<NavTitle>{ tabs[0].caption }</NavTitle>
|
||||
}
|
||||
{ !inPopover && <NavRight><Link icon='icon-expand-down' popupClose=".add-popup"></Link></NavRight> }
|
||||
</Navbar>
|
||||
)
|
||||
|
@ -73,31 +79,41 @@ const AddLayoutContent = ({ tabs }) => {
|
|||
const AddTabs = props => {
|
||||
const { t } = useTranslation();
|
||||
const _t = t('Add', {returnObjects: true});
|
||||
const showPanels = props.showPanels;
|
||||
const tabs = [];
|
||||
tabs.push({
|
||||
caption: _t.textTable,
|
||||
id: 'add-table',
|
||||
icon: 'icon-add-table',
|
||||
component: <AddTableController />
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textShape,
|
||||
id: 'add-shape',
|
||||
icon: 'icon-add-shape',
|
||||
component: <AddShapeController />
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textImage,
|
||||
id: 'add-image',
|
||||
icon: 'icon-add-image',
|
||||
component: <AddImageController />
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textOther,
|
||||
id: 'add-other',
|
||||
icon: 'icon-add-other',
|
||||
component: <AddOtherController />
|
||||
});
|
||||
if (!showPanels) {
|
||||
tabs.push({
|
||||
caption: _t.textTable,
|
||||
id: 'add-table',
|
||||
icon: 'icon-add-table',
|
||||
component: <AddTableController/>
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textShape,
|
||||
id: 'add-shape',
|
||||
icon: 'icon-add-shape',
|
||||
component: <AddShapeController/>
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textImage,
|
||||
id: 'add-image',
|
||||
icon: 'icon-add-image',
|
||||
component: <AddImageController/>
|
||||
});
|
||||
tabs.push({
|
||||
caption: _t.textOther,
|
||||
id: 'add-other',
|
||||
icon: 'icon-add-other',
|
||||
component: <AddOtherController/>
|
||||
});
|
||||
}
|
||||
if (showPanels && showPanels === 'link') {
|
||||
tabs.push({
|
||||
caption: _t.textAddLink,
|
||||
id: 'add-link',
|
||||
component: <AddLinkController noNavbar={true}/>
|
||||
});
|
||||
}
|
||||
return (
|
||||
<View style={props.style} stackPages={true} routes={routes}>
|
||||
<Page pageContent={false}>
|
||||
|
@ -122,10 +138,10 @@ class AddView extends Component {
|
|||
return (
|
||||
show_popover ?
|
||||
<Popover id="add-popover" className="popover__titled" onPopoverClosed={() => this.props.onclosed()}>
|
||||
<AddTabs inPopover={true} onOptionClick={this.onoptionclick} style={{height: '410px'}} />
|
||||
<AddTabs inPopover={true} onOptionClick={this.onoptionclick} style={{height: '410px'}} showPanels={this.props.showPanels} />
|
||||
</Popover> :
|
||||
<Popup className="add-popup" onPopupClosed={() => this.props.onclosed()}>
|
||||
<AddTabs onOptionClick={this.onoptionclick} />
|
||||
<AddTabs onOptionClick={this.onoptionclick} showPanels={this.props.showPanels} />
|
||||
</Popup>
|
||||
)
|
||||
}
|
||||
|
@ -145,7 +161,7 @@ const Add = props => {
|
|||
if ( props.onclosed )
|
||||
props.onclosed();
|
||||
};
|
||||
return <AddView usePopover={!Device.phone} onclosed={onviewclosed} />
|
||||
return <AddView usePopover={!Device.phone} onclosed={onviewclosed} showPanels={props.showOptions} />
|
||||
};
|
||||
|
||||
export default Add;
|
51
apps/documenteditor/mobile/src/view/add/AddLink.jsx
Normal file
51
apps/documenteditor/mobile/src/view/add/AddLink.jsx
Normal file
|
@ -0,0 +1,51 @@
|
|||
import React, {useState} from 'react';
|
||||
import {List, Page, Navbar, Icon, ListButton, ListInput} from 'framework7-react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import {Device} from "../../../../../common/mobile/utils/device";
|
||||
|
||||
const PageLink = props => {
|
||||
const { t } = useTranslation();
|
||||
const _t = t('Add', {returnObjects: true});
|
||||
|
||||
let display = props.getDisplayLinkText();
|
||||
display = typeof display === 'string' ? display : '';
|
||||
|
||||
const [stateLink, setLink] = useState('');
|
||||
const [stateDisplay, setDisplay] = useState(display);
|
||||
const [stateTip, setTip] = useState('');
|
||||
return (
|
||||
<Page>
|
||||
{!props.noNavbar && <Navbar title={_t.textAddLink} backLink={_t.textBack}></Navbar>}
|
||||
<List inlineLabels className='inputs-list'>
|
||||
<ListInput
|
||||
label={_t.textLink}
|
||||
type="text"
|
||||
placeholder={_t.textLink}
|
||||
value={stateLink}
|
||||
onChange={(event) => {setLink(event.target.value)}}
|
||||
></ListInput>
|
||||
<ListInput
|
||||
label={_t.textDisplay}
|
||||
type="text"
|
||||
placeholder={_t.textDisplay}
|
||||
value={stateDisplay}
|
||||
onChange={(event) => {setDisplay(event.target.value)}}
|
||||
></ListInput>
|
||||
<ListInput
|
||||
label={_t.textScreenTip}
|
||||
type="text"
|
||||
placeholder={_t.textScreenTip}
|
||||
value={stateTip}
|
||||
onChange={(event) => {setTip(event.target.value)}}
|
||||
></ListInput>
|
||||
</List>
|
||||
<List>
|
||||
<ListButton className={'button-fill button-raised' + (stateLink.length < 1 ? ' disabled' : '')} title={_t.textInsert} onClick={() => {
|
||||
props.onInsertLink(stateLink, stateDisplay, stateTip)
|
||||
}}></ListButton>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
export {PageLink as PageAddLink};
|
|
@ -4,51 +4,6 @@ import {List, ListItem, Page, Navbar, Icon, ListButton, ListInput, BlockTitle, S
|
|||
import { useTranslation } from 'react-i18next';
|
||||
import {Device} from "../../../../../common/mobile/utils/device";
|
||||
|
||||
const PageLink = props => {
|
||||
const { t } = useTranslation();
|
||||
const _t = t('Add', {returnObjects: true});
|
||||
|
||||
let display = props.getDisplayLinkText();
|
||||
display = typeof display === 'string' ? display : '';
|
||||
|
||||
const [stateLink, setLink] = useState('');
|
||||
const [stateDisplay, setDisplay] = useState(display);
|
||||
const [stateTip, setTip] = useState('');
|
||||
return (
|
||||
<Page>
|
||||
<Navbar title={_t.textAddLink} backLink={_t.textBack}></Navbar>
|
||||
<List inlineLabels className='inputs-list'>
|
||||
<ListInput
|
||||
label={_t.textLink}
|
||||
type="text"
|
||||
placeholder={_t.textLink}
|
||||
value={stateLink}
|
||||
onChange={(event) => {setLink(event.target.value)}}
|
||||
></ListInput>
|
||||
<ListInput
|
||||
label={_t.textDisplay}
|
||||
type="text"
|
||||
placeholder={_t.textDisplay}
|
||||
value={stateDisplay}
|
||||
onChange={(event) => {setDisplay(event.target.value)}}
|
||||
></ListInput>
|
||||
<ListInput
|
||||
label={_t.textScreenTip}
|
||||
type="text"
|
||||
placeholder={_t.textScreenTip}
|
||||
value={stateTip}
|
||||
onChange={(event) => {setTip(event.target.value)}}
|
||||
></ListInput>
|
||||
</List>
|
||||
<List>
|
||||
<ListButton className={'button-fill button-raised' + (stateLink.length < 1 ? ' disabled' : '')} title={_t.textInsert} onClick={() => {
|
||||
props.onInsertLink(stateLink, stateDisplay, stateTip)
|
||||
}}></ListButton>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
const PageNumber = props => {
|
||||
const { t } = useTranslation();
|
||||
const _t = t('Add', {returnObjects: true});
|
||||
|
@ -240,7 +195,6 @@ const AddOther = props => {
|
|||
const AddOtherContainer = inject("storeComments")(observer(AddOther));
|
||||
|
||||
export {AddOtherContainer as AddOther,
|
||||
PageLink as PageAddLink,
|
||||
PageNumber as PageAddNumber,
|
||||
PageBreak as PageAddBreak,
|
||||
PageSectionBreak as PageAddSectionBreak,
|
||||
|
|
Loading…
Reference in a new issue