Доброй минуты, уважаемые знатоки всей этой "нелегкой"
с OleObject в Delphi..
Была задача сделать программу-конвертер, для т.с. поточной обработки текстовых файлов, и вывода с разбиением на колонки (если выбрано) в итоговые *.xls файлы по заранее заданным путям. С задачей, как мне казалось, я успешно справился.. Но не тут то было.. Заказчик стал жаловаться на ошибку в самом начале запущенного процесса — "
Неверный индекс".. На которую у меня (
Windows10x64, Excel 2016) при разностороннем тестировании и намека не было.
Ок, вроде бы нашел решение, почитал на форуме, что такое часто случается, если именно в инструкции
, где к имени книги обращаются по имени, была рекомендация заменить на индекс.. Сделано. После этого у заказчика нарисовался новый крэш — "
OLEObjectError: Вызов был отклонен". Тоже погуглил, и тоже как будто нашел решение. Советовали вычитать из реестра версию "Excel.Application", поправил, получилось что-то вроде:
Код:
xlapp := CreateOleObject('Excel.Application.16');
В аргументе считанное значение. То есть у меня все отлично работало и без этих бесконечных правок. Проверял и на батиной машине с древнючим Office и win10x32, — тоже все тип-топ. Подозрения, что заказким мутит отпали, т.к. он выкладывал мне скрины с перечисленными ошибками.
Ниже выложил экзешник, если у Вас стоит какой-либо Excel на машине, и найдется 2-3 минуты свободного времени (нужно будет нажать одну кнопку, (средняя в верхнем ряду), — пожалуйста проверьте какой у Вас "полет". Все настройки уже заданы, и нужно только, чтобы в папке на раб.столе (источник) был хоть один *.TXT файл.
Робко надеюсь на Ваше внимание!
Ниже код инициализации обьекта Excel.Application, который в моей пр-ме выполняется один лишь раз при 1ом запуске задачи:
Код:
ver:= ExcelVer; // получаем версию Excel из реестра, — у меня это строка "Excel.Application.16"
xlapp := CreateOleObject(ver); // xlapp — глобальная переменная
xlapp.Application.EnableEvents := false;
xlapp.Visible := false;
xlapp.displayalerts := false;
xlapp.workbooks.add; // в прошлой версии после add здесь был аргумент (-4167), убрал его в соответствии с рекомендациями о устранении ошибки "Неверный индекс"
После нажатия кнопки "Запуск Enter", в цикле по всем найденным файлам в источнике , выполняется вот эта функция (откомментировал все, что только смог:
Код:
function Xls_Save(ASheetName, AFileName: string; var err_mes:string): Boolean;
const
xlWBATWorksheet = -4167;
var
Row, Col: Integer;
GridPrevFile: string;
Sheet: OLEVariant;
i, j, r, c: Integer;
er: string;
begin
Result := False;
// grid — это глоб. строковый массив (array of array)
r:=length(Grid); // получаем общую длину
c:=length(Grid[0]); // получаем длину 1ого элемента подмассива grid
{все это требуется, чтобы ниже можно было очистить диапазон ранее заполненный на предыдущем витке цикла, так как XLApp — единственный глоб.обьект}
if r>max_r then max_r:= r; if c>max_c then max_c:= c;
try
try
{очистка обознач.выше}
try XLApp.Range['A1:A'+inttostr(max_r)].ClearContents; except end;
try XLApp.Range['A:'+for_(max_c)].ClearContents; except end;
Sheet := XLApp.Workbooks[1].WorkSheets[1];
Sheet.Name := ASheetName;
{Заполнение ячеек}
for j:= 1 to r do
for i:= 1 to c do
begin
application.ProcessMessages;
sheet.cells[j,i]:=grid[j-1][i-1];
end;
{тут оставил на всякий случай двойной вариант сохр., хотя у меня работает и тот и другой}
try
{если убрать "56" - размер файла станет меньше, но Excel может ругаться при открытии}
XLApp.Workbooks[1].SaveAs(AFileName,56);
result := True;
except
XLApp.Workbooks[1].SaveAs(AFileName);
result := True;
end;
finally
{освобождение лок.переменной sheet}
if not VarIsEmpty(XLApp) then
begin
Sheet := Unassigned;
end;
end;
except
on E: Exception do
if first then
begin
{нужно было пройти цикл до конца, в любом случае, поэтому сделал флажок First}
first:= false;
er:= E.ClassName+': '+E.Message;
err_mes:= er;
{application.MessageBox(pchar(er),'', MB_ICONINFORMATION+MB_OK)}
end;
end;
end;
Несколько дней уже парюсь, никак не выходит долбаный аленький цветочек (((, помогите, ребят..
Архив с экзешником приложил ниже