Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Базы";
Текущий архив: 2005.11.20;
Скачать: [xml.tar.bz2];

Вниз

Просмотр и восстановление "удаленных" записей в DBF таблицах   Найти похожие ветки 

 
АМБ   (2005-07-18 11:15) [0]

Как организовать просмотр помеченных на удаление записей в DBF таблице? Т.е. сначала, записи обрабатываются tblDBF1.Delete; и становятся невидимы в DBGrid-е. Как сделать их видимыми, да еще и другим цветом, или как-то еще их выделить, а затем, выбрав какую-нибудь запись - восстановить ее, т.е. снять пометку на удаление.


 
ЮЮ ©   (2005-07-18 11:24) [1]

А что будешь делать, когда на сервер перейдешь?
Умерла так умерла.
Если кто-то удалил нужные данные, пусть садится в выходные и вбивает заново :)


 
Val ©   (2005-07-18 11:32) [2]

>АМБ   (18.07.05 11:15)
компоненты доступа? если - БДЕ, то тут недавно был пример Подгорецкого с исп. БДЕ-API.


 
Anatoly Podgoretsky ©   (2005-07-18 11:32) [3]

АМБ   (18.07.05 11:15)  
dbiSetProp


 
АМБ   (2005-07-18 11:50) [4]


> Anatoly Podgoretsky

А нельзя ли немного поподробнее.  А если можно, то и с примером.
А то, что-то не понятно...:-(


 
Anatoly Podgoretsky ©   (2005-07-18 11:52) [5]

Можно и подробнее и с примером, который приведен в справке, но это будет верхом невежливости по отношению к другим, копировать примеры из справки.
Так что попробуй немного и сам поработать.


 
АМБ   (2005-07-18 12:09) [6]


> Anatoly Podgoretsky

Спасибо за подсказку. А то я не понял где искать. По инерции думал, что это неизвестное мне свойство TTable или DBGrid-a
Еще раз спасибо.


 
evvcom ©   (2005-07-18 12:13) [7]

Тогда уж лучше добавить в таблицу поле с именем Deleted. По нему и запросы можно будет строить и физического удаления не будет. Всегда можно выяснить существовали ли такие данные, и кто "удалил". Имхо.


 
Johnmen ©   (2005-07-18 12:17) [8]

dbiSetProp + F1


 
АМБ   (2005-07-18 15:28) [9]

Всем спасибо! Все работае! Удаленные записи и показываются и прячуться. Единственная пока проблема: когда удаленные записи показываются, то их не отличишь от обычных. Подскажите, можно ли сделать как-нибудь такое отличие в рамках использования метода dbiSetPropа?


 
Val ©   (2005-07-18 15:33) [10]

обязательно в рамках данного метода? :)
определяем состояние соотв. BDE-API и красим в соотв. обработчике сетки.


 
Anatoly Podgoretsky ©   (2005-07-18 15:34) [11]

А DbiGetRecord на что тебе дан?


 
АМБ   (2005-07-18 16:57) [12]

