IDE: Move code related to many build modes to unit BuildModesManager. Make "Build many Modes" selection persistent.

git-svn-id: trunk@58903 -
This commit is contained in:
juha 2018-09-07 11:03:44 +00:00
parent 9c7329fca7
commit 9f252da8ea
7 changed files with 275 additions and 212 deletions

View File

@ -18,10 +18,11 @@
* *
***************************************************************************
Author: Mattias Gaertner
Author: Mattias Gaertner, Juha Manninen
Abstract:
Modal dialog for editing build modes: add, delete, reorder, rename, diff.
Global functions related to many build modes.
}
unit BuildModesManager;
@ -31,11 +32,16 @@ interface
uses
Classes, SysUtils,
// LCL
Forms, Controls, Dialogs, StdCtrls, Grids, Menus, ComCtrls, ButtonPanel, LCLProc,
IDEOptionsIntf, IDEDialogs,
TransferMacros, Project, CompilerOptions,
EnvironmentOpts, LazarusIDEStrConsts,
BaseBuildManager, Compiler_ModeMatrix, BuildModeDiffDlg;
// LazUtils
LazFileUtils, LazLoggerBase, UITypes,
// IdeIntf
IDEDialogs, CompOptsIntf, IDEOptionsIntf, LazIDEIntf,
// IDE
MainBase, BasePkgManager, PackageDefs, Project, CompilerOptions, EnvironmentOpts,
TransferMacros, BaseBuildManager, Compiler_ModeMatrix, BuildModeDiffDlg,
GenericCheckList, IDEProcs, LazarusIDEStrConsts;
type
@ -99,14 +105,35 @@ type
property ShowSession: boolean read fShowSession write SetShowSession;
end;
var
OnLoadIDEOptionsHook: TOnLoadIDEOptions;
OnSaveIDEOptionsHook: TOnSaveIDEOptions;
{ TBuildModesCheckList }
TBuildModesCheckList = class
private
FListForm: TGenericCheckListForm;
function Show: Boolean;
public
constructor Create(DlgMsg: String);
destructor Destroy; override;
function IsSelected(AIndex: Integer): Boolean;
end;
function ShowBuildModesDlg(aShowSession: Boolean): TModalResult;
procedure SwitchBuildMode(aBuildModeID: string);
procedure UpdateBuildModeCombo(aCombo: TComboBox);
// Functions dealing with many BuildModes. They depend on TBuildModesCheckList.
function AddPathToBuildModes(aPath, CurDirectory: string; IsIncludeFile: Boolean): Boolean;
function BuildManyModes: Boolean;
// Check if UnitDirectory is part of the Unit Search Paths.
// If not, ask user if he wants to extend dependencies or the Unit Search Paths.
// Not strictly for many BuildModes but it adds a path to them all.
function CheckDirIsInSearchPath(UnitInfo: TUnitInfo; AllowAddingDependencies, IsIncludeFile: Boolean): Boolean;
var
OnLoadIDEOptionsHook: TOnLoadIDEOptions;
OnSaveIDEOptionsHook: TOnSaveIDEOptions;
implementation
@ -179,6 +206,160 @@ begin
end;
end;
function AddPathToBuildModes(aPath, CurDirectory: string; IsIncludeFile: Boolean): Boolean;
var
DlgCapt, DlgMsg: String;
i: Integer;
Ok: Boolean;
BMList: TBuildModesCheckList;
begin
Result:=True;
BMList:=TBuildModesCheckList.Create(DlgMsg);
try
if IsIncludeFile then begin
DlgCapt:=lisAddToIncludeSearchPath;
DlgMsg:=lisTheNewIncludeFileIsNotYetInTheIncludeSearchPathAdd;
end
else begin
DlgCapt:=lisAddToUnitSearchPath;
DlgMsg:=lisTheNewUnitIsNotYetInTheUnitSearchPathAddDirectory;
end;
DlgMsg:=Format(DlgMsg,[LineEnding,CurDirectory]);
if Project1.BuildModes.Count > 1 then
Ok:=BMList.Show
else
Ok:=IDEMessageDialog(DlgCapt,DlgMsg,mtConfirmation,[mbYes,mbNo])=mrYes;
if not Ok then Exit(False);
for i:=0 to Project1.BuildModes.Count-1 do
if BMList.IsSelected(i) then
if IsIncludeFile then
Project1.BuildModes[i].CompilerOptions.MergeToIncludePaths(aPath)
else
Project1.BuildModes[i].CompilerOptions.MergeToUnitPaths(aPath);
finally
BMList.Free;
end;
end;
function BuildManyModes(): Boolean;
var
ModeCnt: Integer;
function BuildOneMode(LastMode: boolean): Boolean;
begin
Inc(ModeCnt);
DebugLn('');
DebugLn(Format('Building mode %d: %s ...', [ModeCnt, Project1.ActiveBuildMode.Identifier]));
DebugLn('');
Result := MainIDE.DoBuildProject(crCompile, [], LastMode) = mrOK;
end;
var
BMList: TBuildModesCheckList;
ModeList: TList;
md, ActiveMode: TProjectBuildMode;
BuildActiveMode: Boolean;
i: Integer;
LastMode: boolean;
begin
Result := False;
ModeCnt := 0;
if PrepareForCompileWithMsg <> mrOk then exit;
BMList:=TBuildModesCheckList.Create(lisCompileFollowingModes);
ModeList := TList.Create;
try
if not BMList.Show then Exit;
ActiveMode := Project1.ActiveBuildMode;
BuildActiveMode := False;
// Collect modes to be built.
for i := 0 to Project1.BuildModes.Count-1 do
begin
md := Project1.BuildModes[i];
if BMList.IsSelected(i) then
if md = ActiveMode then
BuildActiveMode := True
else
ModeList.Add(md);
end;
// Build first the active mode so we don't have to switch many times.
if BuildActiveMode then
begin
LastMode := (ModeList.Count=0);
if not BuildOneMode(LastMode) then Exit;
end
else if ModeList.Count=0 then
begin
IDEMessageDialog(lisExit, lisPleaseSelectAtLeastOneBuildMode,
mtInformation, [mbOK]);
Exit(False);
end;
// Build rest of the modes.
for i := 0 to ModeList.Count-1 do
begin
LastMode := (i=(ModeList.Count-1));
Project1.ActiveBuildMode := TProjectBuildMode(ModeList[i]);
if not BuildOneMode(LastMode) then Exit;
end;
// Switch back to original mode.
Project1.ActiveBuildMode := ActiveMode;
LazarusIDE.DoSaveProject([]);
IDEMessageDialog(lisSuccess, Format(lisSelectedModesWereCompiled, [ModeCnt]),
mtInformation, [mbOK]);
Result:=True;
finally
ModeList.Free;
BMList.Free;
end;
end;
function CheckDirIsInSearchPath(UnitInfo: TUnitInfo;
AllowAddingDependencies, IsIncludeFile: Boolean): Boolean;
// Check if the given unit's path is on Unit- or Include-search path.
// Returns true if it is OK to add the unit to current project.
var
CurDirectory, CurPath, ShortDir: String;
Owners: TFPList;
APackage: TLazPackage;
i: Integer;
begin
Result:=True;
if UnitInfo.IsVirtual then exit;
if IsIncludeFile then
CurPath:=Project1.CompilerOptions.GetIncludePath(false)
else
CurPath:=Project1.CompilerOptions.GetUnitPath(false);
CurDirectory:=AppendPathDelim(UnitInfo.GetDirectory);
if SearchDirectoryInSearchPath(CurPath,CurDirectory)<1 then
begin
if AllowAddingDependencies then begin
Owners:=PkgBoss.GetPossibleOwnersOfUnit(UnitInfo.Filename,[]);
try
if (Owners<>nil) then begin
for i:=0 to Owners.Count-1 do begin
if TObject(Owners[i]) is TLazPackage then begin
APackage:=TLazPackage(Owners[i]);
if IDEMessageDialog(lisAddPackageRequirement,
Format(lisAddPackageToProject, [APackage.IDAsString]),
mtConfirmation,[mbYes,mbCancel],'')<>mrYes
then
Exit(True);
PkgBoss.AddProjectDependency(Project1,APackage);
Exit(False);
end;
end;
end;
finally
Owners.Free;
end;
end;
// unit is not in a package => extend unit path
ShortDir:=CurDirectory;
if (not Project1.IsVirtual) then
ShortDir:=CreateRelativePath(ShortDir,Project1.Directory);
Result:=AddPathToBuildModes(ShortDir,CurDirectory,IsIncludeFile);
end;
end;
{ TBuildModesForm }
constructor TBuildModesForm.Create(AOwner: TComponent);
@ -615,5 +796,53 @@ begin
end;
end;
{ TBuildModesCheckList }
constructor TBuildModesCheckList.Create(DlgMsg: String);
begin
FListForm:=TGenericCheckListForm.Create(Nil);
//lisApplyForBuildModes = 'Apply for build modes:';
FListForm.Caption:=lisAvailableProjectBuildModes;
FListForm.InfoLabel.Caption:=DlgMsg;
end;
destructor TBuildModesCheckList.Destroy;
var
i: Integer;
BM: String;
begin
// Remember selected items before freeing the CheckListBox.
EnvironmentOptions.ManyBuildModesSelection.Clear;
for i:=0 to FListForm.CheckListBox1.Items.Count-1 do
begin
if FListForm.CheckListBox1.Checked[i] then
begin
BM:=FListForm.CheckListBox1.Items[i];
EnvironmentOptions.ManyBuildModesSelection.Add(BM);
end;
end;
FListForm.Free;
inherited Destroy;
end;
function TBuildModesCheckList.IsSelected(AIndex: Integer): Boolean;
begin
Result := FListForm.CheckListBox1.Checked[AIndex];
end;
function TBuildModesCheckList.Show: Boolean;
var
i: Integer;
BM: String;
begin
for i:=0 to Project1.BuildModes.Count-1 do begin
BM:=Project1.BuildModes[i].Identifier;
FListForm.CheckListBox1.Items.Add(BM);
if EnvironmentOptions.ManyBuildModesSelection.IndexOf(BM) >= 0 then
FListForm.CheckListBox1.Checked[i]:=True;
end;
Result:=FListForm.ShowModal=mrOK;
end;
end.

