秋·风

  博客园 :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::

为lazarus生成的linux程序提供相关的快捷访问方式,参考fpcupdeluxe源码,编写了一个通用的CreateDesktopShortCut,只要调用CreateDesktopShortCut就可以生成相应的快捷方式及文件关联。
注意:文件关联时的图标用png格式

开始菜单程序名称存放路径:
/home/用户名/.local/share/applications

文件关联放以下2个路径:
/home/用户名/.local/share/mime/application
/home/用户名/.local/share/mime/packages 

桌面快捷方式存放路径:
/home/用户名/桌面

unit Unit1;

{$mode objfpc}{$H+}

interface

uses
  Classes, SysUtils, Forms, Controls, Graphics, Dialogs, StdCtrls, Buttons,
  IniFiles, BaseUnix, FileUtil, process
;

type

  { TForm1 }

  TForm1 = class(TForm)
    Button1: TButton;
    Edit1: TEdit;
    Edit2: TEdit;
    Edit3: TEdit;
    Edit5: TEdit;
    Edit7: TEdit;
    Edit6: TEdit;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Label4: TLabel;
    Label5: TLabel;
    Label6: TLabel;
    OpenDialog1: TOpenDialog;
    SpeedButton1: TSpeedButton;
    SpeedButton2: TSpeedButton;
    procedure Button1Click(Sender: TObject);
    procedure SpeedButton1Click(Sender: TObject);
    procedure SpeedButton2Click(Sender: TObject);
  private

  public

  end;

var
  Form1: TForm1;

implementation

{$R *.lfm}

{ TForm1 }

function ForceDirectoriesSafe(Const Dir: RawByteString): Boolean;
var
  aDir:RawByteString;
begin
  result:=true;
  if (Length(Dir)=0) then exit;
  aDir:=ExcludeTrailingPathDelimiter(Dir);
  if (Length(aDir)=0) then exit;
  if (NOT DirectoryExists(aDir)) then
    result:=ForceDirectories(aDir);
end;

procedure CreateDesktopShortCut(Target,Execs,icons,filetypes,FileExt, ShortcutName: string);
var
  OperationSucceeded: boolean;
  ResultCode: boolean;
  XdgDesktopContent: TStringList;
  XdgMimeContent: TStringList;
  Output,XdgDesktopFile,XdgMimeFile: string;
  aDirectory:string;
  i,j:integer;
  AddContext:boolean;
  ft:TStrings;