К своему стыду, я так и не понял...:-((((((


 
Anatoly Podgoretsky ©   (2005-07-18 16:59) [13]

Поиск вверху форума видишь, попробуй будешь приятно удивлен.


 
АМБ   (2005-07-19 11:52) [14]


> Anatoly Podgoretsky

Еще раз спасибо за подсказку. Но все равно мало, что понял.:о(((
Ваш пример:
function DELETED(Table:TTable);
var
Prop : RECProps;
begin
dbiGetRecord(Table.Handle, dbiNoLock, nil, @Prop);
Result := Prop.bDeleteFlag;
END;

При компиляции выдается ошибка: Function needs result type.
Поставил тип: function DELETED(Table:TTable): Boolean;
Ругаться перестал. Но что с этим делать - не пойму.

В BDE32.HLP написано:
DbiGetRecord retrieves the current record, if any, in the table associated with hCursor. Т.е. вроде бы выдает запись с необходимым для нас условием, в ващей функции - что удалена.
Но как это использовать? А если запись не одна?
Пробовал по разному. Последнее что пробовал, это написал в обработчике dbgDBFDrawColumnCell, следующее:
if DELETED(tblDBF) then
begin
 dbgDBF.Canvas.Brush.Color := $00ff00;
 dbgDBF.Canvas.Font.Color := $0000ff;
 dbgDBF.Canvas.FillRect(Rect);
 dbgDBF.Canvas.TextOut(Rect.Left,Rect.Top,Column.Field.Text);    
end;
Раскрашивается весь DBGrid, да еще как-то тоже не понятно. Но удаленные записи все-равно не отличаются.
Если можно подскажите. Что не так? И как надо?


 
Anatoly Podgoretsky ©   (2005-07-19 12:27) [15]

Зачем же тогда спрашивал как определелить удаленая или нет?


 
АМБ   (2005-07-19 13:29) [16]


> Anatoly Podgoretsky

Мне нужно включать (и выключать) режим просмотра удаленных записей. Если нужно восстанавливать их, а какие уже совсем не нужны тех совсем удалять, физически.
Сейчас у меня уже получилось выводить удаленные записи в просмотр и "прятать" их снова. Если надо, удалять их физически (через DbiPackTable). Но никак не пойму, как сделать, чтобы при просмотре удаленных записей они выделялись другим цветом.
К своему сожалению, я еще не работал с функциями BDE.
Английский тоже перевожу...  со словарем :о(.
Поэтому рад всякой помощи...


 
Val ©   (2005-07-19 14:14) [17]

>[16] АМБ   (19.07.05 13:29)
Как красить сетку в зависимости от разл.условий отлично написано в статьях на "Королевстве Делфи". Сделайте просто условие с использованием вашей функции (кстати, не очень уверен, что вы верно трактуете результат props...) - разница небольшая.


 
АМБ   (2005-07-19 14:34) [18]


> Val

Все верно. Именно с этими статьми я и познакомился. И также верно, что я не так "трактую" результат Props... Но как надо?
Это я и прошу подсказать.


 
Val ©   (2005-07-19 14:43) [19]

>[18] АМБ   (19.07.05 14:34)
Извините, но я не хочу лезть за вас в хелп и смотреть структуру типа этого самого Props, и в зависимости от нее проводить анализ результата.


 
АМБ   (2005-07-19 15:03) [20]

Даже не знаю, что и сказать... Я конечно, извиняю. Но в хелп я и лазил и смотрел, анализировал и пробовал, но не получилось. Потому и обратился за помощью. Может кто знает? Из тех, кто практически уже проходил этот вопрос.


 
Anatoly Podgoretsky ©   (2005-07-19 19:37) [21]

Результат функции BOOLEAN


 
АМБ   (2005-07-20 14:50) [22]

Уважаемый,
> Anatoly Podgoretsky

Подскажите пожалуйста, Ваша функция она показывает свойство bDeleteFlag текущей записи? Т.е. можно перебирать записи и  у каждой проверять это свойство и реагировать не это. Или Ваша функция показывает что в таблице есть записи, помеченные на удаление. Но мои пробы показали, что Ваша функция показывает True, даже после физического удаления записей. Так как с ней можно работать?
Скажите пожалуйста.


 
Anatoly Podgoretsky ©   (2005-07-20 16:26) [23]

Перебирать не надо, это делает dbgDBFDrawColumnCell, а результат используй в IF


 
АМБ   (2005-07-21 10:26) [24]

Уважаемый, Anatoly Podgoretsky (или кто-нибудь). Ну подскажите, пожалуйста. Почему не работает, как надо, следующий код:

procedure TfrmMain.dbgDBFDrawColumnCell(Sender: TObject; const Rect: TRect;
 DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
 if DELETED(tblDBF) then
   begin
     TDBGrid(Sender).Canvas.Brush.Color := $00ff00;
     TDBGrid(Sender).Canvas.Font.Color := $0000ff;
     TDBGrid(Sender).Canvas.FillRect(Rect);
     TDBGrid(Sender).Canvas.TextOut(Rect.Left,Rect.Top,Column.Field.Text);

     IF  gdSelected   IN State Then
       Begin
        TDBGrid(Sender).Canvas.Brush.Color:= clHighLight;
 TDBGrid(Sender).Canvas.Font.Color := clHighLightText;
    End;

     TDBGrid(Sender).DefaultDrawColumnCell(Rect,DataCol,Column,State);
   end;

end;

function DELETED(Table:TTable): Boolean;
var
Prop : RECProps;
begin
dbiGetRecord(Table.Handle, dbiNoLock, nil, @Prop);
Result := Prop.bDeleteFlag;
END;

Напоминаю. Необходимо, чтобы в DBGrid-e удаленные записи были выделены цветом. Но сейчас цветом выделяются все записи. Не зависимо от того включен режим показа удаленных записей или нет.
Извиняюсь по поводу моей "несообразительности". :о((((


 
Anatoly Podgoretsky ©   (2005-07-21 10:49) [25]

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


 
АМБ   (2005-07-21 11:24) [26]

Хорошо:::(((. Можете мне сказать Anatoly Podgoretsky, в каком случае функция DELETE(tblDBF) выдают True, а в каком - False?


 
sniknik ©   (2005-07-21 11:47) [27]

ну код тут явно бракованный... ;о)) но у меня сомнения в том что данный подход вообще работоспособен, даже если его написать правильно (с else и вообще... ;о)).
дело в том, что отрисовка работает через даталинк (данные получает для нее), а она использует ненавигационные методы работы с таблицей, т.е. для получения данных записи делается не Next, а "Внутренний указатель" + 1; ну чтото вроде этого. неохота "углублятся" в тему.
вот. и если это так то BDE будет не в курсе всех этих дел, что там "навернула" его обертка (TTable), рискуем получать неверные данные, и как следствие "неопределенно пятнистый грид".
ну вот например, что будет возвращено при BOF = true? реально указатель "за гридом" на "до первой записи" а в гриде в это время рисуется первая строка (нет строки BOF)...

ну вот, правильнее определять удалена запись или нет в событии где реально определена текущая запись (и в BDE и TTable одна и та же). например в onCalcFields... там вычисляемому полю присваивать значение, ну "Удалено" к примеру, а в отрисовке уже для условия использовать его (если уж действительно необходимо выделять цветом).

p.s. сугубо имхо естественно. BDE это не мой "конек". поэтому и пояснение хромает.. не, оно хорошее. только хромает. ;о)) (© винни пух)


 
sniknik ©   (2005-07-21 11:50) [28]

> в каком случае функция DELETE(tblDBF) выдают True
если запись удалена.


 
АМБ   (2005-07-21 12:14) [29]

А у меня функция DELETE(tblDBF) всегда True?!?!?!? При прохождении Debug-ером.
Хотя в таблице есть и удаленные и не удаленные записи.


 
sniknik ©   (2005-07-21 12:46) [30]

> А у меня функция DELETE(tblDBF) всегда True?!?!?!?
прочитай [27] внимательно (похоже правдв ;), и смени событие.


 
ANB ©   (2005-07-21 12:50) [31]

Самый тупорылый, но самый надежный способ - читать запись напрямую из файла. Если в первой байте записи *,  то она удалена, если пробел, то нет. ИМХО.


 
АМБ   (2005-07-21 13:49) [32]


> ANB

Да... Теоретически выглядит все понятно. Но как считывать 1-й байт записи? Подскажите...


 
ANB ©   (2005-07-21 13:56) [33]

Могу переслать модуль. По исходникам разберешься и сделаешь свой вариант. Модуль умеет читать записи.


 
sniknik ©   (2005-07-21 14:14) [34]

> По исходникам разберешься
терзают меня смутные сомнения. ;о)) человек с выходным параметром единствнной функции в 2 строчки разобратся не может. а ты ему исходники... на сколько строк? ;)

к тому же там тоже вылезет проблема связи записи в TTable с записью в файле. просто уметь читать не самое главное.


 
АМБ   (2005-07-21 14:16) [35]


> ANB

Жду с нетерпением...:о)


 
ANB ©   (2005-07-21 14:33) [36]


> sniknik ©   (21.07.05 14:14) [34]
- да там всего 18 Кб. А в обработчике раскраски разве мы не имеем доступа к полям строки, которую красим ?


 
ANB ©   (2005-07-21 14:34) [37]

А коли имеем, номер записи вполне можно оттуда выдернуть.


 
Anatoly Podgoretsky ©   (2005-07-21 14:52) [38]

ANB ©   (21.07.05 12:50) [31]
Нафиг, функция из БДЕ нормально работает.


 
ANB ©   (2005-07-21 14:57) [39]


> Anatoly Podgoretsky ©   (21.07.05 14:52) [38]
- дык я не против. Я ж написал ИМХО. Может ему легче будет в моем коде разобраться. Кстати, я отправил, а спасибо нету . . .


 
Val ©   (2005-07-21 15:05) [40]

Разбирается. Разберется - скажет. 18 кил символов, означающих странные вещи - не шутки.


 
АМБ   (2005-07-21 15:30) [41]

Всем спасибо! Судя по полученному коду (за что, конечно, БОЛЬШОЕ спасибо ANB) мне еще и до тупорылого шагать и шагать...%((((
Поэтому прийдеться и впрям идти в... дворники, и то, если возьмут.

> Anatoly Podgoretsky ©   (21.07.05 14:52) [38]

Я и не сомневалься, что БДЕ работает нормально, но... так и не понял, почему в моем случае она (функция DELETED) все время показывает True? Ну, да... может когда-нибудь и пойму...
Еще раз ВСЕМ СПАСИБО %о))))(((())))


 
Anatoly Podgoretsky ©   (2005-07-21 15:38) [42]

Ты сначала сделай блок ELSE в своем коде. Потом сделай метку и двигаясь по записям вывод в нее состояние, тогда и говорить можно, а что говорить по ошибочному коду, не понимая как работает OnDrawCell


 
АМБ   (2005-07-21 15:51) [43]


> Anatoly Podgoretsky ©   (21.07.05 15:38) [42]


procedure TfrmMain.dbgDBFDrawColumnCell(Sender: TObject; const Rect: TRect;
 DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
 if DELETED(tblDBF) then   //Место метки
   begin
     TDBGrid(Sender).Canvas.Brush.Color := $00ff00;
     TDBGrid(Sender).Canvas.Font.Color := $0000ff;
     TDBGrid(Sender).Canvas.FillRect(Rect);
     TDBGrid(Sender).Canvas.TextOut(Rect.Left+2,Rect.Top+2,Column.Field.Text);
   end
 else
   begin
     TDBGrid(Sender).Canvas.Brush.Color := $ffffff;
     TDBGrid(Sender).Canvas.Font.Color := $000000;
     TDBGrid(Sender).Canvas.FillRect(Rect);
     TDBGrid(Sender).Canvas.TextOut(Rect.Left+2,Rect.Top+2,Column.Field.Text);
   end;

 IF  gdSelected   IN State Then
  Begin
   TDBGrid(Sender).Canvas.Brush.Color:= clHighLight;
  TDBGrid(Sender).Canvas.Font.Color := clHighLightText;
  End;

TDBGrid(Sender).DefaultDrawColumnCell(Rect,DataCol,Column,State);

end;

"Шагал" по всем записям... Идет по каждой ячейки всей записи, переходит на новую, снова по всем ячейкам и т.д. В блок ELSE ни разу не попадает.


 
Anatoly Podgoretsky ©   (2005-07-21 16:04) [44]

Для начала сделай тестовую версию

n1 := 0;
n2 := 0;
tblDBF.First;
begin
 while not tblDBF.Eof do
 if Deleted(tblDBF) do begin
   N1 := N1 + 1;
   Label1.Caption := IntToStr(N1);
 end;
 else begin
   N2 := N2 + 1;
   Label2.Caption := IntToStr(N1);
 end;
 Application.ProcessMessages;
 tblDBF.Next;
end;


 
АМБ   (2005-07-21 17:20) [45]


> Anatoly Podgoretsky ©   (21.07.05 16:04) [44]

Немного изменил текст кода:


procedure TfrmMain.Button1Click(Sender: TObject);
var
N1, N2: integer;
begin
n1 := 0;
n2 := 0;
tblDBF.First;
while not tblDBF.Eof do
begin
  if Deleted(tblDBF) Then
    begin
      N1 := N1 + 1;
//       Label1.Caption := IntToStr(N1);
    end
  else
    begin
      N2 := N2 + 1;
//       Label2.Caption := IntToStr(N1);
    end;
  Application.ProcessMessages;
  tblDBF.Next;
end;
lblForInfo.Caption:="Del:"+IntToStr(N1)+#10+"NotDel:"+IntToStr(N2);
end;



Результат: Del:14
Т.е., в таблице, которая открывалась в DBGrid-e всего 14 записей: удаленных и неудаленных


 
ANB ©   (2005-07-21 19:13) [46]


>   begin
>       N2 := N2 + 1;
> //       Label2.Caption := IntToStr(N1);
>     end;

- вот это место замени на

>   begin
>       N2 := N2 + 1;
> //       Label2.Caption := IntToStr(N2);
>     end;

Проблеме не поможет, но будет красивее работать.


 
АМБ   (2005-07-25 08:28) [47]

Мастера, извините за назойливость.
В силу "специфики" работы со сторонними организациями, я работаю с DBASE-III.
dbiGetRecord заработала начиная с DBASE-IV.
На DBASE-III не работает.
Это так и надо?


 
sniknik ©   (2005-07-25 08:38) [48]

> Это так и надо?
проверь, открой таблицу текстовым редактором, если значки у удаленных "*" на месте (а куда им дется то ;о))) должно работать...
если есть, а всетаки не работает пришли пример таблици, посмотреть. может и придумаем чего (если не работает).


 
ANB ©   (2005-07-25 12:40) [49]


> АМБ   (25.07.05 08:28) [47]

В коде, который я тебе выслал, самое главное - это определение рекордов заголовка DBF и полей DBF. В сети есть описание структуры DBF файла. Если в мои рекорды записать из файла инфу - то в полях начдешь много полезного и сможешь определить по какому смещению начинается запись с нужным тебе номером. Я, вроде, комментарии воткнул. * юзается для пометки практически во всех DBF. Минус - если заюзал индекс, то я не знаю, как ты будешь искать номер нужной тебе записи. Если нет - то все просто. Работать должно быстро, если все параметры (смещение первой записи и размер записи) ты определишь заранее (до или сразу после открытия таблицы). Затем все сведется к :
- расчитать позицию нужной записи
- прочитать один байт
- проанализить его.
Все имхо. На исчерпывающий вариант не претендую.


 
sniknik ©   (2005-07-25 13:17) [50]

во настырные... и все время через задницу норовят сделать. ;о))

все работает и с 3-м dBase тоже (не выдержал, сам сделал таблицу 3-го и проверил), проблема не в версии, проблема в интерпретации, просто проверялось так понимаю на таблице с малым количеством записей, первая была удаленная...
вот вся неопределенность "неопределенно пятнистого грида" вылилась в одно пятно... (на большее не хватает).

впрочем все это уже описывал, не буду повторятся, если хочеш перечитай ветку.


 
sniknik ©   (2005-07-25 13:25) [51]

кстати способ определить удаленность не единственный (теперь когда практически "заставили" сделать тест, это вижу). но предлагать другое не буду, не вижу смысла. зачем? с одним то не разобрались.


 
ANB ©   (2005-07-25 14:11) [52]


> sniknik ©   (25.07.05 13:17) [50]
> во настырные... и все время через задницу норовят сделать.
> ;о))
- че сразу ругаться то. Через задницу интереснее же. Опять же польза - учимся работать с файлами БД напрямую.


 
Anatoly Podgoretsky ©   (2005-07-25 14:22) [53]

ANB ©   (25.07.05 14:11) [52]
учимся работать с файлами БД напрямую

Тупиковый путь.


 
ANB ©   (2005-07-25 15:06) [54]


> Anatoly Podgoretsky ©   (25.07.05 14:22) [53]
- а вдруг пригодится ?


 
Anatoly Podgoretsky ©   (2005-07-25 15:19) [55]

А попробуй изменить 12 байт в kernel.exe может пригодится.
Зачем чесать левое ухо правой рукой, когда тебе рассказали про нормальные пути? Делать что ли нечего?


 
АМБ   (2005-07-26 10:51) [56]

Всем кому еще не надоело….
Не успел я порадоваться, что все заработало как надо (а ведь действительно работало…), как все перестало работать. И теперь работает, по-новому, но не так как надо. А работает следующим образом. Не зависимо от настройки BDE->Configuration->Native->DBASE->LEVEL=3 (или 4), отработка кода, текст которой выше, выдает следующие результаты.
Форма моей программки может менять размер, меняется и размер DBGrid-a. Если размер DBGrid-a такой, что показываются все записи таблицы без скроллинга, то все записи считаются как удаленные. А если размер формы вместе с размером DBGrid-a изменить так, что появляется скроллинг, то все записи считаются не удаленными. Хотя в таблице есть и удаленные и не удаленные записи.
Не знаю, что я мог изменить неаккуратно в BDE или в тексте программки, но знаю, что работало, а теперь не работает. Если кому интересно могу выслать весь исходник своей программки (архив 41 кб) с тестовыми базами (архив 8 кб ).
Для sniknik я выслал сразу, воспользовавшись его приглашением.


 
sniknik ©   (2005-07-26 11:27) [57]

> Для sniknik я выслал сразу, воспользовавшись его приглашением.
ничего себе сразу ...
предложено (и потом следующим же постом сказал что проверил, значит все, проблема себя исчерпала. неинтересно)
sniknik ©   (25.07.05 13:17) [50]
получено  
Дата: Tue, 26 Jul 2005 10:50:30 +0400 (MSD)

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


 
АМБ   (2005-07-26 11:42) [58]

Для > sniknik . Во-первых, БОЛЬШОЕ СПАСИБО!!!
Во-вторых, "сразу" я имел ввиду не сразу после приглашения, а сразу после моей просьбой разобраться с моим кодом.
А все это время я пыталься выяснить, что я "потерял" и почему программка перестала считать "удаленные" записи и "неудаленные".
Ваш екзешник работает как я и хотел. Это радует.
Правда подсчет записей осталься таким как и был. Это немного огорчает.
Насколько я правильно понял, Вы ввели вычисялемое поле, и по нему уже прорисовываете DBGrid. ЧТо ж буду проповать теперь этот вариант. Хотя нерешенный вопрос о подсчете записей, все-таки висит небольшым, но неприятным грузом.


 
sniknik ©   (2005-07-26 11:59) [59]

> Правда подсчет записей осталься таким как и был.
я его не трогал.

> Насколько я правильно понял, Вы ввели вычисялемое поле, и по нему уже прорисовываете DBGrid.
нет, именно тут я воспользовался другим способом ([51]).
сдесь это проше как оказалось, но не зная ничего о задаче даже не думал о решении в таком аспекте. до получения исходников. а предлогат теоретическое решение, на проверку, но тоже рабочее (см. [50]).

> Хотя нерешенный вопрос о подсчете записей, все-таки висит небольшым, но неприятным грузом.
обьяснял в первом же своем посте, сдесь похоже то самое.
BDE и компонент на его основе это всетаки не одно и тоже.


 
АМБ   (2005-07-27 08:24) [60]

Еще раз БОЛЬШОЕ СПАСИБО > sniknik !!!
Сделал как Вы советовали через вычисляемое поле. Все работает.
Уважаемый > sniknik !
А можно, теперь, узнать и о другом способе?


 
sniknik ©   (2005-07-27 08:49) [61]

> Сделал как Вы советовали через вычисляемое поле.
покажи.


 
Anatoly Podgoretsky ©   (2005-07-27 08:52) [62]

Если надо что бы было почти полное подобие xBase то именно через вычислимое поле и надо, там оно является не функцией, а именно полем _DELETED_, вроде такое имя если память не подводит.
Наличие поля упрощает всю остальную обработку.


 
АМБ   (2005-07-27 09:36) [63]


> sniknik

Показываю...


interface
...
var
...
//Сделал глобальной, т.к. может использоваться и в других процедурах
 CulcDelFld : TField;

//Открытие файла для работы
procedure TfrmMain.N11_OpenFileClick(Sender: TObject);

begin
...
   tblDBF.FieldDefs.Clear;
   tblDBF.FieldDefs.Update;

   //Добавляем все поля
   for i := 0 to tblDBF.FieldDefs.Count-1 do
      tblDBF.FieldDefs[i].CreateField(Self);

   //Создаем вычисляемое поле
   CulcDelFld := TStringField.Create(Self);
   CulcDelFld.FieldName := "flgDelete";
   CulcDelFld.FieldKind := Calculated;        
   CulcDelFld.DataSet := tblDBF;
   CulcDelFld.Calculated := True;
   CulcDelFld.Size := 1;
   CulcDelFld.DataSet.AutoCalcFields := True;
   CulcDelFld.DataSet.OnCalcFields := frmMain.MyCalcField;
/////////////////////////////

   tblDBF.Open;
   tblDBF.First;

   dbgDBF.SetFocus;

...

procedure TfrmMain.dbgDBFDrawColumnCell(Sender: TObject; const Rect: TRect;
 DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
 if tblDBF["flgDelete"] = "*" then
   begin
    TDBGrid(Sender).Canvas.Brush.Color := $00ff00;
    TDBGrid(Sender).Canvas.Font.Color := $0000ff;
    TDBGrid(Sender).Canvas.FillRect(Rect);
    TDBGrid(Sender).Canvas.TextOut(Rect.Left,Rect.Top,Column.Field.Text);

    IF  gdSelected   IN State Then
      Begin
       TDBGrid(Sender).Canvas.Brush.Color:= clHighLight;
       TDBGrid(Sender).Canvas.Font.Color := clHighLightText;
      End;

    TDBGrid(Sender).DefaultDrawColumnCell(Rect,DataCol,Column,State);
   end;
   
end;



Вроде все...
Правда, при открытии другой таблицы, такой же структуры, выдает ошибку дубликата полей на коде:

   for i := 0 to tblDBF.FieldDefs.Count-1 do
      tblDBF.FieldDefs[i].CreateField(Self);

Процедура
tblDBF.FieldDefs.Clear;
не помогает...


 
sniknik ©   (2005-07-27 11:33) [64]

ладно, допустим это работает... т.к. нет функции MyCalcField, нет такого типа Calculated и это не позволит коду даже скомпилится.

кстати ошибка при повторном открытии у тебя от того, что  
tblDBF.FieldDefs[i].CreateField(Self);
это функция. которая возвращает результат (кстати! ;) ... ты его теряеш, но от того что ты на созданные обьекты не обращаеш внимания, они существовать не перестанут...
(в принципе ссылки на них можно и из таблици вытащить, гдето они должны сохранятся)

второй метод о котором я говорил это просто доведенная до логического завершения мысль ANB, он пытался получить информацию из файла (но как тогда связь записей в файле с табличным делать? и зачем если можно проще), я получаю тоже самое из внутреннего буфера самой таблицы ActiveBuffer (строка записи "as is", до разбора на составляющие (поля), в ней признак "*" еще есть.)
все в общемто. думаю достаточно. (кстати тоже не всегда соответствует действительности... если тупо заменить Deleted() в событии по вычисляемому полю на проверку по нему тоже дает неверный результат... странно (может глюк. второйраз проверять не хочется). в событии DrawColumnCell зато соответствие полное)


 
АМБ   (2005-07-27 12:08) [65]

Точно... Переносил код через буфер, а он в окошке не помещалься, да и ремарки на русском не переносились, вот и "напортачил".
Конечно:
CulcDelFld.FieldKind := fkCalculated;
А вот и функция, которую забыл:

procedure TfrmMain.MyCalcField(DtSt: TDataSet);
begin
 if Deleted(tblDBF) Then tblDBF["flgDelete"] := "*";
end;


Что касается, tblDBF.FieldDefs[i].CreateField(Self);
так я пробовал делать tblDBF.FieldDefs.Free;
но также пока не получилось... Буду пробовать дальше...
Спасибо за второй метод. Кажеться более интересным, и кажеться будет свободен от нынешней ошибки при переоткрытии таблицы...
Постараюсь и его реализовать.
Еще раз спасибо.


 
sniknik ©   (2005-07-27 12:31) [66]

> свободен от нынешней ошибки при переоткрытии таблицы...
ошибка при переоткрытии твоя, метод не причем. созданные обьекты надо уничтожать.
а уж будет или нет... как напишеш. (правда в 1-й строчке ошибку сделать труднее чем в пяти/десяти ;о)))

у тебя еще и в отрисовке эти
TDBGrid(Sender).Canvas.FillRect(Rect);
TDBGrid(Sender).Canvas.TextOut(Rect.Left,Rect.Top,Column.Field.Text);
строки лишние.


 
АМБ   (2005-07-27 15:26) [67]

Наконец-то, догадалься, что список полей - это буквально только список, а не сами поля :-(). Так что, теперь в начале процедуры открытия таблицы использую код:

if tblDBF.FieldDefs.Count <> 0 then
     begin
       CulcDelFld.Free;
       for i := tblDBF.FieldDefs.Count-1 downto 0 do
          tblDBF.Fields[i].Free;
     end;


Теперь разные таблицы переоткрываются без ошибок и все, вроде бы, пока хорошо.
А насчет лишних линий при отрисовки ячеек, я это взял из примера статей, которые рекомендовали в этом форуме. Подозревал, что они могут быть излишне, но еще не проверял на практике. Сейчас проверил. Вы правы. Работает и без них.
Так что еще раз БОЛЬШОЕ СПАСИБО!
:о))))


 
АМБ   (2005-07-29 10:59) [68]

