2

ハードコーディングされたパスを使用してGoogle Earthプロセスを開始する次のコード フラグメントがあります。

var process =
    new Process
        {
            StartInfo =
                {
                    //TODO: Get location of google earth executable from registry
                    FileName = @"C:\Program Files\Google\Google Earth\googleearth.exe",
                    Arguments = "\"" + kmlPath + "\""
                }
        };
process.Start();

プログラムでgoogleearth.exeのインストール場所をどこか (おそらくレジストリ) から取得したいと考えています。

4

4 に答える 4

4

与えられた例から、私が実際に KML ファイルを Google Earth に渡そうとしていることがわかります。このため、この問題を解決する最も簡単な方法は、KML と Google Earth のファイルの関連付けに依存し、例全体の代わりに以下を使用することです。

Process.Start(kmlPath);

これは、この質問に対する回答を確認することで見つかりました。

于 2008-10-10T13:30:58.377 に答える
4

プログラムに関連付けられた特定のファイルを開く場合は、そのファイルを介して起動することをお勧めします (たとえば、ユーザーが使用したいファイル タイプに関連付けられたプログラムを持っている場合など)。

これは、特定のファイルの種類に関連付けられたアプリケーションを起動するために過去に使用した方法ですが、実際にはファイルを開かない方法です。もっと良い方法があるかもしれません。

static Regex pathArgumentsRegex = new Regex(@"(%\d+)|(""%\d+"")", RegexOptions.ExplicitCapture);
static string GetPathAssociatedWithFileExtension(string extension)
{
    RegistryKey extensionKey = Registry.ClassesRoot.OpenSubKey(extension);
    if (extensionKey != null)
    {
        object applicationName = extensionKey.GetValue(string.Empty);
        if (applicationName != null)
        {
            RegistryKey commandKey = Registry.ClassesRoot.OpenSubKey(applicationName.ToString() + @"\shell\open\command");
            if (commandKey != null)
            {
                object command = commandKey.GetValue(string.Empty);
                if (command != null)
                {
                    return pathArgumentsRegex.Replace(command.ToString(), "");
                }
            }
        }
    }
    return null;
}

ファイルを開かずに特定のプログラムを起動したい場合もあります。通常、(願わくば) プログラムには、インストール場所を含むレジストリ エントリがあります。このような方法で Google Earth を起動する方法の例を次に示します。

private static string GetGoogleEarthExePath()
{
    RegistryKey googleEarthRK = Registry.CurrentUser.OpenSubKey(@"Software\Google\Google Earth Plus\");
    if (googleEarthRK != null)
    {
        object rootDir = googleEarthRK.GetValue("InstallLocation");
        if (rootDir != null)
        {
            return Path.Combine(rootDir.ToString(), "googleearth.exe");
        }
    }

    return null;
}
于 2008-10-11T15:57:00.407 に答える
3

これも機能します: (C# コード)

        Type type = Type.GetTypeFromProgID("WindowsInstaller.Installer");
        Installer msi = (Installer)Activator.CreateInstance(type);
        foreach (string productcode in msi.Products)
        {
            string productname = msi.get_ProductInfo(productcode, "InstalledProductName");
            if (productname.Contains("Google Earth"))
            {
                string installdir = msi.get_ProductInfo(productcode, "InstallLocation");
                Console.WriteLine("{0}: {1} @({2})", productcode, productname, installdir);
            }
        }
于 2009-08-20T22:33:48.780 に答える
1

これが私が書かなければならなかったC++バージョンです。ICRのC#バージョンから直接取得。

void PrintString(CString string)
{
    std::wcout << static_cast<LPCTSTR>(string) << endl;
}

CString GetClassesRootKeyValue(const wchar_t * keyName)
{
    HKEY hkey;
    TCHAR keyNameCopy[256] = {0};
    _tcscpy_s(keyNameCopy, 256, keyName);
    BOOL bResult = SUCCEEDED(::RegOpenKey(HKEY_CLASSES_ROOT, keyNameCopy, &hkey));
    CString hkeyValue = CString("");
    if (bResult) {
        TCHAR temporaryValueBuffer[256];
        DWORD bufferSize = sizeof (temporaryValueBuffer);
        DWORD type;
        bResult = SUCCEEDED(RegQueryValueEx(hkey, _T(""), NULL, &type, (BYTE*)temporaryValueBuffer, &bufferSize)) && (bufferSize > 1);
        if (bResult) {
            hkeyValue = CString(temporaryValueBuffer);
        }
        RegCloseKey(hkey);
        return hkeyValue;
    }
    return hkeyValue;
}


int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{
    int nRetCode = 0;

    // initialize MFC and print and error on failure
    if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
    {
        // TODO: change error code to suit your needs
        _tprintf(_T("Fatal Error: MFC initialization failed\n"));
        nRetCode = 1;
    }
    else
    {

        CString dwgAppName = GetClassesRootKeyValue(_T(".dwg"));
        PrintString(dwgAppName);

        dwgAppName.Append(_T("\\shell\\open\\command"));
        PrintString(dwgAppName);

        CString trueViewOpenCommand = GetClassesRootKeyValue(static_cast<LPCTSTR>(dwgAppName));
        PrintString(trueViewOpenCommand);

        //  Shell open command usually ends with a "%1" for commandline params.  We don't want that,
        //  so strip it off.
        int firstParameterIndex = trueViewOpenCommand.Find(_T("%"));
        PrintString(trueViewOpenCommand.Left(firstParameterIndex).TrimRight('"').TrimRight(' '));


        cout << "\n\nPress <enter> to exit...";
        getchar();
    }
}
于 2009-05-02T02:31:21.143 に答える