You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@corinthia.apache.org by pm...@apache.org on 2015/04/11 19:49:46 UTC
[2/4] incubator-corinthia git commit: Desktop app: Basic
infrastructure for Editor lib
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/res/sample.html
----------------------------------------------------------------------
diff --git a/consumers/corinthia/res/sample.html b/consumers/corinthia/res/sample.html
new file mode 100644
index 0000000..ef8be70
--- /dev/null
+++ b/consumers/corinthia/res/sample.html
@@ -0,0 +1,395 @@
+<!DOCTYPE html>
+
+<html>
+<head>
+ <meta name="generator" content="UX Write 2.1.1 (build ad61a0a); iOS 8.2">
+ <meta charset="utf-8">
+ <style>
+body {
+ font-family: Palatino;
+ counter-reset: h1 h2 h3 h4 h5 h6 figure table;
+ margin: 10%;
+ text-align: justify;
+ }
+
+ caption {
+ caption-side: bottom;
+ counter-increment: table;
+ }
+
+ caption.Unnumbered {
+ counter-increment: table 0;
+ }
+
+ caption.Unnumbered::before {
+ content: "";
+ }
+
+ caption::before {
+ content: "Table " counter(table) ": ";
+ }
+
+ h1 {
+ counter-increment: h1;
+ counter-reset: h2 h3 h4 h5 h6;
+ }
+
+ h1::before {
+ content: counter(h1) " ";
+ }
+
+ h2 {
+ counter-increment: h2;
+ counter-reset: h3 h4 h5 h6;
+ }
+
+ h2::before {
+ content: counter(h1) "." counter(h2) " ";
+ }
+
+ h3 {
+ counter-increment: h3;
+ counter-reset: h4 h5 h6;
+ }
+
+ h3::before {
+ content: counter(h1) "." counter(h2) "." counter(h3) " ";
+ }
+
+ h4 {
+ counter-increment: h4;
+ counter-reset: h5 h6;
+ }
+
+ h4::before {
+ content: counter(h1) "." counter(h2) "." counter(h3) "." counter(h4) " ";
+ }
+
+ h5 {
+ counter-increment: h5;
+ counter-reset: h6;
+ }
+
+ h5::before {
+ content: counter(h1) "." counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) " ";
+ }
+
+ h6 {
+ counter-increment: h6;
+ }
+
+ h6::before {
+ content: counter(h1) "." counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) "." counter(h6) " ";
+ }
+
+ nav.tableofcontents::before {
+ content: "Contents";
+ display: block;
+ font-size: 2em;
+ font-weight: bold;
+ margin-bottom: .67em;
+ margin-top: .67em;
+ }
+
+ p.toc1 {
+ margin-bottom: 6pt;
+ margin-left: 0pt;
+ margin-top: 12pt;
+ }
+
+ p.toc2 {
+ margin-bottom: 6pt;
+ margin-left: 24pt;
+ margin-top: 6pt;
+ }
+
+ p.toc3 {
+ margin-bottom: 6pt;
+ margin-left: 48pt;
+ margin-top: 6pt;
+ }
+
+ table {
+ border-collapse: collapse;
+ margin-left: auto;
+ margin-right: auto;
+ }
+
+ td > :first-child, th > :first-child {
+ margin-top: 0;
+ }
+
+ td > :last-child, th > :last-child {
+ margin-bottom: 0;
+ }
+
+ td, th {
+ border: 1px solid black;
+ }
+ </style>
+
+ <title></title>
+</head>
+
+<body>
+ <p>Test document</p>
+
+ <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus at lorem
+ augue, at molestie risus. Sed bibendum augue metus, sed cursus tortor. Aenean
+ semper consectetur pulvinar. Aliquam ultrices tempus nibh, ut mollis ligula
+ ultrices nec. Curabitur vel eros in mi mattis vulputate in nec lorem. Nam
+ auctor faucibus diam, eget accumsan lorem auctor eu. Maecenas imperdiet
+ tristique nisi. Sed sed metus lacus. In consectetur tempus justo, vitae porta
+ urna dapibus nec. Duis vitae lorem sit amet quam suscipit mollis eget non
+ orci. Praesent porta neque et mauris molestie nec sagittis nulla
+ volutpat.</p>
+
+ <h1 id="item2">Introduction</h1>
+
+ <p>Vivamus nec cursus massa. Aenean hendrerit sagittis volutpat. Donec diam
+ erat, vehicula at ultrices vel, aliquet ac mauris. Nam vitae lectus eu eros
+ sagittis sollicitudin. Mauris consequat, est suscipit feugiat eleifend, leo
+ erat rutrum dui, at volutpat metus metus vitae leo. Fusce dictum tincidunt
+ dignissim. Vestibulum eu est purus, eu aliquam quam. Aenean ultricies ante
+ sit amet libero sodales eu feugiat velit ornare.</p>
+
+ <h2 id="item3">Background</h2>
+
+ <p>Proin facilisis cursus elementum. Proin ac lorem ut odio ultricies
+ vehicula sit amet in diam. Proin ut nunc et nisl tristique sagittis. Aenean
+ aliquet eleifend enim non molestie. Vivamus tincidunt augue nec erat suscipit
+ ullamcorper. Nulla ornare risus odio. Nullam vestibulum tellus ac odio mattis
+ quis sollicitudin arcu interdum. Donec convallis malesuada ultricies. Sed
+ sodales porta commodo. Ut nec fringilla est. Nulla aliquet feugiat orci in
+ lobortis. Duis adipiscing aliquam orci, ac tempus leo posuere id. Nam neque
+ enim, faucibus id luctus ut, blandit eu est. Nullam non convallis mauris.</p>
+
+ <h2 id="item4">Motivation</h2>
+
+ <p>Nunc tincidunt, ante vel hendrerit cursus, lectus quam dapibus ipsum, eget
+ vestibulum odio turpis eleifend augue. Ut pharetra ultricies risus, id
+ gravida risus tincidunt eget. Nam eros massa, condimentum quis aliquet nec,
+ aliquam id enim. Integer diam justo, sagittis at faucibus eget, vestibulum id
+ lectus. Suspendisse pharetra lobortis diam sit amet fermentum. Donec nisl
+ ipsum, faucibus et bibendum a, viverra nec nunc. Cras vel arcu mauris. In hac
+ habitasse platea dictumst.</p>
+
+ <h2 id="item5">Project overview</h2>
+
+ <p>Donec sagittis dui sollicitudin massa congue et mollis nulla cursus.
+ Maecenas eget tempor risus. Nam euismod placerat ante viverra gravida. Mauris
+ nec arcu eget turpis accumsan vestibulum. Phasellus luctus, massa vel laoreet
+ faucibus, nulla tellus luctus ipsum, nec imperdiet lacus urna id diam. In
+ libero lacus, rutrum id rhoncus at, mollis consequat mauris. Ut et lectus
+ nulla, nec sagittis massa. Praesent tortor dui, elementum sed tempor eget,
+ porta vehicula ligula. Fusce aliquam lacus in ipsum tristique
+ pellentesque.</p>
+
+ <table style="width: 60%;" id="item16">
+ <caption>
+ A sample table
+ </caption>
+ <col width="50%">
+ <col width="50%">
+
+ <tbody>
+ <tr>
+ <td>
+ <p>Cell 1,1</p>
+ </td>
+
+ <td>
+ <p>Cell 1,2</p>
+ </td>
+ </tr>
+
+ <tr>
+ <td>
+ <p>Cell 2,1</p>
+ </td>
+
+ <td>
+ <p>Cell 2,2</p>
+ </td>
+ </tr>
+
+ <tr>
+ <td>
+ <p>Cell 3,1</p>
+ </td>
+
+ <td>
+ <p>Cell 3,2</p>
+ </td>
+ </tr>
+
+ <tr>
+ <td>
+ <p>Cell 4,1</p>
+ </td>
+
+ <td>
+ <p>Cell 4,2</p>
+ </td>
+ </tr>
+ </tbody>
+ </table>
+
+ <p>In nisi felis, ornare nec feugiat at, sodales posuere nibh. Etiam suscipit
+ congue nunc, at sollicitudin est adipiscing viverra. Aenean sed augue quis
+ sem commodo pretium. Maecenas quis elit urna. Donec non arcu dui. Praesent
+ faucibus ornare purus id dignissim. Quisque dictum viverra orci id lacinia.
+ Etiam mollis egestas tortor, id iaculis augue malesuada non. Sed elementum
+ ornare quam, vel iaculis nibh vulputate facilisis.</p>
+
+ <p>Nunc sit amet ipsum tellus, ut laoreet magna. Phasellus consectetur, velit
+ vitae laoreet posuere, eros diam venenatis ante, quis dignissim turpis turpis
+ at quam. Cras ac justo quis nibh sollicitudin gravida. Vestibulum ac
+ vulputate dui. Suspendisse ac nulla mauris, eget condimentum nulla. Nullam
+ mollis metus sed magna facilisis ac accumsan est facilisis. Pellentesque
+ consequat tincidunt sapien in vehicula.</p>
+
+ <h1 id="item6">Implementation</h1>
+
+ <h2 id="item7">Phase One</h2>
+
+ <p>Phasellus dignissim ultricies mauris placerat molestie. Nunc sed orci nec
+ orci mollis suscipit. Maecenas eget quam non arcu dapibus volutpat. Quisque
+ ac turpis ut libero interdum tristique id in quam. Praesent eros velit,
+ dictum eu auctor ut, lobortis ac sem. Duis ipsum neque, volutpat id blandit
+ sed, tempor a dui. Sed ut magna ligula, et sagittis nunc. Phasellus at
+ eleifend orci. Quisque non nunc ipsum. Curabitur eu erat nec ante suscipit
+ mollis. Fusce dictum laoreet volutpat. Vivamus rutrum luctus mattis.</p>
+
+ <p>Sed augue velit, eleifend sed auctor sed, consectetur quis augue. Nulla
+ consectetur imperdiet quam et elementum. Praesent suscipit magna id diam
+ cursus in faucibus arcu semper. Phasellus pretium, nisl in sagittis viverra,
+ arcu tellus aliquam urna, et scelerisque eros lorem et diam. In ut nunc vel
+ nisi imperdiet mattis quis at massa. Phasellus quis tortor est. Sed ac
+ blandit eros. Curabitur ante mauris, condimentum in tempus sit amet, accumsan
+ ac leo. Ut quis tincidunt nunc. Vestibulum ante ipsum primis in faucibus orci
+ luctus et ultrices posuere cubilia Curae; Curabitur tincidunt, nisl id
+ interdum fringilla, mauris tortor volutpat libero, et consectetur purus magna
+ quis nibh.</p>
+
+ <h2 id="item8">Phase Two</h2>
+
+ <p>Aliquam dapibus tincidunt purus in aliquet. In sed ultricies sapien. Cras
+ risus nulla, ultrices ut vulputate ac, luctus in purus. Maecenas at lorem
+ sem, a vestibulum sem. Donec ante nisl, facilisis vel convallis vel, blandit
+ quis turpis. Sed id erat vitae metus cursus consectetur. Integer ac dapibus
+ dui. Nam mi ante, sollicitudin eu fringilla quis, fringilla nec lorem.
+ Aliquam ut nisi accumsan odio pulvinar euismod quis ac libero. Curabitur sit
+ amet ultrices risus. Class aptent taciti sociosqu ad litora torquent per
+ conubia nostra, per inceptos himenaeos. Nulla eu dui ut est aliquet iaculis
+ accumsan et leo. Donec dignissim lorem non arcu hendrerit vel feugiat quam
+ accumsan. Etiam mollis fermentum mi vel egestas. Cum sociis natoque penatibus
+ et magnis dis parturient montes, nascetur ridiculus mus.</p>
+
+ <p>Ut facilisis leo nec neque tempus a molestie libero consequat. Duis et
+ justo eu lorem accumsan eleifend sed nec quam. Duis a ligula ante. Donec
+ egestas lacus id mi convallis ut ullamcorper lorem consequat. Curabitur quis
+ sapien vel odio sodales consequat. Maecenas eget commodo eros. In hac
+ habitasse platea dictumst. Donec commodo venenatis consequat. Nulla
+ vestibulum adipiscing nulla id adipiscing. Nam congue, enim et lobortis
+ rhoncus, urna purus tempor magna, a eleifend mi nisl eu magna. Vestibulum
+ ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia
+ Curae;</p>
+
+ <h2 id="item9">Phase Three</h2>
+
+ <p>Proin placerat sapien eu odio ornare eu pharetra nunc lacinia. Duis tellus
+ nisl, condimentum eget tristique sit amet, imperdiet id felis. Nunc at lectus
+ non risus tristique sollicitudin. Etiam at tellus vitae velit sagittis
+ aliquam. Vivamus bibendum pellentesque dictum. Ut auctor interdum congue.
+ Cras ultrices sem sed sem convallis viverra.</p>
+
+ <p>Nunc pulvinar, diam quis dictum gravida, nulla augue sodales lectus, id
+ pharetra leo purus nec augue. Cum sociis natoque penatibus et magnis dis
+ parturient montes, nascetur ridiculus mus. Praesent consequat venenatis justo
+ tincidunt semper. Praesent egestas, ipsum id pharetra lobortis, arcu risus
+ viverra dui, nec sollicitudin augue leo et neque. Proin commodo pharetra
+ lacus, vitae lobortis libero posuere in. Vestibulum tellus ante, luctus quis
+ luctus at, laoreet feugiat turpis. Morbi commodo tellus non leo faucibus
+ ornare. Ut volutpat, diam et mollis dignissim, felis ante lobortis nibh, sed
+ ullamcorper nibh nunc sed dolor. Phasellus viverra leo erat, luctus vehicula
+ dui. Mauris quis ipsum mollis odio accumsan consectetur lacinia feugiat
+ risus. Pellentesque habitant morbi tristique senectus et netus et malesuada
+ fames ac turpis egestas. Fusce vel lectus non risus facilisis suscipit vitae
+ vitae velit. Fusce lacinia enim dapibus mauris porta luctus. Vivamus
+ venenatis sodales nunc non porttitor. Sed posuere commodo consectetur.</p>
+
+ <h1 id="item10">Required resources</h1>
+
+ <p>Vestibulum suscipit posuere elementum. Nullam volutpat, sapien at eleifend
+ congue, dolor sapien pulvinar nibh, eu vulputate velit urna quis nisl.
+ Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere
+ cubilia Curae; Nunc auctor libero sed metus dictum quis placerat elit
+ varius.</p>
+
+ <h2 id="item11">Equipment</h2>
+
+ <p>Praesent fermentum augue sem. Cum sociis natoque penatibus et magnis dis
+ parturient montes, nascetur ridiculus mus. Fusce non lorem ligula, ac rhoncus
+ odio. Fusce ac magna lectus. Integer iaculis congue quam, sit amet tincidunt
+ orci mattis quis. Maecenas tempor, turpis nec euismod bibendum, orci dui
+ suscipit purus, iaculis mattis nunc magna at dui. Cras non neque tellus.
+ Integer lobortis, elit ac pretium imperdiet, nulla metus tempus nulla, vitae
+ bibendum diam nisl sed tellus. Class aptent taciti sociosqu ad litora
+ torquent per conubia nostra, per inceptos himenaeos.</p>
+
+ <p>Aliquam vehicula magna pharetra tortor pellentesque vestibulum. Vivamus ut
+ ullamcorper ante. Integer eu auctor lorem. Morbi sapien erat, viverra vitae
+ gravida id, bibendum eu augue. Maecenas nec dolor augue. Lorem ipsum dolor
+ sit amet, consectetur adipiscing elit. Donec aliquet dui at odio lacinia
+ placerat. Mauris a ipsum justo, id faucibus risus.</p>
+
+ <p>Sed vitae elit sed lectus varius vehicula. Maecenas pulvinar laoreet
+ metus, quis dignissim ipsum hendrerit fringilla. Quisque in neque sed ipsum
+ eleifend tempor. Etiam at posuere neque. Maecenas dapibus lacus tincidunt
+ neque elementum sed porta mauris luctus. Donec sit amet libero augue, at
+ hendrerit odio. Nulla consectetur, sem a vestibulum viverra, est nisl congue
+ leo, eget consectetur turpis justo et dolor. Fusce mollis mollis dui, eget
+ aliquet enim sollicitudin sed. Proin dictum sollicitudin rutrum. Curabitur
+ lorem risus, tempus ac ultricies id, suscipit ac nisl. Duis ultricies
+ facilisis arcu, vel congue risus tincidunt sit amet.</p>
+
+ <h2 id="item13">Personnel</h2>
+
+ <p>Etiam condimentum neque non dolor faucibus eu commodo nibh sodales.
+ Vivamus tempus est in risus malesuada vitae gravida nulla tristique. Maecenas
+ vitae justo a enim imperdiet euismod. Pellentesque porttitor metus nec enim
+ fermentum accumsan. Duis gravida ultricies aliquet. Etiam a risus turpis, sed
+ consequat arcu. Proin cursus quam non leo rutrum molestie. Ut eu orci ac nisl
+ lobortis porttitor a at massa. Nam id fringilla enim. Aenean pellentesque
+ molestie dui, sed dignissim urna mollis in. Ut ut metus non leo pharetra
+ tempor eu molestie metus. Aliquam iaculis nulla eget nisl ullamcorper vel
+ varius erat pretium.</p>
+
+ <p>Phasellus at magna tortor, eu elementum ligula. Etiam malesuada vehicula
+ elementum. Donec quis blandit dui. Phasellus tincidunt ullamcorper pharetra.
+ Integer egestas elementum egestas. Phasellus porta, neque a ultricies
+ pharetra, elit leo sodales purus, non auctor quam magna sed lectus. In et
+ ligula ipsum. Morbi vehicula auctor dolor cursus elementum. Cras vestibulum,
+ enim quis luctus posuere, metus enim mollis libero, at dictum enim magna eget
+ dolor. Vestibulum sagittis mi ac nibh dignissim placerat. Praesent vehicula
+ facilisis luctus. Donec ultrices, est non convallis lacinia, diam neque
+ blandit est, sed tincidunt felis ante sed dolor. Fusce laoreet justo sed
+ neque congue scelerisque.</p>
+
+ <h1 id="item14">Summary</h1>
+
+ <p>Nulla vitae ipsum orci. Suspendisse potenti. In sagittis quam non augue
+ blandit dapibus. Nulla dignissim viverra ante a egestas. In augue mi, porta
+ sit amet tempus eget, venenatis ac purus. Pellentesque non sapien et quam
+ molestie consectetur at ut magna. Maecenas turpis justo, adipiscing eu
+ tincidunt vulputate, ultricies sit amet magna.</p>
+
+ <p>Maecenas eget felis at massa pellentesque blandit ac eget lectus. Ut sit
+ amet nibh nunc, sit amet consequat massa. Suspendisse sit amet tempor tellus.
+ Vivamus nec lectus metus. Morbi id nibh neque. Pellentesque semper, sapien id
+ suscipit tincidunt, eros velit rhoncus dolor, non sagittis turpis erat vitae
+ velit. Nulla ligula turpis, lacinia non consequat in, lobortis sollicitudin
+ felis. Suspendisse pulvinar est eu felis congue id vehicula est luctus.</p>
+</body>
+</html>
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/src/CMakeLists.txt
----------------------------------------------------------------------
diff --git a/consumers/corinthia/src/CMakeLists.txt b/consumers/corinthia/src/CMakeLists.txt
index 2f56fce..ef4b5ae 100644
--- a/consumers/corinthia/src/CMakeLists.txt
+++ b/consumers/corinthia/src/CMakeLists.txt
@@ -24,11 +24,17 @@ set_property(GLOBAL PROPERTY USE_FOLDERS ON)
## group source objects
###
set(SOURCES
- editWindows.h
- desktop.cpp
- main.cpp)
-set(UI_SOURCES
- desktop.ui)
+ Editor.h
+ Editor.cpp
+ JSInterface.h
+ JSInterface.cpp
+ main.cpp
+ MainWindow.h
+ MainWindow.cpp
+ Toolbar.h
+ Toolbar.cpp)
+#set(UI_SOURCES
+# desktop.ui)
@@ -45,12 +51,14 @@ link_directories(${LIB_DIRS})
###
## Qt magic
###
-set(CMAKE_PREFIX_PATH "C:/Qt/5.4/msvc2013_64")
+set(CMAKE_PREFIX_PATH "/usr/local/opt/qt5")
set(CMAKE_INCLUDE_CURRENT_DIR ON)
set(CMAKE_AUTOMOC ON)
find_package(Qt5Widgets REQUIRED)
-include_directories("C:/Qt/5.4/msvc2013_64/include")
+find_package(Qt5WebKit REQUIRED)
+find_package(Qt5WebKitWidgets REQUIRED)
+include_directories("/usr/local/opt/qt5/include")
qt5_wrap_ui(UI_HEADERS ${UI_SOURCES})
source_group("Generated UI Headers" FILES ${UI_HEADERS})
@@ -62,7 +70,18 @@ source_group("Generated UI Headers" FILES ${UI_HEADERS})
# executable (release artifact)
###
add_executable(corinthia ${SOURCES} ${UI_HEADERS} ${UI_FILES})
-qt5_use_modules(corinthia Widgets)
+qt5_use_modules(corinthia Widgets WebKit WebKitWidgets)
target_link_libraries(corinthia DocFormats ${LIBS})
source_group(src FILES ${SOURCES})
set_property(TARGET corinthia PROPERTY FOLDER consumers)
+
+message(CMAKE_SOURCE_DIR " is " ${CMAKE_SOURCE_DIR})
+message(TARGET_FILE_DIR ":corinthia is " $<TARGET_FILE_DIR:corinthia>)
+message(CMAKE_BINARY_DIR " is " ${CMAKE_BINARY_DIR})
+
+add_custom_command(TARGET corinthia PRE_BUILD
+ COMMAND ${CMAKE_COMMAND} -E copy_directory
+ ${CMAKE_SOURCE_DIR}/Editor/src ${CMAKE_BINARY_DIR}/share/corinthia/js)
+add_custom_command(TARGET corinthia PRE_BUILD
+ COMMAND ${CMAKE_COMMAND} -E copy_directory
+ ${CMAKE_SOURCE_DIR}/consumers/corinthia/res ${CMAKE_BINARY_DIR}/share/corinthia)
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/src/Editor.cpp
----------------------------------------------------------------------
diff --git a/consumers/corinthia/src/Editor.cpp b/consumers/corinthia/src/Editor.cpp
new file mode 100644
index 0000000..9cce7b8
--- /dev/null
+++ b/consumers/corinthia/src/Editor.cpp
@@ -0,0 +1,296 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+#include "Editor.h"
+#include "JSInterface.h"
+#include <QWebView>
+#include <QWebFrame>
+#include <QFile>
+#include <QLayout>
+#include <QBoxLayout>
+#include <QVBoxLayout>
+#include <QHBoxLayout>
+#include <QCoreApplication>
+
+class EditorJSCallbacks : public JSCallbacks
+{
+public:
+ EditorJSCallbacks(Editor *editor) : _editor(editor) {}
+ void debug(const QString &message);
+ void addOutlineItem(const QString &itemId, const QString &type, const QString &title);
+ void updateOutlineItem(const QString &itemId, const QString &title);
+ void removeOutlineItem(const QString &itemId);
+ void outlineUpdated();
+ void setCursor(int x, int y, int width, int height);
+ void setSelectionHandles(int x1, int y1, int height1, int x2, int y2, int height2);
+ void setTableSelection(int x, int y, int width, int height);
+ void setSelectionBounds(int left, int top, int right, int bottom);
+ void clearSelectionHandlesAndCursor();
+ void updateAutoCorrect();
+ void error(const QString &message, const QString &operation);
+//private:
+ Editor *_editor;
+};
+
+class EditorJSEvaluator : public JSEvaluator
+{
+public:
+ EditorJSEvaluator(QWebView *webView, JSCallbacks *callbacks) : _webView(webView), _callbacks(callbacks) {}
+ virtual QString evaluate(const QString &script);
+ virtual JSCallbacks *callbacks() { return _callbacks; }
+private:
+ QWebView *_webView;
+ JSCallbacks *_callbacks;
+};
+
+class EditorPrivate : public QObject
+{
+ Q_OBJECT
+public:
+ EditorPrivate(Editor *editor);
+ virtual ~EditorPrivate();
+ public slots:
+ void webViewloadFinished(bool ok);
+public:
+
+ Editor *_editor;
+ QWebView *_webView;
+ EditorJSCallbacks *_callbacks;
+ EditorJSEvaluator *_evaluator;
+ JSInterface *_js;
+};
+
+
+
+const char *jsSources[] = {
+ "first.js",
+ "ElementTypes.js",
+ "AutoCorrect.js",
+ "ChangeTracking.js",
+ "Clipboard.js",
+ "Cursor.js",
+ "DOM.js",
+ "Editor.js",
+ "Equations.js",
+ "Figures.js",
+ "Formatting.js",
+ "Hierarchy.js",
+ "Input.js",
+ "Lists.js",
+ "Main.js",
+ "Metadata.js",
+ "NodeSet.js",
+ "Outline.js",
+ "Position.js",
+ "PostponedActions.js",
+ "Preview.js",
+ "Range.js",
+ "Scan.js",
+ "Selection.js",
+ "StringBuilder.js",
+ "Styles.js",
+ "Tables.js",
+ "Text.js",
+ "traversal.js",
+ "types.js",
+ "UndoManager.js",
+ "util.js",
+ "Viewport.js",
+ NULL,
+};
+
+
+
+
+void EditorJSCallbacks::debug(const QString &message)
+{
+ qStdOut() << "CB debug \"" << message << "\"" << endl;
+}
+
+void EditorJSCallbacks::addOutlineItem(const QString &itemId, const QString &type, const QString &title)
+{
+ qStdOut() << "CB addOutlineItem " << itemId << " " << type << " \"" << title << "\"" << endl;
+}
+
+void EditorJSCallbacks::updateOutlineItem(const QString &itemId, const QString &title)
+{
+ qStdOut() << "CB updateOutlineItem " << itemId << " \"" << title << "\"" << endl;
+}
+
+void EditorJSCallbacks::removeOutlineItem(const QString &itemId)
+{
+ qStdOut() << "CB removeOutlineItem " << itemId << endl;
+}
+
+void EditorJSCallbacks::outlineUpdated()
+{
+ qStdOut() << "CB outlineUpdated" << endl;
+}
+
+void EditorJSCallbacks::setCursor(int x, int y, int width, int height)
+{
+ qStdOut() << "CB setCursor " << x << " " << y << " " << width << " " << height << endl;
+}
+
+void EditorJSCallbacks::setSelectionHandles(int x1, int y1, int height1, int x2, int y2, int height2)
+{
+ qStdOut() << "CB setSelectionHandles " << x1 << " " << y1 << " " << height1 << " "
+ << x2 << " " << y2 << " " << height2 << endl;
+}
+
+void EditorJSCallbacks::setTableSelection(int x, int y, int width, int height)
+{
+ qStdOut() << "CB setTableSelection" << x << " " << y << " " << width << " " << height << endl;
+}
+
+void EditorJSCallbacks::setSelectionBounds(int left, int top, int right, int bottom)
+{
+ qStdOut() << "CB setSelectionBounds " << left << " " << top << " " << right << " " << bottom << endl;
+}
+
+void EditorJSCallbacks::clearSelectionHandlesAndCursor()
+{
+ qStdOut() << "CB clearSelectionHandlesAndCursor" << endl;
+}
+
+void EditorJSCallbacks::updateAutoCorrect()
+{
+ qStdOut() << "CB updateAutoCorrect" << endl;
+}
+
+void EditorJSCallbacks::error(const QString &message, const QString &operation)
+{
+ qStdOut() << "CB error \"" << message << "\" \"" << operation << "\"" << endl;
+}
+
+QString EditorJSEvaluator::evaluate(const QString &script)
+{
+ QWebFrame *frame = _webView->page()->mainFrame();
+ QVariant result = frame->evaluateJavaScript(script);
+ if (result.userType() != QMetaType::QString)
+ return QString::null;
+ else
+ return result.toString();
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+EditorPrivate::EditorPrivate(Editor *editor) : _editor(editor)
+{
+ _webView = new QWebView(editor);
+ _callbacks = new EditorJSCallbacks(editor);
+ _evaluator = new EditorJSEvaluator(_webView,_callbacks);
+ _js = new JSInterface(_evaluator);
+ QObject::connect(_webView,SIGNAL(loadFinished(bool)),this,SLOT(webViewloadFinished(bool)));
+}
+
+EditorPrivate::~EditorPrivate()
+{
+ delete _webView;
+ delete _callbacks;
+ delete _evaluator;
+ delete _js;
+}
+
+void EditorPrivate::webViewloadFinished(bool ok)
+{
+ qStdOut() << "webViewloadFinished: ok = " << ok << endl;
+ if (!ok)
+ return;
+ QWebFrame *frame = _editor->webView()->page()->mainFrame();
+ // frame->evaluateJavaScript("alert('This is a test')");
+
+ QString appPath = QCoreApplication::applicationDirPath();
+ QString baseDir = appPath + "/../share/corinthia/js";
+ baseDir = QUrl::fromLocalFile(baseDir).path();
+ qStdOut() << "js base dir = " << baseDir << endl;
+
+ for (int i = 0; jsSources[i] != NULL; i++) {
+ QString fullPath = baseDir + "/" + QString(jsSources[i]);
+ QFile file(fullPath);
+ if (file.open(QFile::ReadOnly)) {
+ QTextStream stream(&file);
+ QString content = stream.readAll();
+ frame->evaluateJavaScript(content);
+ }
+ else {
+ qStdOut() << "Can't open file " << fullPath << endl;
+ return;
+ }
+ }
+
+ frame->evaluateJavaScript("Main_init()");
+
+ processCallbacks(_evaluator);
+}
+
+Editor::Editor(QWidget *parent, Qt::WindowFlags f) : QWidget(parent,f)
+{
+ _p = new EditorPrivate(this);
+ QVBoxLayout *layout = new QVBoxLayout(this);
+ layout->addWidget(_p->_webView);
+ setLayout(layout);
+}
+
+Editor::~Editor()
+{
+ delete _p;
+}
+
+QWebView *Editor::webView() const
+{
+ return _p->_webView;
+}
+
+JSInterface *Editor::js() const
+{
+ return _p->_js;
+}
+
+#include <Editor.moc>
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/src/Editor.h
----------------------------------------------------------------------
diff --git a/consumers/corinthia/src/Editor.h b/consumers/corinthia/src/Editor.h
new file mode 100644
index 0000000..117a18d
--- /dev/null
+++ b/consumers/corinthia/src/Editor.h
@@ -0,0 +1,35 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+#import <QWidget>
+
+class Editor;
+class EditorPrivate;
+class QWebView;
+class JSInterface;
+
+class Editor : public QWidget
+{
+ Q_OBJECT
+public:
+ Editor(QWidget *parent = 0, Qt::WindowFlags f = 0);
+ virtual ~Editor();
+ QWebView *webView() const;
+ JSInterface *js() const;
+private:
+ EditorPrivate *_p;
+};
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/src/JSInterface.cpp
----------------------------------------------------------------------
diff --git a/consumers/corinthia/src/JSInterface.cpp b/consumers/corinthia/src/JSInterface.cpp
new file mode 100644
index 0000000..f6b549f
--- /dev/null
+++ b/consumers/corinthia/src/JSInterface.cpp
@@ -0,0 +1,1307 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+#include "JSInterface.h"
+#include <QJsonDocument>
+#include <assert.h>
+
+QTextStream& qStdOut()
+{
+ static QTextStream ts( stdout );
+ return ts;
+}
+
+class JSArgs
+{
+public:
+ QString toString() const;
+ JSArgs &operator<<(int value);
+ JSArgs &operator<<(unsigned int value);
+ JSArgs &operator<<(double value);
+ JSArgs &operator<<(bool value);
+ JSArgs &operator<<(const char *value);
+ JSArgs &operator<<(const QString &value);
+ JSArgs &operator<<(const QJsonArray &value);
+ JSArgs &operator<<(const QJsonObject &value);
+ JSArgs &operator<<(const QJsonValue &value);
+ JSArgs &operator<<(const QRect &value);
+ JSArgs &operator<<(const QPoint &value);
+ JSArgs &operator<<(const QSize &value);
+ JSArgs &operator<<(const QMap<QString,QString> map);
+private:
+ QJsonArray _array;
+};
+
+QString JSArgs::toString() const
+{
+ QString argsStr = QJsonDocument(_array).toJson(QJsonDocument::Compact);
+ assert(argsStr.size() >= 2);
+ assert(argsStr[0] == '[');
+ assert(argsStr[argsStr.size()-1] == ']');
+ argsStr.remove(0,1);
+ argsStr.remove(argsStr.size()-1,1);
+ return argsStr;
+}
+
+JSArgs &JSArgs::operator<<(int value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(unsigned int value)
+{
+ _array.append((double)value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(double value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(bool value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const char *value)
+{
+ if (value == NULL)
+ _array.append(QJsonValue::Null);
+ else
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QString &value)
+{
+ if (value.isNull())
+ _array.append(QJsonValue::Null);
+ else
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QJsonArray &value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QJsonObject &value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QJsonValue &value)
+{
+ _array.append(value);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QRect &value)
+{
+ QJsonObject obj;
+ obj["x"] = QJsonValue(value.x());
+ obj["y"] = QJsonValue(value.y());
+ obj["width"] = QJsonValue(value.width());
+ obj["height"] = QJsonValue(value.height());
+ _array.append(obj);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QPoint &value)
+{
+ QJsonObject obj;
+ obj["x"] = QJsonValue(value.x());
+ obj["y"] = QJsonValue(value.y());
+ _array.append(obj);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QSize &value)
+{
+ QJsonObject obj;
+ obj["width"] = QJsonValue(value.width());
+ obj["height"] = QJsonValue(value.height());
+ _array.append(obj);
+ return *this;
+}
+
+JSArgs &JSArgs::operator<<(const QMap<QString,QString> map)
+{
+ QJsonObject obj;
+ QMapIterator<QString,QString> it(map);
+ while (it.hasNext()) {
+ it.next();
+ QString key = it.key();
+ QString value = it.value();
+ if (value.isNull())
+ obj[key] = QJsonValue::Null;
+ else
+ obj[key] = value;
+ }
+ _array.append(obj);
+ return *this;
+}
+
+void testargs()
+{
+ int intVal = 4294967295;
+ unsigned int uintVal = 4294967295;
+ QMap<QString,QString> map;
+ map["color"] = "red";
+ map["font-size"] = "24";
+ map["font-family"] = "Helvetica";
+ map["background-color"] = QString::null;
+ JSArgs args = JSArgs()
+ << intVal
+ << uintVal
+ << 3.2
+ << true
+ << false
+ << "test"
+ << (char *)NULL
+ << QString("test")
+ << QString::null
+ << QJsonArray()
+ << QJsonObject()
+ << QJsonValue("value")
+ << QRect(1,2,3,4)
+ << QPoint(5,6)
+ << QSize(7,8)
+ << map;
+ qStdOut() << args.toString() << endl;
+}
+
+QRect QRectFromJson(QJsonValue value)
+{
+ if (!value.isObject()) {
+ qStdOut() << "QRectFromJson: value is not an object" << endl;
+ return QRect();
+ }
+
+ QJsonObject obj = value.toObject();
+ QJsonValue x = obj["x"];
+ QJsonValue y = obj["y"];
+ QJsonValue width = obj["width"];
+ QJsonValue height = obj["height"];
+ if (!x.isDouble() || !y.isDouble() || !width.isDouble() || !height.isDouble()) {
+ qStdOut() << "QRectFromJson: invalid value(s)" << endl;
+ return QRect();
+ }
+
+ return QRect(x.toDouble(),y.toDouble(),width.toDouble(),height.toDouble());
+}
+
+QString QRectString(QRect rect)
+{
+ return QString().sprintf("(%d,%d,%d,%d)",rect.x(),rect.y(),rect.width(),rect.height());
+}
+
+void processCallbacks(JSEvaluator *evaluator)
+{
+ JSCallbacks *callbacks = evaluator->callbacks();
+
+ QString messagesStr = evaluator->evaluate("Editor_getBackMessages()");
+ if (messagesStr.isNull()) {
+ qStdOut() << "Editor_getBackMessages failed" << endl;
+ return;
+ }
+
+ // QJsonDocument doc = QJsonDocument::fromVariant(var);
+ QJsonDocument doc = QJsonDocument::fromJson(messagesStr.toUtf8());
+ if (doc.isNull()) {
+ qStdOut() << "JSON parse failed" << endl;
+ return;
+ }
+
+ if (!doc.isArray()) {
+ qStdOut() << "JSON is not an array" << endl;
+ return;
+ }
+
+ qStdOut() << "JSON parse succeeded; top-level is an array with " << doc.array().size() << " items" << endl;
+ QJsonArray topArray = doc.array();
+ for (int i = 0; i < topArray.size(); i++) {
+ QJsonValue val = topArray.at(i);
+ if (!val.isArray()) {
+ qStdOut() << "Entry " << i << " is not an array" << endl;
+ return;
+ }
+ // printf("entry %d: %s\n",i,qcstring(val.toString()));
+ QJsonArray array = val.toArray();
+ if (array.size() < 1) {
+ qStdOut() << "Callback array " << i << " is empty" << endl;
+ return;
+ }
+ if (!array.at(0).isString()) {
+ qStdOut() << "Callback array " << i << " does not start with a string" << endl;
+ return;
+ }
+ QString functionName = array.at(0).toString();
+
+ // if (functionName == "addOutlineItem") {
+ // qStdOut() << "cbName " << i << " = " << functionName << " *************************" << endl;
+ // }
+ // else {
+ // qStdOut() << "cbName " << i << " = " << functionName << endl;
+ // }
+
+ if ((functionName == "debug") &&
+ (array.size() == 2) &&
+ (array.at(1).isString())) {
+ callbacks->debug(array.at(1).toString());
+ }
+ else if ((functionName == "addOutlineItem") &&
+ (array.size() == 4) &&
+ (array.at(1).isString()) &&
+ (array.at(2).isString()) &&
+ ((array.at(3).isString()) || (array.at(3).isNull()))) {
+ callbacks->addOutlineItem(array.at(1).toString(),array.at(2).toString(),array.at(3).toString());
+ }
+ else if ((functionName == "updateOutlineItem") &&
+ (array.size() == 3) &&
+ array.at(1).isString() &&
+ array.at(2).isString()) {
+ callbacks->updateOutlineItem(array.at(1).toString(),array.at(2).toString());
+ }
+ else if ((functionName == "removeOutlineItem") &&
+ (array.size() == 2) &&
+ array.at(1).isString()) {
+ callbacks->removeOutlineItem(array.at(1).toString());
+ }
+ else if ((functionName == "outlineUpdated") &&
+ (array.size() == 1)) {
+ callbacks->outlineUpdated();
+ }
+ else if ((functionName == "setSelectionHandles") &&
+ (array.size() == 7) &&
+ array.at(1).isDouble() &&
+ array.at(2).isDouble() &&
+ array.at(3).isDouble() &&
+ array.at(4).isDouble() &&
+ array.at(5).isDouble() &&
+ array.at(6).isDouble()) {
+ callbacks->setSelectionHandles(array.at(1).toDouble(),
+ array.at(2).toDouble(),
+ array.at(3).toDouble(),
+ array.at(4).toDouble(),
+ array.at(5).toDouble(),
+ array.at(6).toDouble());
+ }
+ else if ((functionName == "setTableSelection") &&
+ (array.size() == 5) &&
+ array.at(1).isDouble() &&
+ array.at(2).isDouble() &&
+ array.at(3).isDouble() &&
+ array.at(4).isDouble()) {
+ callbacks->setTableSelection(array.at(1).toDouble(),
+ array.at(2).toDouble(),
+ array.at(3).toDouble(),
+ array.at(4).toDouble());
+ }
+ else if ((functionName == "setCursor") &&
+ (array.size() == 5) &&
+ array.at(1).isDouble() &&
+ array.at(2).isDouble() &&
+ array.at(3).isDouble() &&
+ array.at(4).isDouble()) {
+ callbacks->setCursor(array.at(1).toDouble(),
+ array.at(2).toDouble(),
+ array.at(3).toDouble(),
+ array.at(4).toDouble());
+ }
+ else if ((functionName == "clearSelectionHandlesAndCursor") &&
+ (array.size() == 1)) {
+ callbacks->clearSelectionHandlesAndCursor();
+ }
+ else if ((functionName == "setSelectionBounds") &&
+ (array.size() == 5) &&
+ array.at(1).isDouble() &&
+ array.at(2).isDouble() &&
+ array.at(3).isDouble() &&
+ array.at(4).isDouble()) {
+ callbacks->setSelectionBounds(array.at(1).toDouble(),
+ array.at(2).toDouble(),
+ array.at(3).toDouble(),
+ array.at(4).toDouble());
+ }
+ else if ((functionName == "updateAutoCorrect") &&
+ (array.size() == 1)) {
+ callbacks->updateAutoCorrect();
+ }
+ else if ((functionName == "error") &&
+ (array.size() == 3) &&
+ array.at(1).isString() &&
+ array.at(2).isString()) {
+ callbacks->error(array.at(1).toString(),array.at(2).toString());
+ }
+ else {
+ qStdOut() << "INVALID CALLBACK OR ARGS: " << functionName << endl;
+ }
+ }
+}
+
+QJsonValue evaljsStr(JSEvaluator *ev, const QString &functionName, const QString &argsStr)
+{
+ QString script;
+ QTextStream stream(&script);
+ stream << "Main_execute(function() { return JSON.stringify({ result: ";
+ stream << functionName << "(";
+ stream << argsStr;
+ stream << ")}); });";
+
+ qStdOut() << "EVALUATE: " << script << endl;
+
+ QString resultStr = ev->evaluate(script);
+ qStdOut() << "RESULT: " << resultStr << endl;
+ processCallbacks(ev);
+ if (resultStr.isNull())
+ return QJsonValue(QJsonValue::Null);
+
+ QJsonDocument doc = QJsonDocument::fromJson(resultStr.toUtf8());
+ if (!doc.isObject()) {
+ ev->callbacks()->error("Error parsing returned JSON","evaluate");
+ return QJsonValue(QJsonValue::Null);
+ }
+
+ QJsonObject obj = doc.object();
+ if (!obj.contains("result")) {
+ return QJsonValue(QJsonValue::Null);
+ // ev->callbacks()->error("Returned JSON does not contain a result","evaluate");
+ // return QJsonValue(QJsonValue::Null);
+ }
+
+ return obj["result"];
+}
+
+QJsonValue evaljs(JSEvaluator *ev, const QString &functionName, const JSArgs &args)
+{
+ return evaljsStr(ev,functionName,args.toString());
+}
+
+// Functions implemented in AutoCorrect.js
+
+void JSAutoCorrect::correctPrecedingWord(int numChars, const QString &replacement, bool confirmed)
+{
+ JSArgs args = JSArgs() << numChars << replacement << confirmed;
+ evaljs(_evaluator,"AutoCorrect_correctPrecedingWord",args);
+}
+
+QJsonObject JSAutoCorrect::getCorrection()
+{
+ QJsonValue result = evaljs(_evaluator,"AutoCorrect_getCorrection",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+QJsonObject JSAutoCorrect::getCorrectionCoords()
+{
+ QJsonValue result = evaljs(_evaluator,"AutoCorrect_getCorrectionCoords",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSAutoCorrect::acceptCorrection()
+{
+ evaljs(_evaluator,"AutoCorrect_acceptCorrection",JSArgs());
+}
+
+void JSAutoCorrect::replaceCorrection(const QString &replacement)
+{
+ JSArgs args = JSArgs() << replacement;
+ evaljs(_evaluator,"AutoCorrect_replaceCorrection",args);
+}
+
+// Functions implemented in ChangeTracking.js
+
+bool JSChangeTracking::showChanges()
+{
+ QJsonValue result = evaljs(_evaluator,"ChangeTracking_showChanges",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+bool JSChangeTracking::trackChanges()
+{
+ QJsonValue result = evaljs(_evaluator,"ChangeTracking_trackChanges",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+void JSChangeTracking::setShowChanges(bool showChanges)
+{
+ JSArgs args = JSArgs() << showChanges;
+ evaljs(_evaluator,"ChangeTracking_setShowChanges",args);
+}
+
+void JSChangeTracking::setTrackChanges(bool trackChanges)
+{
+ JSArgs args = JSArgs() << trackChanges;
+ evaljs(_evaluator,"ChangeTracking_setTrackChanges",args);
+}
+
+// Functions implemented in Clipboard.js
+
+QJsonObject JSClipboard::clipboardCut()
+{
+ QJsonValue result = evaljs(_evaluator,"Clipboard_cut",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+QJsonObject JSClipboard::clipboardCopy()
+{
+ QJsonValue result = evaljs(_evaluator,"Clipboard_copy",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSClipboard::pasteHTML(const QString &html)
+{
+ JSArgs args = JSArgs() << html;
+ evaljs(_evaluator,"Clipboard_pasteHTML",args);
+}
+
+void JSClipboard::pasteText(const QString &text)
+{
+ JSArgs args = JSArgs() << text;
+ evaljs(_evaluator,"Clipboard_pasteText",args);
+}
+
+// Functions implemented in Cursor.js
+
+
+QString JSCursor::positionCursor(int x, int y, bool wordBoundary)
+{
+ JSArgs args = JSArgs() << x << y << wordBoundary;
+ QJsonValue result = evaljs(_evaluator,"Cursor_positionCursor",args);
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QRect JSCursor::getCursorPosition()
+{
+ QJsonValue result = evaljs(_evaluator,"Cursor_getCursorPosition",JSArgs());
+ return QRectFromJson(result);
+}
+
+void JSCursor::moveLeft()
+{
+ evaljs(_evaluator,"Cursor_moveLeft",JSArgs());
+}
+
+void JSCursor::moveRight()
+{
+ evaljs(_evaluator,"Cursor_moveRight",JSArgs());
+}
+
+void JSCursor::moveToStartOfDocument()
+{
+ evaljs(_evaluator,"Cursor_moveToStartOfDocument",JSArgs());
+}
+
+void JSCursor::moveToEndOfDocument()
+{
+ evaljs(_evaluator,"Cursor_moveToEndOfDocument",JSArgs());
+}
+
+void JSCursor::insertReference(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ evaljs(_evaluator,"Cursor_insertReference",args);
+}
+
+void JSCursor::insertLink(const QString &text, const QString &url)
+{
+ JSArgs args = JSArgs() << text << url;
+ evaljs(_evaluator,"Cursor_insertLink",args);
+}
+
+void JSCursor::insertCharacter(unsigned short character, bool allowInvalidPos)
+{
+ JSArgs args = JSArgs() << QString(character) << allowInvalidPos;
+ evaljs(_evaluator,"Cursor_insertCharacter",args);
+}
+
+void JSCursor::deleteCharacter()
+{
+ evaljs(_evaluator,"Cursor_deleteCharacter",JSArgs());
+}
+
+void JSCursor::enterPressed()
+{
+ evaljs(_evaluator,"Cursor_enterPressed",JSArgs());
+}
+
+QString JSCursor::getPrecedingWord()
+{
+ QJsonValue result = evaljs(_evaluator,"Cursor_getPrecedingWord",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QJsonObject JSCursor::getLinkProperties()
+{
+ QJsonValue result = evaljs(_evaluator,"Cursor_getLinkProperties",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSCursor::setLinkProperties(QJsonObject properties)
+{
+ JSArgs args = JSArgs() << properties;
+ evaljs(_evaluator,"Cursor_setLinkProperties",args);
+}
+
+void JSCursor::setReferenceTarget(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ evaljs(_evaluator,"Cursor_setReferenceTarget",args);
+}
+
+void JSCursor::insertFootnote(const QString &content)
+{
+ JSArgs args = JSArgs() << content;
+ evaljs(_evaluator,"Cursor_insertFootnote",args);
+}
+
+void JSCursor::insertEndnote(const QString &content)
+{
+ JSArgs args = JSArgs() << content;
+ evaljs(_evaluator,"Cursor_insertEndnote",args);
+}
+
+// Functions implemented in Equations.js
+
+void JSEquations::insertEquation()
+{
+ evaljs(_evaluator,"Equations_insertEquation",JSArgs());
+}
+
+// Functions implemented in Figures.js
+
+void JSFigures::insertFigure(const QString &filename, const QString &width,
+ bool numbered, const QString &caption)
+{
+ JSArgs args = JSArgs() << filename << width << numbered << caption;
+ evaljs(_evaluator,"Figures_insertFigure",args);
+}
+
+QString JSFigures::getSelectedFigureId()
+{
+ QJsonValue result = evaljs(_evaluator,"Figures_getSelectedFigureId",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QJsonObject JSFigures::getProperties(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ QJsonValue result = evaljs(_evaluator,"Figures_getProperties",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSFigures::setProperties(const QString &itemId, const QString &width, const QString &src)
+{
+ JSArgs args = JSArgs() << itemId << width << src;
+ evaljs(_evaluator,"Figures_setProperties",args);
+}
+
+QJsonObject JSFigures::getGeometry(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ QJsonValue result = evaljs(_evaluator,"Figures_getGeometry",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+// Functions implemented in Formatting.js
+
+QJsonObject JSFormatting::getFormatting()
+{
+ QJsonValue result = evaljs(_evaluator,"Formatting_getFormatting",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSFormatting::applyFormattingChanges(const QString &style, QJsonObject properties)
+{
+ JSArgs args = JSArgs() << style << properties;
+ evaljs(_evaluator,"Formatting_applyFormattingChanges",args);
+}
+
+// Functions implemented in Input.js
+
+void JSInput::removePosition(int posId)
+{
+ JSArgs args = JSArgs() << posId;
+ evaljs(_evaluator,"Input_removePosition",args);
+}
+
+QString JSInput::textInRange(int startId, int startAdjust, int endId, int endAdjust)
+{
+ JSArgs args = JSArgs() << startId << startAdjust << endId << endAdjust;
+ QJsonValue result = evaljs(_evaluator,"Input_textInRange",args);
+ return result.isString() ? result.toString() : QString::null;
+}
+
+void JSInput::replaceRange(int startId, int endId, const QString &text)
+{
+ JSArgs args = JSArgs() << startId << endId << text;
+ evaljs(_evaluator,"Input_replaceRange",args);
+}
+
+QJsonObject JSInput::selectedTextRange()
+{
+ QJsonValue result = evaljs(_evaluator,"Input_selectedTextRange",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSInput::setSelectedTextRange(int startId, int endId)
+{
+ JSArgs args = JSArgs() << startId << endId;
+ evaljs(_evaluator,"Input_setSelectedTextRange",args);
+}
+
+QJsonObject JSInput::markedTextRange()
+{
+ QJsonValue result = evaljs(_evaluator,"Input_markedTextRange",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSInput::setMarkedText(const QString &text, int startOffset, int endOffset)
+{
+ JSArgs args = JSArgs() << text << startOffset << endOffset;
+ evaljs(_evaluator,"Input_setMarkedText",args);
+}
+
+void JSInput::unmarkText()
+{
+ evaljs(_evaluator,"Input_unmarkText",JSArgs());
+}
+
+bool JSInput::forwardSelectionAffinity()
+{
+ QJsonValue result = evaljs(_evaluator,"Input_forwardSelectionAffinity",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+void JSInput::setForwardSelectionAffinity(bool forwardSelectionAffinity)
+{
+ JSArgs args = JSArgs() << forwardSelectionAffinity;
+ evaljs(_evaluator,"Input_setForwardSelectionAffinity",args);
+}
+
+int JSInput::positionFromPositionOffset(int posId, int offset)
+{
+ JSArgs args = JSArgs() << posId << offset;
+ QJsonValue result = evaljs(_evaluator,"Input_positionFromPositionOffset",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::positionFromPositionInDirectionOffset(int posId, const QString &direction, int offset)
+{
+ JSArgs args = JSArgs() << posId << direction << offset;
+ QJsonValue result = evaljs(_evaluator,"Input_positionFromPositionInDirectionOffset",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::comparePositionToPosition(int positionId, int otherId)
+{
+ JSArgs args = JSArgs() << positionId << otherId;
+ QJsonValue result = evaljs(_evaluator,"Input_comparePositionToPosition",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::offsetFromPositionToPosition(int fromPosition, int toPosition)
+{
+ JSArgs args = JSArgs() << fromPosition << toPosition;
+ QJsonValue result = evaljs(_evaluator,"Input_offsetFromPositionToPosition",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::positionWithinRangeFarthestInDirection(int startId, int endId, const QString &direction)
+{
+ JSArgs args = JSArgs() << startId << endId << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_positionWithinRangeFarthestInDirection",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+QJsonObject JSInput::characterRangeByExtendingPositionInDirection(int positionId, const QString &direction)
+{
+ JSArgs args = JSArgs() << positionId << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_characterRangeByExtendingPositionInDirection",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+QJsonObject JSInput::firstRectForRange(int startId, int endId)
+{
+ JSArgs args = JSArgs() << startId << endId;
+ QJsonValue result = evaljs(_evaluator,"Input_firstRectForRange",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+QJsonObject JSInput::caretRectForPosition(int posId)
+{
+ JSArgs args = JSArgs() << posId;
+ QJsonValue result = evaljs(_evaluator,"Input_caretRectForPosition",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+int JSInput::closestPositionToPoint(int x, int y)
+{
+ JSArgs args = JSArgs() << x << y;
+ QJsonValue result = evaljs(_evaluator,"Input_closestPositionToPoint",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::closestPositionToPointWithinRange(int x, int y, int startId, int endId)
+{
+ JSArgs args = JSArgs() << x << y << startId << endId;
+ QJsonValue result = evaljs(_evaluator,"Input_closestPositionToPointWithinRange",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+QJsonObject JSInput::characterRangeAtPoint(int x, int y)
+{
+ JSArgs args = JSArgs() << x << y;
+ QJsonValue result = evaljs(_evaluator,"Input_characterRangeAtPoint",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+int JSInput::positionWithinRangeAtCharacterOffset(int startId, int endId, int offset)
+{
+ JSArgs args = JSArgs() << startId << endId << offset;
+ QJsonValue result = evaljs(_evaluator,"Input_positionWithinRangeAtCharacterOffset",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSInput::characterOffsetOfPositionWithinRange(int positionId, int startId, int endId)
+{
+ JSArgs args = JSArgs() << positionId << startId << endId;
+ QJsonValue result = evaljs(_evaluator,"Input_characterOffsetOfPositionWithinRange",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+bool JSInput::isPositionAtBoundaryGranularityInDirection(int posId, const QString &granularity,
+ const QString &direction)
+{
+ JSArgs args = JSArgs() << posId << granularity << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_isPositionAtBoundaryGranularityInDirection",args);
+ return result.isBool() ? result.toBool() : false;
+}
+
+bool JSInput::isPositionWithinTextUnitInDirection(int posId, const QString &granularity,
+ const QString &direction)
+{
+ JSArgs args = JSArgs() << posId << granularity << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_isPositionWithinTextUnitInDirection",args);
+ return result.isBool() ? result.toBool() : false;
+}
+
+int JSInput::positionFromPositionToBoundaryInDirection(int posId, const QString &granularity,
+ const QString &direction)
+{
+ JSArgs args = JSArgs() << posId << granularity << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_positionFromPositionToBoundaryInDirection",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+QJsonObject JSInput::rangeEnclosingPositionWithGranularityInDirection(int posId,
+ const QString &granularity,
+ const QString &direction)
+{
+ JSArgs args = JSArgs() << posId << granularity << direction;
+ QJsonValue result = evaljs(_evaluator,"Input_rangeEnclosingPositionWithGranularityInDirection",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+// Functions implemented in Lists.js
+
+void JSLists::increaseIndent()
+{
+ evaljs(_evaluator,"Lists_increaseIndent",JSArgs());
+}
+
+void JSLists::decreaseIndent()
+{
+ evaljs(_evaluator,"Lists_decreaseIndent",JSArgs());
+}
+
+void JSLists::clearList()
+{
+ evaljs(_evaluator,"Lists_clearList",JSArgs());
+}
+
+void JSLists::setUnorderedList()
+{
+ evaljs(_evaluator,"Lists_setUnorderedList",JSArgs());
+}
+
+void JSLists::setOrderedList()
+{
+ evaljs(_evaluator,"Lists_setOrderedList",JSArgs());
+}
+
+// Functions implemented in Main.js
+
+QString JSMain::getLanguage()
+{
+ QJsonValue result = evaljs(_evaluator,"Main_getLanguage",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+void JSMain::setLanguage(const QString &language)
+{
+ JSArgs args = JSArgs() << language;
+ evaljs(_evaluator,"Main_setLanguage",args);
+}
+
+QString JSMain::setGenerator(const QString &generator)
+{
+ JSArgs args = JSArgs() << generator;
+ QJsonValue result = evaljs(_evaluator,"Main_setGenerator",args);
+ return result.isString() ? result.toString() : QString::null;
+}
+
+bool JSMain::prepareForSave()
+{
+ QJsonValue result = evaljs(_evaluator,"Main_prepareForSave",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+QString JSMain::getHTML()
+{
+ QJsonValue result = evaljs(_evaluator,"Main_getHTML",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+bool JSMain::isEmptyDocument()
+{
+ QJsonValue result = evaljs(_evaluator,"Main_isEmptyDocument",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+// Functions implemented in Metadata.js
+
+QJsonObject JSMetadata::getMetadata()
+{
+ QJsonValue result = evaljs(_evaluator,"Metadata_getMetadata",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSMetadata::setMetadata(const QJsonObject &metadata)
+{
+ JSArgs args = JSArgs() << metadata;
+ evaljs(_evaluator,"Metadata_setMetadata",args);
+}
+
+// Functions implemented in Outline.js
+
+QJsonObject JSOutline::getOutline()
+{
+ QJsonValue result = evaljs(_evaluator,"Outline_getOutline",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSOutline::moveSection(const QString §ionId, const QString &parentId, const QString &nextId)
+{
+ JSArgs args = JSArgs() << sectionId << parentId << nextId;
+ evaljs(_evaluator,"Outline_moveSection",args);
+}
+
+void JSOutline::deleteItem(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ evaljs(_evaluator,"Outline_deleteItem",args);
+}
+
+void JSOutline::goToItem(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ evaljs(_evaluator,"Outline_goToItem",args);
+}
+
+void JSOutline::scheduleUpdateStructure()
+{
+ evaljs(_evaluator,"Outline_scheduleUpdateStructure",JSArgs());
+}
+
+void JSOutline::setNumbered(const QString &itemId, bool numbered)
+{
+ JSArgs args = JSArgs() << itemId << numbered;
+ evaljs(_evaluator,"Outline_setNumbered",args);
+}
+
+void JSOutline::setTitle(const QString &itemId, const QString &title)
+{
+ JSArgs args = JSArgs() << itemId << title;
+ evaljs(_evaluator,"Outline_setTitle",args);
+}
+
+void JSOutline::insertTableOfContents()
+{
+ evaljs(_evaluator,"Outline_insertTableOfContents",JSArgs());
+}
+
+void JSOutline::insertListOfFigures()
+{
+ evaljs(_evaluator,"Outline_insertListOfFigures",JSArgs());
+}
+
+void JSOutline::insertListOfTables()
+{
+ evaljs(_evaluator,"Outline_insertListOfTables",JSArgs());
+}
+
+void JSOutline::setPrintMode(bool printMode)
+{
+ JSArgs args = JSArgs() << printMode;
+ evaljs(_evaluator,"Outline_setPrintMode",args);
+}
+
+QJsonObject JSOutline::examinePrintLayout(int pageHeight)
+{
+ JSArgs args = JSArgs() << pageHeight;
+ QJsonValue result = evaljs(_evaluator,"Outline_examinePrintLayout",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+bool JSOutline::detectSectionNumbering()
+{
+ QJsonValue result = evaljs(_evaluator,"Outline_detectSectionNumbering",JSArgs());
+ return result.isBool() ? result.toBool() : false;
+}
+
+QJsonObject JSOutline::findUsedStyles()
+{
+ QJsonValue result = evaljs(_evaluator,"Outline_findUsedStyles",JSArgs());
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+// Functions implemented in Preview.js
+
+void JSPreview::showForStyle(const QString &styleId, const QString &uiName, const QString &title)
+{
+ JSArgs args = JSArgs() << styleId << uiName << title;
+ evaljs(_evaluator,"Preview_showForStyle",args);
+ // TODO
+}
+
+// Functions implemented in Scan.js
+
+void JSScan::reset()
+{
+ evaljs(_evaluator,"Scan_reset",JSArgs());
+}
+
+EDScanParagraph *JSScan::next()
+{
+ // TODO
+ return NULL;
+}
+
+int JSScan::addMatch(int start, int end)
+{
+ JSArgs args = JSArgs() << start << end;
+ QJsonValue result = evaljs(_evaluator,"Scan_addMatch",args);
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+void JSScan::showMatch(int matchId)
+{
+ JSArgs args = JSArgs() << matchId;
+ evaljs(_evaluator,"Scan_showMatch",args);
+}
+
+void JSScan::replaceMatch(int matchId, const QString &text)
+{
+ JSArgs args = JSArgs() << matchId << text;
+ evaljs(_evaluator,"Scan_replaceMatch",args);
+}
+
+void JSScan::removeMatch(int matchId)
+{
+ JSArgs args = JSArgs() << matchId;
+ evaljs(_evaluator,"Scan_removeMatch",args);
+}
+
+void JSScan::goToMatch(int matchId)
+{
+ JSArgs args = JSArgs() << matchId;
+ evaljs(_evaluator,"Scan_goToMatch",args);
+}
+
+// Functions implemented in Selection.js
+
+void JSSelection::update()
+{
+ evaljs(_evaluator,"Selection_update",JSArgs());
+}
+
+void JSSelection::selectAll()
+{
+ evaljs(_evaluator,"Selection_selectAll",JSArgs());
+}
+
+void JSSelection::selectParagraph()
+{
+ evaljs(_evaluator,"Selection_selectParagraph",JSArgs());
+}
+
+void JSSelection::selectWordAtCursor()
+{
+ evaljs(_evaluator,"Selection_selectWordAtCursor",JSArgs());
+}
+
+QString JSSelection::dragSelectionBegin(int x, int y, bool selectWord)
+{
+ JSArgs args = JSArgs() << x << y << selectWord;
+ QJsonValue result = evaljs(_evaluator,"Selection_dragSelectionBegin",args);
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QString JSSelection::dragSelectionUpdate(int x, int y, bool selectWord)
+{
+ JSArgs args = JSArgs() << x << y << selectWord;
+ QJsonValue result = evaljs(_evaluator,"Selection_dragSelectionUpdate",args);
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QString JSSelection::moveStartLeft()
+{
+ QJsonValue result = evaljs(_evaluator,"Selection_moveStartLeft",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QString JSSelection::moveStartRight()
+{
+ QJsonValue result = evaljs(_evaluator,"Selection_moveStartRight",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QString JSSelection::moveEndLeft()
+{
+ QJsonValue result = evaljs(_evaluator,"Selection_moveEndLeft",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QString JSSelection::moveEndRight()
+{
+ QJsonValue result = evaljs(_evaluator,"Selection_moveEndRight",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+void JSSelection::setSelectionStartAtCoords(int x, int y)
+{
+ JSArgs args = JSArgs() << x << y;
+ evaljs(_evaluator,"Selection_setSelectionStartAtCoords",args);
+}
+
+void JSSelection::setSelectionEndAtCoords(int x, int y)
+{
+ JSArgs args = JSArgs() << x << y;
+ evaljs(_evaluator,"Selection_setSelectionEndAtCoords",args);
+}
+
+void JSSelection::setTableSelectionEdgeAtCoords(const QString &edge, int x, int y)
+{
+ JSArgs args = JSArgs() << edge << x << y;
+ evaljs(_evaluator,"Selection_setTableSelectionEdgeAtCoords",args);
+}
+
+void JSSelection::print()
+{
+ evaljs(_evaluator,"Selection_print",JSArgs());
+}
+
+// Functions implemented in Styles.js
+
+QString JSStyles::getCSSText()
+{
+ QJsonValue result = evaljs(_evaluator,"Styles_getCSSText",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+void JSStyles::setCSSText(const QString &cssText, const QJsonObject &rules)
+{
+ JSArgs args = JSArgs() << cssText << rules;
+ evaljs(_evaluator,"Styles_setCSSText",args);
+}
+
+QString JSStyles::paragraphClass()
+{
+ QJsonValue result = evaljs(_evaluator,"Styles_getParagraphClass",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+void JSStyles::setParagraphClass(const QString ¶graphClass)
+{
+ JSArgs args = JSArgs() << paragraphClass;
+ evaljs(_evaluator,"Styles_setParagraphClass",args);
+}
+
+// Functions implemented in Tables.js
+
+void JSTables::insertTable(int rows, int cols, const QString &width, bool numbered,
+ const QString &caption, const QString &className)
+{
+ JSArgs args = JSArgs() << rows << cols << width << numbered << caption << className;
+ evaljs(_evaluator,"Tables_insertTable",args);
+}
+
+void JSTables::addAdjacentRow()
+{
+ evaljs(_evaluator,"Tables_addAdjacentRow",JSArgs());
+}
+
+void JSTables::addAdjacentColumn()
+{
+ evaljs(_evaluator,"Tables_addAdjacentColumn",JSArgs());
+}
+
+void JSTables::removeAdjacentRow()
+{
+ evaljs(_evaluator,"Tables_removeAdjacentRow",JSArgs());
+}
+
+void JSTables::removeAdjacentColumn()
+{
+ evaljs(_evaluator,"Tables_removeAdjacentColumn",JSArgs());
+}
+
+void JSTables::clearCells()
+{
+ evaljs(_evaluator,"Tables_clearCells",JSArgs());
+}
+
+void JSTables::mergeCells()
+{
+ evaljs(_evaluator,"Tables_mergeCells",JSArgs());
+}
+
+void JSTables::splitSelection()
+{
+ evaljs(_evaluator,"Tables_splitSelection",JSArgs());
+}
+
+QString JSTables::getSelectedTableId()
+{
+ QJsonValue result = evaljs(_evaluator,"Tables_getSelectedTableId",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+QJsonObject JSTables::getProperties(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ QJsonValue result = evaljs(_evaluator,"Tables_getProperties",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+void JSTables::setProperties(const QString &itemId, const QString &width)
+{
+ JSArgs args = JSArgs() << itemId << width;
+ evaljs(_evaluator,"Tables_setProperties",args);
+}
+
+void JSTables::setColWidths(const QString &itemId, const QJsonArray &colWidths)
+{
+ JSArgs args = JSArgs() << itemId << colWidths;
+ evaljs(_evaluator,"Tables_setColWidths",args);
+}
+
+QJsonObject JSTables::getGeometry(const QString &itemId)
+{
+ JSArgs args = JSArgs() << itemId;
+ QJsonValue result = evaljs(_evaluator,"Tables_getGeometry",args);
+ return result.isObject() ? result.toObject() : QJsonObject();
+}
+
+// Functions implemented in UndoManager.js
+
+int JSUndoManager::getLength()
+{
+ QJsonValue result = evaljs(_evaluator,"UndoManager_getLength",JSArgs());
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+int JSUndoManager::getIndex()
+{
+ QJsonValue result = evaljs(_evaluator,"UndoManager_getIndex",JSArgs());
+ return result.isDouble() ? result.toDouble() : 0;
+}
+
+void JSUndoManager::setIndex(int index)
+{
+ JSArgs args = JSArgs() << index;
+ evaljs(_evaluator,"UndoManager_setIndex",args);
+}
+
+void JSUndoManager::undo()
+{
+ evaljs(_evaluator,"UndoManager_undo",JSArgs());
+}
+
+void JSUndoManager::redo()
+{
+ evaljs(_evaluator,"UndoManager_redo",JSArgs());
+}
+
+void JSUndoManager::newGroup(const QString &name)
+{
+ JSArgs args = JSArgs() << name;
+ evaljs(_evaluator,"UndoManager_newGroup",args);
+}
+
+QString JSUndoManager::groupType()
+{
+ QJsonValue result = evaljs(_evaluator,"UndoManager_groupType",JSArgs());
+ return result.isString() ? result.toString() : QString::null;
+}
+
+// Functions implemented in Viewport.js
+
+void JSViewport::setViewportWidth(int width)
+{
+ JSArgs args = JSArgs() << width;
+ evaljs(_evaluator,"Viewport_setViewportWidth",args);
+}
+
+void JSViewport::setTextScale(int textScale)
+{
+ JSArgs args = JSArgs() << textScale;
+ evaljs(_evaluator,"Viewport_setTextScale",args);
+}
+
+// All modules
+
+JSInterface::JSInterface(JSEvaluator *evaluator)
+: autoCorrect(evaluator),
+ changeTracking(evaluator),
+ clipboard(evaluator),
+ cursor(evaluator),
+ equations(evaluator),
+ figures(evaluator),
+ formatting(evaluator),
+ input(evaluator),
+ lists(evaluator),
+ main(evaluator),
+ metadata(evaluator),
+ outline(evaluator),
+ preview(evaluator),
+ scan(evaluator),
+ selection(evaluator),
+ styles(evaluator),
+ tables(evaluator),
+ undoManager(evaluator),
+ viewport(evaluator)
+{
+}
http://git-wip-us.apache.org/repos/asf/incubator-corinthia/blob/23c028c7/consumers/corinthia/src/JSInterface.h
----------------------------------------------------------------------
diff --git a/consumers/corinthia/src/JSInterface.h b/consumers/corinthia/src/JSInterface.h
new file mode 100644
index 0000000..8cb9e85
--- /dev/null
+++ b/consumers/corinthia/src/JSInterface.h
@@ -0,0 +1,478 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements. See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership. The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License. You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied. See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+#include <QString>
+#include <QRect>
+#include <QJsonObject>
+#include <QJsonArray>
+#include <QTextStream>
+
+/**
+ * \file JSInterface.h
+ *
+ * C++ interface to the JavaScript editor library
+ *
+ * All of the core editing operations for Corinthia are implemented in the Editor library, which is
+ * written in JavaScript. This library can be used either from within a web browser, or, in the case
+ * of the Qt application, from an embedded web view. For this app, we use a QWebView instance which
+ * maintains the in-memory DOM tree of the document, and has injected into it all of the javascript
+ * code that is part of the editor library.
+ *
+ * The source code of the Editor library lives in (repository-root)/Editor/src. During build of the
+ * Qt app, all the javascript files are copied into (build-dir)/share/corinthia/js. If you wish to
+ * make changes to the javascript code, you should modify the files in the former location, as the
+ * latter files will be overwritten on every build.
+ *
+ * The purpose of JSInterface.h and JSInterface.cpp is to provide a C++ wrapper over this. All of
+ * the methods defined in the classes below (with the exception of callbacks) ultimately result in a
+ * call to QWebFrame's evaluateJavaScript() method. See the documentation for JSInterface.cpp for
+ * details.
+ *
+ * The editor library is divided into *modules*, each of which implements a specific aspect of
+ * editing functionality. For example, the Cursor module contains methods for moving the cursor
+ * around the document, and inserting or deleting text at the current cursor position. Similarly,
+ * the Tables module contains methods for inserting, deleting, and modifying tables. A separate C++
+ * class is defined for each module, and an instance of each class is maintained by the "container"
+ * class, JSInterface. When using the code here, you should do so via a JSInterface instance.
+ */
+
+#define JS_MODULE_COMMON(className) \
+Q_DISABLE_COPY(className) \
+public: \
+className(JSEvaluator *evaluator) : JSModule(evaluator) {}
+
+QTextStream& qStdOut();
+QString QRectString(QRect rect);
+
+/**
+ * Callback interface
+ *
+ * While the module classes are for making calls from C++ to JavaScript, the JSCallbacks abstract
+ * class is for responding to requests from JavaScript to invoke C++ code. This is declared here as
+ * an abstract class (that is, with all methods virtual and no implementations provided) to avoid
+ * dependencies between the code in this file and other parts of the application. The
+ * EditorJSCallbacks class in Editor.cpp provides a concrete implementation of this, which is where
+ * the actual callback functions are implemented.
+ *
+ * Callbacks are always invoked *after* the execution of a particular editor library API function,
+ * not during. The reason for this design design in the library was to enable support for web view
+ * classes that did not provide native support for callbacks (as was the case for iOS, at least at
+ * the time the library was originally written).
+ *
+ * The way that callbacks are invoked is that after each editor API call, a query is performed for a
+ * list of pending callback messages. The evaluation logic iterates through these and invokes the
+ * appropriate callback method for each. For this reason, callbacks method are all 'void' - they
+ * never return a value. Callbacks are for notification purposes only - typically telling the
+ * application to update the UI in some manner.
+ */
+class JSCallbacks
+{
+public:
+ virtual ~JSCallbacks() {}
+ virtual void debug(const QString &message) = 0;
+ virtual void addOutlineItem(const QString &itemId, const QString &type, const QString &title) = 0;
+ virtual void updateOutlineItem(const QString &itemId, const QString &title) = 0;
+ virtual void removeOutlineItem(const QString &itemId) = 0;
+ virtual void outlineUpdated() = 0;
+ virtual void setCursor(int x, int y, int width, int height) = 0;
+ virtual void setSelectionHandles(int x1, int y1, int height1, int x2, int y2, int height2) = 0;
+ virtual void setTableSelection(int x, int y, int width, int height) = 0;
+ virtual void setSelectionBounds(int left, int top, int right, int bottom) = 0;
+ virtual void clearSelectionHandlesAndCursor() = 0;
+ virtual void updateAutoCorrect() = 0;
+ virtual void error(const QString &message, const QString &operation) = 0;
+};
+
+/**
+ * The JSEvaluator abstract class provides an evaluate() method which is called (indirectly) by all
+ * of the individual module methods. As with JSCallbacks, it is defined as abstract to avoid a
+ * dependency on the code outside of this file. The EditorJSEvaluator class in Editor.cpp provides a
+ * concrete implementation of this; its evaluate() method simply calls through to the
+ * evaluateJavaScript() method of QWebView.
+ *
+ * JSEvaluator also has a callbacks() method, which must return an instance of JSCallbacks. This
+ * makes JSEvaluator the "central point of contact" between the JavaScript interface and the rest of
+ * the application, in that it provides the necessary access to call *in* to javascript, and to
+ * respond (via callbacks) to calls *out* of javascript. Upon initialisation of a document window,
+ * concrete implementations of both JSCallbacks and JSEvaluator are created, the latter maintaining
+ * a reference to the former. See EditorPrivate::EditorPrivate() for where ths is actually done.
+ */
+class JSEvaluator
+{
+public:
+ virtual ~JSEvaluator() {}
+ virtual QString evaluate(const QString &script) = 0;
+ virtual JSCallbacks *callbacks() = 0;
+};
+
+class JSAutoCorrect;
+class JSChangeTracking;
+class JSClipboard;
+class JSCursor;
+class JSEquations;
+class JSFigures;
+class JSFormatting;
+class JSInput;
+class JSLists;
+class JSMain;
+class JSMetadata;
+class JSOutline;
+class JSPreview;
+class JSScan;
+class JSSelection;
+class JSStyles;
+class JSTables;
+class JSUndoManager;
+class JSViewport;
+class EDScanParagraph;
+
+class JSError
+{
+public:
+ const QString &type() { return _type; }
+ const QString &message() { return _message; }
+ const QString &operation() { return _operation; }
+ const QString &html() { return _html; }
+
+private:
+
+ QString _type;
+ QString _message;
+ QString _operation;
+ QString _html;
+};
+
+class JSModule
+{
+ Q_DISABLE_COPY(JSModule)
+public:
+ JSModule(JSEvaluator *evaluator) : _evaluator(evaluator) {};
+protected:
+ JSEvaluator *_evaluator;
+};
+
+// Functions implemented in AutoCorrect.js
+
+class JSAutoCorrect : public JSModule
+{
+ JS_MODULE_COMMON(JSAutoCorrect)
+ void correctPrecedingWord(int numChars, const QString &replacement, bool confirmed);
+ QJsonObject getCorrection();
+ QJsonObject getCorrectionCoords();
+ void acceptCorrection();
+ void replaceCorrection(const QString &replacement);
+};
+
+// Functions implemented in ChangeTracking.js
+
+class JSChangeTracking : public JSModule
+{
+ JS_MODULE_COMMON(JSChangeTracking)
+ bool showChanges();
+ bool trackChanges();
+ void setShowChanges(bool showChanges);
+ void setTrackChanges(bool trackChanges);
+};
+
+// Functions implemented in Clipboard.js
+
+class JSClipboard : public JSModule
+{
+ JS_MODULE_COMMON(JSClipboard)
+ QJsonObject clipboardCut();
+ QJsonObject clipboardCopy();
+ void pasteHTML(const QString &html);
+ void pasteText(const QString &text);
+};
+
+// Functions implemented in Cursor.js
+
+class JSCursor : public JSModule
+{
+ JS_MODULE_COMMON(JSCursor)
+ QString positionCursor(int x, int y, bool wordBoundary);
+ QRect getCursorPosition();
+ void moveLeft();
+ void moveRight();
+ void moveToStartOfDocument();
+ void moveToEndOfDocument();
+ void insertReference(const QString &itemId);
+ void insertLink(const QString &text, const QString &url);
+ void insertCharacter(unsigned short character, bool allowInvalidPos);
+ void deleteCharacter();
+ void enterPressed();
+ QString getPrecedingWord();
+ QJsonObject getLinkProperties();
+ void setLinkProperties(QJsonObject properties);
+ void setReferenceTarget(const QString &itemId);
+ void insertFootnote(const QString &content);
+ void insertEndnote(const QString &content);
+};
+
+// Functions implemented in Equations.js
+
+class JSEquations : public JSModule
+{
+ JS_MODULE_COMMON(JSEquations)
+ void insertEquation();
+};
+
+// Functions implemented in Figures.js
+
+class JSFigures : public JSModule
+{
+ JS_MODULE_COMMON(JSFigures)
+ void insertFigure(const QString &filename, const QString &width,
+ bool numbered, const QString &caption);
+ QString getSelectedFigureId();
+ QJsonObject getProperties(const QString &itemId);
+ void setProperties(const QString &itemId, const QString &width, const QString &src);
+ QJsonObject getGeometry(const QString &itemId);
+};
+
+// Functions implemented in Formatting.js
+
+class JSFormatting : public JSModule
+{
+ JS_MODULE_COMMON(JSFormatting)
+ QJsonObject getFormatting();
+ void applyFormattingChanges(const QString &style, QJsonObject properties);
+};
+
+// Functions implemented in Input.js
+
+class JSInput : public JSModule
+{
+ JS_MODULE_COMMON(JSInput)
+ void removePosition(int posId);
+
+ QString textInRange(int startId, int startAdjust, int endId, int endAdjust);
+ void replaceRange(int startId, int endId, const QString &text);
+ QJsonObject selectedTextRange();
+ void setSelectedTextRange(int startId, int endId);
+ QJsonObject markedTextRange();
+ void setMarkedText(const QString &text, int startOffset, int endOffset);
+ void unmarkText();
+ bool forwardSelectionAffinity();
+ void setForwardSelectionAffinity(bool forwardSelectionAffinity);
+ int positionFromPositionOffset(int posId, int offset);
+ int positionFromPositionInDirectionOffset(int posId, const QString &direction, int offset);
+ int comparePositionToPosition(int positionId, int otherId);
+ int offsetFromPositionToPosition(int fromPosition, int toPosition);
+ int positionWithinRangeFarthestInDirection(int startId, int endId, const QString &direction);
+ QJsonObject characterRangeByExtendingPositionInDirection(int positionId, const QString &direction);
+ QJsonObject firstRectForRange(int startId, int endId);
+ QJsonObject caretRectForPosition(int posId);
+ int closestPositionToPoint(int x, int y);
+ int closestPositionToPointWithinRange(int x, int y, int startId, int endId);
+ QJsonObject characterRangeAtPoint(int x, int y);
+ int positionWithinRangeAtCharacterOffset(int startId, int endId, int offset);
+ int characterOffsetOfPositionWithinRange(int positionId, int startId, int endId);
+
+ bool isPositionAtBoundaryGranularityInDirection(int posId, const QString &granularity,
+ const QString &direction);
+ bool isPositionWithinTextUnitInDirection(int posId, const QString &granularity,
+ const QString &direction);
+ int positionFromPositionToBoundaryInDirection(int posId, const QString &granularity,
+ const QString &direction);
+ QJsonObject rangeEnclosingPositionWithGranularityInDirection(int posId,
+ const QString &granularity,
+ const QString &direction);
+};
+
+// Functions implemented in Lists.js
+
+class JSLists : public JSModule
+{
+ JS_MODULE_COMMON(JSLists)
+ void increaseIndent();
+ void decreaseIndent();
+ void clearList();
+ void setUnorderedList();
+ void setOrderedList();
+};
+
+// Functions implemented in Main.js
+
+class JSMain : public JSModule
+{
+ JS_MODULE_COMMON(JSMain)
+ QString getLanguage();
+ void setLanguage(const QString &language);
+ QString setGenerator(const QString &generator);
+ bool prepareForSave();
+ QString getHTML();
+ bool isEmptyDocument();
+};
+
+// Functions implemented in Metadata.js
+
+class JSMetadata : public JSModule
+{
+ JS_MODULE_COMMON(JSMetadata)
+ QJsonObject getMetadata();
+ void setMetadata(const QJsonObject &metadata);
+};
+
+// Functions implemented in Outline.js
+
+class JSOutline : public JSModule
+{
+ JS_MODULE_COMMON(JSOutline)
+ QJsonObject getOutline();
+ void moveSection(const QString §ionId, const QString &parentId, const QString &nextId);
+ void deleteItem(const QString &itemId);
+ void goToItem(const QString &itemId);
+ void scheduleUpdateStructure();
+ void setNumbered(const QString &itemId, bool numbered);
+ void setTitle(const QString &itemId, const QString &title);
+ void insertTableOfContents();
+ void insertListOfFigures();
+ void insertListOfTables();
+ void setPrintMode(bool printMode);
+ QJsonObject examinePrintLayout(int pageHeight);
+ bool detectSectionNumbering();
+ QJsonObject findUsedStyles();
+};
+
+// Functions implemented in Preview.js
+
+class JSPreview : public JSModule
+{
+ JS_MODULE_COMMON(JSPreview)
+ void showForStyle(const QString &styleId, const QString &uiName, const QString &title);
+};
+
+// Functions implemented in Scan.js
+
+class JSScan : public JSModule
+{
+ JS_MODULE_COMMON(JSScan)
+ void reset();
+ EDScanParagraph *next();
+ int addMatch(int start, int end);
+ void showMatch(int matchId);
+ void replaceMatch(int matchId, const QString &text);
+ void removeMatch(int matchId);
+ void goToMatch(int matchId);
+};
+
+// Functions implemented in Selection.js
+
+class JSSelection : public JSModule
+{
+ JS_MODULE_COMMON(JSSelection)
+ void update();
+ void selectAll();
+ void selectParagraph();
+ void selectWordAtCursor();
+ QString dragSelectionBegin(int x, int y, bool selectWord);
+ QString dragSelectionUpdate(int x, int y, bool selectWord);
+ QString moveStartLeft();
+ QString moveStartRight();
+ QString moveEndLeft();
+ QString moveEndRight();
+ void setSelectionStartAtCoords(int x, int y);
+ void setSelectionEndAtCoords(int x, int y);
+ void setTableSelectionEdgeAtCoords(const QString &edge, int x, int y);
+ void print();
+};
+
+// Functions implemented in Styles.js
+
+class JSStyles : public JSModule
+{
+ JS_MODULE_COMMON(JSStyles)
+ QString getCSSText();
+ void setCSSText(const QString &cssText, const QJsonObject &rules);
+ QString paragraphClass();
+ void setParagraphClass(const QString ¶graphClass);
+};
+
+// Functions implemented in Tables.js
+
+class JSTables : public JSModule
+{
+ JS_MODULE_COMMON(JSTables)
+ void insertTable(int rows, int cols, const QString &width, bool numbered,
+ const QString &caption, const QString &className);
+ void addAdjacentRow();
+ void addAdjacentColumn();
+ void removeAdjacentRow();
+ void removeAdjacentColumn();
+ void clearCells();
+ void mergeCells();
+ void splitSelection();
+ QString getSelectedTableId();
+ QJsonObject getProperties(const QString &itemId);
+ void setProperties(const QString &itemId, const QString &width);
+ void setColWidths(const QString &itemId, const QJsonArray &colWidths);
+ QJsonObject getGeometry(const QString &itemId);
+};
+
+// Functions implemented in UndoManager.js
+
+class JSUndoManager : public JSModule
+{
+ JS_MODULE_COMMON(JSUndoManager)
+ int getLength();
+ int getIndex();
+ void setIndex(int index);
+ void undo();
+ void redo();
+ void newGroup(const QString &name);
+ QString groupType();
+};
+
+// Functions implemented in Viewport.js
+
+class JSViewport : public JSModule
+{
+ JS_MODULE_COMMON(JSViewport)
+ void setViewportWidth(int width);
+ void setTextScale(int textScale);
+};
+
+// All modules
+
+class JSInterface
+{
+ Q_DISABLE_COPY(JSInterface)
+public:
+ JSInterface(JSEvaluator *evaluator);
+ JSAutoCorrect autoCorrect;
+ JSChangeTracking changeTracking;
+ JSClipboard clipboard;
+ JSCursor cursor;
+ JSEquations equations;
+ JSFigures figures;
+ JSFormatting formatting;
+ JSInput input;
+ JSLists lists;
+ JSMain main;
+ JSMetadata metadata;
+ JSOutline outline;
+ JSPreview preview;
+ JSScan scan;
+ JSSelection selection;
+ JSStyles styles;
+ JSTables tables;
+ JSUndoManager undoManager;
+ JSViewport viewport;
+};
+
+void processCallbacks(JSEvaluator *evaluator);