Извините за назойливость... Но мы забыли вторую часть вопроса:
"... а затем, выбрав какую-нибудь запись - восстановить ее, т.е. снять пометку на удаление."
Подскажите, пожалуйста.


 
ANB ©   (2005-07-29 11:09) [69]

Надо заменить * на пробел


 
АМБ   (2005-07-29 11:23) [70]

Да, об этом я догадывалься ;о)
Согласно Вашей методике

> Опять же польза - учимся работать с файлами БД напрямую.

, так, я думаю, и надо делать. Правда, я ее еще не освоил, хотя за исходники спасибо.
А нет ли функций, типа UnDelete?


 
sniknik ©   (2005-07-29 11:28) [71]

ты в хелп так и не научился заглядывать? ;) BDE-шная функция DbiUndeleteRecord
но подозреваю могут быть опять проблемы ;о)), изза тогоже несоответствия...

а попробуй в ActiveBuffer исправить. получится?


 
АМБ   (2005-07-29 13:53) [72]

Да. Вариант с DbiUndeleteRecord сразу пока не идет.
Взял пример прямо из BDE32.HLP. На строке:
Check(DbiUndeleteRecord(dBASETbl.Handle));
выдает ошибку: Operation not applicable.
Работа с ActiveBuffer как-то больше нравиться. Не знаю еще почему. Написал код:

