كيف يمكنني إنشاء أو قراءة جداول بيانات OpenOffice من Perl؟

StackOverflow https://stackoverflow.com/questions/278090

سؤال

ما هي الطريقة الجيدة لإنشاء وقراءة جدول بيانات OpenOffice في Perl؟

هل كانت مفيدة؟

المحلول

أعتقد أن تنسيق المستند الأصلي Open Open Office يعتمد على مواصفات OpenDocument ، وهو عبارة عن تنسيق XML مضغوط مضغوط. هذا صحيح ، ربما يمكنك معالجته باستخدام أدوات معالجة Perl XML المفضلة لديك.

بدلاً من ذلك ، هناك Open Office Opendocument Connector Suite من الوحدات النمطية على CPAN الذي يوفر واجهة برمجة تطبيقات عالية المستوى لمواصفات OpenDocument.

على حد علمي ، يجب أن تسمح أساليب الجدول في هذه الوحدات بالبيانات القراءة والكتابة في مستندات حساب OO.

نصائح أخرى

إستعملت OpenOffice :: Oocbuilder لإنشاء طاولات كبيرة مشفرة بالألوان. لقد أحببت هذا جدا. للحصول على مهام أبسط ، غالبًا ما أستخدم تنسيق CSV العادي الذي يتم فتحه بسهولة بواسطة أي برنامج جدول بيانات

ومع ذلك ، قد تختار أشياء Excel للتوافق مع الآخرين.

يدعم OpenOffice عددًا من التنسيقات ، إذا كنت تبحث عن شيء يمكنه قراءة/كتابة جداول بيانات متوافقة مع Excel جدول البيانات :: parseexcel للقراءة ، و جدول البيانات :: WriteExcel للكتابة. لقد استخدمتهما على حد سواء ، فهي ناضجة للغاية وتعمل بشكل جيد.

هذا مع الإصدار 2.4 ، لأن أحدث إصدار غير مستقر. إنه يعمل مع الأحدث على الرغم من في بعض الأحيان. سيتيح ذلك في الوقت الفعلي ميزات DDE في CALC بدلاً من معالجة الملفات. هذا يستخدم Cygwin Perl على XP ولكن يجب أن يعمل مع الآخرين. أريد فقط أن أقول أن API Excel VBA Programming هو أفضل 10 مرات وأقل مربكًا 10 مرات. هذا سيء جدا.

الشفرة

use Win32::OLE;

Win32::OLE->Option(Warn => 3); # Turn on warnings for easier debugging

#Win32::OLE->GetActiveObject
# Get the currently running process or create a new one
$objServiceManager = Win32::OLE->GetActiveObject("com.sun.star.ServiceManager") || Win32::OLE->new("com.sun.star.ServiceManager") || die "CreateObject: $!"; 

$Stardesktop = $objServiceManager->createInstance("com.sun.star.frame.Desktop");

# $Stardesktop->terminate();exit; # will kill ALL OpenOffice docs!!!
# Doc = StarDesktop.loadComponentFromURL(sURL, "_default", 0, aMediaDesc)

$propValue[0] = $objServiceManager->Bridge_GetStruct("com.sun.star.beans.PropertyValue");
$propValue[0]->{Name} = "Hidden"; # This does not work!
$propValue[0]->{Value} = 1;

#Open the file and update its links if you have DDE links in your file
$propValue[1] = $objServiceManager->Bridge_GetStruct("com.sun.star.beans.PropertyValue");
$propValue[1]->{Name} = "UpdateDocMode";
$propValue[1]->{Value} = 3; # com.sun.star.document.UpdateDocMode.FULL_UPDATE

$calc = $Stardesktop->loadComponentfromUrl("file:///C:/Documents and Settings/Chloe/Desktop/MyFile.ods", "MyCalc", 0, \@propValue );
# load a new blank spreadsheet
$calc = $Stardesktop->loadComponentFromURL( "private:factory/scalc", "_blank", 0, [] );

# How to hide, as loading the document hidden does not work.
$calc->getCurrentController->getFrame->getContainerWindow()->setVisible(0);

$oSheet = $calc->getSheets->getByIndex(0);

# how to execute an UNO command, such as menu items
# http://wiki.services.openoffice.org/wiki/Framework/Article/OpenOffice.org_2.x_Commands
$frame = $calc->getCurrentController->getFrame;
$dispatchHelper = $objServiceManager->createInstance("com.sun.star.frame.DispatchHelper");
$dispatchHelper->executeDispatch(
    $frame, 
    ".uno:CalculateHard",
    #".uno:UpdateAll", 
    #".uno:UpdateAllLinks", 
    #".uno:DataAreaRefresh",
    "_self",
    0,
    []
);


$row = 5;
$cellValue = $oSheet->getCellByPosition(0, $row)->getString(); # get a cell value

# sort in decending order
$range = $oSheet->getCellRangeByName("A1:P$row");
$fields[0] = $objServiceManager->Bridge_GetStruct("com.sun.star.table.TableSortField");
$fields[0]->{Field} = 7; # column number
$fields[0]->{IsAscending} = 0;
$unoWrap = $objServiceManager->Bridge_GetValueObject;
$unoWrap->Set ("[]com.sun.star.table.TableSortField", \@fields);
$sortDx = $range->createSortDescriptor();
$sortDx->[0]->{Name} = "ContainsHeader";
$sortDx->[0]->{Value} = 1;
$sortDx->[3]->{Name} = "SortFields";
$sortDx->[3]->{Value} = $unoWrap;
#$sortDx->[3]->{Value} = \@fields; # You would think this would work? It doesn't.
$range->sort($sortDx);


# create a new sheet to paste to
$calc->getSheets->insertNewByName("NewSheet", 1 );
$sheet2 = $calc->getSheets->getByIndex(1);
$calc->CurrentController->Select($sheet2);

# copy row
$pasteHere = $sheet2->getCellByPosition(0, 0)->CellAddress;
$copyRange = $oSheet->getCellRangeByName("A1:Q1")->RangeAddress;
$oSheet->copyRange($pasteHere, $copyRange);

$cellValue = $sheet2->getCellByPosition(16, $row)->getValue()); # get cell value as integer
$date = $sheet2->getCellByPosition(5, $row)->getString(); # must get dates as strings

$calc->getCurrentController->getFrame->getContainerWindow()->setVisible(1); # set visible
$calc->close(0); # close program window
#print Win32::OLE->LastError, "\n";

/الشفرة

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top