View File

@ -548,6 +548,7 @@ type
FMakeFileHistory: TStringList;
FTestBuildDirHistory: TStringList;
FCompilerMessagesFileHistory: TStringList;
FManyBuildModesSelection: TStringList;
FBuildMatrixOptions: TBuildMatrixOptions;
FIsGlobalMode: TStrToBoolEvent;
@ -812,6 +813,7 @@ type
property CompilerMessagesFilename: string read GetCompilerMessagesFilename
write SetCompilerMessagesFilename; // non English translation file
property CompilerMessagesFileHistory: TStringList read FCompilerMessagesFileHistory;
property ManyBuildModesSelection: TStringList read FManyBuildModesSelection;
// Primary-config verification
property LastCalledByLazarusFullPath: String read FLastCalledByLazarusFullPath write FLastCalledByLazarusFullPath;
@ -1709,6 +1711,7 @@ begin
FTestBuildDirHistory:=TStringList.Create;
CompilerMessagesFilename:='';
FCompilerMessagesFileHistory:=TStringList.Create;
FManyBuildModesSelection:=TStringList.Create;
// recent files and directories
FRecentOpenFiles:=TStringList.Create;
@ -1786,6 +1789,7 @@ begin
FreeAndNil(FDebuggerFileHistory);
for i := 0 to FDebuggerProperties.Count - 1 do
FDebuggerProperties.Objects[i].Free;
FreeAndNil(FManyBuildModesSelection);
FreeAndNil(FDebuggerProperties);
FreeAndNil(FTestBuildDirHistory);
FreeAndNil(FCompilerMessagesFileHistory);
@ -1932,6 +1936,7 @@ begin
GetDefaultTestBuildDirs(FTestBuildDirHistory);
CompilerMessagesFilename:=FXMLCfg.GetValue(Path+'CompilerMessagesFilename/Value',CompilerMessagesFilename);
LoadRecentList(FXMLCfg,FCompilerMessagesFileHistory,Path+'CompilerMessagesFilename/History/',rltFile);
LoadRecentList(FXMLCfg,FManyBuildModesSelection,Path+'ManyBuildModesSelection/',rltCaseInsensitive);
// Primary-config verification
FLastCalledByLazarusFullPath:=FXMLCfg.GetValue(Path+'LastCalledByLazarusFullPath/Value','');
@ -2316,6 +2321,7 @@ begin
SaveRecentList(FXMLCfg,FTestBuildDirHistory,Path+'TestBuildDirectory/History/');
FXMLCfg.SetDeleteValue(Path+'CompilerMessagesFilename/Value',CompilerMessagesFilename,'');
SaveRecentList(FXMLCfg,FCompilerMessagesFileHistory,Path+'CompilerMessagesFilename/History/');
SaveRecentList(FXMLCfg,FManyBuildModesSelection,Path+'ManyBuildModesSelection/');
// Primary-config verification
FXMLCfg.SetDeleteValue(Path+'LastCalledByLazarusFullPath/Value',FLastCalledByLazarusFullPath,'');

