Конференция "Corba" » TWebBrowser -> OleObject - проверить является ли элемент NULL [Delphi, Windows]
 
  • Edgar_Wine (24.09.12 08:43) [0]
    Здравствуйте. Подскажите как проверить, делаю так вот:

    Var Element: OleVariant;
    .....
    Element:=WebBrowser1.OleObject.document.all.tags('div').namedItem('my_id');
    // работа с Element
    .....



    Когда в странице есть хотя бы один тег [div] у которого id="my_id" или name="my_id" - то всё работает как нужно.
    Но если таковых нет - функция вылетает в небеса. =(

    Руководствуясь этим: http://msdn.microsoft.com/en-us/library/ms536634(v=vs.85).aspx
    метод namedItem() должен: либо вернуть первый из подходящих элементов, либо вернуть NULL.

    Пытался проверить на NULL этими функциями: VarIsEmpty(), VarIsNull() - без результатов. =(
  • sniknik © (24.09.12 13:50) [1]
    > Пытался проверить на NULL этими функциями: VarIsEmpty(), VarIsNull() - без результатов. =(
    значит не то проверял. VarIsNull при том что возвращается именно он, то что надо...
  • sniknik © (24.09.12 13:51) [2]
    > метод namedItem() должен:
    a tags('div') не должен?
  • Edgar_Wine (24.09.12 14:34) [3]
    оой.. Куда-то я кажется в не тот раздел вообще написал.. 2 суток без сна.. Тока теперь подремав понял, простите.. =((

    ну... В том конкретном случае у меня там были ещё div, так что вылетало точно не там. хмм. Надо проверить что будет если вообще нет div, спасибо. =)

    Msg:='|';
    Element:=WebBrowser1.OleObject.document.all.tags('DIV').namedItem('test');
    if VarIsNull(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    if VarIsEmpty(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    if VarIsError(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    ShowMessage(Msg); // Все 3 пишут "false" (в обоих случаях), а если попытаться что-то делать дальше с Element - вылетает в трубу. =(
    ShowMessage(Element.InnerText); // Например вот это: AV at 0045DE47 ... Read of address 00000000



    Может в Делфи заголовочник как-то не так что-то? А что тогда делать? =(
  • sniknik © (24.09.12 16:21) [4]
    // Все 3 пишут "false" (в обоих случаях), а если попытаться что-то делать дальше с Element - вылетает в трубу. =(
    а та проверь что пишут после каждого... кашу маслом можно испортить.

    // ... Например вот это: AV at 0045DE47 ... Read of address 00000000
    + VarToStr

    > Может в Делфи заголовочник как-то не так что-то?
    начинаешь задаваться такими вопросами, значит нужен ответ на другой "а программирование это мое? не пойти ли в дворники...".
    глюки у тебя! в 99,98% случаев, точка. по другому не думай.
  • Edgar_Wine (24.09.12 17:08) [5]
    Ну отчего же? Просто заголовочники у моей D7 древние, много раз приходилось что-то вручную объявлять, некоторое объявлено не так как в оригинальном MSDN, например GradientFill() в D7 слегка через одно место... Ну это другая история уже. =))

    Не очень понял что сделать после чего. VarToStr() в первом случае говорит [object], а во втором вылетает на ней с "EVariantTypeCastError -> Could not convert variant of type (Dispatch) into type (String)".

    Брутфорс спасёт Мир! © =))
    Перепробовал всё что начинается с VarIs - кажется мне нужно проверять по VarIsClear() - во всяком случае тока оно дало "true" на втором случае.
  • sniknik © (24.09.12 17:19) [6]
    > "EVariantTypeCastError -> Could not convert variant of type (Dispatch) into type (String)".
    означает что
    > метод namedItem() должен: либо вернуть первый из подходящих элементов, либо вернуть NULL.
    не правда... иначе хватило бы VarIsNull.
  • Edgar_Wine (24.09.12 20:24) [7]
    А я тут причём? =)
    Это в MSDN так написано, я же давал ссыль: «Returns an object or a collection of objects if successful, or null otherwise.»

    Ну ладно, сейчас ещё поподробнее потестю, с пристрастием... >:3
    Но конструктивные идеи или ссылки приветствуются! =)
  • sniknik © (25.09.12 00:44) [8]
    > я же давал ссыль:
    а я говорил
    > значит не то проверял.

    > Но конструктивные идеи или ссылки приветствуются! =)
    ошибка в программе. это самая что ни на есть конструктивная правда жизни. на 99.98%.
  • sniknik © (25.09.12 08:03) [9]
    хм. все методы namedItem любых объектов в MSHTML_TLB возвращают интерфейс. в описанном случае не найдености это нулевой интерфейс, а не null. почему в мсдн написано null... не знаю, может справка не та, для net, или с++ где либо авто приведение типа либо игнорирование, в дельфи есть разница.

    сорри, ошибался, дело не в твоей программе. 0,02% тоже бывают.
  • Плохиш © (26.09.12 00:06) [10]

    > Edgar_Wine   (24.09.12 14:34) [3]

    null в Delphi называется nil.
  • sniknik © (26.09.12 07:45) [11]
    > null в Delphi называется nil.
    > "EVariantTypeCastError -> Could not convert variant of type (Dispatch) into type (String)".
  • cobalt © (28.09.12 14:31) [12]

    >
    Msg:='|';
    > Element:=WebBrowser1.OleObject.document.all.tags('DIV').
    > namedItem('test');
    > if VarIsNull(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    >
    > if VarIsEmpty(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    >
    > if VarIsError(Element) then Msg:=Msg+'true|' else Msg:=Msg+'false|';
    >
    > ShowMessage(Msg); // Все 3 пишут "false" (в обоих случаях),
    >  а если попытаться что-то делать дальше с Element - вылетает
    > в трубу. =(
    > ShowMessage(Element.InnerText); // Например вот это: AV
    > at 0045DE47 ... Read of address 00000000


    >
    > Может в Делфи заголовочник как-то не так что-то? А что тогда
    > делать? =(

    А что показывает отладчик на Element?

    ЗЫ. У коллекции есть InnerText?
  • Edgar_Wine (29.09.12 02:17) [13]
    namedItem() возвращает не коллекцию, а один элемент. Вроде как. =)
    У коллекции нету innerText. А нужно ли? =)))

    Показывает $00000000, а толку?

    хм... VarIsNull() даёт false даже когда переменная вообще не инициализирована. Ну то есть не использовалась ни разу, тока в var написана - видимо компилятор или-кто-там расстарались. =)
    Зато VarIsClear() даёт true и когда не инициализирована и когда не найдено ничего в namedItem(). :3
  • sniknik © (29.09.12 11:54) [14]
    > Зато VarIsClear() даёт true
    там проверяется как раз на пустой интерфейс.

    varEmpty    = $0000; { vt_empty        0 }
    varNull     = $0001; { vt_null         1 }

    function VarIsNull(const V: Variant): Boolean;
    begin
     Result := FindVarData(V)^.VType = varNull;
    end;

    function VarIsClear(const V: Variant): Boolean;
    var
     LHandler: TCustomVariantType;
     LVarData: TVarData;
    begin
     LVarData := FindVarData(V)^;
     with LVarData do
       if VType < CFirstUserType then
         Result := (VType = varEmpty) or
                   (((VType = varDispatch) or (VType = varUnknown)) and
                     (VDispatch = nil))
       else if FindCustomVariantType(VType, LHandler) then
         Result := LHandler.IsClear(LVarData)
       else
         Result := False;
    end;

  • Плохиш © (29.09.12 16:01) [15]

    > Показывает $00000000, а толку?

    Это и есть nil. А "толк" программист знать должен.
  • Edgar_Wine (30.09.12 02:09) [16]
    Говорю же - VarIsNull() даёт false.

    >> null в Delphi называется nil.
    >> Это и есть nil.

    Я знаю! Только попробуйте сделайте проверку на него в if чтоб оно работало. У меня не вышло. =(
    Видимо компилятор как-то особо обрабатывает тип OleVariant.
  • Плохиш © (30.09.12 04:37) [17]
    If <какаятофигня> <> nil then делаем чë-то с <какаятофигня>
  • Edgar_Wine (30.09.12 05:17) [18]
    Именно так я прежде всего и пробовал:

    >> [Error] Incompatible types
  • Плохиш © (30.09.12 11:33) [19]

    > Edgar_Wine   (30.09.12 05:17) [18]
    > Именно так я прежде всего и пробовал:
    >
    > >> [Error] Incompatible types
    >
    >

    nil соместим с любым ссылочным типом. Есть подозрение, что пора искать программиста.
 
Конференция "Corba" » TWebBrowser -> OleObject - проверить является ли элемент NULL [Delphi, Windows]
Есть новые Нет новых   [118448   +36][b:0][p:0.002]