begin
  ft:=TStringList.Create;
  ft.Delimiter:=';';
  ft.DelimitedText:=FileExt;
  j:=ft.Count;
  if (j>0) and (filetypes<>'') then AddContext:=true
  ELSE addcontext:=false;

  // Fail by default:
  OperationSucceeded:=false;

  XdgDesktopFile:=IncludeTrailingPathDelimiter(GetTempDir(false))+shortcutname+'.desktop';
  XdgDesktopContent:=TStringList.Create;
  try
    XdgDesktopContent.Add('[Desktop Entry]');
    XdgDesktopContent.Add('Version=1.0');
    XdgDesktopContent.Add('Encoding=UTF-8');
    XdgDesktopContent.Add('Type=Application');
    XdgDesktopContent.Add('Icon='+icons);
    XdgDesktopContent.Add('Exec='+execs+' %u');
    XdgDesktopContent.Add('Name='+ShortcutName);
    XdgDesktopContent.Add('Category=Application;');
    XdgDesktopContent.Add('Categories=Application;Programming;');

    if AddContext then
    begin
      XdgDesktopContent.Add('MimeType=application/x-'+filetypes+';');
    end;

    try
      XdgDesktopContent.SaveToFile(XdgDesktopFile);
      FpChmod(XdgDesktopFile, &711); //rwx--x--x
      OperationSucceeded:=RunCommand('xdg-desktop-icon' ,['install','--novendor',XdgDesktopFile],Output,[poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});
      OperationSucceeded:=RunCommand('xdg-desktop-menu' ,['install','--novendor',XdgDesktopFile],Output,[poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});
    except
      OperationSucceeded:=false;
    end;

    if (true) then
    begin
      aDirectory:=ConcatPaths(['usr','share','applications']);
      if ( (FpGeteuid=0) AND DirectoryExists(aDirectory) ) then
      begin
        FileUtil.CopyFile(XdgDesktopFile,aDirectory+DirectorySeparator+ExtractFileName(XdgDesktopFile),[]);
      end
      else
      begin
        // Create shortcut directly on User-Desktop
        aDirectory:=ConcatPaths([GetUserDir,'Desktop']);
        if DirectoryExists(aDirectory) then
           FileUtil.CopyFile(XdgDesktopFile,aDirectory+DirectorySeparator+ExtractFileName(XdgDesktopFile),[]);
        // Create user menu item
        if (NOT OperationSucceeded) then
        begin
          aDirectory:=ConcatPaths([GetUserDir,'.local','share','applications']);
          if DirectoryExists(aDirectory) then
            FileUtil.CopyFile(XdgDesktopFile,aDirectory+DirectorySeparator+ExtractFileName(XdgDesktopFile),[]);
        end;
      end;
    end;
    // Temp file is no longer needed....
    try
      SysUtils.DeleteFile(XdgDesktopFile);
    finally
      // Swallow, let filesystem maintenance clear it up
    end;
  finally
    XdgDesktopContent.Free;
    OperationSucceeded:=true;
  end;

  if (OperationSucceeded) then
  begin
    aDirectory:=ConcatPaths([GetUserDir,'.local','share','applications']);
    OperationSucceeded:=RunCommand('update-desktop-database' ,[aDirectory],Output,[poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});
  end;
  if AddContext then
  begin
    {$ifdef LCL}
    Application.ProcessMessages;
    {$endif}

    aDirectory:=ConcatPaths([GetUserDir,'.local','share','mime']);
    ForceDirectoriesSafe(aDirectory);

    //Create mime file associations
    XdgMimeFile:=IncludeTrailingPathDelimiter(GetTempDir(false))+shortcutname+'.xml';
    XdgMimeContent:=TStringList.Create;
    try
      XdgMimeContent.Add('<?xml version="1.0" encoding="UTF-8"?>');
      XdgMimeContent.Add('<mime-info xmlns="http://www.freedesktop.org/standards/shared-mime-info">');
      XdgMimeContent.Add('    <mime-type type="application/x-'+filetypes+'">');
      XdgMimeContent.Add('        <comment>TEXT file</comment>');
      XdgMimeContent.Add('        <icon name="application-x-'+filetypes+'"/>');
      XdgMimeContent.Add('        <glob-deleteall/>');
      for i:=0 to j-1 do
      begin
        XdgMimeContent.Add('        <glob pattern="'+ft[i]+'"/>');
      end;
      XdgMimeContent.Add('    </mime-type>');
      XdgMimeContent.Add('</mime-info>');
      aDirectory:=ConcatPaths([GetUserDir,'.local','share','mime','packages']);
      ForceDirectoriesSafe(aDirectory);
      XdgMimeContent.SaveToFile(XdgMimeFile);
      OperationSucceeded:=RunCommand('xdg-mime' ,['install','--novendor',XdgMimeFile],Output,[poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});
      SysUtils.DeleteFile(XdgMimeFile);
    finally
      XdgMimeContent.Free;
    end;

    //Process icon
    aDirectory:=ConcatPaths([GetUserDir,'.local','share','icons']);
    ForceDirectoriesSafe(aDirectory);
    OperationSucceeded:=RunCommand('xdg-icon-resource' ,['install','--novendor',
    '--context','mimetypes','--size','64',icons,'application-x-'+filetypes+''],Output,
    [poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});

    //Update mime database
    aDirectory:=ConcatPaths([GetUserDir,'.local','share','mime']);
    OperationSucceeded:=RunCommand('update-mime-database' ,[aDirectory],Output,
    [poUsePipes, poStderrToOutPut]{$IF DEFINED(FPC_FULLVERSION) AND (FPC_FULLVERSION >= 30200)},swoHide{$ENDIF});
  end;
  ft.free;

end;


procedure TForm1.Button1Click(Sender: TObject);
var aDirectory,vFileName,Output,deskname:String;
begin
  deskname:=edit1.Text;
  aDirectory := ConcatPaths([GetUserDir, '桌面']);
  if not DirectoryExists(aDirectory) then
      aDirectory := ConcatPaths([GetUserDir, 'Desktop']);
  CreateDesktopShortCut(aDirectory,edit2.text,edit5.text,Edit6.text,Edit7.text,deskname);
end;

procedure TForm1.SpeedButton1Click(Sender: TObject);
begin
  if opendialog1.Execute then
  Begin
     edit2.Text:= opendialog1.FileName;
     edit1.Text:=ExtractFileName(edit2.Text);
  end;
end;

procedure TForm1.SpeedButton2Click(Sender: TObject);
begin
  if opendialog1.Execute then
  Begin
     edit5.Text:= opendialog1.FileName;
  end;

end;

end.



 

posted on 2022-06-28 07:26  秋·风  阅读(651)  评论(0编辑  收藏  举报