Recent

Author Topic: [SOLVED] Browsing For Folder in Linux  (Read 451 times)

Sandstone

  • New Member
  • *
  • Posts: 11
[SOLVED] Browsing For Folder in Linux
« on: November 02, 2020, 02:44:49 am »
I have some existing Pascal Windows code I'm trying to port for Linux and am getting multiple errors:

function TMainForm.BrowseForFolder(var Path: string): Boolean;
var
  BI: TBrowseInfo;
  p: PItemIDList;
  s, t: string;
const
  BIF_NONEWFOLDERBUTTON = $00000200;
begin
  Result := False;
  ZeroMemory(@BI,SizeOf(BI));
  SetLength(t,MAX_PATH);
  with BI do begin
    hwndOwner := Handle;
    pidlRoot := nil;
    pszDisplayName := PChar(t);
    lpszTitle := PChar(S_SelectPathToExplore);
    ulFlags := BIF_NEWDIALOGSTYLE or BIF_NONEWFOLDERBUTTON or BIF_RETURNONLYFSDIRS or BIF_VALIDATE;
  end;
  p := SHBrowseForFolder(BI);
  if Assigned(p) then
    try
      SetLength(s, MAX_PATH);
      if SHGetPathFromIDList(p, PChar(s)) then begin
        Result := True;
        Path := PChar(s);
      end;
    finally
      CoTaskMemFree(p);
    end;
end;

MainFormUnit.pas(2152,7) Error: Identifier not found "TBrowseInfo"
MainFormUnit.pas(2153,6) Error: Identifier not found "PItemIDList"
MainFormUnit.pas(2159,3) Error: Identifier not found "ZeroMemory"
MainFormUnit.pas(2162,5) Error: Identifier not found "hwndOwner"
MainFormUnit.pas(2163,5) Error: Identifier not found "pidlRoot"
MainFormUnit.pas(2164,5) Error: Identifier not found "pszDisplayName"
MainFormUnit.pas(2165,5) Error: Identifier not found "lpszTitle"
MainFormUnit.pas(2166,5) Error: Identifier not found "ulFlags"
MainFormUnit.pas(2166,16) Error: Identifier not found "BIF_NEWDIALOGSTYLE"
MainFormUnit.pas(2166,63) Error: Identifier not found "BIF_RETURNONLYFSDIRS"
MainFormUnit.pas(2166,87) Error: Identifier not found "BIF_VALIDATE"
MainFormUnit.pas(2168,8) Error: Identifier not found "SHBrowseForFolder"

Am I missing a package or unit that handles this?

Units I have are:
uses
  LCLIntf, LCLType, LMessages, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, IniFiles, StdCtrls, Grids, ComCtrls, Types,
  ExtCtrls, Buttons, Organ, ToolWin, Menus, VirtualTrees, ImgList,
  FakeActiveX,  CheckLst, ObjectMatrixFrameUnit,
  Themes,
  {project units}
  WoodFormUnit, ScanFormUnit, ExportFormUnit,
  WarningFormUnit, ConfigurationFormUnit, SplashFormUnit;                 
« Last Edit: November 06, 2020, 10:13:54 pm by Sandstone »

Handoko

  • Hero Member
  • *****
  • Posts: 4017
  • My goal: build my own game engine using Lazarus
Re: Browsing For Folder in Linux
« Reply #1 on: November 02, 2020, 04:19:56 am »
Free Pascal Compiler is a cross platform compiler. But that does not mean you can just compile all the source codes that work on a platform to other platforms. The codes must be written to support cross compiling, which usually mean not using any platform or OS specific function.

In the list of units you provided, I think these are not able to compile to Linux:
Organ, ToolWin, FakeActiveX, ObjectMatrixFramUnit.

The name ToolWin suggests it works on Windows only. And as far as I know Linux does not support ActiveX technology.

If you really want to make the existing BrowseForFolder code to be able to compile to Linux, you have some possible solutions:
- If you have the source codes of all the units, study them and manually convert them to Linux-friendly units
- Or you can share all of them on the forum and ask someone to help you if the licenses allow you to do that
- You can consider to create a bounty for the task

But I think the most easiest thing to do is abandon the code and write a new cross-compile-friendly code. Browse for folder does not sound difficult. Not exactly what you want but Lazarus itself has components that you can use or study: TOpenDialog, TFileListBox, TShellListView.

lucamar

  • Hero Member
  • *****
  • Posts: 3454
Re: Browsing For Folder in Linux
« Reply #2 on: November 02, 2020, 06:34:42 am »
All that code is entirely Windows-specific so you won't be able to make it work on Linux. Also, note that, generally speaking, Linux neither has or need a "Browse for folder" dialog, since most, if not all, of its funcions are present in the standard "Open file" dialog or its Lazarus specialization TSelectDirectory.

If you really want one looking more or less like the Windows one you might mimic it by building your own; the easiest way will probably be using a TShellListView, as Handoko said.

But if I were you I would just replace all that for a SelectDirectoryDialog for all platforms.
« Last Edit: November 02, 2020, 06:44:23 am by lucamar »
Turbo Pascal 3 CP/M - Amstrad PCW 8256 (512 KB !!!) :P
Lazarus/FPC 2.0.8/3.0.4 & 2.0.10/3.2.0 - 32/64 bits on:
(K|L|X)Ubuntu 12..18, Windows XP, 7, 10 and various DOSes.

Sandstone

  • New Member
  • *
  • Posts: 11
Re: Browsing For Folder in Linux
« Reply #3 on: November 02, 2020, 06:14:12 pm »
But I think the most easiest thing to do is abandon the code and write a new cross-compile-friendly code.

I expected that this would be where I would end up with this.  8-) No worries, I still have the Windows version that will run in Wine 5.0.2

GetMem

  • Hero Member
  • *****
  • Posts: 3807
Re: Browsing For Folder in Linux
« Reply #4 on: November 02, 2020, 08:55:19 pm »
@Sandstone

There is a crossplatform TSelectDirectoryDialog component(Dialog palette) shipped with Lazarus. If you check Options->ofOldStyleDialog it looks exactly like the one created with your BrowseForFolder function.

Bart

  • Hero Member
  • *****
  • Posts: 4113
    • Bart en Mariska's Webstek
Re: Browsing For Folder in Linux
« Reply #5 on: November 02, 2020, 09:21:55 pm »
If you insist on using the old function (so you don't have to change the code that is calling it), try something like this:

Code: Pascal  [Select][+][-]
  1. function TMainForm.BrowseForFolder(var Path: string): Boolean;
  2. var
  3.   Dlg: TSelectDirectoryDialog;
  4. begin
  5.   Dlg := TSelectDirectoryDialog.Create(nil);
  6.   try
  7.     Dlg.InitialDir := Path;
  8.     Result := Dlg.Execute;
  9.     if Result then
  10.       Path := Dlg.FileName;
  11.   finally
  12.    Dlg.Free;
  13.   end;
  14. end;

Bart

 

TinyPortal © 2005-2018