1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 package com.sun.star.wizards.text; 28 29 import java.util.Calendar; 30 import java.util.GregorianCalendar; 31 32 import com.sun.star.container.NoSuchElementException; 33 import com.sun.star.container.XNameAccess; 34 import com.sun.star.document.XDocumentProperties; 35 import com.sun.star.document.XDocumentPropertiesSupplier; 36 import com.sun.star.frame.XController; 37 import com.sun.star.frame.XComponentLoader; 38 import com.sun.star.frame.XDesktop; 39 import com.sun.star.frame.XFramesSupplier; 40 import com.sun.star.frame.XLoadable; 41 import com.sun.star.frame.XModel; 42 import com.sun.star.frame.XModule; 43 import com.sun.star.frame.XTerminateListener; 44 import com.sun.star.frame.XStorable; 45 import com.sun.star.i18n.NumberFormatIndex; 46 import com.sun.star.awt.Size; 47 import com.sun.star.awt.XWindow; 48 import com.sun.star.awt.XWindowPeer; 49 import com.sun.star.beans.PropertyValue; 50 import com.sun.star.beans.PropertyVetoException; 51 import com.sun.star.lang.Locale; 52 import com.sun.star.lang.WrappedTargetException; 53 import com.sun.star.lang.XComponent; 54 import com.sun.star.lang.XMultiServiceFactory; 55 56 import com.sun.star.style.XStyle; 57 import com.sun.star.style.XStyleFamiliesSupplier; 58 import com.sun.star.task.XStatusIndicatorFactory; 59 import com.sun.star.text.XPageCursor; 60 import com.sun.star.text.XSimpleText; 61 import com.sun.star.text.XText; 62 import com.sun.star.text.XTextContent; 63 import com.sun.star.text.XTextCursor; 64 import com.sun.star.text.XTextDocument; 65 import com.sun.star.text.XTextViewCursor; 66 import com.sun.star.text.XTextViewCursorSupplier; 67 import com.sun.star.uno.UnoRuntime; 68 import com.sun.star.util.DateTime; 69 import com.sun.star.util.XModifiable; 70 import com.sun.star.util.XNumberFormatsSupplier; 71 import com.sun.star.util.XRefreshable; 72 import com.sun.star.wizards.common.Configuration; 73 import com.sun.star.wizards.common.Desktop; 74 import com.sun.star.wizards.common.Helper; 75 import com.sun.star.wizards.common.JavaTools; 76 import com.sun.star.wizards.common.Helper.DateUtils; 77 import com.sun.star.wizards.common.PropertyNames; 78 import com.sun.star.wizards.document.OfficeDocument; 79 80 public class TextDocument 81 { 82 83 public XComponent xComponent; 84 public com.sun.star.text.XTextDocument xTextDocument; 85 public com.sun.star.util.XNumberFormats NumberFormats; 86 public com.sun.star.document.XDocumentProperties m_xDocProps; 87 public com.sun.star.task.XStatusIndicator xProgressBar; 88 public com.sun.star.frame.XFrame xFrame; 89 public XText xText; 90 public XMultiServiceFactory xMSFDoc; 91 public XMultiServiceFactory xMSF; 92 public com.sun.star.util.XNumberFormatsSupplier xNumberFormatsSupplier; 93 public com.sun.star.awt.XWindowPeer xWindowPeer; 94 public int PageWidth; 95 public int ScaleWidth; 96 public Size DocSize; 97 public com.sun.star.awt.Rectangle PosSize; 98 public com.sun.star.lang.Locale CharLocale; 99 public XStorable xStorable; 100 101 // creates an instance of TextDocument and creates a named frame. No document is actually loaded into this frame. 102 public TextDocument(XMultiServiceFactory xMSF, XTerminateListener listener, String FrameName) 103 { 104 this.xMSF = xMSF; 105 xFrame = OfficeDocument.createNewFrame(xMSF, listener, FrameName); 106 } 107 108 // creates an instance of TextDocument by loading a given URL as preview 109 public TextDocument(XMultiServiceFactory xMSF, String _sPreviewURL, boolean bShowStatusIndicator, XTerminateListener listener) 110 { 111 this.xMSF = xMSF; 112 113 xFrame = OfficeDocument.createNewFrame(xMSF, listener); 114 xTextDocument = loadAsPreview(_sPreviewURL, true); 115 xComponent = UnoRuntime.queryInterface(XComponent.class, xTextDocument); 116 117 if (bShowStatusIndicator) 118 { 119 showStatusIndicator(); 120 } 121 init(); 122 } 123 124 // creates an instance of TextDocument from the desktop's current frame 125 public TextDocument(XMultiServiceFactory xMSF, boolean bShowStatusIndicator, XTerminateListener listener) 126 { 127 this.xMSF = xMSF; 128 129 XDesktop xDesktop = Desktop.getDesktop(xMSF); 130 XFramesSupplier xFrameSupplier = UnoRuntime.queryInterface(XFramesSupplier.class, xDesktop); 131 xFrame = xFrameSupplier.getActiveFrame(); 132 xComponent = UnoRuntime.queryInterface(XComponent.class, xFrame.getController().getModel()); 133 xTextDocument = UnoRuntime.queryInterface(XTextDocument.class, xComponent); 134 135 if (bShowStatusIndicator) 136 { 137 showStatusIndicator(); 138 } 139 init(); 140 } 141 142 public static class ModuleIdentifier 143 { 144 145 private String m_identifier; 146 147 protected final String getIdentifier() 148 { 149 return m_identifier; 150 } 151 152 public ModuleIdentifier(String _identifier) 153 { 154 m_identifier = _identifier; 155 } 156 } 157 158 // creates an instance of TextDocument containing a blank text document 159 public TextDocument(XMultiServiceFactory xMSF, ModuleIdentifier _moduleIdentifier, boolean bShowStatusIndicator) 160 { 161 this.xMSF = xMSF; 162 163 try 164 { 165 // create the empty document, and set its module identifier 166 xTextDocument = UnoRuntime.queryInterface(XTextDocument.class, 167 xMSF.createInstance("com.sun.star.text.TextDocument")); 168 169 XLoadable xLoadable = UnoRuntime.queryInterface(XLoadable.class, xTextDocument); 170 xLoadable.initNew(); 171 172 XModule xModule = UnoRuntime.queryInterface(XModule.class, 173 xTextDocument); 174 xModule.setIdentifier(_moduleIdentifier.getIdentifier()); 175 176 // load the document into a blank frame 177 XDesktop xDesktop = Desktop.getDesktop(xMSF); 178 XComponentLoader xLoader = UnoRuntime.queryInterface(XComponentLoader.class, xDesktop); 179 PropertyValue[] loadArgs = new PropertyValue[] 180 { 181 new PropertyValue("Model", -1, xTextDocument, com.sun.star.beans.PropertyState.DIRECT_VALUE) 182 }; 183 xLoader.loadComponentFromURL("private:object", "_blank", 0, loadArgs); 184 185 // remember some things for later usage 186 xFrame = xTextDocument.getCurrentController().getFrame(); 187 xComponent = UnoRuntime.queryInterface(XComponent.class, xTextDocument); 188 } 189 catch (Exception e) 190 { 191 // TODO: it seems the whole project does not really have an error handling. Other menthods 192 // seem to generally silence errors, so we can't do anything else here ... 193 } 194 195 if (bShowStatusIndicator) 196 { 197 showStatusIndicator(); 198 } 199 init(); 200 } 201 202 //creates an instance of TextDocument from a given XTextDocument 203 public TextDocument(XMultiServiceFactory xMSF, XTextDocument _textDocument, boolean bshowStatusIndicator) 204 { 205 this.xMSF = xMSF; 206 xFrame = _textDocument.getCurrentController().getFrame(); 207 xComponent = UnoRuntime.queryInterface(XComponent.class, _textDocument); 208 xTextDocument = UnoRuntime.queryInterface(XTextDocument.class, xComponent); 209 //PosSize = xFrame.getComponentWindow().getPosSize(); 210 if (bshowStatusIndicator) 211 { 212 XStatusIndicatorFactory xStatusIndicatorFactory = UnoRuntime.queryInterface(XStatusIndicatorFactory.class, xFrame); 213 xProgressBar = xStatusIndicatorFactory.createStatusIndicator(); 214 xProgressBar.start(PropertyNames.EMPTY_STRING, 100); 215 xProgressBar.setValue(5); 216 } 217 xWindowPeer = UnoRuntime.queryInterface(XWindowPeer.class, xFrame.getComponentWindow()); 218 xMSFDoc = UnoRuntime.queryInterface(XMultiServiceFactory.class, xTextDocument); 219 xNumberFormatsSupplier = UnoRuntime.queryInterface(XNumberFormatsSupplier.class, xTextDocument); 220 221 XDocumentPropertiesSupplier xDocPropsSuppl = UnoRuntime.queryInterface(XDocumentPropertiesSupplier.class, xTextDocument); 222 m_xDocProps = xDocPropsSuppl.getDocumentProperties(); 223 CharLocale = (Locale) Helper.getUnoStructValue((Object) xComponent, "CharLocale"); 224 xText = xTextDocument.getText(); 225 } 226 227 private void init() 228 { 229 xWindowPeer = UnoRuntime.queryInterface(XWindowPeer.class, xFrame.getComponentWindow()); 230 xMSFDoc = UnoRuntime.queryInterface(XMultiServiceFactory.class, xTextDocument); 231 xNumberFormatsSupplier = UnoRuntime.queryInterface(XNumberFormatsSupplier.class, xTextDocument); 232 XDocumentPropertiesSupplier xDocPropsSuppl = UnoRuntime.queryInterface(XDocumentPropertiesSupplier.class, xTextDocument); 233 m_xDocProps = xDocPropsSuppl.getDocumentProperties(); 234 CharLocale = (Locale) Helper.getUnoStructValue((Object) xComponent, "CharLocale"); 235 xStorable = UnoRuntime.queryInterface(XStorable.class, xTextDocument); 236 xText = xTextDocument.getText(); 237 } 238 239 private void showStatusIndicator() 240 { 241 XStatusIndicatorFactory xStatusIndicatorFactory = UnoRuntime.queryInterface(XStatusIndicatorFactory.class, xFrame); 242 xProgressBar = xStatusIndicatorFactory.createStatusIndicator(); 243 xProgressBar.start(PropertyNames.EMPTY_STRING, 100); 244 xProgressBar.setValue(5); 245 } 246 247 public XTextDocument loadAsPreview(String sDefaultTemplate, boolean asTemplate) 248 { 249 PropertyValue loadValues[] = new PropertyValue[3]; 250 // open document in the Preview mode 251 loadValues[0] = new PropertyValue(); 252 loadValues[0].Name = PropertyNames.READ_ONLY; 253 loadValues[0].Value = Boolean.TRUE; 254 loadValues[1] = new PropertyValue(); 255 loadValues[1].Name = "AsTemplate"; 256 loadValues[1].Value = asTemplate ? Boolean.TRUE : Boolean.FALSE; 257 loadValues[2] = new PropertyValue(); 258 loadValues[2].Name = "Preview"; 259 loadValues[2].Value = Boolean.TRUE; 260 261 //set the preview document to non-modified mode in order to avoid the 'do u want to save' box 262 if (xTextDocument != null) 263 { 264 try 265 { 266 XModifiable xModi = UnoRuntime.queryInterface(XModifiable.class, xTextDocument); 267 xModi.setModified(false); 268 } 269 catch (PropertyVetoException e1) 270 { 271 e1.printStackTrace(System.out); 272 } 273 } 274 Object oDoc = OfficeDocument.load(xFrame, sDefaultTemplate, "_self", loadValues); 275 xTextDocument = (com.sun.star.text.XTextDocument) oDoc; 276 DocSize = getPageSize(); 277 xMSFDoc = UnoRuntime.queryInterface(XMultiServiceFactory.class, xTextDocument); 278 279 ViewHandler myViewHandler = new ViewHandler(xMSFDoc, xTextDocument); 280 try 281 { 282 myViewHandler.setViewSetting("ZoomType", new Short(com.sun.star.view.DocumentZoomType.ENTIRE_PAGE)); 283 } 284 catch (Exception e) 285 { 286 e.printStackTrace(); 287 } 288 289 TextFieldHandler myFieldHandler = new TextFieldHandler(xMSF, xTextDocument); 290 myFieldHandler.updateDocInfoFields(); 291 292 return xTextDocument; 293 294 } 295 296 public Size getPageSize() 297 { 298 try 299 { 300 XStyleFamiliesSupplier xStyleFamiliesSupplier = UnoRuntime.queryInterface(XStyleFamiliesSupplier.class, xTextDocument); 301 com.sun.star.container.XNameAccess xNameAccess = null; 302 xNameAccess = xStyleFamiliesSupplier.getStyleFamilies(); 303 com.sun.star.container.XNameContainer xPageStyleCollection = null; 304 xPageStyleCollection = UnoRuntime.queryInterface(com.sun.star.container.XNameContainer.class, xNameAccess.getByName("PageStyles")); 305 XStyle xPageStyle = UnoRuntime.queryInterface(XStyle.class, xPageStyleCollection.getByName("First Page")); 306 return (Size) Helper.getUnoPropertyValue(xPageStyle, "Size"); 307 308 } 309 catch (Exception exception) 310 { 311 exception.printStackTrace(System.out); 312 return null; 313 } 314 } 315 316 //creates an instance of TextDocument and creates a frame and loads a document 317 public TextDocument(XMultiServiceFactory xMSF, String URL, PropertyValue[] xArgs, XTerminateListener listener) 318 { 319 this.xMSF = xMSF; 320 XDesktop xDesktop = Desktop.getDesktop(xMSF); 321 322 xFrame = OfficeDocument.createNewFrame(xMSF, listener); 323 Object oDoc = OfficeDocument.load(xFrame, URL, "_self", xArgs); 324 xTextDocument = (XTextDocument) oDoc; 325 xComponent = UnoRuntime.queryInterface(XComponent.class, xTextDocument); 326 XWindow xWindow = xFrame.getComponentWindow(); 327 328 xWindowPeer = UnoRuntime.queryInterface(XWindowPeer.class, xFrame.getComponentWindow()); 329 xMSFDoc = UnoRuntime.queryInterface(XMultiServiceFactory.class, xTextDocument); 330 xNumberFormatsSupplier = UnoRuntime.queryInterface(XNumberFormatsSupplier.class, xTextDocument); 331 332 XDocumentPropertiesSupplier xDocPropsSuppl = UnoRuntime.queryInterface(XDocumentPropertiesSupplier.class, xTextDocument); 333 m_xDocProps = xDocPropsSuppl.getDocumentProperties(); 334 CharLocale = (Locale) Helper.getUnoStructValue((Object) xComponent, "CharLocale"); 335 } 336 337 public static XTextCursor createTextCursor(Object oCursorContainer) 338 { 339 XSimpleText xText = UnoRuntime.queryInterface(XSimpleText.class, oCursorContainer); 340 return xText.createTextCursor(); 341 } 342 343 // Todo: This method is unsecure because the last index is not necessarily the last section 344 345 // Todo: This Routine should be modified, because I cannot rely on the last Table in the document to be the last in the TextTables sequence 346 // to make it really safe you must acquire the Tablenames before the insertion and after the insertion of the new Table. By comparing the 347 // two sequences of tablenames you can find out the tablename of the last inserted Table 348 349 // Todo: This method is unsecure because the last index is not necessarily the last section 350 public int getCharWidth(String ScaleString) 351 { 352 int iScale = 200; 353 xTextDocument.lockControllers(); 354 int iScaleLen = ScaleString.length(); 355 com.sun.star.text.XTextCursor xTextCursor = createTextCursor(xTextDocument.getText()); 356 xTextCursor.gotoStart(false); 357 com.sun.star.wizards.common.Helper.setUnoPropertyValue(xTextCursor, "PageDescName", "First Page"); 358 xTextCursor.setString(ScaleString); 359 XTextViewCursorSupplier xViewCursor = UnoRuntime.queryInterface(XTextViewCursorSupplier.class, xTextDocument.getCurrentController()); 360 XTextViewCursor xTextViewCursor = xViewCursor.getViewCursor(); 361 xTextViewCursor.gotoStart(false); 362 int iFirstPos = xTextViewCursor.getPosition().X; 363 xTextViewCursor.gotoEnd(false); 364 int iLastPos = xTextViewCursor.getPosition().X; 365 iScale = (iLastPos - iFirstPos) / iScaleLen; 366 xTextCursor.gotoStart(false); 367 xTextCursor.gotoEnd(true); 368 xTextCursor.setString(PropertyNames.EMPTY_STRING); 369 unlockallControllers(); 370 return iScale; 371 } 372 373 public void unlockallControllers() 374 { 375 while (xTextDocument.hasControllersLocked()) 376 { 377 xTextDocument.unlockControllers(); 378 } 379 } 380 381 public void refresh() 382 { 383 XRefreshable xRefreshable = UnoRuntime.queryInterface(XRefreshable.class, xTextDocument); 384 xRefreshable.refresh(); 385 } 386 387 /** 388 * This method sets the Author of a Wizard-generated template correctly 389 * and adds a explanatory sentence to the template description. 390 * @param WizardName The name of the Wizard. 391 * @param TemplateDescription The old Description which is being appended with another sentence. 392 * @return void. 393 */ 394 public void setWizardTemplateDocInfo(String WizardName, String TemplateDescription) 395 { 396 try 397 { 398 Object uD = Configuration.getConfigurationRoot(xMSF, "/org.openoffice.UserProfile/Data", false); 399 XNameAccess xNA = UnoRuntime.queryInterface(XNameAccess.class, uD); 400 Object gn = xNA.getByName("givenname"); 401 Object sn = xNA.getByName("sn"); 402 String fullname = gn + PropertyNames.SPACE + sn; 403 404 Calendar cal = new GregorianCalendar(); 405 int year = cal.get(Calendar.YEAR); 406 int month = cal.get(Calendar.MONTH); 407 int day = cal.get(Calendar.DAY_OF_MONTH); 408 DateTime currentDate = new DateTime(); 409 currentDate.Day = (short) day; 410 currentDate.Month = (short) month; 411 currentDate.Year = (short) year; 412 DateUtils du = new DateUtils(xMSF, this.xTextDocument); 413 int ff = du.getFormat(NumberFormatIndex.DATE_SYS_DDMMYY); 414 String myDate = du.format(ff, currentDate); 415 416 XDocumentPropertiesSupplier xDocPropsSuppl = UnoRuntime.queryInterface(XDocumentPropertiesSupplier.class, xTextDocument); 417 XDocumentProperties xDocProps2 = xDocPropsSuppl.getDocumentProperties(); 418 xDocProps2.setAuthor(fullname); 419 xDocProps2.setModifiedBy(fullname); 420 String description = xDocProps2.getDescription(); 421 description = description + PropertyNames.SPACE + TemplateDescription; 422 description = JavaTools.replaceSubString(description, WizardName, "<wizard_name>"); 423 description = JavaTools.replaceSubString(description, myDate, "<current_date>"); 424 xDocProps2.setDescription(description); 425 } 426 catch (NoSuchElementException e) 427 { 428 // TODO Auto-generated catch block 429 e.printStackTrace(); 430 } 431 catch (WrappedTargetException e) 432 { 433 // TODO Auto-generated catch block 434 e.printStackTrace(); 435 } 436 catch (Exception e) 437 { 438 // TODO Auto-generated catch block 439 e.printStackTrace(); 440 } 441 } 442 443 /** 444 * removes an arbitrary Object which supports the 'XTextContent' interface 445 * @param oTextContent 446 * @return 447 */ 448 public boolean removeTextContent(Object oTextContent) 449 { 450 try 451 { 452 XTextContent xTextContent = UnoRuntime.queryInterface(XTextContent.class, oTextContent); 453 xText.removeTextContent(xTextContent); 454 return true; 455 } 456 catch (NoSuchElementException e) 457 { 458 e.printStackTrace(System.out); 459 return false; 460 } 461 } 462 463 /** 464 * Apparently there is no other way to get the 465 * page count of a text document other than using a cursor and 466 * making it jump to the last page... 467 * @param model the document model. 468 * @return the page count of the document. 469 */ 470 public static int getPageCount(Object model) 471 { 472 XModel xModel = UnoRuntime.queryInterface(XModel.class, model); 473 XController xController = xModel.getCurrentController(); 474 XTextViewCursorSupplier xTextVCS = UnoRuntime.queryInterface(XTextViewCursorSupplier.class, xController); 475 XTextViewCursor xTextVC = xTextVCS.getViewCursor(); 476 XPageCursor xPC = UnoRuntime.queryInterface(XPageCursor.class, xTextVC); 477 xPC.jumpToLastPage(); 478 return xPC.getPage(); 479 } 480 481 /* Possible Values for "OptionString" are: "LoadCellStyles", "LoadTextStyles", "LoadFrameStyles", 482 "LoadPageStyles", "LoadNumberingStyles", "OverwriteStyles" */ 483 } 484