在DLL放入一个普通窗体其实很容易,我的困难实际上是:我在DLL中放入的窗体风格是fsMDIChild,而主程序的窗口风格是fsMDIForm,在主程序中调用DLL中的导出函数建立子窗体时出错,出错信息大意是“没有主窗体可用”。请问怎样解决这个问题?最好有源代码例程。

解决方案 »

  1.   

    想在DLL中有Form,只需提供动态建立,初始化,访问它属性和数据的函数。
    Form可以是任何类型。Sample如下:(From <Delphi 3从入门到精通P648>)
     Libraray FormDll;
      uses
        ScrollF in 'scrollf.pas' 
     exports
         GetColor;
     end;在Scollf.pas除正常TForm1定义外,加上
    一个function GetColor;function GetColor(col:LongInt):LongInt;
    begin
      try
        FormScroll:=TForm1.Create(Application);
        with FormScroll do
         begin 
           //init some data
          if ShowModal = mrOK then
            //set your return data
         end;
       finally 
         FormScroll.Free;
        end;
      Except
        On E:Exception do
          ShowMessage('Error in Form DLL');
      end; 
          
       end;
    end;
      

  2.   

    希望公司翻译出版的<<Borland C++ Builder 3自学培训教程>>有此问题
    的标准答案(节选):
     DLL中的MDI子窗体是个特例.假设有个C++ Builder应用程序,主窗体是MDI窗体,
    如果使用DLL中的子窗体,则VCL会仍出异常.
     要显示MDI子窗体, VCL检查Application对象的MainForm属性是否有效.如果Main
    Form属性无效,则VCL扔出异常.DLL中也包含Application对象.由于DLL没有MainForm所以失败.
     为解决这个问题,将DLL的Application对象赋予调用应用程序的Application.
    但在DLL删除之前,还要恢复原Application.
     第一步在DLL顶部放上
       TApplication *DLLapp=0;
     二,
      
      void ShowMDIChildForm(TApplication *mainApp)
     {
       if(!DLLapp){
         DLLapp=Application;
         Application=mainApp;
        }
      TChildForm  *child=new TChildForm(Application->MainForm);
      Child->Show();
     }
    三,在DLL删除之前恢复Application.
     在OnCloseQuery事件中执行下面函数
    void ResetDLLApplication()
     {
       if(DLLapp)
         Application=DLLapp;
     }
      

  3.   

    //入口函数
    function Entry(iFuncID: integer): TForm; stdcall; export;
    begin
      case iFuncID of
        1: begin
          if frmFinancing = nil then
    frmFinancing := TfrmFinancing.Create(Application)
          else 
    frmFinancing.Show;
          Result := frmFinancing;
      end;
    end;
    //frmFinancing是要创建的子窗体变量
    同时设置编译属性为Build with runtime packages即可