View File

@ -34,8 +34,6 @@
</BuildModes>
<PublishOptions>
<Version Value="2"/>
<IncludeFileFilter Value="*.(pas|pp|inc|lfm|lpr|lrs|lpi|lpk|sh|xml)"/>
<ExcludeFileFilter Value="*.(bak|ppu|ppw|o|so);*~;backup"/>
</PublishOptions>
<RunParams>
<FormatVersion Value="2"/>
@ -880,6 +878,7 @@
<Unit134>
<Filename Value="dialogprocs.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="DialogProcs"/>
</Unit134>
<Unit135>
<Filename Value="abstractsmethodsdlg.pas"/>
@ -1013,6 +1012,7 @@
<Unit162>
<Filename Value="publishmodule.pas"/>
<IsPartOfProject Value="True"/>
<UnitName Value="PublishModule"/>
</Unit162>
<Unit163>
<Filename Value="checkcompileropts.pas"/>
@ -1061,12 +1061,12 @@
<IsPartOfProject Value="True"/>
</Unit172>
<Unit173>
<Filename Value="publishprojectdlg.pas"/>
<Filename Value="publishmoduledlg.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="PublishProjectDialog"/>
<ComponentName Value="PublishModuleDialog"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="PublishProjectDlg"/>
<UnitName Value="PublishModuleDlg"/>
</Unit173>
<Unit174>
<Filename Value="findoverloadsdlg.pas"/>
@ -1123,11 +1123,14 @@
<Filename Value="genericchecklist.pas"/>
<IsPartOfProject Value="True"/>
<HasResources Value="True"/>
<UnitName Value="GenericCheckList"/>
</Unit184>
<Unit185>
<Filename Value="patheditordlg.pas"/>
<IsPartOfProject Value="True"/>
<ComponentName Value="PathEditorDialog"/>
<HasResources Value="True"/>
<ResourceBaseClass Value="Form"/>
<UnitName Value="PathEditorDlg"/>
</Unit185>
<Unit186>