begin
sBuffer := tblDBF.ActiveBuffer;
ShowMessage(tblDBF.ActiveBuffer[0]); //Показывает "*"
tblDBF.ActiveBuffer[0]:=" ";
ShowMessage(tblDBF.ActiveBuffer[0]); //Показывает " "
tblDBF.Edit;
tblDBF.Post;
end;

Проходит без ошибок, но запись не удаляет.
Продолжаю разбираться... Но, если подскажите, то буду рад...:о)


 
АМБ   (2005-07-29 13:55) [73]

Прощу прощения. Ошибся.

> но запись не удаляет.

т.е. запись не восстанавливается.


 
АМБ   (2005-07-29 14:04) [74]

Спешу поделиться радостью...;о)))
Немного изменил процедуру:

tblDBF.Edit;
sBuffer := tblDBF.ActiveBuffer;
ShowMessage(tblDBF.ActiveBuffer[0]);
tblDBF.ActiveBuffer[0]:=" ";
ShowMessage(tblDBF.ActiveBuffer[0]);
tblDBF.Post;

Все заработало... Пока...
Большое СПАСИБО > sniknik


 
sweet lou   (2005-09-05 14:39) [75]

интересные тут такие рассуждения были.......но я так и не понял, как же сделать чтобы в моем гриде удаленные записи отличались другим цветом!!!!


 
Anatoly Podgoretsky ©   (2005-09-05 16:00) [76]

