Merge branch 'feature/reactjs-container-component-with-mobx' into feature/mobile-apps-on-reactjs
# Conflicts: # apps/documenteditor/mobile/locale/en.json # apps/documenteditor/mobile/src/components/app.jsx # apps/documenteditor/mobile/src/components/settings/Settings.jsx # apps/documenteditor/mobile/src/components/settings/document-settings/DocumentSettings.jsx # apps/documenteditor/mobile/src/js/routes.js # apps/documenteditor/mobile/src/pages/home.jsx # apps/documenteditor/mobile/src/store/reducers/root.js # apps/documenteditor/mobile/src/store/store.js
This commit is contained in:
commit
b041083933
|
@ -1,17 +1,17 @@
|
|||
import React, { useState } from 'react'
|
||||
import { resetUsers } from '../store/actions/actions.js'
|
||||
import React, { Component } from 'react'
|
||||
import Notifications from '../../utils/notifications.js'
|
||||
import {observer, inject} from "mobx-react"
|
||||
|
||||
const Collaboration = () => {
|
||||
const onChangeEditUsers = (users) => {
|
||||
const store = Common.Store.get();
|
||||
store.dispatch(resetUsers(Object.values(users)));
|
||||
};
|
||||
|
||||
@inject('users')
|
||||
class CollaborationController extends Component {
|
||||
constructor(props){
|
||||
super(props)
|
||||
|
||||
Common.Notifications.on('engineCreated', api => {
|
||||
// this.api = api;
|
||||
api.asc_registerCallback('asc_onAuthParticipantsChanged', onChangeEditUsers);
|
||||
api.asc_registerCallback('asc_onParticipantsChanged', onChangeEditUsers);
|
||||
api.asc_registerCallback('asc_onAuthParticipantsChanged', this.onChangeEditUsers.bind(this));
|
||||
api.asc_registerCallback('asc_onParticipantsChanged', this.onChangeEditUsers.bind(this));
|
||||
// this.api.asc_registerCallback('asc_onAddComment', _.bind(this.onApiAddComment, this));
|
||||
// this.api.asc_registerCallback('asc_onAddComments', _.bind(this.onApiAddComments, this));
|
||||
// this.api.asc_registerCallback('asc_onChangeCommentData', _.bind(this.onApiChangeCommentData, this));
|
||||
|
@ -20,11 +20,16 @@ const Collaboration = () => {
|
|||
// this.api.asc_registerCallback('asc_onShowComment', _.bind(this.apiShowComments, this));
|
||||
// this.api.asc_registerCallback('asc_onHideComment', _.bind(this.apiHideComments, this));
|
||||
});
|
||||
|
||||
return {
|
||||
setApi(api) {
|
||||
}
|
||||
|
||||
onChangeEditUsers(users) {
|
||||
const storeUsers = this.props.users;
|
||||
storeUsers.reset(users);
|
||||
};
|
||||
|
||||
render() {
|
||||
return null
|
||||
}
|
||||
};
|
||||
|
||||
export {Collaboration as CollaborationController}
|
||||
export default CollaborationController;
|
|
@ -1,8 +0,0 @@
|
|||
export const RESET_USERS = 'RESET_USERS';
|
||||
|
||||
export const resetUsers = list => {
|
||||
return {
|
||||
type: RESET_USERS,
|
||||
payload: list
|
||||
}
|
||||
};
|
|
@ -1,11 +1,10 @@
|
|||
import * as actionTypes from './actions/actions'
|
||||
|
||||
const usersReducer = (state = [], action) => {
|
||||
if (action.type == actionTypes.RESET_USERS) {
|
||||
return [...action.payload];
|
||||
import {observable, action} from 'mobx';
|
||||
|
||||
export class storeUsers {
|
||||
@observable users = []
|
||||
|
||||
@action reset(users) {
|
||||
this.users = Object.values(users)
|
||||
}
|
||||
}
|
||||
|
||||
return state;
|
||||
};
|
||||
|
||||
export default usersReducer
|
|
@ -1,24 +1,34 @@
|
|||
import React, { Component } from 'react';
|
||||
import { useSelector } from 'react-redux';
|
||||
import React, { Component, useEffect } from 'react';
|
||||
import { observer, inject } from "mobx-react";
|
||||
import { Popover, List, ListItem, Navbar, NavTitle, NavRight } from 'framework7-react';
|
||||
import { Sheet, Toolbar, BlockTitle, Link, Page, View, Icon } from 'framework7-react';
|
||||
import { f7 } from 'framework7-react';
|
||||
import { withTranslation, useTranslation } from 'react-i18next';
|
||||
|
||||
const PageUsers = () => {
|
||||
const { t } = useTranslation();
|
||||
const userlist = useSelector(state => state.users);
|
||||
@inject('users')
|
||||
@observer
|
||||
class PageUsers extends Component {
|
||||
constructor(props){
|
||||
super(props)
|
||||
}
|
||||
|
||||
render() {
|
||||
const { t } = this.props;
|
||||
const userlist = this.props.users;
|
||||
return (
|
||||
<Page name="collab__users">
|
||||
<Navbar title="Users" backLink="Back"></Navbar>
|
||||
<BlockTitle>{t("Collaboration.textEditUser")}</BlockTitle>
|
||||
<List className="coauth__list">
|
||||
{userlist.map((model, i) => (
|
||||
{userlist.users.map((model, i) => (
|
||||
<ListItem title={model.asc_getUserName()} key={i}>
|
||||
<Icon slot="media" icon="coauth__list__icon" style={{ backgroundColor:model.asc_getColor() }}></Icon>
|
||||
<Icon slot="media" icon="coauth__list__icon"
|
||||
style={{backgroundColor: model.asc_getColor()}}></Icon>
|
||||
</ListItem>
|
||||
))}
|
||||
</List>
|
||||
</Page>)
|
||||
}
|
||||
};
|
||||
|
||||
const PageCollaboration = () => {
|
||||
|
@ -68,7 +78,7 @@ class CollaborationSheet extends Component {
|
|||
}
|
||||
render() {
|
||||
return (
|
||||
<Sheet className="collab__sheet" push>
|
||||
<Sheet className="coauth__sheet" push onSheetClosed={e => this.props.onclosed()}>
|
||||
<View>
|
||||
<PageCollaboration />
|
||||
</View>
|
||||
|
@ -77,5 +87,25 @@ class CollaborationSheet extends Component {
|
|||
}
|
||||
}
|
||||
|
||||
const CollaborationView = props => {
|
||||
useEffect(() => {
|
||||
f7.sheet.open('.coauth__sheet');
|
||||
|
||||
return () => {
|
||||
// component will unmount
|
||||
}
|
||||
});
|
||||
|
||||
const onviewclosed = () => {
|
||||
if ( props.onclosed ) props.onclosed();
|
||||
};
|
||||
|
||||
return (
|
||||
<CollaborationSheet onclosed={onviewclosed} />
|
||||
)
|
||||
};
|
||||
|
||||
const pageusers = withTranslation()(PageUsers);
|
||||
// export withTranslation()(CollaborationPopover);
|
||||
export {CollaborationPopover, CollaborationSheet, PageCollaboration, PageUsers, }
|
||||
export {CollaborationPopover, CollaborationSheet, PageCollaboration, pageusers as PageUsers}
|
||||
export default CollaborationView;
|
||||
|
|
52
apps/common/mobile/resources/less/common-ios.less
Normal file
52
apps/common/mobile/resources/less/common-ios.less
Normal file
|
@ -0,0 +1,52 @@
|
|||
|
||||
.device-ios {
|
||||
.popover__titled {
|
||||
.popover-inner {
|
||||
//border-radius: var(--f7-popover-border-radius);
|
||||
|
||||
> .view {
|
||||
border-radius: var(--f7-popover-border-radius);
|
||||
}
|
||||
}
|
||||
|
||||
.navbar-bg {
|
||||
//-webkit-backdrop-filter: none;
|
||||
backdrop-filter: none;
|
||||
}
|
||||
|
||||
.list:first-child {
|
||||
li:first-child {
|
||||
a {
|
||||
border-radius: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.list:last-child {
|
||||
li:last-child {
|
||||
a {
|
||||
border-radius: 0;
|
||||
}
|
||||
|
||||
&:after {
|
||||
content: '';
|
||||
position: absolute;
|
||||
background-color: var(--f7-navbar-border-color, var(--f7-bars-border-color));
|
||||
display: block;
|
||||
//z-index: 15;
|
||||
top: auto;
|
||||
right: auto;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
height: 1px;
|
||||
width: 100%;
|
||||
transform-origin: 50% 100%;
|
||||
transform: scaleY(calc(1 / var(--f7-device-pixel-ratio)));
|
||||
|
||||
-webkit-backface-visibility: hidden;
|
||||
backface-visibility: hidden;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
12
apps/common/mobile/resources/less/common-material.less
Normal file
12
apps/common/mobile/resources/less/common-material.less
Normal file
|
@ -0,0 +1,12 @@
|
|||
|
||||
.device-android {
|
||||
.popover__titled {
|
||||
.list:last-child {
|
||||
li:last-child {
|
||||
a {
|
||||
border-radius: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
41
apps/common/mobile/utils/device.jsx
Normal file
41
apps/common/mobile/utils/device.jsx
Normal file
|
@ -0,0 +1,41 @@
|
|||
|
||||
import React from 'react';
|
||||
import { f7 } from 'framework7-react';
|
||||
|
||||
class Device {
|
||||
constructor(){
|
||||
const ua = navigator.userAgent,
|
||||
isMobile = /Mobile(\/|\s|;)/.test(ua);
|
||||
|
||||
this.isPhone = /(iPhone|iPod)/.test(ua) ||
|
||||
(!/(Silk)/.test(ua) && (/(Android)/.test(ua) && (/(Android 2)/.test(ua) || isMobile))) ||
|
||||
(/(BlackBerry|BB)/.test(ua) && isMobile) ||
|
||||
/(Windows Phone)/.test(ua);
|
||||
|
||||
this.isTablet = !this.isPhone && (/iPad/.test(ua) || /Android/.test(ua) || /(RIM Tablet OS)/.test(ua) ||
|
||||
(/MSIE 10/.test(ua) && /; Touch/.test(ua)));
|
||||
}
|
||||
|
||||
get phone() {
|
||||
return this.isPhone
|
||||
}
|
||||
|
||||
get tablet() {
|
||||
return this.isTablet
|
||||
}
|
||||
|
||||
get sailfish() {
|
||||
return /Sailfish/.test(navigator.userAgent) || /Jolla/.test(navigator.userAgent);
|
||||
}
|
||||
|
||||
get android() {
|
||||
return f7.device.android;
|
||||
}
|
||||
|
||||
get ios() {
|
||||
return f7.device.ios;
|
||||
}
|
||||
}
|
||||
|
||||
const device = new Device();
|
||||
export {device as Device};
|
|
@ -19,5 +19,40 @@
|
|||
},
|
||||
"Collaboration": {
|
||||
"textEditUser": "Users who are editing the file:"
|
||||
},
|
||||
"Edit": {
|
||||
"textClose": "Close",
|
||||
"textBack": "Back",
|
||||
"textText": "Text",
|
||||
"textParagraph": "Paragraph",
|
||||
"textTable": "Table",
|
||||
"textFooter": "Footer",
|
||||
"textHeader": "Header",
|
||||
"textShape": "Shape",
|
||||
"textImage": "Image",
|
||||
"textChart": "Chart",
|
||||
"textHyperlink": "Hyperlink",
|
||||
"textSelectObjectToEdit": "Select object to edit",
|
||||
"textSettings": "Settings",
|
||||
"textFontColor": "Font Color",
|
||||
"textHighlightColor": "Highlight Color",
|
||||
"textAdditionalFormatting": "Additional Formatting",
|
||||
"textAdditional": "Additional",
|
||||
"textBullets": "Bullets",
|
||||
"textNumbers": "Numbers",
|
||||
"textLineSpacing": "Line Spacing",
|
||||
"textFonts": "Fonts",
|
||||
"textAuto": "Auto",
|
||||
"textPt": "pt",
|
||||
"textSize": "Size",
|
||||
"textAuto": "Auto",
|
||||
"textStrikethrough": "Strikethrough",
|
||||
"textDoubleStrikethrough": "Double Strikethrough",
|
||||
"textSuperscript": "Superscript",
|
||||
"textSubscript": "Subscript",
|
||||
"textSmallCaps": "Small Caps",
|
||||
"textAllCaps": "All Caps",
|
||||
"textLetterSpacing": "Letter Spacing",
|
||||
"textNone": "None"
|
||||
}
|
||||
}
|
|
@ -1,19 +1,15 @@
|
|||
import React from 'react';
|
||||
import { connect } from 'react-redux';
|
||||
import { bindActionCreators } from 'redux';
|
||||
import { App, Panel, View, Popup, Page, Navbar, NavRight, Link, Block, BlockTitle, List, ListItem } from 'framework7-react';
|
||||
|
||||
import i18n from '../js/i18n';
|
||||
import {App,Panel,Views,View,Popup,Page,Navbar,Toolbar,NavRight,Link,Block,BlockTitle,List,ListItem,ListInput,ListButton,BlockFooter} from 'framework7-react';
|
||||
|
||||
import routes from '../js/routes';
|
||||
|
||||
import { initApi } from '../store/actions/actions';
|
||||
|
||||
import '../../../../common/Gateway.js';
|
||||
import '../../../../common/main/lib/util/utils.js';
|
||||
import { CollaborationController } from '../../../../common/mobile/lib/controller/Collaboration.jsx';
|
||||
import Notifications from '../../../../common/mobile/utils/notifications.js'
|
||||
import MainController from '../controller/Main';
|
||||
|
||||
class ComponentApp extends React.Component {
|
||||
export default class extends React.Component {
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
|
@ -23,20 +19,12 @@ class ComponentApp extends React.Component {
|
|||
name: 'Desktop Editor', // App name
|
||||
theme: 'auto', // Automatic theme detection
|
||||
|
||||
|
||||
|
||||
// App routes
|
||||
routes: routes,
|
||||
},
|
||||
// Login screen demo data
|
||||
username: '',
|
||||
password: '',
|
||||
}
|
||||
|
||||
Common.Notifications = new Notifications();
|
||||
|
||||
Common.Controllers = {};
|
||||
Common.Controllers.Collaboration = new CollaborationController();
|
||||
}
|
||||
render() {
|
||||
return (
|
||||
|
@ -70,6 +58,7 @@ class ComponentApp extends React.Component {
|
|||
|
||||
{/* Your main view, should have "view-main" class */}
|
||||
<View main className="safe-areas" url="/" />
|
||||
<MainController ref="mainController" />
|
||||
|
||||
{/* Popup */}
|
||||
<Popup id="my-popup">
|
||||
|
@ -89,168 +78,12 @@ class ComponentApp extends React.Component {
|
|||
</App>
|
||||
)
|
||||
}
|
||||
alertLoginData() {
|
||||
this.$f7.dialog.alert('Username: ' + this.state.username + '<br>Password: ' + this.state.password, () => {
|
||||
this.$f7.loginScreen.close();
|
||||
});
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
this.$f7ready((f7) => {
|
||||
// Call F7 APIs here
|
||||
});
|
||||
|
||||
const script = document.createElement("script");
|
||||
script.src = "../../../../sdkjs/develop/sdkjs/word/scripts.js";
|
||||
script.async = true;
|
||||
script.onload = () => {
|
||||
let dep_scripts = ['../../../vendor/xregexp/xregexp-all-min.js',
|
||||
'../../../vendor/sockjs/sockjs.min.js',
|
||||
'../../../vendor/jszip/jszip.min.js',
|
||||
'../../../vendor/jszip-utils/jszip-utils.min.js'];
|
||||
dep_scripts.push(...sdk_scripts);
|
||||
|
||||
const promise_get_script = (scriptpath) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const script = document.createElement("script");
|
||||
script.src = scriptpath;
|
||||
script.onload = () => {
|
||||
console.log('loaded ' + scriptpath);
|
||||
resolve('ok');
|
||||
};
|
||||
script.onerror = () => {
|
||||
console.log('error ' + scriptpath);
|
||||
reject('error');
|
||||
};
|
||||
|
||||
document.body.appendChild(script);
|
||||
});
|
||||
};
|
||||
|
||||
const loadConfig = data => {
|
||||
let me = this;
|
||||
console.log('load config');
|
||||
|
||||
me.editorConfig = Object.assign({}, this.editorConfig, data.config);
|
||||
me.appOptions.user = Common.Utils.fillUserInfo(me.editorConfig.user, me.editorConfig.lang, "Local.User"/*me.textAnonymous*/);
|
||||
};
|
||||
|
||||
const loadDocument = data => {
|
||||
this.permissions = {};
|
||||
this.document = data.doc;
|
||||
|
||||
let docInfo = {};
|
||||
|
||||
if (data.doc) {
|
||||
this.permissions = Object.assign(this.permissions, data.doc.permissions);
|
||||
|
||||
let _permissions = Object.assign({}, data.doc.permissions),
|
||||
_user = new Asc.asc_CUserInfo();
|
||||
_user.put_Id(this.appOptions.user.id);
|
||||
_user.put_FullName(this.appOptions.user.fullname);
|
||||
|
||||
docInfo = new Asc.asc_CDocInfo();
|
||||
docInfo.put_Id(data.doc.key);
|
||||
docInfo.put_Url(data.doc.url);
|
||||
docInfo.put_Title(data.doc.title);
|
||||
docInfo.put_Format(data.doc.fileType);
|
||||
docInfo.put_VKey(data.doc.vkey);
|
||||
docInfo.put_Options(data.doc.options);
|
||||
docInfo.put_UserInfo(_user);
|
||||
docInfo.put_CallbackUrl(this.editorConfig.callbackUrl);
|
||||
docInfo.put_Token(data.doc.token);
|
||||
docInfo.put_Permissions(_permissions);
|
||||
docInfo.put_EncryptedInfo(this.editorConfig.encryptionKeys);
|
||||
|
||||
// var enable = !this.editorConfig.customization || (this.editorConfig.customization.macros!==false);
|
||||
// docInfo.asc_putIsEnabledMacroses(!!enable);
|
||||
// enable = !this.editorConfig.customization || (this.editorConfig.customization.plugins!==false);
|
||||
// docInfo.asc_putIsEnabledPlugins(!!enable);
|
||||
|
||||
// let type = /^(?:(pdf|djvu|xps))$/.exec(data.doc.fileType);
|
||||
// if (type && typeof type[1] === 'string') {
|
||||
// this.permissions.edit = this.permissions.review = false;
|
||||
// }
|
||||
}
|
||||
|
||||
this.api.asc_registerCallback('asc_onGetEditorPermissions', onEditorPermissions);
|
||||
// this.api.asc_registerCallback('asc_onLicenseChanged', _.bind(this.onLicenseChanged, this));
|
||||
// this.api.asc_registerCallback('asc_onRunAutostartMacroses', _.bind(this.onRunAutostartMacroses, this));
|
||||
this.api.asc_setDocInfo(docInfo);
|
||||
this.api.asc_getEditorPermissions(this.editorConfig.licenseUrl, this.editorConfig.customerId);
|
||||
|
||||
// Common.SharedSettings.set('document', data.doc);
|
||||
|
||||
// if (data.doc) {
|
||||
// DE.getController('Toolbar').setDocumentTitle(data.doc.title);
|
||||
// if (data.doc.info) {
|
||||
// data.doc.info.author && console.log("Obsolete: The 'author' parameter of the document 'info' section is deprecated. Please use 'owner' instead.");
|
||||
// data.doc.info.created && console.log("Obsolete: The 'created' parameter of the document 'info' section is deprecated. Please use 'uploaded' instead.");
|
||||
// }
|
||||
// }
|
||||
};
|
||||
|
||||
const onEditorPermissions = params => {
|
||||
let me = this;
|
||||
const licType = params.asc_getLicenseType();
|
||||
|
||||
me.appOptions.canLicense = (licType === Asc.c_oLicenseResult.Success || licType === Asc.c_oLicenseResult.SuccessLimit);
|
||||
// me.appOptions.canEdit = (me.permissions.edit !== false || me.permissions.review === true) && // can edit or review
|
||||
// (me.editorConfig.canRequestEditRights || me.editorConfig.mode !== 'view') && // if mode=="view" -> canRequestEditRights must be defined
|
||||
// (!me.appOptions.isReviewOnly || me.appOptions.canLicense) && // if isReviewOnly==true -> canLicense must be true
|
||||
// me.isSupportEditFeature();
|
||||
// me.appOptions.isEdit = me.appOptions.canLicense && me.appOptions.canEdit && me.editorConfig.mode !== 'view';
|
||||
|
||||
// me.api.asc_setViewMode(!me.appOptions.isEdit);
|
||||
me.api.asc_setViewMode(false);
|
||||
me.api.asc_LoadDocument();
|
||||
me.api.Resize();
|
||||
};
|
||||
|
||||
const _process_array = (array, fn) => {
|
||||
let results = [];
|
||||
return array.reduce(function(p, item) {
|
||||
return p.then(function() {
|
||||
return fn(item).then(function(data) {
|
||||
results.push(data);
|
||||
return results;
|
||||
});
|
||||
});
|
||||
}, Promise.resolve());
|
||||
};
|
||||
|
||||
_process_array(dep_scripts, promise_get_script)
|
||||
.then ( result => {
|
||||
this.api = new Asc.asc_docs_api({
|
||||
'id-view' : 'editor_sdk',
|
||||
'mobile' : true,
|
||||
// 'translate': translate
|
||||
});
|
||||
|
||||
this.appOptions = {};
|
||||
|
||||
Common.Gateway.on('init', loadConfig);
|
||||
// Common.Gateway.on('showmessage', _.bind(me.onExternalMessage, me));
|
||||
Common.Gateway.on('opendocument', loadDocument);
|
||||
Common.Gateway.appReady();
|
||||
|
||||
Common.Notifications.trigger('engineCreated', this.api);
|
||||
const { initApi } = this.props;
|
||||
initApi(this.api);
|
||||
}, error => {
|
||||
console.log('promise failed ' + error);
|
||||
});
|
||||
};
|
||||
|
||||
script.onerror = () => {
|
||||
console.log('error');
|
||||
};
|
||||
|
||||
document.body.appendChild(script);
|
||||
this.refs.mainController.initSdk();
|
||||
}
|
||||
}
|
||||
|
||||
const mapDispatchToProps = dispatch => bindActionCreators({
|
||||
initApi
|
||||
}, dispatch);
|
||||
|
||||
export default connect(undefined, mapDispatchToProps)(ComponentApp);
|
||||
|
|
|
@ -1,57 +1,162 @@
|
|||
import React, {Component} from 'react';
|
||||
import {
|
||||
Page,
|
||||
Navbar,
|
||||
NavRight,
|
||||
NavLeft,
|
||||
Link,
|
||||
Popup,
|
||||
Tabs,
|
||||
Tab
|
||||
} from 'framework7-react';
|
||||
import EditText from "./EditText";
|
||||
import React, {useState, useEffect} from 'react';
|
||||
import {observer, inject} from "mobx-react";
|
||||
import { Page, Navbar, NavRight, NavLeft, NavTitle, Link, Sheet, Tabs, Tab, View } from 'framework7-react';
|
||||
import { f7 } from 'framework7-react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
import EditTextController from "./controller/EditText";
|
||||
import EditParagraph from "./EditParagraph";
|
||||
|
||||
export default class EditContainer extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
popupOpened: false,
|
||||
};
|
||||
}
|
||||
render() {
|
||||
const editors = ['text', 'paragraph'];//, 'table', 'header', 'shape', 'image', 'chart', 'hyperlink'];
|
||||
const tabLinks = editors.map((item, index) =>
|
||||
<Link key={"de-tablink-" + item} tabLink={"#" + item} tabLinkActive={index === 0}>{item}</Link>
|
||||
);
|
||||
const tabs = editors.map((item, index) =>
|
||||
<Tab key={"de-tab-" + item} id={item} className="page-content" tabActive={index === 0}>
|
||||
{item === 'text' && <EditText />}
|
||||
{item === 'paragraph' && <EditParagraph />}
|
||||
{/*{item === 'table' && <EditTable />}
|
||||
{item === 'header' && <EditHeader />}
|
||||
{item === 'shape' && <EditShape />}
|
||||
{item === 'image' && <EditImage />}
|
||||
{item === 'chart' && <EditChart />}
|
||||
{item === 'hyperlink' && <EditHyperlink />}*/}
|
||||
</Tab>
|
||||
);
|
||||
const EmptyEditLayout = () => {
|
||||
const { t } = useTranslation();
|
||||
return (
|
||||
<Page>
|
||||
<div className="content-block inset">
|
||||
<div className="content-block-inner">
|
||||
<p>{t("Edit.textSelectObjectToEdit")}</p>
|
||||
</div>
|
||||
</div>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
const EditLayoutNavbar = ({ editors }) => {
|
||||
const { t } = useTranslation();
|
||||
return (
|
||||
<Popup className="edit-popup" opened={this.state.popupOpened} onPopupClosed={() => this.setState({popupOpened : false})}>
|
||||
<Page pageContent={false}>
|
||||
<Navbar>
|
||||
{
|
||||
editors.length > 1 ?
|
||||
<NavLeft tabbar>
|
||||
{tabLinks}
|
||||
</NavLeft>
|
||||
{editors.map((item, index) => <Link key={"de-link-" + item.id} tabLink={"#" + item.id} tabLinkActive={index === 0}>{item.caption}</Link>)}
|
||||
</NavLeft> :
|
||||
<NavTitle>{ editors[0].caption }</NavTitle>
|
||||
}
|
||||
<NavRight>
|
||||
<Link popupClose=".edit-popup">Close</Link>
|
||||
<Link sheetClose>{t("Edit.textClose")}</Link>
|
||||
</NavRight>
|
||||
</Navbar>
|
||||
)
|
||||
};
|
||||
|
||||
const EditLayoutContent = ({ editors }) => {
|
||||
if (editors.length > 1) {
|
||||
return (
|
||||
<Tabs animated>
|
||||
{tabs}
|
||||
{editors.map((item, index) =>
|
||||
<Tab key={"de-tab-" + item.id} id={item.id} className="page-content" tabActive={index === 0}>
|
||||
{item.component}
|
||||
</Tab>
|
||||
)}
|
||||
</Tabs>
|
||||
)
|
||||
} else {
|
||||
return (
|
||||
<Page>
|
||||
{editors[0].component}
|
||||
</Page>
|
||||
</Popup>
|
||||
)
|
||||
}
|
||||
};
|
||||
|
||||
const EditSheet = props => {
|
||||
const { t } = useTranslation();
|
||||
|
||||
const settings = props.storeFocusObjects.settings;
|
||||
const headerType = props.storeFocusObjects.headerType;
|
||||
let editors = [];
|
||||
if (settings.length < 1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textSettings"),
|
||||
component: <EmptyEditLayout />
|
||||
});
|
||||
} else {
|
||||
if (settings.indexOf('text') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textText"),
|
||||
id: 'edit-text',
|
||||
component: <EditTextController />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('paragraph') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textParagraph"),
|
||||
id: 'edit-paragraph',
|
||||
component: <EditParagraph />
|
||||
})
|
||||
}
|
||||
/*if (settings.indexOf('table') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textTable"),
|
||||
id: 'edit-table',
|
||||
component: <EditTable />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('header') > -1) {
|
||||
editors.push({
|
||||
caption: headerType==2 ? t("Edit.textFooter") : t("Edit.textHeader"),
|
||||
id: 'edit-header',
|
||||
component: <EditHeader />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('shape') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textShape"),
|
||||
id: 'edit-shape',
|
||||
component: <EditShape />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('image') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textImage"),
|
||||
id: 'edit-image',
|
||||
component: <EditImage />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('chart') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textChart"),
|
||||
id: 'edit-chart',
|
||||
component: <EditChart />
|
||||
})
|
||||
}
|
||||
if (settings.indexOf('hyperlink') > -1) {
|
||||
editors.push({
|
||||
caption: t("Edit.textHyperlink"),
|
||||
id: 'edit-link',
|
||||
component: <EditHyperlink />
|
||||
})
|
||||
}*/
|
||||
}
|
||||
|
||||
return (
|
||||
<Sheet className="edit__sheet" push onSheetClosed={e => props.onclosed()}>
|
||||
<View>
|
||||
<Page pageContent={false}>
|
||||
<EditLayoutNavbar editors={editors} />
|
||||
<EditLayoutContent editors={editors} />
|
||||
</Page>
|
||||
</View>
|
||||
</Sheet>
|
||||
)
|
||||
};
|
||||
|
||||
const HOC_EditSheet = inject("storeFocusObjects")(observer(EditSheet));
|
||||
|
||||
const EditOptions = props => {
|
||||
useEffect(() => {
|
||||
f7.sheet.open('.edit__sheet');
|
||||
|
||||
return () => {
|
||||
// component will unmount
|
||||
}
|
||||
});
|
||||
|
||||
const onsheetclosed = () => {
|
||||
if ( props.onclosed ) props.onclosed();
|
||||
};
|
||||
|
||||
return (
|
||||
<HOC_EditSheet onclosed={onsheetclosed} />
|
||||
)
|
||||
};
|
||||
|
||||
export default EditOptions;
|
||||
|
|
|
@ -1,96 +1,301 @@
|
|||
import React, {Component, Fragment} from 'react';
|
||||
import {
|
||||
List,
|
||||
ListItem,
|
||||
Icon,
|
||||
Row,
|
||||
Col,
|
||||
Button
|
||||
} from 'framework7-react';
|
||||
import React, {Fragment, useState} from 'react';
|
||||
import {observer, inject} from "mobx-react";
|
||||
import {List, ListItem, Icon, Row, Col, Button, Page, Navbar, Segmented, BlockTitle} from 'framework7-react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
export default class EditText extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
const PageFonts = props => {
|
||||
const { t } = useTranslation();
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const size = storeTextSettings.fontSize;
|
||||
const displaySize = typeof size === 'undefined' ? t('Edit.textAuto') : size + ' ' + t('Edit.textPt');
|
||||
const curFontName = storeTextSettings.fontName;
|
||||
const fonts = storeTextSettings.fontsArray;
|
||||
const [vlFonts, setVlFonts] = useState({
|
||||
vlData: {
|
||||
items: [],
|
||||
}
|
||||
render() {
|
||||
const textFontColor = "Font Color";
|
||||
const textHighlightColor = "Highlight Color";
|
||||
const textAdditionalFormatting = "Additional Formatting";
|
||||
const textBullets = "Bullets";
|
||||
const textNumbers = "Numbers";
|
||||
const textLineSpacing = "Line Spacing";
|
||||
});
|
||||
const renderExternal = (vl, vlData) => {
|
||||
setVlFonts((prevState) => {
|
||||
let fonts = [...prevState.vlData.items];
|
||||
fonts.splice(vlData.fromIndex, vlData.toIndex, ...vlData.items);
|
||||
return {vlData: {
|
||||
items: fonts,
|
||||
}}
|
||||
});
|
||||
};
|
||||
return (
|
||||
<Page>
|
||||
<Navbar title={t('Edit.textFonts')} backLink={t('Edit.textBack')} />
|
||||
<List>
|
||||
<ListItem title={t('Edit.textSize')}>
|
||||
<div slot='after-start'>{displaySize}</div>
|
||||
<div slot='after'>
|
||||
<Segmented>
|
||||
<Button outline className='decrement' onClick={() => {props.changeFontSize(size, true)}}> - </Button>
|
||||
<Button outline className='increment' onClick={() => {props.changeFontSize(size, false)}}> + </Button>
|
||||
</Segmented>
|
||||
</div>
|
||||
</ListItem>
|
||||
</List>
|
||||
<BlockTitle>{t('Edit.textFonts')}</BlockTitle>
|
||||
<List virtualList virtualListParams={{
|
||||
items: fonts,
|
||||
renderExternal: renderExternal
|
||||
}}>
|
||||
<ul>
|
||||
{vlFonts.vlData.items.map((item, index) => (
|
||||
<ListItem
|
||||
key={index}
|
||||
radio
|
||||
checked={curFontName === item.name}
|
||||
title={item.name}
|
||||
style={{fontFamily: `${item.name}`}}
|
||||
onClick={() => {props.changeFontFamily(item.name)}}
|
||||
></ListItem>
|
||||
))}
|
||||
</ul>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
const fontName = 'Arial';
|
||||
const fontSize = '11pt';
|
||||
const PageAdditionalFormatting = props => {
|
||||
const { t } = useTranslation();
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const storeFocusObjects = props.storeFocusObjects;
|
||||
const paragraph = storeFocusObjects.paragraphObject;
|
||||
const isStrikeout = paragraph.get_Strikeout();
|
||||
const isDStrikeout = paragraph.get_DStrikeout();
|
||||
const isSuperscript = storeTextSettings.isSuperscript;
|
||||
const isSubscript = storeTextSettings.isSubscript;
|
||||
const isSmallCaps = paragraph.get_SmallCaps();
|
||||
const isAllCaps = paragraph.get_AllCaps();
|
||||
const letterSpacing = Common.Utils.Metric.fnRecalcFromMM(paragraph.get_TextSpacing());
|
||||
return(
|
||||
<Page>
|
||||
<Navbar title={t('Edit.textAdditional')} backLink={t('Edit.textBack')} />
|
||||
<List>
|
||||
<ListItem title={t('Edit.textStrikethrough')} radio checked={isStrikeout} onClick={() => {props.onAdditionalStrikethrough('strikeout', !isStrikeout)}}/>
|
||||
<ListItem title={t('Edit.textDoubleStrikethrough')} radio checked={isDStrikeout} onClick={() => {props.onAdditionalStrikethrough('dbStrikeout', !isDStrikeout)}}/>
|
||||
<ListItem title={t('Edit.textSuperscript')} radio checked={isSuperscript} onClick={() => {props.onAdditionalScript('superscript', !isSuperscript)}}/>
|
||||
<ListItem title={t('Edit.textSubscript')} radio checked={isSubscript} onClick={() => {props.onAdditionalScript('subscript', !isSubscript)}}/>
|
||||
<ListItem title={t('Edit.textSmallCaps')} radio checked={isSmallCaps} onClick={() => {props.onAdditionalCaps('small', !isSmallCaps)}}/>
|
||||
<ListItem title={t('Edit.textAllCaps')} radio checked={isAllCaps} onClick={() => {props.onAdditionalCaps('all', !isAllCaps)}}/>
|
||||
</List>
|
||||
<List>
|
||||
<ListItem title={t('Edit.textLetterSpacing')}>
|
||||
<div slot='after-start'>{letterSpacing + ' ' + Common.Utils.Metric.getCurrentMetricName()}</div>
|
||||
<div slot='after'>
|
||||
<Segmented>
|
||||
<Button outline className='decrement' onClick={() => {props.changeLetterSpacing(letterSpacing, true)}}> - </Button>
|
||||
<Button outline className='increment' onClick={() => {props.changeLetterSpacing(letterSpacing, false)}}> + </Button>
|
||||
</Segmented>
|
||||
</div>
|
||||
</ListItem>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
import bulletImg1 from '../../../resources/img/bullets/bullet-01.png';
|
||||
import bulletImg2 from '../../../resources/img/bullets/bullet-02.png';
|
||||
import bulletImg3 from '../../../resources/img/bullets/bullet-03.png';
|
||||
import bulletImg4 from '../../../resources/img/bullets/bullet-04.png';
|
||||
import bulletImg5 from '../../../resources/img/bullets/bullet-05.png';
|
||||
import bulletImg6 from '../../../resources/img/bullets/bullet-06.png';
|
||||
import bulletImg7 from '../../../resources/img/bullets/bullet-07.png';
|
||||
const PageBullets = props => {
|
||||
const { t } = useTranslation();
|
||||
const bulletArrays = [
|
||||
[
|
||||
{type: -1, thumb: ''},
|
||||
{type: 1, thumb: bulletImg1},
|
||||
{type: 2, thumb: bulletImg2},
|
||||
{type: 3, thumb: bulletImg3}
|
||||
],
|
||||
[
|
||||
{type: 4, thumb: bulletImg4},
|
||||
{type: 5, thumb: bulletImg5},
|
||||
{type: 6, thumb: bulletImg6},
|
||||
{type: 7, thumb: bulletImg7}
|
||||
]
|
||||
];
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const typeBullets = storeTextSettings.typeBullets;
|
||||
return(
|
||||
<Page>
|
||||
<Navbar title={t('Edit.textBullets')} backLink={t('Edit.textBack')} />
|
||||
{bulletArrays.map((bullets, index) => (
|
||||
<ul className="row" style={{listStyle: 'none'}} key={'bullets-' + index}>
|
||||
{bullets.map((bullet) => (
|
||||
<li key={'bullet-' + bullet.type} data-type={bullet.type} className={bullet.type === typeBullets ? 'active' : ''} onClick={() => {props.onBullet(bullet.type)}}>
|
||||
{bullet.thumb.length < 1 ?
|
||||
<div className="thumb" style={{position: 'relative'}}>
|
||||
<label>{t('Edit.textNone')}</label>
|
||||
</div> :
|
||||
<div className="thumb" style={{height: '70px', width: '70px', backgroundImage: `url("${bullet.thumb}")`, backgroundRepeat: 'no-repeat', backgroundPosition: 'center'}}></div>
|
||||
}
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
))}
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
import numberImg1 from '../../../resources/img/numbers/number-01.png';
|
||||
import numberImg2 from '../../../resources/img/numbers/number-02.png';
|
||||
import numberImg3 from '../../../resources/img/numbers/number-03.png';
|
||||
import numberImg4 from '../../../resources/img/numbers/number-04.png';
|
||||
import numberImg5 from '../../../resources/img/numbers/number-05.png';
|
||||
import numberImg6 from '../../../resources/img/numbers/number-06.png';
|
||||
import numberImg7 from '../../../resources/img/numbers/number-07.png';
|
||||
const PageNumbers = props => {
|
||||
const { t } = useTranslation();
|
||||
const numberArrays = [
|
||||
[
|
||||
{type: -1, thumb: ''},
|
||||
{type: 4, thumb: numberImg1},
|
||||
{type: 5, thumb: numberImg2},
|
||||
{type: 6, thumb: numberImg3}
|
||||
],
|
||||
[
|
||||
{type: 1, thumb: numberImg4},
|
||||
{type: 2, thumb: numberImg5},
|
||||
{type: 3, thumb: numberImg6},
|
||||
{type: 7, thumb: numberImg7}
|
||||
]
|
||||
];
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const typeNumbers = storeTextSettings.typeNumbers;
|
||||
return(
|
||||
<Page>
|
||||
<Navbar title={t('Edit.textNumbers')} backLink={t('Edit.textBack')} />
|
||||
{numberArrays.map((numbers, index) => (
|
||||
<ul className="row" style={{listStyle: 'none'}} key={'numbers-' + index}>
|
||||
{numbers.map((number) => (
|
||||
<li key={'number-' + number.type} data-type={number.type} className={number.type === typeNumbers ? 'active' : ''} onClick={() => {props.onNumber(number.type)}}>
|
||||
{number.thumb.length < 1 ?
|
||||
<div className="thumb" style={{position: 'relative'}}>
|
||||
<label>{t('Edit.textNone')}</label>
|
||||
</div> :
|
||||
<div className="thumb" style={{height: '70px', width: '70px', backgroundImage: `url("${number.thumb}")`, backgroundRepeat: 'no-repeat', backgroundPosition: 'center'}}></div>
|
||||
}
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
))}
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
const PageLineSpacing = props => {
|
||||
const { t } = useTranslation();
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const lineSpacing = storeTextSettings.lineSpacing;
|
||||
return(
|
||||
<Page>
|
||||
<Navbar title={t('Edit.textLineSpacing')} backLink={t('Edit.textBack')} />
|
||||
<List>
|
||||
<ListItem radio checked={lineSpacing === 1.0} title={1.0} onClick={() => {props.onLineSpacing(1.0)}}></ListItem>
|
||||
<ListItem radio checked={lineSpacing === 1.15} title={1.15} onClick={() => {props.onLineSpacing(1.15)}}></ListItem>
|
||||
<ListItem radio checked={lineSpacing === 1.5} title={1.5} onClick={() => {props.onLineSpacing(1.5)}}></ListItem>
|
||||
<ListItem radio checked={lineSpacing === 2.0} title={2.0} onClick={() => {props.onLineSpacing(2.0)}}></ListItem>
|
||||
<ListItem radio checked={lineSpacing === 2.5} title={2.5} onClick={() => {props.onLineSpacing(2.5)}}></ListItem>
|
||||
<ListItem radio checked={lineSpacing === 3.0} title={3.0} onClick={() => {props.onLineSpacing(3.0)}}></ListItem>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
const EditText = props => {
|
||||
const { t } = useTranslation();
|
||||
const storeTextSettings = props.storeTextSettings;
|
||||
const fontName = storeTextSettings.fontName || t('Edit.textFonts');
|
||||
const fontSize = storeTextSettings.fontSize;
|
||||
const displaySize = typeof fontSize === 'undefined' ? t('Edit.textAuto') : fontSize + ' ' + t('Edit.textPt');
|
||||
const isBold = storeTextSettings.isBold;
|
||||
const isItalic = storeTextSettings.isItalic;
|
||||
const isUnderline = storeTextSettings.isUnderline;
|
||||
const isStrikethrough = storeTextSettings.Strikethrough;
|
||||
const paragraphAlign = storeTextSettings.paragraphAlign;
|
||||
return (
|
||||
<Fragment>
|
||||
<List>
|
||||
<ListItem title={fontName} link="#" after={fontSize}></ListItem>
|
||||
<ListItem title={fontName} link="/edit-text-fonts/" after={displaySize} routeProps={{
|
||||
changeFontSize: props.changeFontSize,
|
||||
changeFontFamily: props.changeFontFamily
|
||||
}}/>
|
||||
<ListItem>
|
||||
<Row>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<a className={'button' + (isBold ? ' active' : '')} onClick={() => { props.toggleBold(!isBold)}}><b>B</b></a>
|
||||
<a className={'button' + (isItalic ? ' active' : '')} onClick={() => {props.toggleItalic(!isItalic)}}><i>I</i></a>
|
||||
<a className={'button' + (isUnderline ? ' active' : '')} onClick={() => {props.toggleUnderline(!isUnderline)}} style={{textDecoration: "underline"}}>U</a>
|
||||
<a className={'button' + (isStrikethrough ? ' active' : '')} onClick={() => {props.toggleStrikethrough(!isStrikethrough)}} style={{textDecoration: "line-through"}}>S</a>
|
||||
</Row>
|
||||
</ListItem>
|
||||
<ListItem title={textFontColor} link="#">
|
||||
<ListItem title={t("Edit.textFontColor")} link="#">
|
||||
<Icon slot="media" icon="icon-text-color"></Icon>
|
||||
<span className="color-preview"></span>
|
||||
</ListItem>
|
||||
<ListItem title={textHighlightColor} link="#">
|
||||
<ListItem title={t("Edit.textHighlightColor")} link="#">
|
||||
<Icon slot="media" icon="icon-text-selection"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={textAdditionalFormatting} link="#">
|
||||
<ListItem title={t("Edit.textAdditionalFormatting")} link="/edit-text-add-formatting/" routeProps={{
|
||||
onAdditionalStrikethrough: props.onAdditionalStrikethrough,
|
||||
onAdditionalCaps: props.onAdditionalCaps,
|
||||
onAdditionalScript: props.onAdditionalScript,
|
||||
changeLetterSpacing: props.changeLetterSpacing
|
||||
}}>
|
||||
<Icon slot="media" icon="icon-text-additional"></Icon>
|
||||
</ListItem>
|
||||
</List>
|
||||
<List>
|
||||
<ListItem>
|
||||
<Row>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<a className={'button' + (paragraphAlign === 'left' ? ' active' : '')} onClick={() => {props.onParagraphAlign('left')}}>left</a>
|
||||
<a className={'button' + (paragraphAlign === 'center' ? ' active' : '')} onClick={() => {props.onParagraphAlign('center')}}>center</a>
|
||||
<a className={'button' + (paragraphAlign === 'right' ? ' active' : '')} onClick={() => {props.onParagraphAlign('right')}}>right</a>
|
||||
<a className={'button' + (paragraphAlign === 'just' ? ' active' : '')} onClick={() => {props.onParagraphAlign('just')}}>just</a>
|
||||
</Row>
|
||||
</ListItem>
|
||||
<ListItem>
|
||||
<Row>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<Col>
|
||||
<Button>Button</Button>
|
||||
</Col>
|
||||
<a className='button' onClick={() => {props.onParagraphMove(true)}}>moveleft</a>
|
||||
<a className='button' onClick={() => {props.onParagraphMove(false)}}>moveright</a>
|
||||
</Row>
|
||||
</ListItem>
|
||||
<ListItem title={textBullets} link="#">
|
||||
<ListItem title={t("Edit.textBullets")} link='/edit-text-bullets/' routeProps={{
|
||||
onBullet: props.onBullet
|
||||
}}>
|
||||
<Icon slot="media" icon="icon-bullets"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={textNumbers} link="#">
|
||||
<ListItem title={t("Edit.textNumbers")} link='/edit-text-numbers/' routeProps={{
|
||||
onNumber: props.onNumber
|
||||
}}>
|
||||
<Icon slot="media" icon="icon-numbers"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={textLineSpacing} link="#">
|
||||
<ListItem title={t("Edit.textLineSpacing")} link='/edit-text-line-spacing/' routeProps={{
|
||||
onLineSpacing: props.onLineSpacing
|
||||
}}>
|
||||
<Icon slot="media" icon="icon-linespacing"></Icon>
|
||||
</ListItem>
|
||||
</List>
|
||||
</Fragment>
|
||||
)
|
||||
}
|
||||
};
|
||||
|
||||
const EditTextContainer = inject("storeTextSettings", "storeFocusObjects")(observer(EditText));
|
||||
const PageFontsContainer = inject("storeTextSettings", "storeFocusObjects")(observer(PageFonts));
|
||||
const PageAddFormattingContainer = inject("storeTextSettings", "storeFocusObjects")(observer(PageAdditionalFormatting));
|
||||
const PageBulletsContainer = inject("storeTextSettings")(observer(PageBullets));
|
||||
const PageNumbersContainer = inject("storeTextSettings")(observer(PageNumbers));
|
||||
const PageLineSpacingContainer = inject("storeTextSettings")(observer(PageLineSpacing));
|
||||
|
||||
export {EditTextContainer as EditText,
|
||||
PageFontsContainer as PageFonts,
|
||||
PageAddFormattingContainer as PageAdditionalFormatting,
|
||||
PageBulletsContainer as PageBullets,
|
||||
PageNumbersContainer as PageNumbers,
|
||||
PageLineSpacingContainer as PageLineSpacing};
|
|
@ -0,0 +1,195 @@
|
|||
import React, {Component} from 'react';
|
||||
import { EditText } from '../EditText'
|
||||
|
||||
class EditTextController extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
const api = Common.EditorApi.get();
|
||||
api && api.UpdateInterfaceState();
|
||||
}
|
||||
|
||||
changeFontSize(curSize, isDecrement) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
let size = curSize;
|
||||
if (isDecrement) {
|
||||
typeof size === 'undefined' ? api.FontSizeOut() : size = Math.max(1, --size);
|
||||
} else {
|
||||
typeof size === 'undefined' ? api.FontSizeIn : size = Math.min(100, ++size);
|
||||
}
|
||||
if (typeof size !== 'undefined') {
|
||||
api.put_TextPrFontSize(size);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
changeFontFamily(name) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api && name) {
|
||||
api.put_TextPrFontName(name);
|
||||
}
|
||||
}
|
||||
|
||||
toggleBold(value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_TextPrBold(value);
|
||||
}
|
||||
}
|
||||
|
||||
toggleItalic(value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_TextPrItalic(value);
|
||||
}
|
||||
}
|
||||
|
||||
toggleUnderline(value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_TextPrUnderline(value);
|
||||
}
|
||||
}
|
||||
|
||||
toggleStrikethrough(value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_TextPrStrikeout(value);
|
||||
}
|
||||
}
|
||||
|
||||
// Additional
|
||||
|
||||
onAdditionalStrikethrough(type, value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
if ('strikeout' === type) {
|
||||
api.put_TextPrStrikeout(value);
|
||||
} else {
|
||||
api.put_TextPrDStrikeout(value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onAdditionalCaps(type, value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
const paragraphProps = new Asc.asc_CParagraphProperty();
|
||||
if ('small' === type) {
|
||||
paragraphProps.put_AllCaps(false);
|
||||
paragraphProps.put_SmallCaps(value);
|
||||
} else {
|
||||
paragraphProps.put_AllCaps(value);
|
||||
paragraphProps.put_SmallCaps(false);
|
||||
}
|
||||
api.paraApply(paragraphProps);
|
||||
}
|
||||
}
|
||||
|
||||
onAdditionalScript(type, value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
if ('superscript' === type) {
|
||||
api.put_TextPrBaseline(value ? 1 : 0);
|
||||
} else {
|
||||
api.put_TextPrBaseline(value ? 2 : 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
changeLetterSpacing(curSpacing, isDecrement) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
let spacing = curSpacing;
|
||||
if (isDecrement) {
|
||||
spacing = Math.max(-100, --spacing);
|
||||
} else {
|
||||
spacing = Math.min(100, ++spacing);
|
||||
}
|
||||
const properties = new Asc.asc_CParagraphProperty();
|
||||
properties.put_TextSpacing(Common.Utils.Metric.fnRecalcToMM(spacing));
|
||||
api.paraApply(properties);
|
||||
}
|
||||
}
|
||||
|
||||
onParagraphAlign(type) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
let value;
|
||||
switch (type) {
|
||||
case 'just':
|
||||
value = 3;
|
||||
break;
|
||||
case 'right':
|
||||
value = 0;
|
||||
break;
|
||||
case 'center':
|
||||
value = 2;
|
||||
break;
|
||||
default:
|
||||
value = 1;
|
||||
break;
|
||||
}
|
||||
api.put_PrAlign(value);
|
||||
}
|
||||
}
|
||||
|
||||
onParagraphMove(isLeft) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
if (isLeft) {
|
||||
api.DecreaseIndent();
|
||||
} else {
|
||||
api.IncreaseIndent();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onBullet(type) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_ListType(0, parseInt(type));
|
||||
}
|
||||
}
|
||||
|
||||
onNumber(type) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
api.put_ListType(1, parseInt(type));
|
||||
}
|
||||
}
|
||||
|
||||
onLineSpacing(value) {
|
||||
const api = Common.EditorApi.get();
|
||||
if (api) {
|
||||
const LINERULE_AUTO = 1;
|
||||
api.put_PrLineSpacing(LINERULE_AUTO, value);
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
return (
|
||||
<EditText changeFontSize={this.changeFontSize}
|
||||
changeFontFamily={this.changeFontFamily}
|
||||
toggleBold={this.toggleBold}
|
||||
toggleItalic={this.toggleItalic}
|
||||
toggleUnderline={this.toggleUnderline}
|
||||
toggleStrikethrough={this.toggleStrikethrough}
|
||||
onAdditionalStrikethrough={this.onAdditionalStrikethrough}
|
||||
onAdditionalCaps={this.onAdditionalCaps}
|
||||
onAdditionalScript={this.onAdditionalScript}
|
||||
changeLetterSpacing={this.changeLetterSpacing}
|
||||
onParagraphAlign={this.onParagraphAlign}
|
||||
onParagraphMove={this.onParagraphMove}
|
||||
onBullet={this.onBullet}
|
||||
onNumber={this.onNumber}
|
||||
onLineSpacing={this.onLineSpacing}
|
||||
/>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default EditTextController;
|
|
@ -1,39 +1,65 @@
|
|||
import React, { Component } from 'react';
|
||||
import { View, Page, Navbar, NavRight, Link, Popup, Icon, ListItem, List } from 'framework7-react';
|
||||
import React, {Component, useEffect} from 'react';
|
||||
import {View,Page,Navbar,NavRight,Link,Popup,Popover,Icon,ListItem,List} from 'framework7-react';
|
||||
import { withTranslation } from 'react-i18next';
|
||||
import {changePageOrient} from "../../store/actions/actions";
|
||||
import {f7} from 'framework7-react';
|
||||
import {Device} from '../../../../../common/mobile/utils/device'
|
||||
|
||||
class Settings extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
popupOpened: false,
|
||||
import DocumentSettingsController from "../settings/controller/DocumentSettings.jsx";
|
||||
import Margins from "../settings/document-settings/Margins.jsx";
|
||||
import DocumentFormats from "../settings/document-settings/DocumentFormats.jsx";
|
||||
|
||||
const routes = [
|
||||
{
|
||||
path: '/',
|
||||
component: 'TSettingsView'
|
||||
},
|
||||
{
|
||||
path: '/document-settings/',
|
||||
component: DocumentSettingsController,
|
||||
},
|
||||
{
|
||||
path: '/margins/',
|
||||
component: Margins,
|
||||
},
|
||||
{
|
||||
path: '/document-formats/',
|
||||
component: DocumentFormats,
|
||||
},
|
||||
];
|
||||
|
||||
|
||||
const SettingsList = withTranslation()(props => {
|
||||
const {t} = props;
|
||||
const _t = t('ViewSettings', {returnObjects: true});
|
||||
const navbar = <Navbar title={t('ViewSettings.textSettings')}>
|
||||
{!props.inPopover && <NavRight><Link popupClose=".settings-popup">{t('ViewSettings.textDone')}</Link></NavRight>}
|
||||
</Navbar>;
|
||||
|
||||
const onoptionclick = page => {
|
||||
if ( props.onOptionClick )
|
||||
props.onOptionClick(page)
|
||||
};
|
||||
}
|
||||
render() {
|
||||
const { t } = this.props;
|
||||
const _trarr = t('ViewSettings', {returnObjects: true});
|
||||
|
||||
useEffect(() => {
|
||||
});
|
||||
|
||||
return (
|
||||
<Popup className="settings-popup" opened={this.state.popupOpened} onPopupClosed={() => this.setState({popupOpened : false})}>
|
||||
<View>
|
||||
<View style={props.style} stackPages={true} routes={routes}>
|
||||
<Page>
|
||||
<Navbar title={t('ViewSettings.textSettings')}>
|
||||
<NavRight>
|
||||
<Link popupClose=".settings-popup">{t('ViewSettings.textDone')}</Link>
|
||||
</NavRight>
|
||||
</Navbar>
|
||||
{navbar}
|
||||
<List>
|
||||
<ListItem title={_trarr.textFindAndReplace}>
|
||||
{!props.inPopover &&
|
||||
<ListItem title={_t.textFindAndReplace}>
|
||||
<Icon slot="media" icon="icon-search"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={_trarr.textDocumentSettings} link="/document-settings/">
|
||||
}
|
||||
<ListItem link="#" title={_t.textDocumentSettings} onClick={onoptionclick.bind(this, '/document-settings/')}>
|
||||
<Icon slot="media" icon="icon-doc-setup"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={_trarr.textApplicationSettings} link="#">
|
||||
<ListItem title={_t.textApplicationSettings} link="#">
|
||||
<Icon slot="media" icon="icon-app-settings"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={_trarr.textDownload} link="#">
|
||||
<ListItem title={_t.textDownload} link="#">
|
||||
<Icon slot="media" icon="icon-download"></Icon>
|
||||
</ListItem>
|
||||
<ListItem title={t('ViewSettings.textPrint')}>
|
||||
|
@ -51,9 +77,56 @@ class Settings extends Component {
|
|||
</List>
|
||||
</Page>
|
||||
</View>
|
||||
)
|
||||
});
|
||||
|
||||
class SettingsView extends Component {
|
||||
constructor(props) {
|
||||
super(props)
|
||||
|
||||
this.onoptionclick = this.onoptionclick.bind(this);
|
||||
}
|
||||
|
||||
onoptionclick(page){
|
||||
this.$f7.views.current.router.navigate(page);
|
||||
}
|
||||
|
||||
render() {
|
||||
const show_popover = this.props.usePopover;
|
||||
return (
|
||||
show_popover ?
|
||||
<Popover id="settings-popover" className="popover__titled" onPopoverClosed={() => this.props.onclosed()}>
|
||||
<SettingsList inPopover={true} onOptionClick={this.onoptionclick} style={{height: '410px'}} />
|
||||
</Popover> :
|
||||
<Popup className="settings-popup" onPopupClosed={() => this.props.onclosed()}>
|
||||
<SettingsList onOptionClick={this.onoptionclick} />
|
||||
</Popup>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
const Settings = props => {
|
||||
useEffect(() => {
|
||||
if ( Device.phone )
|
||||
f7.popup.open('.settings-popup');
|
||||
else f7.popover.open('#settings-popover', '#btn-settings');
|
||||
|
||||
return () => {
|
||||
// component will unmount
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
const onviewclosed = () => {
|
||||
if ( props.onclosed )
|
||||
props.onclosed();
|
||||
};
|
||||
|
||||
export default withTranslation()(Settings);
|
||||
// if ( Device.phone ) {
|
||||
// return <SettingsPopup onclosed={onviewclosed} />
|
||||
// }
|
||||
|
||||
return <SettingsView usePopover={!Device.phone} onclosed={onviewclosed} />
|
||||
};
|
||||
|
||||
export default Settings;
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
|
||||
import React, {Component} from 'react';
|
||||
import DocumentSettings from '../document-settings/DocumentSettings'
|
||||
|
||||
|
||||
class DocumentSettingsController extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
}
|
||||
|
||||
onPageOrientation(value){
|
||||
const api = Common.EditorApi.get();
|
||||
api.change_PageOrient(value=='portrait');
|
||||
}
|
||||
|
||||
render() {
|
||||
return (
|
||||
<DocumentSettings onPageOrientation={this.onPageOrientation} />
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default DocumentSettingsController;
|
|
@ -1,27 +1,35 @@
|
|||
import React from 'react';
|
||||
import React, {Component} from 'react';
|
||||
import {observer, inject} from "mobx-react";
|
||||
import {Page,Navbar,List,ListItem,BlockTitle} from 'framework7-react';
|
||||
import { useTranslation } from 'react-i18next';
|
||||
|
||||
const PageDocumentSettings = (props) => {
|
||||
const { t } = useTranslation();
|
||||
const DocumentSettings = props => {
|
||||
const textDocumentSettings = "Document Settings";
|
||||
const textBack = "Back";
|
||||
const textOrientation = "Orientation";
|
||||
const textPortrait = "Portrait";
|
||||
const textLandscape = "Landscape";
|
||||
const textFormat = "Format";
|
||||
const textMargins = "Margins";
|
||||
|
||||
const format = "A4";
|
||||
const formatSize = "21 cm x 29.7 cm";
|
||||
|
||||
const storeSettings = props.storeDocumentSettings;
|
||||
return (
|
||||
<Page>
|
||||
<Navbar title={t('ViewSettings.textDocumentSettings')} backLink={t('ViewSettings.textBack')} />
|
||||
<BlockTitle>{t('ViewSettings.textOrientation')}</BlockTitle>
|
||||
<Navbar title={textDocumentSettings} backLink={textBack} />
|
||||
<BlockTitle>{textOrientation}</BlockTitle>
|
||||
<List>
|
||||
<ListItem checkbox title={t('ViewSettings.textPortrait')} name="orientation-checkbox" checked={props.isPortrait} onClick={(e) => props.changePageOrient(true)}></ListItem>
|
||||
<ListItem checkbox title={t('ViewSettings.textLandscape')} name="orientation-checkbox" checked={!props.isPortrait} onClick={(e) => props.changePageOrient(false)}></ListItem>
|
||||
<ListItem radio title={textPortrait} name="orientation-checkbox" checked={storeSettings.isPortrait} onClick={e => props.onPageOrientation('portrait')}></ListItem>
|
||||
<ListItem radio title={textLandscape} name="orientation-checkbox" checked={!storeSettings.isPortrait} onClick={e => props.onPageOrientation('landscape')}></ListItem>
|
||||
</List>
|
||||
<BlockTitle>{t('ViewSettings.textFormat')}</BlockTitle>
|
||||
<BlockTitle>{textFormat}</BlockTitle>
|
||||
<List mediaList>
|
||||
<ListItem title={format} subtitle={formatSize} link="/document-formats/"></ListItem>
|
||||
<ListItem checkbox title={t('ViewSettings.textMargins')} link="/margins/"></ListItem>
|
||||
<ListItem checkbox title={textMargins} link="/margins/"></ListItem>
|
||||
</List>
|
||||
</Page>
|
||||
)
|
||||
};
|
||||
|
||||
export default PageDocumentSettings;
|
||||
export default inject("storeDocumentSettings")(observer(DocumentSettings));
|
||||
|
|
228
apps/documenteditor/mobile/src/controller/Main.jsx
Normal file
228
apps/documenteditor/mobile/src/controller/Main.jsx
Normal file
|
@ -0,0 +1,228 @@
|
|||
|
||||
import React, {Component} from 'react'
|
||||
import {inject} from "mobx-react";
|
||||
import CollaborationController from '../../../../common/mobile/lib/controller/Collaboration.jsx'
|
||||
|
||||
@inject("storeDocumentSettings", "storeFocusObjects", "storeTextSettings")
|
||||
class MainController extends Component {
|
||||
constructor(props) {
|
||||
super(props)
|
||||
}
|
||||
|
||||
initSdk() {
|
||||
const script = document.createElement("script");
|
||||
script.src = "../../../../sdkjs/develop/sdkjs/word/scripts.js";
|
||||
script.async = true;
|
||||
script.onload = () => {
|
||||
let dep_scripts = ['../../../vendor/xregexp/xregexp-all-min.js',
|
||||
'../../../vendor/sockjs/sockjs.min.js',
|
||||
'../../../vendor/jszip/jszip.min.js',
|
||||
'../../../vendor/jszip-utils/jszip-utils.min.js'];
|
||||
dep_scripts.push(...sdk_scripts);
|
||||
|
||||
const promise_get_script = (scriptpath) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
const script = document.createElement("script");
|
||||
script.src = scriptpath;
|
||||
script.onload = () => {
|
||||
resolve('ok');
|
||||
};
|
||||
script.onerror = () => {
|
||||
reject('error');
|
||||
};
|
||||
|
||||
document.body.appendChild(script);
|
||||
});
|
||||
};
|
||||
|
||||
const loadConfig = data => {
|
||||
let me = this;
|
||||
console.log('load config');
|
||||
|
||||
me.editorConfig = Object.assign({}, this.editorConfig, data.config);
|
||||
me.appOptions.user = Common.Utils.fillUserInfo(me.editorConfig.user, me.editorConfig.lang, "Local.User"/*me.textAnonymous*/);
|
||||
};
|
||||
|
||||
const loadDocument = data => {
|
||||
this.permissions = {};
|
||||
this.document = data.doc;
|
||||
|
||||
let docInfo = {};
|
||||
|
||||
if (data.doc) {
|
||||
this.permissions = Object.assign(this.permissions, data.doc.permissions);
|
||||
|
||||
let _permissions = Object.assign({}, data.doc.permissions),
|
||||
_user = new Asc.asc_CUserInfo();
|
||||
_user.put_Id(this.appOptions.user.id);
|
||||
_user.put_FullName(this.appOptions.user.fullname);
|
||||
|
||||
docInfo = new Asc.asc_CDocInfo();
|
||||
docInfo.put_Id(data.doc.key);
|
||||
docInfo.put_Url(data.doc.url);
|
||||
docInfo.put_Title(data.doc.title);
|
||||
docInfo.put_Format(data.doc.fileType);
|
||||
docInfo.put_VKey(data.doc.vkey);
|
||||
docInfo.put_Options(data.doc.options);
|
||||
docInfo.put_UserInfo(_user);
|
||||
docInfo.put_CallbackUrl(this.editorConfig.callbackUrl);
|
||||
docInfo.put_Token(data.doc.token);
|
||||
docInfo.put_Permissions(_permissions);
|
||||
docInfo.put_EncryptedInfo(this.editorConfig.encryptionKeys);
|
||||
|
||||
// var enable = !this.editorConfig.customization || (this.editorConfig.customization.macros!==false);
|
||||
// docInfo.asc_putIsEnabledMacroses(!!enable);
|
||||
// enable = !this.editorConfig.customization || (this.editorConfig.customization.plugins!==false);
|
||||
// docInfo.asc_putIsEnabledPlugins(!!enable);
|
||||
|
||||
// let type = /^(?:(pdf|djvu|xps))$/.exec(data.doc.fileType);
|
||||
// if (type && typeof type[1] === 'string') {
|
||||
// this.permissions.edit = this.permissions.review = false;
|
||||
// }
|
||||
}
|
||||
|
||||
this.api.asc_registerCallback('asc_onGetEditorPermissions', onEditorPermissions);
|
||||
// this.api.asc_registerCallback('asc_onLicenseChanged', _.bind(this.onLicenseChanged, this));
|
||||
// this.api.asc_registerCallback('asc_onRunAutostartMacroses', _.bind(this.onRunAutostartMacroses, this));
|
||||
this.api.asc_setDocInfo(docInfo);
|
||||
this.api.asc_getEditorPermissions(this.editorConfig.licenseUrl, this.editorConfig.customerId);
|
||||
|
||||
// Common.SharedSettings.set('document', data.doc);
|
||||
|
||||
// if (data.doc) {
|
||||
// DE.getController('Toolbar').setDocumentTitle(data.doc.title);
|
||||
// if (data.doc.info) {
|
||||
// data.doc.info.author && console.log("Obsolete: The 'author' parameter of the document 'info' section is deprecated. Please use 'owner' instead.");
|
||||
// data.doc.info.created && console.log("Obsolete: The 'created' parameter of the document 'info' section is deprecated. Please use 'uploaded' instead.");
|
||||
// }
|
||||
// }
|
||||
};
|
||||
|
||||
const onEditorPermissions = params => {
|
||||
let me = this;
|
||||
const licType = params.asc_getLicenseType();
|
||||
|
||||
me.appOptions.canLicense = (licType === Asc.c_oLicenseResult.Success || licType === Asc.c_oLicenseResult.SuccessLimit);
|
||||
// me.appOptions.canEdit = (me.permissions.edit !== false || me.permissions.review === true) && // can edit or review
|
||||
// (me.editorConfig.canRequestEditRights || me.editorConfig.mode !== 'view') && // if mode=="view" -> canRequestEditRights must be defined
|
||||
// (!me.appOptions.isReviewOnly || me.appOptions.canLicense) && // if isReviewOnly==true -> canLicense must be true
|
||||
// me.isSupportEditFeature();
|
||||
// me.appOptions.isEdit = me.appOptions.canLicense && me.appOptions.canEdit && me.editorConfig.mode !== 'view';
|
||||
|
||||
// me.api.asc_setViewMode(!me.appOptions.isEdit);
|
||||
me.api.asc_setViewMode(false);
|
||||
me.api.asc_LoadDocument();
|
||||
me.api.Resize();
|
||||
};
|
||||
|
||||
const _process_array = (array, fn) => {
|
||||
let results = [];
|
||||
return array.reduce(function(p, item) {
|
||||
return p.then(function() {
|
||||
return fn(item).then(function(data) {
|
||||
results.push(data);
|
||||
return results;
|
||||
});
|
||||
});
|
||||
}, Promise.resolve());
|
||||
};
|
||||
|
||||
_process_array(dep_scripts, promise_get_script)
|
||||
.then ( result => {
|
||||
this.api = new Asc.asc_docs_api({
|
||||
'id-view' : 'editor_sdk',
|
||||
'mobile' : true,
|
||||
// 'translate': translate
|
||||
});
|
||||
|
||||
this.appOptions = {};
|
||||
this.bindEvents();
|
||||
|
||||
Common.Gateway.on('init', loadConfig);
|
||||
// Common.Gateway.on('showmessage', _.bind(me.onExternalMessage, me));
|
||||
Common.Gateway.on('opendocument', loadDocument);
|
||||
Common.Gateway.appReady();
|
||||
|
||||
Common.Notifications.trigger('engineCreated', this.api);
|
||||
Common.EditorApi = {get: () => this.api};
|
||||
}, error => {
|
||||
console.log('promise failed ' + error);
|
||||
});
|
||||
};
|
||||
|
||||
script.onerror = () => {
|
||||
console.log('error');
|
||||
};
|
||||
|
||||
document.body.appendChild(script);
|
||||
}
|
||||
|
||||
bindEvents() {
|
||||
const storeSettings = this.props.storeDocumentSettings;
|
||||
this.api.asc_registerCallback('asc_onPageOrient', isPortrait => {
|
||||
storeSettings.isPortrait = isPortrait === true;
|
||||
});
|
||||
const storeFocusObjects = this.props.storeFocusObjects;
|
||||
this.api.asc_registerCallback('asc_onFocusObject', objects => {
|
||||
storeFocusObjects.resetFocusObjects(objects);
|
||||
});
|
||||
|
||||
const storeTextSettings = this.props.storeTextSettings;
|
||||
this.api.asc_registerCallback('asc_onInitEditorFonts', (fonts, select) => {
|
||||
storeTextSettings.initEditorFonts(fonts, select);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onFontFamily', (font) => {
|
||||
storeTextSettings.resetFontName(font);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onFontSize', (size) => {
|
||||
storeTextSettings.resetFontSize(size);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onBold', (isBold) => {
|
||||
storeTextSettings.resetIsBold(isBold);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onItalic', (isItalic) => {
|
||||
storeTextSettings.resetIsItalic(isItalic);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onUnderline', (isUnderline) => {
|
||||
storeTextSettings.resetIsUnderline(isUnderline);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onStrikeout', (isStrikeout) => {
|
||||
storeTextSettings.resetIsStrikeout(isStrikeout);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onVerticalAlign', (typeBaseline) => {
|
||||
storeTextSettings.resetTypeBaseline(typeBaseline);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onListType', (data) => {
|
||||
let type = data.get_ListType();
|
||||
let subtype = data.get_ListSubType();
|
||||
storeTextSettings.resetListType(type);
|
||||
switch (type) {
|
||||
case 0:
|
||||
storeTextSettings.resetBullets(subtype);
|
||||
break;
|
||||
case 1:
|
||||
storeTextSettings.resetNumbers(subtype);
|
||||
break;
|
||||
}
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onPrAlign', (align) => {
|
||||
storeTextSettings.resetParagraphAlign(align);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onTextColor', (color) => {
|
||||
storeTextSettings.resetTextColor(color);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onParaSpacingLine', (vc) => {
|
||||
storeTextSettings.resetLineSpacing(vc);
|
||||
});
|
||||
this.api.asc_registerCallback('asc_onTextShd', (shd) => {
|
||||
let color = shd.get_Color();
|
||||
storeTextSettings.resetBackgroundColor(color);
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
return <CollaborationController />
|
||||
}
|
||||
}
|
||||
|
||||
export default MainController;
|
3
apps/documenteditor/mobile/src/css/app-ios.less
Normal file
3
apps/documenteditor/mobile/src/css/app-ios.less
Normal file
|
@ -0,0 +1,3 @@
|
|||
|
||||
.device-ios {
|
||||
}
|
12
apps/documenteditor/mobile/src/css/app-material.less
Normal file
12
apps/documenteditor/mobile/src/css/app-material.less
Normal file
|
@ -0,0 +1,12 @@
|
|||
|
||||
// Colors
|
||||
@themeColor: #446995; // (64,102,215)
|
||||
@themeColorLight: #a2bdde;
|
||||
@navBarIconColor: #fff;
|
||||
|
||||
|
||||
.device-android {
|
||||
--f7-navbar-bg-color: @themeColor;
|
||||
--f7-navbar-link-color: @navBarIconColor;
|
||||
--f7-navbar-text-color: @navBarIconColor;
|
||||
}
|
|
@ -1,5 +1,9 @@
|
|||
|
||||
@import '../../../../common/mobile/resources/less/collaboration.less';
|
||||
@import '../../../../common/mobile/resources/less/common-ios.less';
|
||||
@import '../../../../common/mobile/resources/less/common-material.less';
|
||||
@import './app-material.less';
|
||||
@import './app-ios.less';
|
||||
|
||||
/* Left Panel right border when it is visible by breakpoint */
|
||||
.panel-left.panel-in-breakpoint:before {
|
||||
|
@ -32,3 +36,7 @@
|
|||
content: '';
|
||||
z-index: 6000;
|
||||
}
|
||||
|
||||
:root {
|
||||
--f7-popover-width: 360px;
|
||||
}
|
||||
|
|
|
@ -28,6 +28,11 @@
|
|||
</head>
|
||||
<body>
|
||||
<script>
|
||||
const isAndroid = /Android/.test(navigator.userAgent);
|
||||
if ( isAndroid && navigator.platform == 'Win32' )
|
||||
// Framework7 doesn't set Device.android flag when navigator.platform == 'Win32', change it for debug
|
||||
navigator.__defineGetter__('platform', () => 'Win32Debug');
|
||||
|
||||
const getUrlParams = () => {
|
||||
let e,
|
||||
a = /\+/g, // Regex for replacing addition symbol with a space
|
||||
|
@ -53,7 +58,7 @@
|
|||
logo = /*params["headerlogo"] ? encodeUrlParam(params["headerlogo"]) : */null,
|
||||
logoOO = null;
|
||||
if (!logo) {
|
||||
logoOO = /Android/.test(navigator.userAgent) ? "../../common/mobile/resources/img/header/header-logo-android.png" : "../../common/mobile/resources/img/header/header-logo-ios.png";
|
||||
logoOO = isAndroid ? "../../common/mobile/resources/img/header/header-logo-android.png" : "../../common/mobile/resources/img/header/header-logo-ios.png";
|
||||
}
|
||||
|
||||
window.frameEditorId = params["frameEditorId"];
|
||||
|
@ -62,7 +67,7 @@
|
|||
|
||||
let brendpanel = document.getElementsByClassName('brendpanel')[0];
|
||||
if (brendpanel) {
|
||||
if (/Android/.test(navigator.userAgent)) {
|
||||
if ( isAndroid ) {
|
||||
brendpanel.classList.add('android');
|
||||
}
|
||||
brendpanel.classList.add('visible');
|
||||
|
@ -74,7 +79,7 @@
|
|||
elem.style.opacity = 1;
|
||||
}
|
||||
var placeholder = document.getElementsByClassName('placeholder')[0];
|
||||
if (placeholder && /Android/.test(navigator.userAgent)) {
|
||||
if (placeholder && isAndroid) {
|
||||
placeholder.classList.add('android');
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,8 +24,8 @@ import App from '../components/app.jsx';
|
|||
import { I18nextProvider } from 'react-i18next';
|
||||
import i18n from './i18n';
|
||||
|
||||
import { Provider } from 'react-redux'
|
||||
import { store } from '../store/store.js'
|
||||
import { Provider } from 'mobx-react'
|
||||
import { stores } from '../store/mainStore'
|
||||
|
||||
// Init F7 React Plugin
|
||||
Framework7.use(Framework7React)
|
||||
|
@ -33,7 +33,7 @@ Framework7.use(Framework7React)
|
|||
// Mount React App
|
||||
ReactDOM.render(
|
||||
<I18nextProvider i18n={i18n}>
|
||||
<Provider store={store}>
|
||||
<Provider {...stores}>
|
||||
<Suspense fallback="loading">
|
||||
<App />
|
||||
</Suspense>
|
||||
|
|
|
@ -1,8 +1,5 @@
|
|||
|
||||
import HomePage from '../pages/home.jsx';
|
||||
import { DocumentSettings } from "../controllers/Settings";
|
||||
import Margins from "../components/settings/document-settings/Margins.jsx";
|
||||
import DocumentFormats from "../components/settings/document-settings/DocumentFormats.jsx";
|
||||
|
||||
import LeftPage1 from '../pages/left-page-1.jsx';
|
||||
import LeftPage2 from '../pages/left-page-2.jsx';
|
||||
|
@ -11,31 +8,39 @@ import RequestAndLoad from '../pages/request-and-load.jsx';
|
|||
|
||||
import { PageCollaboration, PageUsers } from '../../../../common/mobile/lib/view/Collaboration.jsx';
|
||||
|
||||
// Edit text
|
||||
import { PageFonts, PageAdditionalFormatting, PageBullets, PageNumbers, PageLineSpacing } from "../components/edit/EditText";
|
||||
|
||||
var routes = [
|
||||
{
|
||||
path: '/',
|
||||
component: HomePage,
|
||||
},
|
||||
//Edit text
|
||||
{
|
||||
path: '/document-settings/',
|
||||
component: DocumentSettings
|
||||
path: '/edit-text-fonts/',
|
||||
component: PageFonts,
|
||||
},
|
||||
{
|
||||
path: '/edit-text-add-formatting/',
|
||||
component: PageAdditionalFormatting,
|
||||
},
|
||||
{
|
||||
path: '/edit-text-bullets/',
|
||||
component: PageBullets,
|
||||
},
|
||||
{
|
||||
path: '/edit-text-numbers/',
|
||||
component: PageNumbers,
|
||||
},
|
||||
{
|
||||
path: '/edit-text-line-spacing/',
|
||||
component: PageLineSpacing,
|
||||
},
|
||||
{
|
||||
path: '/users/',
|
||||
component: PageUsers
|
||||
},
|
||||
{
|
||||
path: '/collab-main/',
|
||||
component: PageCollaboration
|
||||
},
|
||||
{
|
||||
path: '/margins/',
|
||||
component: Margins,
|
||||
},
|
||||
{
|
||||
path: '/document-formats/',
|
||||
component: DocumentFormats,
|
||||
},
|
||||
{
|
||||
path: '/left-page-1/',
|
||||
component: LeftPage1,
|
||||
|
|
|
@ -1,32 +1,48 @@
|
|||
import React, { Component } from 'react';
|
||||
import {
|
||||
Page,
|
||||
View,
|
||||
Navbar,
|
||||
NavLeft,
|
||||
NavTitle,
|
||||
NavTitleLarge,
|
||||
NavRight,
|
||||
Link,
|
||||
Toolbar,
|
||||
Block,
|
||||
BlockTitle,
|
||||
List,
|
||||
ListItem,
|
||||
Row,
|
||||
Col,
|
||||
Button,
|
||||
Icon, Popup
|
||||
} from 'framework7-react';
|
||||
import { Page, View, Navbar, NavLeft, NavRight, Link, Icon } from 'framework7-react';
|
||||
|
||||
import EditPopup from '../components/edit/Edit';
|
||||
import SettingsPopup from '../components/settings/Settings';
|
||||
import { CollaborationPopover, CollaborationSheet } from '../../../../common/mobile/lib/view/Collaboration.jsx';
|
||||
import EditOptions from '../components/edit/Edit.jsx';
|
||||
import Settings from '../components/settings/Settings.jsx';
|
||||
import CollaborationView from '../../../../common/mobile/lib/view/Collaboration.jsx'
|
||||
|
||||
export default class Home extends Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
this.state = {
|
||||
editOptionsVisible: false,
|
||||
settingsVisible: false,
|
||||
collaborationVisible: false,
|
||||
};
|
||||
}
|
||||
|
||||
handleClickToOpenOptions = opts => {
|
||||
this.setState(state => {
|
||||
if ( opts == 'edit' )
|
||||
return {editOptionsVisible: true};
|
||||
else
|
||||
if ( opts == 'settings' )
|
||||
return {settingsVisible: true};
|
||||
else
|
||||
if ( opts == 'coauth' )
|
||||
return {collaborationVisible: true}
|
||||
});
|
||||
};
|
||||
|
||||
handleOptionsViewClosed = opts => {
|
||||
(async () => {
|
||||
await 1 && this.setState(state => {
|
||||
if ( opts == 'edit' )
|
||||
return {editOptionsVisible: false};
|
||||
else
|
||||
if ( opts == 'settings' )
|
||||
return {settingsVisible: false};
|
||||
else
|
||||
if ( opts == 'coauth' )
|
||||
return {collaborationVisible: false}
|
||||
})
|
||||
})();
|
||||
};
|
||||
|
||||
render() {
|
||||
console.log(this.$f7router)
|
||||
return (
|
||||
|
@ -36,22 +52,29 @@ export default class Home extends Component {
|
|||
<div slot="before-inner" className="main-logo"><Icon icon="icon-logo"></Icon></div>
|
||||
<NavLeft>
|
||||
<Link>Undo</Link>
|
||||
<Link>Redu</Link>
|
||||
<Link>Redo</Link>
|
||||
</NavLeft>
|
||||
<NavRight>
|
||||
<Link href={false} popupOpen=".edit-popup">Edit</Link>
|
||||
{/*<Link href={false} popoverOpen=".collab__popover">Users</Link>*/}
|
||||
<Link href={false} sheetOpen=".collab__sheet">Users</Link>
|
||||
<Link href={false} popupOpen=".settings-popup">Settings</Link>
|
||||
<Link href={false} onClick={e => this.handleClickToOpenOptions('edit')}>Edit</Link>
|
||||
<Link href={false} onClick={e => this.handleClickToOpenOptions('coauth')}>Users</Link>
|
||||
<Link href={false} onClick={e => this.handleClickToOpenOptions('settings')} id='btn-settings'>Settings</Link>
|
||||
</NavRight>
|
||||
</Navbar>
|
||||
{/* Page content */}
|
||||
<View id="editor_sdk">
|
||||
</View>
|
||||
<EditPopup />
|
||||
<SettingsPopup />
|
||||
<CollaborationPopover />
|
||||
<CollaborationSheet />
|
||||
{
|
||||
!this.state.editOptionsVisible ? null :
|
||||
<EditOptions onclosed={this.handleOptionsViewClosed.bind(this, 'edit')} />
|
||||
}
|
||||
{
|
||||
!this.state.settingsVisible ? null :
|
||||
<Settings onclosed={this.handleOptionsViewClosed.bind(this, 'settings')} />
|
||||
}
|
||||
{
|
||||
!this.state.collaborationVisible ? null :
|
||||
<CollaborationView onclosed={this.handleOptionsViewClosed.bind(this, 'coauth')} />
|
||||
}
|
||||
</Page>
|
||||
)
|
||||
}
|
||||
|
|
6
apps/documenteditor/mobile/src/store/documentSettings.js
Normal file
6
apps/documenteditor/mobile/src/store/documentSettings.js
Normal file
|
@ -0,0 +1,6 @@
|
|||
|
||||
import {action, observable} from 'mobx';
|
||||
|
||||
export class storeDocumentSettings {
|
||||
@observable isPortrait = true
|
||||
}
|
60
apps/documenteditor/mobile/src/store/focusObjects.js
Normal file
60
apps/documenteditor/mobile/src/store/focusObjects.js
Normal file
|
@ -0,0 +1,60 @@
|
|||
import {action, observable, computed} from 'mobx';
|
||||
|
||||
export class storeFocusObjects {
|
||||
@observable _focusObjects = [];
|
||||
@observable _headerType = 1;
|
||||
|
||||
@action resetFocusObjects (objects) {
|
||||
this._focusObjects = objects;
|
||||
}
|
||||
|
||||
@computed get settings() {
|
||||
let _settings = [];
|
||||
for (let object of this._focusObjects) {
|
||||
let type = object.get_ObjectType();
|
||||
if (Asc.c_oAscTypeSelectElement.Paragraph === type) {
|
||||
_settings.push('text', 'paragraph');
|
||||
} else if (Asc.c_oAscTypeSelectElement.Table === type) {
|
||||
_settings.push('table');
|
||||
} else if (Asc.c_oAscTypeSelectElement.Image === type) {
|
||||
if (object.get_ObjectValue().get_ChartProperties()) {
|
||||
// Exclude shapes if chart exist
|
||||
let si = _settings.indexOf('shape');
|
||||
si < 0 ? _settings.push('chart') : _settings.splice(si,1,'chart');
|
||||
} else if (object.get_ObjectValue().get_ShapeProperties() && !_settings.includes('chart')) {
|
||||
_settings.push('shape');
|
||||
} else {
|
||||
_settings.push('image');
|
||||
}
|
||||
} else if (Asc.c_oAscTypeSelectElement.Hyperlink === type) {
|
||||
_settings.push('hyperlink');
|
||||
} else if (Asc.c_oAscTypeSelectElement.Header === type) {
|
||||
_settings.push('header');
|
||||
}
|
||||
}
|
||||
return _settings.filter((value, index, self) => self.indexOf(value) === index);
|
||||
}
|
||||
@computed get headerType() {
|
||||
for (let object of this._focusObjects) {
|
||||
let type = object.get_ObjectType();
|
||||
if (Asc.c_oAscTypeSelectElement.Header === type) {
|
||||
return object.get_ObjectValue().get_Type();
|
||||
}
|
||||
}
|
||||
return this._headerType;
|
||||
}
|
||||
@computed get paragraphObject() {
|
||||
let paragraphs = [];
|
||||
for (let object of this._focusObjects) {
|
||||
if (object.get_ObjectType() == Asc.c_oAscTypeSelectElement.Paragraph) {
|
||||
paragraphs.push(object);
|
||||
}
|
||||
}
|
||||
if (paragraphs.length > 0) {
|
||||
let object = paragraphs[paragraphs.length - 1]; // get top
|
||||
return object.get_ObjectValue();
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
}
|
13
apps/documenteditor/mobile/src/store/mainStore.js
Normal file
13
apps/documenteditor/mobile/src/store/mainStore.js
Normal file
|
@ -0,0 +1,13 @@
|
|||
|
||||
import {storeDocumentSettings} from './documentSettings';
|
||||
import {storeFocusObjects} from "./focusObjects";
|
||||
import {storeUsers} from '../../../../common/mobile/lib/store/users';
|
||||
import {storeTextSettings} from "./textSettings";
|
||||
|
||||
export const stores = {
|
||||
storeFocusObjects: new storeFocusObjects(),
|
||||
storeDocumentSettings: new storeDocumentSettings(),
|
||||
users: new storeUsers(),
|
||||
storeTextSettings: new storeTextSettings()
|
||||
};
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
import { combineReducers } from 'redux';
|
||||
import apiReducer from "./initApi";
|
||||
import usersReducer from '../../../../../common/mobile/lib/store/users'
|
||||
import settingsReducer from './settings'
|
||||
|
||||
export const initialState = {
|
||||
users: []
|
||||
};
|
||||
|
||||
export const rootReducer = combineReducers({
|
||||
api: apiReducer,
|
||||
users: usersReducer,
|
||||
settings: settingsReducer
|
||||
});
|
|
@ -1,10 +0,0 @@
|
|||
import { createStore, applyMiddleware } from 'redux';
|
||||
import { rootReducer, initialState } from './reducers/root'
|
||||
import thunk from 'redux-thunk';
|
||||
|
||||
const store = createStore(rootReducer, initialState, applyMiddleware(thunk));
|
||||
|
||||
!window.Common && (window.Common = {});
|
||||
Common.Store = { get: () => store };
|
||||
|
||||
export { store };
|
132
apps/documenteditor/mobile/src/store/textSettings.js
Normal file
132
apps/documenteditor/mobile/src/store/textSettings.js
Normal file
|
@ -0,0 +1,132 @@
|
|||
import {action, observable, computed} from 'mobx';
|
||||
|
||||
export class storeTextSettings {
|
||||
@observable fontsArray = [];
|
||||
@observable fontName = '';
|
||||
@observable fontSize = undefined;
|
||||
@observable isBold = false;
|
||||
@observable isItalic = false;
|
||||
@observable isUnderline = false;
|
||||
@observable isStrikethrough = false;
|
||||
@observable typeBaseline = undefined;
|
||||
@observable listType = undefined;
|
||||
@observable typeBullets = undefined;
|
||||
@observable typeNumbers = undefined;
|
||||
@observable paragraphAlign = undefined;
|
||||
@observable textColor = undefined;
|
||||
@observable lineSpacing = undefined;
|
||||
@observable backgroundColor = undefined;
|
||||
|
||||
|
||||
@action initEditorFonts (fonts, select) {
|
||||
let array = [];
|
||||
for (let font of fonts) {
|
||||
let fontId = font.asc_getFontId();
|
||||
array.push({
|
||||
id : fontId,
|
||||
name : font.asc_getFontName(),
|
||||
//displayValue: font.asc_getFontName(),
|
||||
imgidx : font.asc_getFontThumbnail(),
|
||||
type : font.asc_getFontType()
|
||||
});
|
||||
}
|
||||
this.fontsArray = array;
|
||||
}
|
||||
@action resetFontName (font) {
|
||||
let name = (typeof font.get_Name) === "function" ? font.get_Name() : font.asc_getName();
|
||||
this.fontName = name;
|
||||
}
|
||||
@action resetFontSize (size) {
|
||||
this.fontSize = size;
|
||||
}
|
||||
@action resetIsBold (isBold) {
|
||||
this.isBold = isBold;
|
||||
}
|
||||
@action resetIsItalic (isItalic) {
|
||||
this.isItalic = isItalic;
|
||||
}
|
||||
@action resetIsUnderline (isUnderline) {
|
||||
this.isUnderline = isUnderline;
|
||||
}
|
||||
@action resetIsStrikeout (isStrikethrough) {
|
||||
this.isStrikethrough = isStrikethrough;
|
||||
}
|
||||
|
||||
// vertical align
|
||||
@action resetTypeBaseline (typeBaseline) {
|
||||
this.typeBaseline = typeBaseline;
|
||||
}
|
||||
@computed get isSuperscript() {
|
||||
return (this.typeBaseline === 1);
|
||||
}
|
||||
@computed get isSubscript() {
|
||||
return (this.typeBaseline === 2);
|
||||
}
|
||||
|
||||
// bullets
|
||||
@action resetListType (type) {
|
||||
this.listType = type;
|
||||
}
|
||||
@action resetBullets (type) {
|
||||
this.typeBullets = type;
|
||||
}
|
||||
@action resetNumbers (type) {
|
||||
this.typeNumbers = type;
|
||||
}
|
||||
|
||||
@action resetParagraphAlign (align) {
|
||||
let value;
|
||||
switch (align) {
|
||||
case 0:
|
||||
value = 'right';
|
||||
break;
|
||||
case 1:
|
||||
value = 'left';
|
||||
break;
|
||||
case 2:
|
||||
value = 'center';
|
||||
break;
|
||||
case 3:
|
||||
value = 'just';
|
||||
break;
|
||||
}
|
||||
this.paragraphAlign = value;
|
||||
}
|
||||
|
||||
@action resetTextColor (color) {
|
||||
let value;
|
||||
if (color) {
|
||||
if (color.get_auto()) {
|
||||
value = '000000';
|
||||
} else {
|
||||
if (color.get_type() == Asc.c_oAscColor.COLOR_TYPE_SCHEME) {
|
||||
value = {
|
||||
color: Common.Utils.ThemeColor.getHexColor(color.get_r(), color.get_g(), color.get_b()),
|
||||
effectValue: color.get_value()
|
||||
}
|
||||
} else {
|
||||
value = Common.Utils.ThemeColor.getHexColor(color.get_r(), color.get_g(), color.get_b());
|
||||
}
|
||||
}
|
||||
}
|
||||
this.textColor = value;
|
||||
}
|
||||
|
||||
@action resetLineSpacing (vc) {
|
||||
let line = (vc.get_Line() === null || vc.get_LineRule() === null || vc.get_LineRule() != 1) ? -1 : vc.get_Line();
|
||||
this.lineSpacing = line;
|
||||
}
|
||||
|
||||
@action resetBackgroundColor (color) {
|
||||
let value;
|
||||
if (color.get_type() == Asc.c_oAscColor.COLOR_TYPE_SCHEME) {
|
||||
value = {
|
||||
color: Common.Utils.ThemeColor.getHexColor(color.get_r(), color.get_g(), color.get_b()),
|
||||
effectValue: color.get_value()
|
||||
}
|
||||
} else {
|
||||
value = Common.Utils.ThemeColor.getHexColor(color.get_r(), color.get_g(), color.get_b());
|
||||
}
|
||||
this.backgroundColor = value;
|
||||
}
|
||||
}
|
2
vendor/framework7-react/babel.config.js
vendored
2
vendor/framework7-react/babel.config.js
vendored
|
@ -8,5 +8,7 @@ module.exports = {
|
|||
plugins: [
|
||||
'@babel/plugin-transform-runtime',
|
||||
'@babel/plugin-syntax-dynamic-import',
|
||||
['@babel/plugin-proposal-decorators', {'legacy': true }],
|
||||
['@babel/plugin-proposal-class-properties',{'loose':true}],
|
||||
],
|
||||
};
|
||||
|
|
4
vendor/framework7-react/package.json
vendored
4
vendor/framework7-react/package.json
vendored
|
@ -35,6 +35,8 @@
|
|||
},
|
||||
"devDependencies": {
|
||||
"@babel/core": "^7.11.0",
|
||||
"@babel/plugin-proposal-class-properties": "^7.10.4",
|
||||
"@babel/plugin-proposal-decorators": "^7.10.5",
|
||||
"@babel/plugin-syntax-dynamic-import": "^7.8.3",
|
||||
"@babel/plugin-transform-runtime": "^7.11.0",
|
||||
"@babel/preset-env": "^7.11.0",
|
||||
|
@ -52,6 +54,8 @@
|
|||
"less": "^3.12.2",
|
||||
"less-loader": "^6.2.0",
|
||||
"mini-css-extract-plugin": "^0.9.0",
|
||||
"mobx": "^5.15.7",
|
||||
"mobx-react": "^6.3.0",
|
||||
"optimize-css-assets-webpack-plugin": "^5.0.3",
|
||||
"ora": "^4.0.5",
|
||||
"postcss-loader": "^3.0.0",
|
||||
|
|
Loading…
Reference in a new issue