View File

@ -6171,7 +6171,6 @@ resourcestring
regdlgOctal = 'Octal';
regdlgBinary = 'Binary';
regdlgRaw = 'Raw';
// Event log dialog
lisEventLogOptions = 'Event Log Options ...';
lisEventLogClear = 'Clear Events';
@ -6179,9 +6178,10 @@ resourcestring
lisEventsLogAddComment = 'Add Comment ...';
lisEventsLogAddComment2 = 'Add Comment';
lisCleanUpAndBuildProject = 'Clean up and build project';
lisBuildFollowingModes = 'Build the following modes';
lisSelectedModesWereBuilt = 'Selected %d modes were successfully built.';
// Many Build Modes
lisCompileFollowingModes = 'Compile the following modes';
lisPleaseSelectAtLeastOneBuildMode = 'Please select at least one build mode';
lisSelectedModesWereCompiled = 'Selected %d modes were successfully compiled.';
// Clean Build Project Dialog
lisProjectOutputDirectory = 'Project output directory';
lisProjectSourceDirectories = 'Project source directories';

View File

@ -85,9 +85,8 @@ uses
// protocol
IDEProtocol,
// compile
CompilerOptions, CheckCompilerOpts, BuildProjectDlg,
ApplicationBundle,
ExtTools, ExtToolsIDE,
CompilerOptions, CheckCompilerOpts, BuildProjectDlg, BuildModesManager,
ApplicationBundle, ExtTools, ExtToolsIDE,
// projects
ProjectResources, Project, ProjectDefs, NewProjectDlg,
PublishModuleDlg, ProjectInspector, PackageDefs, ProjectDescriptors,
@ -4287,14 +4286,14 @@ end;
procedure TMainIDE.mnuCleanUpAndBuildProjectClicked(Sender: TObject);
begin
if SourceFileMgr.PrepareForCompileWithMsg<>mrOk then exit;
if PrepareForCompileWithMsg<>mrOk then exit;
if ShowBuildProjectDialog(Project1)<>mrOk then exit;
DoBuildProject(crBuild,[]);
end;
procedure TMainIDE.mnuBuildManyModesClicked(Sender: TObject);
begin
SourceFileMgr.BuildManyModes;
BuildManyModes;
end;
procedure TMainIDE.mnuAbortBuildProjectClicked(Sender: TObject);
@ -6696,7 +6695,7 @@ begin
exit(mrCancel);
end;
Result:=SourceFileMgr.PrepareForCompileWithMsg;
Result:=PrepareForCompileWithMsg;
if Result<>mrOk then begin
debugln(['Error: (lazarus) [TMainIDE.DoBuildProject] PrepareForCompile failed']);
exit;
@ -12319,7 +12318,7 @@ begin
BeginCodeTool(ActiveSourceEditor,ActiveUnitInfo,[]);
OkToAdd:=True;
if FilenameIsPascalUnit(AnUnitInfo.Filename) then begin
OkToAdd:=SourceFileMgr.CheckDirIsInSearchPath(AnUnitInfo,False,False);
OkToAdd:=CheckDirIsInSearchPath(AnUnitInfo,False,False);
if (pfMainUnitHasUsesSectionForAllUnits in Project1.Flags) then begin
AnUnitInfo.ReadUnitNameFromSource(false);
ShortUnitName:=AnUnitInfo.Unit_Name;
@ -12336,7 +12335,7 @@ begin
end;
end
else if CompareFileExt(AnUnitInfo.Filename,'inc',false)=0 then
OkToAdd:=SourceFileMgr.CheckDirIsInSearchPath(AnUnitInfo,False,True);
OkToAdd:=CheckDirIsInSearchPath(AnUnitInfo,False,True);
if OkToAdd then
;
Project1.Modified:=true;

