Commit 21d1c8ab authored by Alexandros Georgantas's avatar Alexandros Georgantas

Merge branch 'everything' into 'master'

Super merge

See merge request !3
parents 81590970 fafcd24c
Pipeline #9296 failed with stages
in 9 seconds
......@@ -30,6 +30,9 @@
"react-redux": "5.0.4",
"react-router-bootstrap": "0.24.4",
"react-router-dom": "4.2.2",
"react-select": "^2.0.0",
"react-codemirror": "^1.0.0",
"codemirror": "^5.40.2",
"redux": "3.7.2"
},
"devDependencies": {
......
......@@ -247,7 +247,7 @@ export class BookBuilder extends React.Component {
// }
render() {
const { book, chapters } = this.props
const { book, chapters, history } = this.props
const {
createFragment,
htmlToEpub,
......@@ -293,10 +293,11 @@ export class BookBuilder extends React.Component {
</button>
</Authorize>
</div>
<h1 className={`${styles.bookTitle}`}>{this.props.book.title}</h1>
<div className={`${styles.btnContainer}`}>
<div className={`${styles.lineUploading} `} />
<div className={styles.btnContainerButtons}>
<div className={`${styles.headerContainer}`}>
<div className={`${styles.bookTitleContainer}`}>
<h1>{this.props.book.title}</h1>
</div>
<div className={`${styles.btnContainer}`}>
<Authorize
object={book}
operation="can view multipleFilesUpload"
......@@ -314,6 +315,7 @@ export class BookBuilder extends React.Component {
</Authorize>
<VivliostyleExporter
book={book}
history={history}
htmlToEpub={htmlToEpub}
outerContainer={outerContainer}
showModal={this.state.showModal}
......
......@@ -6,12 +6,19 @@ import ErrorModal from './ErrorModal'
const DownloadEpub = ({ book, showModal, showModalToggle, outerContainer }) => {
let modal
let converter
if (config['pubsweet-client'] && config['pubsweet-client'].converter) {
converter = config['pubsweet-client'].converter
}
const handleDownload = () => {
axios
.get(
`${config['pubsweet-server'].baseUrl}/api/collections/${
book.id
}/epub?destination=attachment&converter=wax&style=epub.css`,
}/epub?destination=attachment&converter=${
!converter ? 'default' : converter
}&style=epub.css`,
)
.then(res => {
window.location.replace(res.request.responseURL)
......@@ -34,10 +41,8 @@ const DownloadEpub = ({ book, showModal, showModalToggle, outerContainer }) => {
return (
<div className={`${classes.exportBookContainer}`} onClick={handleDownload}>
<span>
<label className={classes.exportToBookIcon} />
<span className={classes.donwloadEpubText}>Download Epub</span>
</span>
<i className={classes.exportToBookIcon} />
<label className={classes.donwloadEpubText}>Download Epub</label>
{modal}
</div>
)
......
......@@ -4,14 +4,14 @@ $upload-multiple: #b1b1b1;
$black: #000;
.exportBookContainer {
bottom: 15px;
// left: -50px;
// display: inline-block;
position: relative;
}
display: flex;
align-items: center;
justify-content: flex-start;
.exportToBookIcon {
background-color: $light-grey;
margin-right: 10px;
color: $black;
cursor: pointer;
font-weight: 500;
......@@ -24,15 +24,13 @@ $black: #000;
width: 24px;
}
.donwloadEpubText {
bottom: 10px;
label.donwloadEpubText {
color: $upload-multiple;
margin-bottom: 0;
cursor: pointer;
font-family: 'Fira Sans Condensed';
font-size: 16px;
font-style: normal;
// left: 10px;
margin: 0 10px;
position: relative;
text-transform: uppercase;
}
}
\ No newline at end of file
import React from 'react'
import React, { Component } from 'react'
import Select from 'react-select'
import PropTypes from 'prop-types'
import config from 'config'
import classes from './VivliostyleExporter.local.scss'
import ErrorModal from './ErrorModal'
const VivliostyleExporter = ({
book,
htmlToEpub,
showModal,
showModalToggle,
outerContainer,
}) => {
let modal
class VivliostyleExporter extends Component {
constructor(props) {
super(props)
this.state = { selectedOption: undefined }
this.handleHTMLToEpub = this.handleHTMLToEpub.bind(this)
this.toggleModal = this.toggleModal.bind(this)
this.handleChange = this.handleChange.bind(this)
}
handleHTMLToEpub = e => {
e.preventDefault()
const { book, htmlToEpub, showModalToggle, history } = this.props
console.log('propsss', this.props)
const { selectedOption } = this.state
const handleHTMLToEpub = () => {
let converter
if (config['pubsweet-client'] && config['pubsweet-client'].converter) {
converter = config['pubsweet-client'].converter
}
const queryParams = {
destination: 'folder',
converter: 'wax',
converter: !converter ? 'default' : `${converter}`,
previewer: `${selectedOption.value}`,
style: 'epub.css',
}
// console.log('queryPar', queryParams)
htmlToEpub(book.id, queryParams)
.then(res => {
const path = res.extractedEpubPath
const viliostylePath = '/vivliostyle/viewer/vivliostyle-viewer.html'
const url = `${viliostylePath}#b=/uploads/${path}`
window.open(url, '_blank')
let url
if (selectedOption.value === 'vivliostyle') {
const viliostylePath = '/vivliostyle/viewer/vivliostyle-viewer.html'
url = `${viliostylePath}#b=/uploads/${path}`
window.open(url, '_blank')
} else {
const pagedPath = '/paged/previewer/index.html'
const stylePath = `/uploads/${path}/default.css`
url = `${pagedPath}?url=/uploads/${path}/index.html&stylesheet=${stylePath}`
history.push(`/books/${book.id}/pagedPreviewer/${path}`)
}
})
.catch(error => {
console.log('er', error)
showModalToggle()
})
}
const toggleModal = () => {
toggleModal = () => {
const { showModalToggle } = this.props
showModalToggle()
}
if (showModal) {
modal = (
<ErrorModal
container={outerContainer}
show={showModal}
toggle={toggleModal}
/>
)
handleChange = currentValue => {
this.setState({ selectedOption: currentValue })
}
return (
<div
className={`${classes.exportBookContainer}`}
onClick={handleHTMLToEpub}
>
<span>
<label className={classes.exportToBookIcon} />
<span className={classes.vivliostyleExportText}>Export Book</span>
</span>
{modal}
</div>
)
render() {
const { selectedOption } = this.state
const { showModal, outerContainer } = this.props
const options = [
{ value: 'vivliostyle', label: 'Vivliostyle' },
{ value: 'paged', label: 'PagedJS' },
]
let modal
const customStyles = {
container: base => ({
...base,
width: 120,
margin: 0,
padding: 0,
fontFamily: 'Fira Sans Condensed',
}),
dropdownIndicator: base => ({
...base,
padding: 0,
}),
valueContainer: base => ({
...base,
paddingTop: 0,
paddingBottom: 0,
}),
control: base => ({
...base,
borderRadius: 0,
minHeight: 0,
}),
}
if (showModal) {
modal = (
<ErrorModal
container={outerContainer}
show={showModal}
toggle={this.toggleModal}
/>
)
}
return (
<form
className={classes.exportBookContainer}
onSubmit={this.handleHTMLToEpub}
>
<label className={classes.exportLabel}>
<i className={classes.exportToBookIcon} />
<span className={classes.vivliostyleExportText}>Export Book</span>
</label>
<Select
isClearable={false}
isSearchable={false}
onChange={this.handleChange}
options={options}
styles={customStyles}
value={selectedOption}
/>
<button className={classes.submitBtn} disabled={!selectedOption}>
Go
</button>
{modal}
</form>
)
}
}
VivliostyleExporter.propTypes = {
......
......@@ -4,35 +4,51 @@ $upload-multiple: #b1b1b1;
$black: #000;
.exportBookContainer {
bottom: 15px;
display: flex;
align-items: center;
justify-content: space-between;
flex-grow: 0.2;
// left: -50px;
// display: inline-block;
position: relative;
}
// position: relative;
.exportLabel {
display: flex;
align-items: center;
justify-content: flex-start;
margin-bottom: 0;
.exportToBookIcon {
background-color: $light-grey;
color: $black;
cursor: pointer;
font-weight: 500;
height: 24px;
-webkit-mask: url('../styles/images/book.svg') no-repeat 100% 100%;
mask: url('../styles/images/book.svg') no-repeat 100% 100%;
-webkit-mask-size: cover;
mask-size: cover;
text-align: center;
width: 24px;
}
.vivliostyleExportText {
color: $upload-multiple;
font-family: 'Fira Sans Condensed';
font-size: 16px;
font-style: normal;
text-transform: uppercase;
}
.vivliostyleExportText {
bottom: 10px;
color: $upload-multiple;
cursor: pointer;
font-family: 'Fira Sans Condensed';
font-size: 16px;
font-style: normal;
// left: 10px;
margin: 0 10px;
position: relative;
text-transform: uppercase;
.exportToBookIcon {
background-color: $light-grey;
color: $black;
margin-right: 10px;
font-weight: 500;
height: 24px;
-webkit-mask: url('../styles/images/book.svg') no-repeat 100% 100%;
mask: url('../styles/images/book.svg') no-repeat 100% 100%;
-webkit-mask-size: cover;
mask-size: cover;
text-align: center;
width: 24px;
}
}
button.submitBtn {
color: $upload-multiple;
font-family: 'Fira Sans Condensed';
font-size: 16px;
font-style: normal;
text-transform: uppercase;
background: none;
border: none;
padding: 0;
cursor: pointer;
outline: inherit;
}
}
......@@ -257,8 +257,8 @@ class FileUploader extends React.Component {
return (
<div className={`${styles.multipleUploadContainer}`}>
<span>
<label className={styles.uploadIcon} htmlFor="file-uploader" />
<i className={styles.uploadIcon} htmlFor="file-uploader" />
<label className={styles.uploadMultipleText} htmlFor="file-uploader">
{labelText}
......@@ -275,7 +275,7 @@ class FileUploader extends React.Component {
}}
type="file"
/>
</span>
</div>
)
}
......
import React, { Component } from 'react'
import PropTypes from 'prop-types'
import axios from 'axios'
import config from 'config'
import CodeMirror from 'react-codemirror'
import 'codemirror/mode/css/css'
// import './codemirror.local.css'
import 'codemirror/lib/codemirror.css'
import classes from './PagedStyler.local.scss'
class PagedStyler extends Component {
constructor(props) {
super(props)
this.state = {
isLoading: true,
location: undefined,
css: undefined,
changed: undefined,
shouldRefresh: false,
random: 0,
}
this.handleChange = this.handleChange.bind(this)
this.handleClick = this.handleClick.bind(this)
this.handlePrint = this.handlePrint.bind(this)
this.handleDownload = this.handleDownload.bind(this)
}
componentDidMount() {
const { match } = this.props
const { params } = match
axios
.get(
`${config['pubsweet-server'].baseUrl}/uploads/paged/${
params.hashed
}/default.css`,
)
.then(res => {
this.setState({ css: res.data, isLoading: false })
})
}
handleChange(doc, change) {
this.setState({ changed: doc })
}
handlePrint(e) {
e.preventDefault()
const pri = document.getElementById('printBook').contentWindow
pri.focus()
pri.print()
}
handleClick(e) {
e.preventDefault()
const { match } = this.props
const { params } = match
const { hashed } = params
const { changed } = this.state
axios
.post(
`${
config['pubsweet-server'].baseUrl
}/api/pagedStyler/stylesheet/${hashed}/`,
{
source: changed,
},
)
.then(res => {
this.setState({
shouldRefresh: true,
random: this.state.random + 1,
})
})
}
handleDownload(e) {
e.preventDefault()
const { match } = this.props
const { params } = match
const { hashed } = params
axios
.get(
`${
config['pubsweet-server'].baseUrl
}/api/pagedStyler/exportHTML/${hashed}/`,
)
.then(res => {
window.location.replace(res.request.responseURL)
// console.log('res', res)
})
}
render() {
const { css } = this.state
const { match } = this.props
const { params } = match
const { hashed } = params
if (!css) {
return <p>Loading</p>
}
return (
<div className={classes.container}>
<div className={classes.codeEditorContainer}>
<div className={classes.buttonsContainer}>
<button className={classes.buttonStyler} onClick={this.handleClick}>
Sync
</button>
<button className={classes.buttonStyler} onClick={this.handlePrint}>
Print
</button>
<button
className={classes.buttonStyler}
onClick={this.handleDownload}
>
Download HTML
</button>
</div>
<CodeMirror
className={classes.editor}
onChange={this.handleChange}
options={{
mode: 'css',
lineNumbers: true,
}}
value={css}
/>
</div>
<iframe
className={classes.previewerContainer}
frameBorder="0"
id="printBook"
key={this.state.random}
src={`${
config['pubsweet-server'].baseUrl
}/paged/previewer/index.html?url=/uploads/paged/${hashed}/index.html&stylesheet=/uploads/paged/${hashed}/default.css`}
title="desktop-payment-page"
/>
</div>
)
}
}
PagedStyler.propTypes = {}
export default PagedStyler
.container {
display: flex;
align-items: center;
justify-content: flex-start;
height: calc(100% - 100px);
flex-basis: 100%;
padding: 8px;
.codeEditorContainer {
max-width: 650px;
width: 650px;
height: 100%;
display: flex;
flex-direction: column;
.buttonsContainer {
display: flex;
flex-direction: row;
margin-bottom: 10px;
justify-content: flex-end;
height: 30px;
border-bottom: 1px solid #666;
button {
background: none;
color: #0d78f2;;
border: none;
padding: 0;
font: inherit;
cursor: pointer;
outline: inherit;
margin-right: 20px;
}
}
.editor {
height: calc(100% - 35px);
}
}
.previewerContainer {
flex-grow: 1;
height: 100%;
}
}
:global .CodeMirror {
height: 80vh;
}
\ No newline at end of file
......@@ -102,39 +102,48 @@ $upload-multiple: #b1b1b1;
// }
}
}
.bookTitle {
.headerContainer {
display: flex;
flex-basis: 100%;
align-items: flex-end;
justify-content: flex-start;
}
.bookTitleContainer {
font-family: 'Vollkorn';
font-size: 36px;
font-style: italic;
word-wrap: break-word;
flex-basis: 40%;
border-bottom: 2px solid $line-grey;
h1 {
margin: 0;
}
}
.btnContainer {
display: flex;
flex-direction: row;
justify-content: flex-end;
justify-content: space-between;
align-items: center;
flex-basis: 60%;
}
.btnContainerButtons {
display: flex;
// flex-direction: row;
// justify-content: space-between;
// min-width: 487px;
}
// .btnContainerButtons {
// display: flex;
// flex-direction: row;
// justify-content: space-between;
// min-width: 487px;
// }
.lineUploading {
border-top: 2px solid $line-grey;
margin-right: 10px;
// width: 100%;
flex-grow: 1;
}
.multipleUploadContainer {