Delphi excel сортировка по столбцу

There are more than one offending parameters. The thing what is wrong with them is they don’t like EmptyParam, although it is what we should be passing for an unused optional parameter.

It is difficult to locate which one(s) because of two reasons. One is that, the way you supply parameters works quite alright when you use late binding. The other one is the misleading error message:

… EVariantTypeCastError with message ‘Could not convert variant of type
(Error) into type (Boolean)’.

An EmptyParam is a variant set to type varError, so first part suggests that we should suspect EmptyParams. Conversion to boolean fails, then what we’ll be looking for is an EmptyParam passed for an optional boolean parameter. Unfortunately there are none, not even anything boolean-like. In fact any one of the ‘DataOption’ enumerations cause the above error message.

Here is a possible systematic approach that might help to find a working solution:

  • Use late binding first, pass as little parameters as required.
  • Fill all remaining parameters with EmptyParam, test, then adapt the call to early binding.
  • From right to left, replace unused optional parameters with actual values until you get a different error, or make it work.

Here is my working sample:

procedure TForm1.Button1Click(Sender: TObject);
var
  oExcel : ExcelApplication;
  RawDataSheet :_Worksheet;
begin
    oExcel := CreateOleObject('Excel.Application') as ExcelApplication;
    oExcel.Visible[LOCALE_USER_DEFAULT] := True;

   // Add a New Workbook, with a single sheet
   oExcel.Workbooks.Add(EmptyParam, LOCALE_USER_DEFAULT);
   // Get the handle to the active Sheet, and insert some dummy data
   RawDataSheet :=  oExcel.ActiveSheet as _Worksheet;
   RawDataSheet.Range['A1', 'F1'].value2 := 'head';
   RawDataSheet.Range['A2', 'F2'].value2 := 8;
   RawDataSheet.Range['A3', 'F3'].value2 := 17;
   RawDataSheet.Range['A4', 'F4'].value2 := 4;
   RawDataSheet.Range['A5', 'A5'].value2 := 10;
     RawDataSheet.Range['B5', 'F5'].Value2 := 11;
   RawDataSheet.Range['A6', 'F6'].value2 := 7;
   RawDataSheet.Range['A7', 'F7'].value2 := 1;
   RawDataSheet.Range['A8', 'F8'].value2 := 2;
   RawDataSheet.Range['A9', 'A9'].value2 := 10;
     RawDataSheet.Range['B9', 'B9'].value2 := 11;
       RawDataSheet.Range['C9', 'F9'].value2 := 9;
   RawDataSheet.Range['A10', 'F10'].value2 := 10;

   RawDataSheet.Sort.SortFields.Clear;

   // Now actually do the sort...
  // SYNTAX at https://msdn.microsoft.com/en-us/library/microsoft.office.tools.excel.namedrange.sort.aspx
   RawDataSheet.UsedRange[LOCALE_USER_DEFAULT].Sort
       (RawDataSheet.Range['A1', 'A10'], xlAscending,
        RawDataSheet.Range['B1', 'B10'], EmptyParam, xlAscending,
        RawDataSheet.Range['C1', 'C10'], xlAscending,
        xlYes, NULL, False, xlSortColumns,
        xlPinYin, xlSortNormal, xlSortNormal, xlSortNormal);
end;

Finally I’m glad that Type parameter did not complain passing an EmptyParam because I don’t understand what it is.

Old answer follows:


I tested your parameters by using the IDispatch/Invoke route, late binding, it generally has a higher probability of getting to work despite loosing some performance and type safety. None of them are wrong, I also tested other keys. Although parameters are not wrong, excel throws an error if early binding is used. Here is one working example:

procedure TForm1.Button1Click(Sender: TObject);
var
  oExcel : ExcelApplication;
  RawDataSheet :_Worksheet;
  V: OleVariant;   // Range
