Version 3.6.0.4, tag libreoffice-3.6.0.4
[LibreOffice.git] / sfx2 / source / dialog / versdlg.cxx
blob9a4fa8eaafe9a534c5962c12636db92e062e0203
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*************************************************************************
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6 * Copyright 2000, 2010 Oracle and/or its affiliates.
8 * OpenOffice.org - a multi-platform office productivity suite
10 * This file is part of OpenOffice.org.
12 * OpenOffice.org is free software: you can redistribute it and/or modify
13 * it under the terms of the GNU Lesser General Public License version 3
14 * only, as published by the Free Software Foundation.
16 * OpenOffice.org is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License version 3 for more details
20 * (a copy is included in the LICENSE file that accompanied this code).
22 * You should have received a copy of the GNU Lesser General Public License
23 * version 3 along with OpenOffice.org. If not, see
24 * <http://www.openoffice.org/license.html>
25 * for a copy of the LGPLv3 License.
27 ************************************************************************/
29 #include <unotools/localedatawrapper.hxx>
30 #include <comphelper/processfactory.hxx>
31 #include <svl/eitem.hxx>
32 #include <svl/intitem.hxx>
33 #include <svl/stritem.hxx>
34 #include <svl/itemset.hxx>
35 #include <unotools/useroptions.hxx>
36 #include <vcl/msgbox.hxx>
37 #include <vcl/svapp.hxx>
38 #include <tools/datetime.hxx>
39 #include <svl/svstdarr.hxx>
41 #include "versdlg.hrc"
42 #include "versdlg.hxx"
43 #include <sfx2/viewfrm.hxx>
44 #include "sfx2/sfxresid.hxx"
45 #include <sfx2/docfile.hxx>
46 #include <sfx2/objsh.hxx>
47 #include <sfx2/sfxsids.hrc>
48 #include <sfx2/dispatch.hxx>
49 #include <sfx2/request.hxx>
51 #include <sfx2/sfxuno.hxx>
52 #include <vector>
54 using namespace com::sun::star;
55 using ::std::vector;
57 // **************************************************************************
58 struct SfxVersionInfo
60 String aName;
61 String aComment;
62 String aAuthor;
63 DateTime aCreationDate;
65 SfxVersionInfo();
66 SfxVersionInfo( const SfxVersionInfo& rInfo )
67 : aCreationDate( DateTime::EMPTY )
68 { *this = rInfo; }
70 SfxVersionInfo& operator=( const SfxVersionInfo &rInfo )
72 aName = rInfo.aName;
73 aComment = rInfo.aComment;
74 aAuthor = rInfo.aAuthor;
75 aCreationDate = rInfo.aCreationDate;
76 return *this;
80 typedef vector< SfxVersionInfo* > _SfxVersionTable;
82 class SfxVersionTableDtor
84 private:
85 _SfxVersionTable aTableList;
86 public:
87 SfxVersionTableDtor( const SfxVersionTableDtor &rCpy )
88 { *this = rCpy; }
90 SfxVersionTableDtor( const uno::Sequence < util::RevisionTag >& rInfo );
92 ~SfxVersionTableDtor()
93 { DelDtor(); }
95 SfxVersionTableDtor& operator=( const SfxVersionTableDtor &rCpy );
96 void DelDtor();
97 SvStream& Read( SvStream & );
98 SvStream& Write( SvStream & ) const;
100 size_t size() const
101 { return aTableList.size(); }
103 SfxVersionInfo* at( size_t i ) const
104 { return aTableList[ i ]; }
107 SfxVersionTableDtor::SfxVersionTableDtor( const uno::Sequence < util::RevisionTag >& rInfo )
109 for ( sal_Int32 n=0; n<(sal_Int32)rInfo.getLength(); n++ )
111 SfxVersionInfo* pInfo = new SfxVersionInfo;
112 pInfo->aName = rInfo[n].Identifier;
113 pInfo->aComment = rInfo[n].Comment;
114 pInfo->aAuthor = rInfo[n].Author;
116 Date aDate ( rInfo[n].TimeStamp.Day, rInfo[n].TimeStamp.Month, rInfo[n].TimeStamp.Year );
117 Time aTime ( rInfo[n].TimeStamp.Hours, rInfo[n].TimeStamp.Minutes, rInfo[n].TimeStamp.Seconds, rInfo[n].TimeStamp.HundredthSeconds );
119 pInfo->aCreationDate = DateTime( aDate, aTime );
120 aTableList.push_back( pInfo );
124 void SfxVersionTableDtor::DelDtor()
126 for ( size_t i = 0, n = aTableList.size(); i < n; ++i )
127 delete aTableList[ i ];
128 aTableList.clear();
131 SfxVersionTableDtor& SfxVersionTableDtor::operator=( const SfxVersionTableDtor& rTbl )
133 DelDtor();
134 for ( size_t i = 0, n = rTbl.size(); i < n; ++i )
136 SfxVersionInfo* pNew = new SfxVersionInfo( *(rTbl.at( i )) );
137 aTableList.push_back( pNew );
139 return *this;
142 //----------------------------------------------------------------
143 SfxVersionInfo::SfxVersionInfo()
144 : aCreationDate( DateTime::EMPTY )
148 static String ConvertDateTime_Impl(const DateTime& rTime, const LocaleDataWrapper& rWrapper)
150 const String pDelim ( DEFINE_CONST_UNICODE( ", "));
151 String aStr(rWrapper.getDate(rTime));
152 aStr += pDelim;
153 aStr += rWrapper.getTime(rTime, sal_True, sal_False);
154 return aStr;
157 // Caution in the code this array si indexed directly (0, 1, ...)
158 static long nTabs_Impl[] =
160 3, // Number of Tabs
161 0, 62, 124
164 void SfxVersionsTabListBox_Impl::KeyInput( const KeyEvent& rKeyEvent )
166 const KeyCode& rCode = rKeyEvent.GetKeyCode();
167 switch ( rCode.GetCode() )
169 case KEY_RETURN :
170 case KEY_ESCAPE :
171 case KEY_TAB :
172 Window::GetParent()->KeyInput( rKeyEvent );
173 break;
174 default:
175 SvTabListBox::KeyInput( rKeyEvent );
176 break;
180 SfxVersionsTabListBox_Impl::SfxVersionsTabListBox_Impl( Window* pParent, const ResId& rResId )
181 : SvTabListBox( pParent, rResId )
185 SfxVersionDialog::SfxVersionDialog ( SfxViewFrame* pVwFrame, sal_Bool bIsSaveVersionOnClose )
186 : SfxModalDialog( NULL, SfxResId( DLG_VERSIONS ) )
187 , aNewGroup( this, SfxResId( GB_NEWVERSIONS ) )
188 , aSaveButton( this, SfxResId( PB_SAVE ) )
189 , aSaveCheckBox( this, SfxResId( CB_SAVEONCLOSE ) )
190 , aExistingGroup( this, SfxResId( GB_OLDVERSIONS ) )
191 , aDateTimeText( this, SfxResId( FT_DATETIME ) )
192 , aSavedByText( this, SfxResId( FT_SAVEDBY ) )
193 , aCommentText( this, SfxResId( FT_COMMENTS ) )
194 , aVersionBox( this, SfxResId( TLB_VERSIONS ) )
195 , aCloseButton( this, SfxResId( PB_CLOSE ) )
196 , aOpenButton( this, SfxResId( PB_OPEN ) )
197 , aViewButton( this, SfxResId( PB_VIEW ) )
198 , aDeleteButton( this, SfxResId( PB_DELETE ) )
199 , aCompareButton( this, SfxResId( PB_COMPARE ) )
200 , aHelpButton( this, SfxResId( PB_HELP ) )
201 , pViewFrame( pVwFrame )
202 , mpTable( NULL )
203 , mpLocaleWrapper( NULL )
204 , mbIsSaveVersionOnClose( bIsSaveVersionOnClose )
206 FreeResource();
208 Link aClickLink = LINK( this, SfxVersionDialog, ButtonHdl_Impl );
209 aViewButton.SetClickHdl ( aClickLink );
210 aSaveButton.SetClickHdl ( aClickLink );
211 aDeleteButton.SetClickHdl ( aClickLink );
212 aCompareButton.SetClickHdl ( aClickLink );
213 aOpenButton.SetClickHdl ( aClickLink );
214 aSaveCheckBox.SetClickHdl ( aClickLink );
216 aVersionBox.SetSelectHdl( LINK( this, SfxVersionDialog, SelectHdl_Impl ) );
217 aVersionBox.SetDoubleClickHdl( LINK( this, SfxVersionDialog, DClickHdl_Impl ) );
219 aVersionBox.GrabFocus();
220 aVersionBox.SetStyle( aVersionBox.GetStyle() | WB_HSCROLL | WB_CLIPCHILDREN );
221 aVersionBox.SetSelectionMode( SINGLE_SELECTION );
222 aVersionBox.SetTabs( &nTabs_Impl[0], MAP_APPFONT );
223 aVersionBox.Resize(); // OS: Hack for correct selection
224 RecalcDateColumn();
226 // set dialog title (filename or docinfo title)
227 String sText = GetText();
228 ( sText += ' ' ) += pViewFrame->GetObjectShell()->GetTitle();
229 SetText( sText );
231 Init_Impl();
234 String ConvertWhiteSpaces_Impl( const String& rText )
236 // converted linebreaks and tabs to blanks; it's necessary for the display
237 String sConverted;
238 const sal_Unicode* pChars = rText.GetBuffer();
239 while ( *pChars )
241 switch ( *pChars )
243 case '\n' :
244 case '\t' :
245 sConverted += ' ';
246 break;
248 default:
249 sConverted += *pChars;
252 ++pChars;
255 return sConverted;
258 void SfxVersionDialog::Init_Impl()
260 SfxObjectShell *pObjShell = pViewFrame->GetObjectShell();
261 SfxMedium* pMedium = pObjShell->GetMedium();
262 uno::Sequence < util::RevisionTag > aVersions = pMedium->GetVersionList( true );
263 delete mpTable;
264 mpTable = new SfxVersionTableDtor( aVersions );
266 for ( size_t n = 0; n < mpTable->size(); ++n )
268 SfxVersionInfo *pInfo = mpTable->at( n );
269 String aEntry = ConvertDateTime_Impl( pInfo->aCreationDate, *mpLocaleWrapper );
270 aEntry += '\t';
271 aEntry += pInfo->aAuthor;
272 aEntry += '\t';
273 aEntry += ConvertWhiteSpaces_Impl( pInfo->aComment );
274 SvLBoxEntry *pEntry = aVersionBox.InsertEntry( aEntry );
275 pEntry->SetUserData( pInfo );
279 aSaveCheckBox.Check( mbIsSaveVersionOnClose );
281 sal_Bool bEnable = !pObjShell->IsReadOnly();
282 aSaveButton.Enable( bEnable );
283 aSaveCheckBox.Enable( bEnable );
285 aOpenButton.Disable();
286 aViewButton.Disable();
287 aDeleteButton.Disable();
288 aCompareButton.Disable();
290 SelectHdl_Impl( &aVersionBox );
293 SfxVersionDialog::~SfxVersionDialog ()
295 delete mpTable;
296 delete mpLocaleWrapper;
299 void SfxVersionDialog::Open_Impl()
301 SfxObjectShell *pObjShell = pViewFrame->GetObjectShell();
303 SvLBoxEntry *pEntry = aVersionBox.FirstSelected();
304 sal_uIntPtr nPos = aVersionBox.GetModel()->GetRelPos( pEntry );
305 SfxInt16Item aItem( SID_VERSION, (short)nPos+1 );
306 SfxStringItem aTarget( SID_TARGETNAME, DEFINE_CONST_UNICODE("_blank") );
307 SfxStringItem aReferer( SID_REFERER, DEFINE_CONST_UNICODE("private:user") );
308 SfxStringItem aFile( SID_FILE_NAME, pObjShell->GetMedium()->GetName() );
310 uno::Sequence< beans::NamedValue > aEncryptionData;
311 if ( GetEncryptionData_Impl( pObjShell->GetMedium()->GetItemSet(), aEncryptionData ) )
313 // there is a password, it should be used during the opening
314 SfxUnoAnyItem aEncryptionDataItem( SID_ENCRYPTIONDATA, uno::makeAny( aEncryptionData ) );
315 pViewFrame->GetDispatcher()->Execute(
316 SID_OPENDOC, SFX_CALLMODE_ASYNCHRON, &aFile, &aItem, &aTarget, &aReferer, &aEncryptionDataItem, 0L );
318 else
319 pViewFrame->GetDispatcher()->Execute(
320 SID_OPENDOC, SFX_CALLMODE_ASYNCHRON, &aFile, &aItem, &aTarget, &aReferer, 0L );
322 Close();
325 void SfxVersionDialog::RecalcDateColumn()
327 // recalculate the datetime column width
328 DateTime aNow( DateTime::SYSTEM );
329 mpLocaleWrapper = new LocaleDataWrapper(
330 ::comphelper::getProcessServiceFactory(), Application::GetSettings().GetLocale() );
331 String sDateTime = ConvertDateTime_Impl( aNow, *mpLocaleWrapper );
332 long nWidth = aVersionBox.GetTextWidth( sDateTime );
333 nWidth += 15; // a little offset
334 long nTab = aVersionBox.GetTab(1);
335 if ( nWidth > nTab )
337 // resize columns
338 long nDelta = nWidth - nTab;
339 aVersionBox.SetTab( 1, nTab + nDelta, MAP_PIXEL );
340 nTab = aVersionBox.GetTab(2);
341 aVersionBox.SetTab( 2, nTab + nDelta, MAP_PIXEL );
343 // resize and move header
344 Size aSize = aDateTimeText.GetSizePixel();
345 aSize.Width() += nDelta;
346 aDateTimeText.SetSizePixel( aSize );
347 Point aPos = aSavedByText.GetPosPixel();
348 aPos.X() += nDelta;
349 aSavedByText.SetPosPixel( aPos );
350 aPos = aCommentText.GetPosPixel();
351 aPos.X() += nDelta;
352 aCommentText.SetPosPixel( aPos );
356 IMPL_LINK_NOARG(SfxVersionDialog, DClickHdl_Impl)
358 Open_Impl();
359 return 0L;
362 IMPL_LINK_NOARG(SfxVersionDialog, SelectHdl_Impl)
364 bool bEnable = ( aVersionBox.FirstSelected() != NULL );
365 SfxObjectShell* pObjShell = pViewFrame->GetObjectShell();
366 aDeleteButton.Enable( bEnable!= false && !pObjShell->IsReadOnly() );
367 aOpenButton.Enable( bEnable!= false );
368 aViewButton.Enable( bEnable!= false );
370 const SfxPoolItem *pDummy=NULL;
371 SfxItemState eState = pViewFrame->GetDispatcher()->QueryState( SID_DOCUMENT_MERGE, pDummy );
372 eState = pViewFrame->GetDispatcher()->QueryState( SID_DOCUMENT_COMPARE, pDummy );
373 aCompareButton.Enable( bEnable!= false && eState >= SFX_ITEM_AVAILABLE );
375 return 0L;
378 IMPL_LINK( SfxVersionDialog, ButtonHdl_Impl, Button*, pButton )
380 SfxObjectShell *pObjShell = pViewFrame->GetObjectShell();
381 SvLBoxEntry *pEntry = aVersionBox.FirstSelected();
383 if ( pButton == &aSaveCheckBox )
385 mbIsSaveVersionOnClose = aSaveCheckBox.IsChecked();
387 else if ( pButton == &aSaveButton )
389 SfxVersionInfo aInfo;
390 aInfo.aAuthor = SvtUserOptions().GetFullName();
391 SfxViewVersionDialog_Impl* pDlg = new SfxViewVersionDialog_Impl( this, aInfo, sal_True );
392 short nRet = pDlg->Execute();
393 if ( nRet == RET_OK )
395 SfxStringItem aComment( SID_DOCINFO_COMMENTS, aInfo.aComment );
396 pObjShell->SetModified( sal_True );
397 const SfxPoolItem* aItems[2];
398 aItems[0] = &aComment;
399 aItems[1] = NULL;
400 pViewFrame->GetBindings().ExecuteSynchron( SID_SAVEDOC, aItems, 0 );
401 aVersionBox.SetUpdateMode( sal_False );
402 aVersionBox.Clear();
403 Init_Impl();
404 aVersionBox.SetUpdateMode( sal_True );
407 delete pDlg;
409 if ( pButton == &aDeleteButton && pEntry )
411 pObjShell->GetMedium()->RemoveVersion_Impl( ((SfxVersionInfo*) pEntry->GetUserData())->aName );
412 pObjShell->SetModified( sal_True );
413 aVersionBox.SetUpdateMode( sal_False );
414 aVersionBox.Clear();
415 Init_Impl();
416 aVersionBox.SetUpdateMode( sal_True );
418 else if ( pButton == &aOpenButton && pEntry )
420 Open_Impl();
422 else if ( pButton == &aViewButton && pEntry )
424 SfxVersionInfo* pInfo = (SfxVersionInfo*) pEntry->GetUserData();
425 SfxViewVersionDialog_Impl* pDlg = new SfxViewVersionDialog_Impl( this, *pInfo, sal_False );
426 pDlg->Execute();
427 delete pDlg;
429 else if ( pEntry && pButton == &aCompareButton )
431 SfxAllItemSet aSet( pObjShell->GetPool() );
432 sal_uIntPtr nPos = aVersionBox.GetModel()->GetRelPos( pEntry );
433 aSet.Put( SfxInt16Item( SID_VERSION, (short)nPos+1 ) );
434 aSet.Put( SfxStringItem( SID_FILE_NAME, pObjShell->GetMedium()->GetName() ) );
436 SfxItemSet* pSet = pObjShell->GetMedium()->GetItemSet();
437 SFX_ITEMSET_ARG( pSet, pFilterItem, SfxStringItem, SID_FILTER_NAME, sal_False );
438 SFX_ITEMSET_ARG( pSet, pFilterOptItem, SfxStringItem, SID_FILE_FILTEROPTIONS, sal_False );
439 if ( pFilterItem )
440 aSet.Put( *pFilterItem );
441 if ( pFilterOptItem )
442 aSet.Put( *pFilterOptItem );
444 pViewFrame->GetDispatcher()->Execute( SID_DOCUMENT_COMPARE, SFX_CALLMODE_ASYNCHRON, aSet );
445 Close();
448 return 0L;
451 SfxViewVersionDialog_Impl::SfxViewVersionDialog_Impl ( Window *pParent, SfxVersionInfo& rInfo, sal_Bool bEdit )
452 : SfxModalDialog( pParent, SfxResId( DLG_COMMENTS ) )
453 , aDateTimeText( this, SfxResId( FT_DATETIME ) )
454 , aSavedByText( this, SfxResId( FT_SAVEDBY ) )
455 , aEdit( this, SfxResId( ME_VERSIONS ) )
456 , aOKButton( this, SfxResId( PB_OK ) )
457 , aCancelButton( this, SfxResId( PB_CANCEL ) )
458 , aCloseButton( this, SfxResId( PB_CLOSE ) )
459 , aHelpButton( this, SfxResId( PB_HELP ) )
460 , pInfo( &rInfo )
462 FreeResource();
464 LocaleDataWrapper aLocaleWrapper( ::comphelper::getProcessServiceFactory(), Application::GetSettings().GetLocale() );
465 aDateTimeText.SetText( aDateTimeText.GetText().Append(ConvertDateTime_Impl( pInfo->aCreationDate, aLocaleWrapper )) );
466 aSavedByText.SetText( aSavedByText.GetText().Append(pInfo->aAuthor) );
467 aEdit.SetText( rInfo.aComment );
469 aCloseButton.SetClickHdl ( LINK( this, SfxViewVersionDialog_Impl, ButtonHdl ) );
470 aOKButton.SetClickHdl ( LINK( this, SfxViewVersionDialog_Impl, ButtonHdl ) );
472 aEdit.GrabFocus();
473 if ( !bEdit )
475 aOKButton.Hide();
476 aCancelButton.Hide();
477 aEdit.SetReadOnly( sal_True );
479 else
481 aDateTimeText.Hide();
482 aCloseButton.Hide();
486 IMPL_LINK( SfxViewVersionDialog_Impl, ButtonHdl, Button*, pButton )
488 if ( pButton == &aCloseButton )
490 EndDialog( RET_CANCEL );
492 else if ( pButton == &aOKButton )
494 pInfo->aComment = aEdit.GetText();
495 EndDialog( RET_OK );
498 return 0L;
501 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */