The Battle for Wesnoth  1.15.12+dev
open.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2013 - 2018 by Iris Morelle <shadowm2006@gmail.com>
3  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2 of the License, or
8  (at your option) any later version.
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY.
11 
12  See the COPYING file for more details.
13 */
14 
15 #include "desktop/open.hpp"
16 
17 #include "log.hpp"
19 
20 #if defined(_X11) || defined(__APPLE__)
21 
22 #include <thread>
23 
24 #include <sys/types.h>
25 #include <sys/wait.h>
26 #include <unistd.h> // fork(), exec family
27 
28 #elif defined(_WIN32)
29 
30 #ifndef UNICODE
31 #define UNICODE
32 #endif
33 #define WIN32_LEAN_AND_MEAN
34 
35 #include <windows.h>
36 #include <shellapi.h> // ShellExecute()
37 
38 #endif
39 
40 static lg::log_domain log_desktop("desktop");
41 #define ERR_DU LOG_STREAM(err, log_desktop)
42 #define LOG_DU LOG_STREAM(info, log_desktop)
43 
44 namespace desktop {
45 
46 bool open_object([[maybe_unused]] const std::string& path_or_url)
47 {
48  LOG_DU << "open_object(): requested object: " << path_or_url << '\n';
49 
50 #if defined(_X11) || defined(__APPLE__)
51 
52 #ifndef __APPLE__
53  LOG_DU << "open_object(): on X11, will use xdg-open\n";
54  const char launcher[] = "xdg-open";
55 #else
56  LOG_DU << "open_object(): on OS X, will use open\n";
57  const char launcher[] = "open";
58 #endif
59 
60  const pid_t child = fork();
61 
62  if(child == -1) {
63  ERR_DU << "open_object(): fork() failed" << std::endl;
64  return false;
65  } else if(child == 0) {
66  execlp(launcher, launcher, path_or_url.c_str(), nullptr);
67  _exit(1); // This shouldn't happen.
68  }
69 
70  std::thread t { [child](){ int status; waitpid(child, &status, 0); } };
71  t.detach();
72 
73  return true;
74 
75 #elif defined(_WIN32)
76 
77  LOG_DU << "open_object(): on Win32, will use ShellExecute()\n";
78 
79  std::wstring u16path = unicode_cast<std::wstring>(path_or_url);
80 
81  const ptrdiff_t res = reinterpret_cast<ptrdiff_t>(ShellExecute(nullptr, L"open", u16path.c_str(), nullptr, nullptr, SW_SHOW));
82  if(res <= 32) {
83  ERR_DU << "open_object(): ShellExecute() failed (" << res << ")" << std::endl;
84  return false;
85  }
86 
87  return true;
88 
89 #else
90 
91  ERR_DU << "open_object(): unsupported platform" << std::endl;
92  return false;
93 
94 #endif
95 }
96 
97 }
#define ERR_DU
Definition: open.cpp:41
ucs4_convert_impl::enableif< TD, typename TS::value_type >::type unicode_cast(const TS &source)
Desktop environment interaction functions.
#define LOG_DU
Definition: open.cpp:42
bool open_object([[maybe_unused]] const std::string &path_or_url)
Definition: open.cpp:46
double t
Definition: astarsearch.cpp:64
Standard logging facilities (interface).
static lg::log_domain log_desktop("desktop")