begin
    oExcel := CreateOleObject('Excel.Application') as ExcelApplication;
    oExcel.Visible[LOCALE_USER_DEFAULT] := True;

   // Add a New Workbook, with a single sheet
   oExcel.Workbooks.Add(EmptyParam, LOCALE_USER_DEFAULT);
   // Get the handle to the active Sheet, and insert some dummy data
   RawDataSheet :=  oExcel.ActiveSheet as _Worksheet;
   RawDataSheet.Range['A1', 'F1'].value2 := 'head';
   RawDataSheet.Range['A2', 'F2'].value2 := 8;
   RawDataSheet.Range['A3', 'F3'].value2 := 17;
   RawDataSheet.Range['A4', 'F4'].value2 := 4;
   RawDataSheet.Range['A5', 'A5'].value2 := 10;
     RawDataSheet.Range['B5', 'F5'].Value2 := 11;
   RawDataSheet.Range['A6', 'F6'].value2 := 7;
   RawDataSheet.Range['A7', 'F7'].value2 := 1;
   RawDataSheet.Range['A8', 'F8'].value2 := 2;
   RawDataSheet.Range['A9', 'A9'].value2 := 10;
     RawDataSheet.Range['B9', 'B9'].value2 := 11;
       RawDataSheet.Range['C9', 'F9'].value2 := 9;
   RawDataSheet.Range['A10', 'F10'].value2 := 10;

   RawDataSheet.Sort.SortFields.Clear;
{
   // Now actually do the sort...
  // SYNTAX at https://msdn.microsoft.com/en-us/library/microsoft.office.tools.excel.namedrange.sort.aspx
   RawDataSheet.UsedRange[LOCALE_USER_DEFAULT].Sort (
         RawDataSheet.Range['A1:A10', EmptyParam], xlAscending, // Key1, Order1
         EmptyParam, EmptyParam, xlAscending,  // key2, Type_, Order2
         EmptyParam, xlAscending,  // key3, Order3
         xlYes, EmptyParam, False, xlSortRows, // Header, OrderCustom, MatchCase, Orientation
         xlPinYin, EmptyParam, EmptyParam, EmptyParam); // Sort, Data Option1, Data Option2, Data Option3
}
  V := RawDataSheet.Range['A1', 'F10'];
  V.Sort(RawDataSheet.Range['A1:A10', EmptyParam], xlAscending,
        RawDataSheet.Range['B1', 'B10'], EmptyParam, xlAscending,
        RawDataSheet.Range['C1', 'C10'], xlAscending,
        xlYes, EmptyParam, False, xlSortColumns,
        xlPinYin, EmptyParam, EmptyParam, EmptyParam);
end;

 
TDM
 
(2002-03-18 12:04)
[0]

Привет.

Помогите плиз сортировать из делфи в ексель приложениях. Если можно то киньте отрывок кода?

Заранее благодарен!


 
Кулюкин Олег
 
(2002-03-18 12:25)
[1]

Range.Sort(WorkBook.WorkSheets[1].Columns[5], 2);

Сортирует по пятой колонке п оубыванию.

Range — сотрируемая область

WorkBook.WorkSheets[1].Columns[5] — сортировка по этому столбцу

Последний параметр — тип сортировки (1 — по возрастанию, 2 — по убыванию)

Подробнее см. Help по VBA


 
TDM
 
(2002-03-18 12:41)
[2]

Спасибо, щас проверю


 
TDM
 
(2002-03-18 13:04)
[3]

