我需要将一些Applescript代码移动到Scripting Bridge,以便在不需要Applescript-ObjC的情况下利用一些Cocoa挂钩。
使用带有Applescript的Excel 2008,很容易获得一个范围的值:
set myList to GetValuesFromColumnRange("A", 1, 100)
on GetValuesFromColumnRange(ColumnLetter, FirstRow, LastRow) -- (string, integer, integer) as list
set theList to {}
tell application "Microsoft Excel"
set theRange to ColumnLetter & FirstRow & ":" & ColumnLetter & LastRow
set AppleScript's text item delimiters to {return}
set theList to (get value of range theRange as list)
set AppleScript's text item delimiters to {""}
end tell
set theList to ConvertItemizedListToValueList(theList) of me -- Note this dependency due to how MSE2008 returns the data
return theList
end GetValuesFromColumnRange但是在Scripting Bridge中,我在获取基于范围的工作表的单元格时遇到了问题。以下是我到目前为止所掌握的。
Excel2008Application *excelApp = [SBApplication applicationWithBundleIdentifier:@"com.microsoft.Excel"];
Excel2008Workbook *workbook = excelApp.activeWorkbook;
SBElementArray *sheets = [workbook sheets];
Excel2008Sheet *targetSheet;
int thisSheet = 0;
int lastSheet = [sheets count];
for (thisSheet = 0; thisSheet < lastSheet; thisSheet++) {
Excel2008Sheet *currentSheet = [sheets objectAtIndex:thisSheet];
NSString *currentSheetName = currentSheet.name;
if ([currentSheetName isEqualToString:@"Metadata"]) {
targetSheet = currentSheet;
[targetSheet retain];
}
}
Excel2008Range *range = [[[excelApp classForScriptingClass:@"range"] alloc] initWithProperties:[NSDictionary dictionaryWithObjectsAndKeys:@"A1:A10", @"formulaR1c1", nil]];
[[targetSheet ranges] addObject:range];
range = [[targetSheet ranges] lastObject]; // not null; stated class in log: MicrosoftExcelRange
Excel2008Sheet *valueSheet = range.worksheetObject; // supposed to be new worksheet based upon values within the range; not null; stated class in log: MicrosoftExcelSheet
[valueSheet retain];
SBElementArray *valueCells = [valueSheet cells]; // not null, but count is 0
[valueCells retain];当我实际从valueSheet获取单元格时,最后一行出现了问题,因为返回的SBElementArray不是null,但它也不包含任何对象。同样的道理也适用于在targetSheet中获取单元。
从我所有的搜索来看,几乎不存在这样做的文档,我已经尽我所能地做了这件事。
发布于 2010-12-15 01:19:12
解决了。
NSString *rangeName = @"A1:A10";
Excel2008Range *range = [[[excelApp classForScriptingClass:@"range"] alloc] initWithProperties:[NSDictionary dictionaryWithObjectsAndKeys:rangeName, @"name", nil]];
[[targetSheet ranges] addObject:range];
Excel2008Range *currentRange;
if ([[[targetSheet ranges] objectWithName:rangeName] exists]) {
currentRange = [[targetSheet ranges] objectWithName:rangeName];
}
NSLog(@"[currentRange.value get] = %@", [currentRange.value get]);
// result: ((key),(1),(2),(3),(4),(5),(6),(7),(8),(9)) = NSArray诀窍似乎是将范围字符串设置到Excel2008Range的name属性中。在处理这个问题时,我发现了一个陷阱,那就是永远不会填充范围的formulaR1c1 -就像在[NSDictionary dictionaryWithObjectsAndKeys:rangeName, @"formulaR1c1", nil]-because中一样,它将使用范围字符串的值填充范围。
事后看来,当在两个Applescript中读取完全相同的命令的语法时,这实际上是有意义的。
tell application "Microsoft Excel"
set theValues to get value of range "A1:A10"
end tell...and objc-appscript...
NSString *rangeString = @"A1:A10"
MEApplication *microsoftExcel = [MEApplication applicationWithName: @"Microsoft Excel"];
MEReference *cells = [[[microsoftExcel ranges] byName:rangeString] value];
NSArray *cellValues = [cells getItem];在这两种情况下,范围的值都是通过获取带有其名称的值的范围来获得的。但是使用Scripting Bridge,我可以说,名称必须在创建range对象时显式地应用。
我确信有更好的方法来实现这一点(通常是有的),但至少这是可行的。
https://stackoverflow.com/questions/4379001
复制相似问题