Date: prev next · Thread: first prev next last
2011 Archives by date, by thread · List index


Hi Markus,

On 08/04/11 01:38, Markus Mohrhard wrote:
Hello,

here the patch for the EasyHack: http://wiki.documentfoundation.org/Development/Easy_Hacks#VBA_support_add_support_for_Worksheets.Copy or Bug: https://bugs.freedesktop.org/show_bug.cgi?id=34763 .

It needs the patch from this afternoon to work correctly.

Patch is under LGPLv3+/MPL.

Thanks for the patch, unfortunately there are a couple of problems with it, I tried some examples and the results weren't as expected e.g.

starting with a workbook with the following sheets 'sheet1', 'sheet2' and 'sheet3'
and trying a macro like:

sub test
    worksheets.copy after:=worksheets(2)
end sub

results in the following sheets in the workbook 'sheet1', 'sheet2', 'sheet1_2', 'sheet2_2', 'sheet1_2_2', 'sheet3' the expected result should be something like 'sheet1', 'sheet2', 'sheet1_2', 'sheet2_2', 'sheet3_2', 'sheet3'

and similarly running the following macro

sub test
    worksheets.copy before:=worksheets(2)
end sub

results in a workbook with the following sheets 'sheet1', 'sheet1_2', 'sheet1_2_2', 'sheet1_2_2_2', 'sheet2', 'sheet3' expected results would be 'sheet1', 'sheet1_2', 'sheet2_2', 'sheet3_2', 'sheet2','sheet3'

I think you are falling victim to the fact that you are modifying the underlying container ( e.g. the sheets container ) whilst iterating over it. Also, although I appreciate the fact you moved some methods into the excelvbahelper.cxx file in order to share code I don't really think those methods belong there. Those methods are really local utility functions and really couldn't be considered to be of general use. Personally I am not such a stickler for such things and normally would take the approach that sharing the code is more important that obeying some lofty design idea. However in this case I see alot of duplication in the Worksheets::Copy and the Worksheet::Copy, to my mind the Worksheets::Copy should use ( or delegate to ) the Worksheet:::Copy ( and/or ) methods of the Worksheet object to achieve the desired result and in this case this to me reinforces the idea we shouldn't unnecessarily make public those helper methods.

So.. I am sorry first that I don't think the patch is suitable to commit right now, also I am sorry that the so called easy hack has like alot of things that seem initially easy thrown some unexpected problems. But please don't despair, I spend some time having a look and thinking about what we could do to reorganize things such that the Worksheets::Copy can reuse the Worksheet object to do the business.

Here's what I propose

First I think for the normal case where you specify a 'Before' or 'After' parameter things should just work out pretty easily e.g. in psuedo code

Worksheets::Copy( before, after )
{
   if ( before.hasValue OR after.hasValue )
   {
      vector< excel::XWorksheet > xSheets;
      // A) grab a local copy of the sheets in the sheet container
      foreach sheet in sheets
         xSheets.push_back( sheet )
      next sheet

// B) prevent problems modifying the sheet container by working with the copy
      foreach sheet in XSheets
         sheet.Copy( before, after )
      next sheet
   }
}

you will probably need to be a bit creative with some twisty logic to ensure the order of the sheets in (A) is correct for when you want to insert before/after

e.g. for workbook with sheets ( 'sheet1', 'sheet2', 'sheet3' ) and if xSheets = { 'sheet1', 'sheet2', 'sheet3 } thenthe first example above 'Worksheets.Copy after:=Worksheets(2)

would end up with 'sheet1', 'sheet2', 'sheet2'_2, 'sheet3_2', 'sheet1_2' whereas

Worksheets.Copy before:=Worksheets(2) will naturally work out as expected e.g. 'sheet1', 'sheet1_2', 'sheet2_2', 'sheet3_2', 'sheet2','sheet3'

dealing with the case where if ( !before.hasValue AND !after.hasValue promises ) to be trickier I think in this case we need to modify the Worksheet object to have a method like
uno::Reference< ov::excel::XWorksheet >
    ScVbaWorksheet::createSheetCopyInNewDoc();
The existing ScVbaWorksheet::Copy would then use that like

ScVbaWorksheet::Copy( before, after )
{
    if ( ( before AND after ) are Empty ) then
createSheetCopyInNewDoc()
    " "
    " "
}

and the ScVbaWorksheets::Copy you will need to do something like

ScVbaWorksheets::Copy( before, after )
{
   if ( ( before AND after ) are Empty ) then
   {
// B) prevent problems modifying the sheet container by working with the copy
      foreach sheet in XSheets
         if ( first sheet )
            before = sheet->createSheetCopyInNewDoc()
         else
            sheet->copy( before, after )
      next sheet
         sheet.Copy( before, after )
      next sheet
   }
}

I did some mini experiments with parts of the above and it seems to work out ( although I have some logic problems mostly due to lack of brains ) but I hope you get what I mean. I hope you are still interested to stick at it and work through this and I would be happy to help you with that. Anyway sorry for such a long mail and look forward to hearing from you

Noel








Context


Privacy Policy | Impressum (Legal Info) | Copyright information: Unless otherwise specified, all text and images on this website are licensed under the Creative Commons Attribution-Share Alike 3.0 License. This does not include the source code of LibreOffice, which is licensed under the Mozilla Public License (MPLv2). "LibreOffice" and "The Document Foundation" are registered trademarks of their corresponding registered owners or are in actual use as trademarks in one or more countries. Their respective logos and icons are also subject to international copyright laws. Use thereof is explained in our trademark policy.