Не работает !!! :=( Объясняю подробнее как все происходит…

Подключаюсь к листу с данными:

ExcelWorksheet1.ConnectTo(ExcelWorkbook1.Worksheets[1] as ExcelWorksheet);

далее пытаюсь отсортировать данные по первому столбцу:

ExcelWorksheet1.Range[«A2», «A2»].EntireColumn.Sort(«A1», xlAscending);

если оставить так то пишет ошибку что нехватает параметров, а если все остальные параметры сделать EmptyParam то в процессе работы получается ошибка «Invalid variant type conversion»


 
Кулюкин Олег
 
(2002-03-18 14:29)
[4]

1. Я работал с Excel через OLE, а не через ЕExcelWorksheet, так что о компонентах не скажу ничего.

2. ExcelWorksheet1.Range[«A2», «A2»].EntireColumn.Sort(«A1», xlAscending);

«A1» — это ячейка, а не столбец.


 
TDM
 
(2002-03-19 13:37)
[5]

Я так понимаю сдесь нет людей которые помогли бы с этим разобраться?

А куда делись все профиссионалы?

:-(((


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
 unit Unit1;
 
interface
 
uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, Grids, StdCtrls,ComObj;
 
type
  TForm1 = class(TForm)
    StringGrid1: TStringGrid;
    Button1: TButton;
    OpenDialog1: TOpenDialog;
    Edit1: TEdit;
    Label1: TLabel;
    Button2: TButton;
    procedure Button1Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
    procedure StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
      Rect: TRect; State: TGridDrawState);
  private
 
    { Private declarations }
  public
 
    { Public declarations }
  end;
 
var
  Form1: TForm1;
 
implementation
 
{$R *.dfm}
 
//прописываем процедуру очистки таблицы StringGrid
procedure ClearGrid (Grid:TStringGrid);
var
  I: Integer;
begin
 
  for I := 0 to Grid.RowCount - 1 do
    Grid.Rows[I].Clear();    //т.к. у StringGrid нет метода очистки всей таблицы, а у Rows (Cols) есть то чистим построчно (можно по столбцам)
 
end;
 
 
procedure Xls_Open_filter(XLSFile:string; Grid:TStringGrid; criterion:string);
 const
  xlCellTypeLastCell = $0000000B;
var
  ExlApp, Sheet: OLEVariant;
  i, j, r, c:integer;
 
begin
 
     //создаем объект Excel
  ExlApp := CreateOleObject('Excel.Application');
 
  //делаем окно Excel невидимым
  ExlApp.Visible := false;
 
  //открываем файл XLSFile
  ExlApp.Workbooks.Open(XLSFile);
 
  //создаем объект Sheet(страница) и указываем номер листа (1)
  //в книге, с которого будем осуществлять чтение
  Sheet := ExlApp.Workbooks[ExtractFileName(XLSFile)].WorkSheets[1];
 
  //активируем последнюю ячейку на листе
  Sheet.Cells.SpecialCells(xlCellTypeLastCell, EmptyParam).Activate;
 
    // Возвращает номер последней строки
    r := ExlApp.ActiveCell.Row;
 
    // Возвращает номер последнего столбца
    c := ExlApp.ActiveCell.Column;
 
    //устанавливаем кол-во столбцов и строк в StringGrid
   ClearGrid (Grid); //очистка таблицы
    Grid.RowCount:=2; //по умолчанию 2 строки
    Grid.ColCount:=c;
 
     //заполняем шапку таблицы (наименование полей)
    for i:= 1 to c do
          Grid.Cells[i-1,0]:= sheet.cells[1,i];
 
 
    //считываем значение из каждой ячейки и проверяем на совпадение по 5 столбцу (должность)
     for j:= 1 to r do
        //собственно сравниваем наш критерий со значением в Excel
        //функция trim убирает все лишние пробелы в строке т.е. пробелы перед и после текста
        //функция lowercase возвращает строку в нижнем регистре. uppercase - в верхнем регистре
 
         if trim (lowercase(sheet.cells[j,5]))=trim(lowercase(criterion)) then
            begin
            //если значения совпали то заносим его в таблицу grid. Не забываем что в объекте Excel нумерация строк и столбцов с 1, в Grid c 0
               for i:= 1 to c do
                  Grid.Cells[i-1,grid.RowCount-1]:= sheet.cells[j,i];
            grid.RowCount:=grid.RowCount+1; //добавляем пустую строку в grid.
            end;
             
 //закрываем приложение Excel
 ExlApp.Quit;
 
 //очищаем выделенную память
 ExlApp := Unassigned;
 Sheet := Unassigned;
 
end;
 
 
procedure Xls_Open(XLSFile:string; Grid:TStringGrid);
 const
  xlCellTypeLastCell = $0000000B;
var
  ExlApp, Sheet: OLEVariant;
  i, j, r, c:integer;
 
begin
     //создаем объект Excel
  ExlApp := CreateOleObject('Excel.Application');
 
  //делаем окно Excel невидимым
  ExlApp.Visible := false;
 
  //открываем файл XLSFile
  ExlApp.Workbooks.Open(XLSFile);
 
  //создаем объект Sheet(страница) и указываем номер листа (1)
  //в книге, с которого будем осуществлять чтение
  Sheet := ExlApp.Workbooks[ExtractFileName(XLSFile)].WorkSheets[1];
 
  //активируем последнюю ячейку на листе
  Sheet.Cells.SpecialCells(xlCellTypeLastCell, EmptyParam).Activate;
 
    // Возвращает номер последней строки
    r := ExlApp.ActiveCell.Row;
 
    // Возвращает номер последнего столбца
    c := ExlApp.ActiveCell.Column;
 
    //устанавливаем кол-во столбцов и строк в StringGrid
    Grid.RowCount:=r;
    Grid.ColCount:=c;
 
    //считываем значение из каждой ячейки и копируем в нашу таблицу
     for j:= 1 to r do
       for i:= 1 to c do
         Grid.Cells[i-1,j-1]:= sheet.cells[j,i];
        //если необходимо прочитать формулы то
       //Grid.Cells[i-1,j-1]:= sheet.cells[j,i].formula;
 
 //закрываем приложение Excel
 ExlApp.Quit;
 
 //очищаем выделенную память
 ExlApp := Unassigned;
 Sheet := Unassigned;
 
end;
 
procedure TForm1.Button1Click(Sender: TObject);
begin
 
  If OpenDialog1.Execute then Xls_Open (OpenDialog1.FileName, StringGrid1);
end;
 
procedure TForm1.Button2Click(Sender: TObject);
begin
  If OpenDialog1.Execute then Xls_Open_filter (OpenDialog1.FileName, StringGrid1, Edit1.Text);
end;
 
//и для красоты делаем заголовок нашей таблицы с жирным шрифтом
// событие OnDrawCell на вкладке Events
procedure TForm1.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
  Rect: TRect; State: TGridDrawState);
begin
 
     if ARow = 0 then   //если строка 0 то перерисовываем в ней текст
    with StringGrid1.Canvas do
    begin
     //задаем стиль шрифта
      Font.Style := [fsBold];
        
      //перерисовка фиксированной строки т.е. 0-вой
      // Rect.Left+3 и Rect.Top+3 собственно отступ в ячейке
      TextRect(Rect, Rect.Left+3, Rect.Top+3, StringGrid1.Cells[ACol, ARow]);
    end;
end;
 
end.

I was asked to prepare a table for the OP’s flagship database, which shows for each question how many people have answered ‘yes’ and how many ‘no’. Getting the data itself was fairly easy but displaying it was something else again.

Basically, I had an array with 480 rows and seven columns, where I had to sort the array by the fourth column; the spreadsheet has a header row. I thought that it would be easy to output the data to Excel then let Excel do the sorting. As it turns out,  I have never had cause to sort in Excel via automation before now, so first I recorded an Excel macro which would sort. This is the result

    
Range("A1:G481").Sort Key1:= Range("D2"), Order1:= xlAscending, Header:= _
  xlGuess, OrderCustom:= 1, MatchCase:= True, Orientation:= xlTopToBottom, _
  DataOption1:= xlSortNormal

While Excel might be able to understand that, it wasn’t at all clear how I was going to translate that into a form that Delphi could understand. So I started googling, finding several solutions, none of which worked. Eventually I found the solution which I am documenting here.

 
const
 xlAscending = 1;
 xlNo = 0;
 xlTopToBottom = 1;
 xlSyllabary = 1;

 sheet.Range['A1', 'G481'].Sort (sheet.Range['D2'], xlAscending,
                                 EmptyParam, EmptyParam,  // key2
                                 EmptyParam, EmptyParam,  // key3
                                 xlAscending, xlNo, EmptyParam, True,
                                 xlTopToBottom, xlSyllabary);

Let me explain the ‘G481’ term: there are seven columns, and Excel labels them alphabetically. So ‘A1’ refers to the cell at the intersection of the first column and the first row, its neighbour is ‘B1’, etc. So ‘G1’ refers to the cell at the intersection of the seventh column and the first row. As there are 480 rows in the array along with a header row, the final cell is G481.

The first parameter to the ‘sort’ procedure is the column by which the spreadsheet will be sorted; the second parameter presumably states that the sort will be in ascending order. In this case there is no second nor third key, but if there were, they would be the third and fifth parameters. The eighth parameter (xlNo) would appear to relate to the existence of the header. Don’t ask me about the rest (what does syllabary mean? Now I know).

Unfortunately, for the time being,  I am going to have to relate to this code as a magical spell as I don’t really understand what each parameter does. All I know is that it does what is required.

Note to myself: following is the definition of the ‘sort’ procedure from MSDN:

 
Object Sort(
 Object Key1,
 XlSortOrder Order1,
 Object Key2,
 Object Type,
 XlSortOrder Order2,
 Object Key3,
 XlSortOrder Order3,
 XlYesNoGuess Header,
 Object OrderCustom,
 Object MatchCase,
 XlSortOrientation Orientation,
 XlSortMethod SortMethod,
 XlSortDataOption DataOption1,
 XlSortDataOption DataOption2,
 XlSortDataOption DataOption3
)

Содержание

  1. Невозможно заставить Delphi Sort с Excel работать
  2. 2 ответа
  3. Delphi excel сортировка по столбцу
  4. Unable to get Delphi Sort with Excel to Work
  5. 2 Answers 2
  6. Delphi excel сортировка по столбцу

Невозможно заставить Delphi Sort с Excel работать

Я пишу программу на Delphi 10 / Seattle для управления Excel 2013. Мне нужно выполнить сортировку по столбцу. У столбца есть заголовки. Пока мой код компилируется, фактическая команда SORT выдает ошибку «Не удалось преобразовать вариант типа (Ошибка) в тип (логический)». Короче говоря, у меня неверный параметр, но я не могу определить КАКОЙ параметр. Я просмотрел синтаксис MS (URL-адрес указан ниже), но не нашел ничего неправильного. Вот рабочий образец, который показывает проблему. Я ДЕЙСТВИТЕЛЬНО создал свою собственную библиотеку типов, которая находится в предложении USES.

2 ответа

Есть несколько параметров, вызывающих нарушение. Что с ними не так, им не нравится EmptyParam , хотя это то, что мы должны передать в качестве неиспользуемого необязательного параметра.

Трудно определить, какой из них, по двум причинам. Во-первых, то, как вы задаете параметры, работает нормально при использовании позднего связывания. Другой — вводящее в заблуждение сообщение об ошибке:

. EVariantTypeCastError с сообщением «Не удалось преобразовать вариант типа (ошибка) в тип (логический)».

EmptyParam — это вариант, установленный для типа varError , поэтому первая часть предполагает, что мы должны подозревать EmptyParam s. Преобразование в логическое значение не выполняется, тогда мы будем искать EmptyParam , переданное в качестве необязательного логического параметра. К сожалению, нет none, даже ничего подобного логическому. Фактически любое одно из перечислений DataOption вызывает указанное выше сообщение об ошибке.

Вот возможный систематический подход, который может помочь найти рабочее решение:

  • Сначала используйте позднее связывание, передавая как можно меньше параметров.
  • Заполните все оставшиеся параметры EmptyParam , проверьте, затем адаптируйте вызов к раннему связыванию.
  • Справа налево заменяйте неиспользуемые необязательные параметры фактическими значениями, пока не получите другую ошибку или не заставите ее работать.

Вот мой рабочий образец:

Наконец, я рад, что параметр Type не пожаловался на передачу EmptyParam , потому что я не понимаю, что это такое.

Старый ответ следует:

Я проверил ваши параметры с помощью маршрута IDispatch / Invoke, позднее связывание, как правило, у него более высокая вероятность приступить к работе, несмотря на потерю некоторой производительности и безопасности типов. Ни один из них не ошибается, я тестировал и другие ключи. Хотя параметры не являются неправильными, Excel выдает ошибку, если используется раннее связывание. Вот один рабочий пример:

Думаю, у вас было несоответствие требуемым параметрам. Ты должен попытаться

Удалите все непонятные параметры и замените их на Emptyparam, даже «true» или «false» иногда могут быть неясными, иногда мне приходилось использовать «wordbool (1)» или «msotrue» в коде Delphi вместо true

Источник

Delphi excel сортировка по столбцу

. Но да будет слово ваше: да, да; нет, нет; а что сверх этого, то от лукавого. (Мф.,5-37)

но показывает, как параметрами Sort, в частности, являются вариантные типы — через них заданы колонки для сортировки.
Так что для того, что бы докончить ваш код осталось совсем чуть-чуть.

Мил человек, меня поражает Ваше искусство уходить от прямого ответа: либо Вы его не знаете, либо просто насмехаетесь, — что несколько даже обидно. Именно Вашего «совсем чуть-чуть» мне и не перейти. Мне не надо показывать, что

параметрами Sort, в частности, являются вариантные типы — через них заданы колонки для сортировки

— я не слепой и в списке параметров разбираюсь.
Я просил — и все еще прошу! — о вполне конкретной помощи (читай: услуге!) в написании конкретной строки программного кода. Вы же талантливо (ловко?) предлагаете мне теоретические общие посылки.

Либо Вы беретесь мне помочь, — тогда помогайте. Либо Вы не беретесь — тогда не будите во мне надежду. Я, как это ни обидно, откажусь от этого пути, — варианты всегда есть и много их. А ждать помощи — и получать что-либо наподобие Ваших. намеков — лучше ничего не получать, честное слово!

С глубоким к Вам уважением, Дельфиненок

У меня орёт в рантайме
EVariantCastError «Could not convert of type (Error) into type (Boolean)»

Попробуй частично использовать позднее связывание.
Такая байда у меня работает . (D7, Excel XP/2003)

Спасибо, уважаемый Wild User!

Ниже с чуйством удовлетворения привожу работающую сортировку (Sort).

Имеется лист Excel с границами («А2», «E100») — первая строка, как обычно — шапка. Ключи сортировки: первый (Key1) — «Е2», второй — «А2» и третий — «В2».
Тогда вызов сортировки записывается так:

И это — раннее связывание, что и требовалось.
Можно и через позднее, через OleVariant, но мне не нравится, немного дебильная, на мой вкус, конструкция.

У меня орёт в рантайме
EVariantCastError «Could not convert of type (Error) into type (Boolean)»

Сие проистекает из списка параметров. Большинство — OleVariant, — для них EmptyParam, часть TOleNum — здесь я ставил нули, где не доставало ума TOleNum — это LongWord, т.е. по жизни — целые (?). Если параметр TOleNum попал на место OleVariant — идет попытка конверсии — отсюда весь базар. ИМХО В твоем случае не на месте False — с попыткой привести его к типу Error. Почему Error? Ну, почему-то отладчик при останове сигналит по поводу значения EmptyParam — Error(-23456789) — что-то вроде этого. Не помню числа.

Самое смешное — это желанный параметр Type_ — он оказалса из группы констант XlSortType — никогда бы не додумался. — все же доков никаких. ну или почти никаких. Так, намеки одни!

Заодно (до кучи!) приведу правильный вызов поиска (Find) по листу Excel. В данном случае поиск идет по столбцу с фамилиями в столбце «А»:

Кстати, обрати внимание на экзотику: Range[‘E2’,EmptyParam]. Сильная штука этот самый EmptyParam, посильнее «Фауста» Гете

Рассказал бы я по этому поводу о двух мухах на оконном стекле. Но неззя!
А можно поблагодарить тебя за соучастие и за помощь. Мне было интересно с тобой говорить, чесслово! Хоть и не всегда приятно.

Источник

Unable to get Delphi Sort with Excel to Work

I am writing a program in Delphi 10/Seattle to control Excel 2013. I need to do a sort based on a column. The column has headers. While my code compiles, the actual SORT command gives the error ‘Could not convert variant of type (Error) into type (Boolean).’ In short, I have a parameter wrong, but I can’t determine WHICH parameter. I have gone through the MS syntax (URL listed below), but can’t find anything wrong. Here is a working sample which shows the problem. I DID generate my own type library, which is in the USES clause.

2 Answers 2

There are more than one offending parameters. The thing what is wrong with them is they don’t like EmptyParam , although it is what we should be passing for an unused optional parameter.

It is difficult to locate which one(s) because of two reasons. One is that, the way you supply parameters works quite alright when you use late binding. The other one is the misleading error message:

. EVariantTypeCastError with message ‘Could not convert variant of type (Error) into type (Boolean)’.

An EmptyParam is a variant set to type varError , so first part suggests that we should suspect EmptyParam s. Conversion to boolean fails, then what we’ll be looking for is an EmptyParam passed for an optional boolean parameter. Unfortunately there are none, not even anything boolean-like. In fact any one of the ‘DataOption’ enumerations cause the above error message.

Here is a possible systematic approach that might help to find a working solution:

  • Use late binding first, pass as little parameters as required.
  • Fill all remaining parameters with EmptyParam , test, then adapt the call to early binding.
  • From right to left, replace unused optional parameters with actual values until you get a different error, or make it work.

Here is my working sample:

Finally I’m glad that Type parameter did not complain passing an EmptyParam because I don’t understand what it is.

Old answer follows:

I tested your parameters by using the IDispatch/Invoke route, late binding, it generally has a higher probability of getting to work despite loosing some performance and type safety. None of them are wrong, I also tested other keys. Although parameters are not wrong, excel throws an error if early binding is used. Here is one working example:

Источник

Delphi excel сортировка по столбцу

Шустрый

Профиль
Группа: Участник
Сообщений: 53
Регистрация: 7.12.2006

Репутация: нет
Всего: нет

demoded
Дата 28.3.2007, 11:03 (ссылка) | (нет голосов) Загрузка .
Код
WorkSheet3.Range[‘A2′,’Z9’].Sort(WorkSheet3.Range[‘A2′,’A2’],xlAscending, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, xlGuess, 1, False, xlTopToBottom, EmptyParam);

WorkSheet3.Range[‘A2′,’Z9’].Sort(WorkSheet3.Range[‘A2′,’A2’],xlAscending, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, xlGuess, 1, False, xlTopToBottom, 0);

WorkSheet3.Range[‘A2′,’Z9’].Sort(WorkSheet3.Cells.Item[2,1] ,xlAscending, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, xlGuess, 1, False, xlTopToBottom, EmptyParam);

WorkSheet3.Range[‘A2′,’Z9’].Sort(1 ,xlAscending, EmptyParam, EmptyParam, EmptyParam, EmptyParam, EmptyParam, xlGuess, 1, False, xlTopToBottom, 0);

Сдается мне ему ненравится как указан столбец по которому сортировать, так как больше то ничего такого не задается

еще что заметил во всех примерах пишут запросто Sheet.Range[‘A1’] и все у меня обязательно требует в Range 2 параметра. обычно я указывал [A2,A2] и это работало, а тут грабли какие-то.

Шустрый

Профиль
Группа: Участник
Сообщений: 53
Регистрация: 7.12.2006

Репутация: нет
Всего: нет

следующий код вызывает ошибку «Неверная Ссылка»

demoded
Дата 29.3.2007, 11:18 (ссылка) | (нет голосов) Загрузка .
Код
WorkSheet3.Range[‘A2′,’Z9’].Sort(WorkSheet3.Range[‘A2’,EmptyParam],xlAscending, WorkSheet3.Range[‘B2’,EmptyParam], xlSortValues, xlAscending, WorkSheet3.Range[‘C2’,EmptyParam], xlAscending, xlGuess, 1, False, xlTopToBottom, xlValues);

но хочется всетаки отсортировать.

Шустрый

Профиль
Группа: Участник
Сообщений: 53
Регистрация: 7.12.2006

Репутация: нет
Всего: нет

demoded
Дата 29.3.2007, 13:06 (ссылка) | (нет голосов) Загрузка .
Код
Range : OleVariant;
Range:=WorkSheet3.Range[‘A2′,’Z74’];
Range.Sort(WorkSheet3.Range[‘A2’,EmptyParam]);

ни в одном FAQ я подобного невидел, предлагаю занести это во всевозможные инстанциии ибо 2 дня у меня сожрало.

Шустрый

Профиль
Группа: Участник
Сообщений: 55
Регистрация: 20.2.2007

Репутация: нет
Всего: нет

CTapMex
Дата 1.10.2007, 14:02 (ссылка) | (нет голосов) Загрузка .
Veroonya
Дата 24.7.2009, 05:27 (ссылка) | (нет голосов) Загрузка .

Шустрый

Профиль
Группа: Участник
Сообщений: 69
Регистрация: 10.10.2008
Где: Россия, Омск

Репутация: нет
Всего: 1

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

  • Литературу по Delphi обсуждаем здесь
  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Вопросы по реализации алгоритмов рассматриваются здесь
  • 90% ответов на свои вопросы можно найти в DRKB (Delphi Russian Knowledge Base) — крупнейшем в рунете сборнике материалов по Delphi
  • Вопросы по SQL и вопросы по базам данных, не связанные с Delphi, задавать здесь

Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, Rrader, Girder.

Правила форума «Delphi: ActiveX/СОМ/CORBA»
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Delphi: ActiveX/СОМ/CORBA | Следующая тема »

[ Время генерации скрипта: 0.1032 ] [ Использовано запросов: 21 ] [ GZIP включён ]

Источник

Adblock
detector

Like this post? Please share to your friends:
  • Delphi excel содержимое ячейки
  • Delphi excel снять выделение
  • Delphi excel размеры ячейки
  • Delphi excel размер ячейки
  • Delphi excel размер шрифта