| 213 | } |
| 214 | |
| 215 | void PDFBridgeSumatra::OpenDocument(const PDFFile &pdfFile) { |
| 216 | auto pdfPath = pdfFile.getPath(); |
| 217 | |
| 218 | if (!filesystem::exists(pdfPath)) { // PDF file does not exist, do not attempt to load |
| 219 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "PDFBridgeSumatra PDF file '%s' does not exist", pdfPath.string().c_str()); |
| 220 | return; |
| 221 | } |
| 222 | this->pdfPathString = filesystem::canonical(pdfPath).wstring(); |
| 223 | |
| 224 | if (!this->InitializeDDE()) |
| 225 | return; |
| 226 | |
| 227 | this->StartDDEServer(this->szServerService, this->pdfPathString); |
| 228 | |
| 229 | // Spawn Sumatra PDF process if DDE connection failed (processs probably not running) |
| 230 | if (!this->ConnectDDEClient(this->szService, this->szTopic)) { |
| 231 | // Get path of current executable to use SumatraPDF executable from the same directory |
| 232 | std::vector<wchar_t> currentExePathBuf(32768); |
| 233 | DWORD ret = GetModuleFileNameW(nullptr, currentExePathBuf.data(), currentExePathBuf.size() - 1); |
| 234 | if (ret == 0L) { |
| 235 | ret = GetLastError(); |
| 236 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "PDFBridgeSumatra OpenDocument GetModuleFileNameW failed: 0x%08lx", ret); |
| 237 | return; |
| 238 | } |
| 239 | filesystem::path currentExePath(currentExePathBuf.begin(), currentExePathBuf.end()); |
| 240 | currentExePathBuf.clear(); |
| 241 | |
| 242 | filesystem::path pdfSoftwarePath{this->obvConfig.ParseStr("pdfSoftwarePath", "SumatraPDF.exe")}; |
| 243 | if (pdfSoftwarePath.empty()) { |
| 244 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "%s", "PDFBridgeSumatra OpenDocument: PDF software executable path empty"); |
| 245 | return; |
| 246 | } |
| 247 | |
| 248 | std::error_code ec; |
| 249 | std::wstring exec = filesystem::relative(pdfSoftwarePath, currentExePath.parent_path(), ec).wstring(); |
| 250 | if (ec) { |
| 251 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "PDFBridgeSumatra OpenDocument: %d - %s", ec.value(), ec.message().c_str()); |
| 252 | return; |
| 253 | } |
| 254 | if (exec.empty()) { |
| 255 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "PDFBridgeSumatra OpenDocument Executable path empty, PDF software path: %s, current directory: %s", pdfSoftwarePath.string().c_str(), currentExePath.parent_path().string().c_str()); |
| 256 | return; |
| 257 | } |
| 258 | |
| 259 | std::wstring args = L"\"" + exec + L"\"" + L" " + L"\"" + pdfPathString + L"\""; |
| 260 | std::vector<wchar_t> buf(args.c_str(), args.c_str() + args.size() + 1); |
| 261 | STARTUPINFO si{}; |
| 262 | si.cb = sizeof(si); |
| 263 | PROCESS_INFORMATION pi{}; |
| 264 | bool success = CreateProcessW(nullptr, buf.data(), nullptr, nullptr, false, 0, nullptr, nullptr, &si, &pi); |
| 265 | if (!success) { |
| 266 | ret = GetLastError(); |
| 267 | SDL_LogError(SDL_LOG_CATEGORY_ERROR, "PDFBridgeSumatra OpenDocument CreateProcess '%s' failed: 0x%08lx", utf16_to_utf8(args).c_str(), ret); |
| 268 | } else { |
| 269 | SDL_LogDebug(SDL_LOG_CATEGORY_APPLICATION, "PDFBridgeSumatra spawned '%s'", utf16_to_utf8(args).c_str()); |
| 270 | } |
| 271 | } else { |
| 272 | std::wstring ddeCmd = L"[Open(\"" + this->pdfPathString + L"\",0,1,1)]"; |
nothing calls this directly
no test coverage detected