View File

@ -311,6 +311,7 @@ type
end;
function GetMainIde: TMainIDEBase;
function PrepareForCompileWithMsg: TModalResult; // Ensure starting compilation is OK.
property MainIDE: TMainIDEBase read GetMainIde;
@ -326,6 +327,17 @@ begin
Result := TMainIDEBase(MainIDEInterface)
end;
function PrepareForCompileWithMsg: TModalResult;
begin
Result:=mrCancel;
if Project1=nil then exit;
if Project1.MainUnitInfo=nil then
// this project has no source to compile
IDEMessageDialog(lisCanNotCompileProject,lisTheProjectHasNoMainSourceFile,mtError,[mbCancel])
else
Result:=MainIDE.PrepareForCompile;
end;
{ TSetBuildModeToolButton.TBuildModeMenu }
procedure TSetBuildModeToolButton.TBuildModeMenu.DoPopup(Sender: TObject);

View File

@ -52,7 +52,7 @@ uses
MainBase, MainBar, MainIntf, Project, ProjectDefs, ProjectInspector, CompilerOptions,
SourceSynEditor, SourceEditor, EditorOptions, EnvironmentOpts, CustomFormEditor,
ControlSelection, FormEditor, EmptyMethodsDlg, BaseDebugManager, TransferMacros,
BuildManager, EditorMacroListViewer, FindRenameIdentifier, GenericCheckList,
BuildManager, EditorMacroListViewer, FindRenameIdentifier, BuildModesManager,
ViewUnit_Dlg, DiskDiffsDialog, InputHistory, CheckLFMDlg, etMessagesWnd,
ConvCodeTool, BasePkgManager, PackageDefs, PackageSystem, Designer, DesignerProcs;
@ -170,15 +170,12 @@ type
TLazSourceFileManager = class
private
FProject: TProject;
FListForm: TGenericCheckListForm;
FCheckFilesOnDiskNeeded: boolean;
function AskToSaveEditors(EditorList: TList): TModalResult;
function AddPathToBuildModes(aPath, CurDirectory: string; IsIncludeFile: Boolean): Boolean;
function CheckMainSrcLCLInterfaces(Silent: boolean): TModalResult;
function FileExistsInIDE(const Filename: string;
SearchFlags: TProjectFileSearchFlags): boolean;
procedure RemovePathFromBuildModes(ObsoletePaths: String; pcos: TParsedCompilerOptString);
function ShowCheckListBuildModes(DlgMsg: String): Boolean;
public
constructor Create;
destructor Destroy; override;
@ -236,16 +233,6 @@ type
procedure CloseAll;
procedure InvertedFileClose(PageIndex: LongInt; SrcNoteBook: TSourceNotebook);
// Ensure compilation is OK, build many modes at one go.
function PrepareForCompileWithMsg: TModalResult;
function BuildManyModes: Boolean;
// Project Inspector
// Checks if the UnitDirectory is part of the Unit Search Paths, if not,
// ask the user if he wants to extend dependencies or the Unit Search Paths.
function CheckDirIsInSearchPath(UnitInfo: TUnitInfo; AllowAddingDependencies, IsIncludeFile: Boolean): Boolean;
private
// methods for 'new unit'
function CreateNewCodeBuffer(Descriptor: TProjectFileDescriptor;
@ -4456,179 +4443,6 @@ begin
end;
end;
function TLazSourceFileManager.ShowCheckListBuildModes(DlgMsg: String): Boolean;
var
i: Integer;
begin
FListForm:=TGenericCheckListForm.Create(Nil);
//lisApplyForBuildModes = 'Apply for build modes:';
FListForm.Caption:=lisAvailableProjectBuildModes;
FListForm.InfoLabel.Caption:=DlgMsg;
for i:=0 to Project1.BuildModes.Count-1 do begin
FListForm.CheckListBox1.Items.Add(Project1.BuildModes[i].Identifier);
FListForm.CheckListBox1.Checked[i]:=True;
end;
Result:=FListForm.ShowModal=mrOK;
end;
function TLazSourceFileManager.AddPathToBuildModes(aPath, CurDirectory: string;
IsIncludeFile: Boolean): Boolean;
var
DlgCapt, DlgMsg: String;
i: Integer;
Ok: Boolean;
begin
Result:=True;
FListForm:=Nil;
try
if IsIncludeFile then begin
DlgCapt:=lisAddToIncludeSearchPath;
DlgMsg:=lisTheNewIncludeFileIsNotYetInTheIncludeSearchPathAdd;
end
else begin
DlgCapt:=lisAddToUnitSearchPath;
DlgMsg:=lisTheNewUnitIsNotYetInTheUnitSearchPathAddDirectory;
end;
DlgMsg:=Format(DlgMsg,[LineEnding,CurDirectory]);
if Project1.BuildModes.Count > 1 then
Ok:=ShowCheckListBuildModes(DlgMsg)
else
Ok:=IDEMessageDialog(DlgCapt,DlgMsg,mtConfirmation,[mbYes,mbNo])=mrYes;
if not Ok then Exit(False);
for i:=0 to Project1.BuildModes.Count-1 do
if (FListForm=Nil) or FListForm.CheckListBox1.Checked[i] then
if IsIncludeFile then
Project1.BuildModes[i].CompilerOptions.MergeToIncludePaths(aPath)
else
Project1.BuildModes[i].CompilerOptions.MergeToUnitPaths(aPath);
finally
FListForm.Free;
end;
end;
function TLazSourceFileManager.PrepareForCompileWithMsg: TModalResult;
begin
Result:=mrCancel;
if Project1=nil then exit;
if Project1.MainUnitInfo=nil then
// this project has no source to compile
IDEMessageDialog(lisCanNotCompileProject,lisTheProjectHasNoMainSourceFile,mtError,[mbCancel])
else
Result:=MainIDE.PrepareForCompile;
end;
function TLazSourceFileManager.BuildManyModes(): Boolean;
var
ModeCnt: Integer;
function BuildOneMode(LastMode: boolean): Boolean;
begin
Inc(ModeCnt);
DebugLn('');
DebugLn(Format('Building mode %d: %s ...', [ModeCnt, Project1.ActiveBuildMode.Identifier]));
DebugLn('');
Result := MainIDE.DoBuildProject(crCompile, [], LastMode) = mrOK;
end;
var
ModeList: TList;
md, ActiveMode: TProjectBuildMode;
BuildActiveMode: Boolean;
i: Integer;
LastMode: boolean;
begin
Result := False;
ModeCnt := 0;
if PrepareForCompileWithMsg <> mrOk then exit;
FListForm := Nil;
ModeList := TList.Create;
try
if not ShowCheckListBuildModes(lisBuildFollowingModes) then Exit;
ActiveMode := Project1.ActiveBuildMode;
BuildActiveMode := False;
// Collect modes to be built.
for i := 0 to Project1.BuildModes.Count-1 do
begin
md := Project1.BuildModes[i];
if (FListForm=Nil) or FListForm.CheckListBox1.Checked[i] then
if md = ActiveMode then
BuildActiveMode := True
else
ModeList.Add(md);
end;
// Build first the active mode so we don't have to switch many times.
if BuildActiveMode then
begin
LastMode := (ModeList.Count=0);
if not BuildOneMode(LastMode) then Exit;
end;
// Build rest of the modes.
for i := 0 to ModeList.Count-1 do
begin
LastMode := (i=(ModeList.Count-1));
Project1.ActiveBuildMode := TProjectBuildMode(ModeList[i]);
if not BuildOneMode(LastMode) then Exit;
end;
// Switch back to original mode.
Project1.ActiveBuildMode := ActiveMode;
SaveProject([]);
IDEMessageDialog(lisSuccess, Format(lisSelectedModesWereBuilt, [ModeCnt]),
mtInformation, [mbOK]);
Result:=True;
finally
ModeList.Free;
FListForm.Free;
end;
end;
function TLazSourceFileManager.CheckDirIsInSearchPath(UnitInfo: TUnitInfo;
AllowAddingDependencies, IsIncludeFile: Boolean): Boolean;
// Check if the given unit's path is on Unit- or Include-search path.
// Returns true if it is OK to add the unit to current project.
var
CurDirectory, CurPath, ShortDir: String;
Owners: TFPList;
APackage: TLazPackage;
i: Integer;
begin
Result:=True;
if UnitInfo.IsVirtual then exit;
if IsIncludeFile then
CurPath:=Project1.CompilerOptions.GetIncludePath(false)
else
CurPath:=Project1.CompilerOptions.GetUnitPath(false);
CurDirectory:=AppendPathDelim(UnitInfo.GetDirectory);
if SearchDirectoryInSearchPath(CurPath,CurDirectory)<1 then
begin
if AllowAddingDependencies then begin
Owners:=PkgBoss.GetPossibleOwnersOfUnit(UnitInfo.Filename,[]);
try
if (Owners<>nil) then begin
for i:=0 to Owners.Count-1 do begin
if TObject(Owners[i]) is TLazPackage then begin
APackage:=TLazPackage(Owners[i]);
if IDEMessageDialog(lisAddPackageRequirement,
Format(lisAddPackageToProject, [APackage.IDAsString]),
mtConfirmation,[mbYes,mbCancel],'')<>mrYes
then
Exit(True);
PkgBoss.AddProjectDependency(Project1,APackage);
Exit(False);
end;
end;
end;
finally
Owners.Free;
end;
end;
// unit is not in a package => extend unit path
ShortDir:=CurDirectory;
if (not Project1.IsVirtual) then
ShortDir:=CreateRelativePath(ShortDir,Project1.Directory);
Result:=AddPathToBuildModes(ShortDir,CurDirectory,IsIncludeFile);
end;
end;
function TLazSourceFileManager.CreateNewCodeBuffer(Descriptor: TProjectFileDescriptor;
NewOwner: TObject; NewFilename: string;
var NewCodeBuffer: TCodeBuffer; var NewUnitName: string): TModalResult;