Так это надо рисовать в OnDrawCell - кстати а ты то тут причем, этот вопрос от АМБ  
А тебе надо задать свой вопрос как рисовать строки другим цветом или посмотреть в каком ни будь Чаво, ими просто завален Интернет да и в справке есть пример.


 
Kacnep ©   (2005-10-07 11:30) [77]

АМБ   (27.07.05 15:26) [67]
Наконец-то, догадалься, что список полей - это буквально только список, а не сами поля :-(). Так что, теперь в начале процедуры открытия таблицы использую код:

if tblDBF.FieldDefs.Count <> 0 then
    begin
      CulcDelFld.Free;
      for i := tblDBF.FieldDefs.Count-1 downto 0 do
         tblDBF.Fields[i].Free;
    end;

Теперь разные таблицы переоткрываются без ошибок и все, вроде бы, пока хорошо.
А насчет лишних линий при отрисовки ячеек, я это взял из примера статей, которые рекомендовали в этом форуме. Подозревал, что они могут быть излишне, но еще не проверял на практике. Сейчас проверил. Вы правы. Работает и без них.
Так что еще раз БОЛЬШОЕ СПАСИБО!
:о))))


У меня не получилось :(((( не работает. Не работает переоткрытие в adoTable разных таблиц.
Вот что у меня...

s:="ТАБЛИЦА_АКЦЕССА1";
with dm.adot_Meh do begin
      if FieldDefs.Count>0 then for row:=FieldDefs.Count-1 downto 0 do Fields[row].Free;
      FieldDefs.Clear;
      TableName:=s;  --- указываю с какой табл буду работать
      FieldDefs.Update; --- получаю список полей в датасет
      Filtered:=false;
      for row:=0 to FieldDefs.Count-1 do begin
          FieldDefs.Items[row].CreateField(dm.adot_Meh);  -- создаю поля из датасета динамически
       end;
       f:=TStringField.Create(dm.adot_Meh);  дальше создаю дополнит поле
       f.Name:="adot_MehSumm";
       f.FieldName:="Summ";
       f.DisplayLabel:="Сумма";
       f.DataSet:=dm.adot_Meh;
       f.Calculated:=true;
       f.FieldKind:=fkCalculated;
       Open; -- открываю набор данных
{поработал с набором в ДБгриде, Закрыл набор данных}
 end;
 s:="ТАБЛИЦА2"
вызываю код приведенный выше.... иии НА        FieldDefs.Update; --- получаю список полей в датасет

ошибка таковая...
Debugger Exception Notification
---------------------------
Project balance.exe raised exception class EOleException with message "Item cannot be found in the collection corresponding to the requested name or ordinal". Process stopped. Use Step or Run to continue.

Если гуру подскажут спасут то что осталось от мозга решавшего этот трабл  на протяжении 6и часов :((
Блин перепробовал все.


 
Seg   (2005-10-07 11:39) [78]

Как организовать просмотр помеченных на удаление записей в DBF таблице? Т.е. сначала, записи обрабатываются tblDBF1.Delete; и становятся невидимы в DBGrid-е. Как сделать их видимыми, да еще и другим цветом, или как-то еще их выделить, а затем, выбрав какую-нибудь запись - восстановить ее, т.е. снять пометку на удаление.

Добавляешь еще одно поле в таблицу например DELETED.
Для удаленных записей устанавливаешь 1, для неудаленных 0.
Таким образом ты можещь показывать
1.Все неудаленные
2.Все удаленные
3.Все удаленные и неудаленные.
4.Ничего не показывать

С обработчиком строк (раскраской) тоже не должно возникнуть проблем.
Ну и установку/отмену статуса строки тоже легко можно реализовать.


 
Kacnep ©   (2005-10-07 12:04) [79]

Да у меня вопрос не в удаленных зхаписях
а в
if FieldDefs.Count>0 then for row:=FieldDefs.Count-1 downto 0 do Fields[row].Free;
     FieldDefs.Clear;
     TableName:=s;  --- указываю с какой табл буду работать
     FieldDefs.Update; --- получаю список полей в датасет

если сначала открыть таблицу считать ее поля потом закрыть и попытаьтся считать поля другой таблицы - выдастся ошибка.
вывод - надо удалить поля старой. А КАК?

if FieldDefs.Count>0 then for row:=FieldDefs.Count-1 downto 0 do Fields[row].Free;
     FieldDefs.Clear;

ЭТО НЕ РАБОТАЕТ!
Вот ошибка
Debugger Exception Notification
---------------------------
Project balance.exe raised exception class EOleException with message "Item cannot be found in the collection corresponding to the requested name or ordinal". Process stopped. Use Step or Run to continue.



Страницы: 1 2 вся ветка

Форум: "Базы";
Текущий архив: 2005.11.20;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.7 MB
Время: 0.046 c
2-1130828309
DimaDima
2005-11-01 09:58
2005.11.20
Требует всё больше памяти.


1-1130307574
DVM
2005-10-26 10:19
2005.11.20
Правильно ли я превел с С на Pascal?


6-1123497734
ronyn
2005-08-08 14:42
2005.11.20
Как синхронизировать страницу?


11-1111908939
Serr
2005-03-27 11:35
2005.11.20
Вопрос по базам


1-1130396063
VID
2005-10-27 10:54
2005.11.20
Я не могу прочитать свойство ячейки Cell.Comment.Text в Excel





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский