mirror of
https://github.com/kunkundi/crossdesk.git
synced 2026-03-23 16:47:32 +08:00
[feat] add controller info and file transfer in server window
This commit is contained in:
@@ -1,50 +1,11 @@
|
||||
#include "layout_relative.h"
|
||||
#include "localization.h"
|
||||
#include "rd_log.h"
|
||||
#include "render.h"
|
||||
|
||||
namespace crossdesk {
|
||||
|
||||
namespace {
|
||||
constexpr float kDragThresholdPx = 3.0f;
|
||||
|
||||
// Handles dragging for the *last submitted ImGui item*.
|
||||
// `reset_on_deactivate` should be false when the caller needs to know whether a
|
||||
// deactivation was a click (no drag) vs a drag-release (dragging==true).
|
||||
inline void HandleWindowDragForLastItem(SDL_Window* window, bool& dragging,
|
||||
float& start_mouse_x,
|
||||
float& start_mouse_y, int& start_win_x,
|
||||
int& start_win_y,
|
||||
bool reset_on_deactivate = true) {
|
||||
if (!window) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (ImGui::IsItemActivated()) {
|
||||
SDL_GetGlobalMouseState(&start_mouse_x, &start_mouse_y);
|
||||
SDL_GetWindowPosition(window, &start_win_x, &start_win_y);
|
||||
dragging = false;
|
||||
}
|
||||
|
||||
if (ImGui::IsItemActive()) {
|
||||
if (!dragging &&
|
||||
ImGui::IsMouseDragging(ImGuiMouseButton_Left, kDragThresholdPx)) {
|
||||
dragging = true;
|
||||
}
|
||||
|
||||
if (dragging) {
|
||||
float mouse_x = 0.0f;
|
||||
float mouse_y = 0.0f;
|
||||
SDL_GetGlobalMouseState(&mouse_x, &mouse_y);
|
||||
const int dx = (int)(mouse_x - start_mouse_x);
|
||||
const int dy = (int)(mouse_y - start_mouse_y);
|
||||
SDL_SetWindowPosition(window, start_win_x + dx, start_win_y + dy);
|
||||
}
|
||||
}
|
||||
|
||||
if (reset_on_deactivate && ImGui::IsItemDeactivated()) {
|
||||
dragging = false;
|
||||
}
|
||||
}
|
||||
} // namespace
|
||||
namespace {} // namespace
|
||||
|
||||
int Render::ServerWindow() {
|
||||
ImGui::SetNextWindowSize(ImVec2(server_window_width_, server_window_height_),
|
||||
@@ -57,44 +18,6 @@ int Render::ServerWindow() {
|
||||
ImGuiWindowFlags_NoScrollbar |
|
||||
ImGuiWindowFlags_NoScrollWithMouse);
|
||||
|
||||
// Collapsed mode: no buttons; drag to move; click to restore.
|
||||
if (server_window_collapsed_) {
|
||||
ImGui::SetCursorPos(ImVec2(0.0f, 0.0f));
|
||||
ImGui::InvisibleButton("##server_collapsed_area",
|
||||
ImVec2(server_window_width_, server_window_height_));
|
||||
|
||||
HandleWindowDragForLastItem(server_window_,
|
||||
server_window_collapsed_dragging_,
|
||||
server_window_collapsed_drag_start_mouse_x_,
|
||||
server_window_collapsed_drag_start_mouse_y_,
|
||||
server_window_collapsed_drag_start_win_x_,
|
||||
server_window_collapsed_drag_start_win_y_,
|
||||
/*reset_on_deactivate=*/false);
|
||||
|
||||
const bool request_restore =
|
||||
ImGui::IsItemDeactivated() && !server_window_collapsed_dragging_;
|
||||
if (ImGui::IsItemDeactivated()) {
|
||||
server_window_collapsed_dragging_ = false;
|
||||
}
|
||||
|
||||
if (request_restore && server_window_) {
|
||||
int w = 0;
|
||||
int x = 0;
|
||||
int y = 0;
|
||||
int h = 0;
|
||||
SDL_GetWindowSize(server_window_, &w, &h);
|
||||
SDL_GetWindowPosition(server_window_, &x, &y);
|
||||
|
||||
const int normal_h = server_window_normal_height_;
|
||||
SDL_SetWindowSize(server_window_, w, normal_h);
|
||||
SDL_SetWindowPosition(server_window_, x, y);
|
||||
server_window_collapsed_ = false;
|
||||
}
|
||||
|
||||
ImGui::End();
|
||||
return 0;
|
||||
}
|
||||
|
||||
ImGui::PushStyleColor(ImGuiCol_ChildBg, ImVec4(1.0f, 1.0f, 1.0f, 1.0f));
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0));
|
||||
ImGui::SetNextWindowPos(ImVec2(0, 0), ImGuiCond_Always);
|
||||
@@ -105,97 +28,132 @@ int Render::ServerWindow() {
|
||||
ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoMove |
|
||||
ImGuiWindowFlags_NoBringToFrontOnFocus);
|
||||
|
||||
ImDrawList* draw_list = ImGui::GetWindowDrawList();
|
||||
|
||||
float server_title_bar_button_width = server_window_title_bar_height_;
|
||||
float server_title_bar_button_height = server_window_title_bar_height_;
|
||||
|
||||
// Drag area: the title bar excluding the right-side buttons.
|
||||
// Collapse/expand toggle button (FontAwesome icon).
|
||||
{
|
||||
const float drag_w =
|
||||
server_window_width_ - server_title_bar_button_width * 2;
|
||||
const float drag_h = server_title_bar_button_height;
|
||||
ImGui::SetCursorPos(ImVec2(0.0f, 0.0f));
|
||||
ImGui::InvisibleButton("##server_title_drag_area", ImVec2(drag_w, drag_h));
|
||||
|
||||
HandleWindowDragForLastItem(
|
||||
server_window_, server_window_dragging_,
|
||||
server_window_drag_start_mouse_x_, server_window_drag_start_mouse_y_,
|
||||
server_window_drag_start_win_x_, server_window_drag_start_win_y_);
|
||||
}
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImVec4(0, 0, 0, 0.1f));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonActive,
|
||||
ImVec4(1.0f, 1.0f, 1.0f, 1.0f));
|
||||
|
||||
float minimize_button_pos_x =
|
||||
server_window_width_ - server_title_bar_button_width * 2;
|
||||
ImGui::SetCursorPos(ImVec2(minimize_button_pos_x, 0.0f));
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImVec4(0, 0, 0, 0.1f));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImVec4(1.0f, 1.0f, 1.0f, 1.0f));
|
||||
ImGui::SetWindowFontScale(0.5f);
|
||||
const char* icon =
|
||||
server_window_collapsed_ ? ICON_FA_ANGLE_DOWN : ICON_FA_ANGLE_UP;
|
||||
std::string toggle_label = std::string(icon) + "##server_toggle";
|
||||
if (ImGui::Button(toggle_label.c_str(),
|
||||
ImVec2(server_title_bar_button_width,
|
||||
server_title_bar_button_height))) {
|
||||
if (server_window_) {
|
||||
int w = 0;
|
||||
int h = 0;
|
||||
int x = 0;
|
||||
int y = 0;
|
||||
SDL_GetWindowSize(server_window_, &w, &h);
|
||||
SDL_GetWindowPosition(server_window_, &x, &y);
|
||||
|
||||
float minimize_pos_x =
|
||||
minimize_button_pos_x + server_title_bar_button_width * 0.33f;
|
||||
float minimize_pos_y = server_title_bar_button_height * 0.5f;
|
||||
std::string server_minimize_button = "##minimize"; // ICON_FA_MINUS;
|
||||
if (ImGui::Button(server_minimize_button.c_str(),
|
||||
ImVec2(server_title_bar_button_width,
|
||||
server_title_bar_button_height))) {
|
||||
if (server_window_) {
|
||||
int w = 0;
|
||||
int h = 0;
|
||||
int x = 0;
|
||||
int y = 0;
|
||||
SDL_GetWindowSize(server_window_, &w, &h);
|
||||
SDL_GetWindowPosition(server_window_, &x, &y);
|
||||
|
||||
const int collapsed_h = (int)server_window_title_bar_height_;
|
||||
// Collapse upward: keep top edge stable.
|
||||
SDL_SetWindowSize(server_window_, w, collapsed_h);
|
||||
SDL_SetWindowPosition(server_window_, x, y);
|
||||
server_window_collapsed_ = true;
|
||||
if (server_window_collapsed_) {
|
||||
const int normal_h = server_window_normal_height_;
|
||||
SDL_SetWindowSize(server_window_, w, normal_h);
|
||||
SDL_SetWindowPosition(server_window_, x, y);
|
||||
server_window_collapsed_ = false;
|
||||
} else {
|
||||
const int collapsed_h = (int)server_window_title_bar_height_;
|
||||
// Collapse upward: keep top edge stable.
|
||||
SDL_SetWindowSize(server_window_, w, collapsed_h);
|
||||
SDL_SetWindowPosition(server_window_, x, y);
|
||||
server_window_collapsed_ = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
ImGui::SetWindowFontScale(1.0f);
|
||||
|
||||
ImGui::PopStyleColor(3);
|
||||
}
|
||||
draw_list->AddLine(
|
||||
ImVec2(minimize_pos_x, minimize_pos_y),
|
||||
ImVec2(minimize_pos_x + server_title_bar_button_width * 0.33f,
|
||||
minimize_pos_y),
|
||||
IM_COL32(0, 0, 0, 255));
|
||||
ImGui::PopStyleColor(3);
|
||||
|
||||
float xmark_button_pos_x =
|
||||
server_window_width_ - server_title_bar_button_width;
|
||||
ImGui::SetCursorPos(ImVec2(xmark_button_pos_x, 0.0f));
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0, 0, 0, 0));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImVec4(1.0f, 0, 0, 1.0f));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImVec4(1.0f, 0, 0, 0.5f));
|
||||
|
||||
float xmark_pos_x = xmark_button_pos_x + server_title_bar_button_width * 0.5f;
|
||||
float xmark_pos_y = server_title_bar_button_height * 0.5f;
|
||||
float xmark_size = server_title_bar_button_width * 0.33f;
|
||||
std::string server_close_button = "##xmark"; // ICON_FA_XMARK;
|
||||
if (ImGui::Button(server_close_button.c_str(),
|
||||
ImVec2(server_title_bar_button_width,
|
||||
server_title_bar_button_height))) {
|
||||
LOG_ERROR("Close button clicked");
|
||||
LeaveConnection(peer_, self_hosted_id_);
|
||||
}
|
||||
|
||||
draw_list->AddLine(ImVec2(xmark_pos_x - xmark_size / 2 - 0.25f,
|
||||
xmark_pos_y - xmark_size / 2 + 0.75f),
|
||||
ImVec2(xmark_pos_x + xmark_size / 2 - 1.5f,
|
||||
xmark_pos_y + xmark_size / 2 - 0.5f),
|
||||
IM_COL32(0, 0, 0, 255));
|
||||
draw_list->AddLine(
|
||||
ImVec2(xmark_pos_x + xmark_size / 2 - 1.75f,
|
||||
xmark_pos_y - xmark_size / 2 + 0.75f),
|
||||
ImVec2(xmark_pos_x - xmark_size / 2, xmark_pos_y + xmark_size / 2 - 1.0f),
|
||||
IM_COL32(0, 0, 0, 255));
|
||||
|
||||
ImGui::PopStyleColor(3);
|
||||
|
||||
ImGui::EndChild();
|
||||
ImGui::PopStyleVar();
|
||||
ImGui::PopStyleColor();
|
||||
|
||||
RemoteClientInfoWindow();
|
||||
|
||||
ImGui::End();
|
||||
return 0;
|
||||
}
|
||||
|
||||
int Render::RemoteClientInfoWindow() {
|
||||
float remote_client_info_window_width = server_window_width_ * 0.75f;
|
||||
float remote_client_info_window_height =
|
||||
(server_window_height_ - server_window_title_bar_height_) * 0.3f;
|
||||
|
||||
ImGui::PushStyleColor(ImGuiCol_ChildBg, ImVec4(1.0f, 1.0f, 1.0f, 1.0f));
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_ChildRounding, 5.0f);
|
||||
ImGui::BeginChild(
|
||||
"RemoteClientInfoWindow",
|
||||
ImVec2(remote_client_info_window_width, remote_client_info_window_height),
|
||||
ImGuiChildFlags_Border,
|
||||
ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoMove |
|
||||
ImGuiWindowFlags_NoBringToFrontOnFocus);
|
||||
ImGui::PopStyleVar();
|
||||
ImGui::PopStyleColor();
|
||||
|
||||
ImGui::SetWindowFontScale(0.7f);
|
||||
ImGui::Text("%s",
|
||||
localization::controller[localization_language_index_].c_str());
|
||||
ImGui::SameLine();
|
||||
ImGui::Text("%s", remote_client_id_.c_str());
|
||||
|
||||
ImGui::SetWindowFontScale(1.0f);
|
||||
|
||||
ImGui::EndChild();
|
||||
|
||||
ImGui::SameLine();
|
||||
|
||||
float close_connection_button_width = server_window_width_ * 0.15f;
|
||||
float close_connection_button_height = remote_client_info_window_height;
|
||||
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(1.0f, 0.0f, 0.0f, 1.0f));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonHovered, ImVec4(1.0f, 0.3f, 0.3f, 1.0f));
|
||||
ImGui::PushStyleColor(ImGuiCol_ButtonActive, ImVec4(1.0f, 0.5f, 0.5f, 1.0f));
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_FrameRounding, 5.0f);
|
||||
ImGui::SetWindowFontScale(0.7f);
|
||||
if (ImGui::Button(ICON_FA_XMARK, ImVec2(close_connection_button_width,
|
||||
close_connection_button_height))) {
|
||||
LeaveConnection(peer_, self_hosted_id_);
|
||||
}
|
||||
ImGui::SetWindowFontScale(1.0f);
|
||||
ImGui::PopStyleColor(3);
|
||||
ImGui::PopStyleVar();
|
||||
|
||||
ImGui::PushStyleColor(ImGuiCol_Border, ImVec4(1.0f, 1.0f, 1.0f, 0.0f));
|
||||
ImGui::BeginChild(
|
||||
"RemoteClientInfoFileTransferWindow",
|
||||
ImVec2(remote_client_info_window_width, remote_client_info_window_height),
|
||||
ImGuiChildFlags_Border,
|
||||
ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoMove |
|
||||
ImGuiWindowFlags_NoBringToFrontOnFocus);
|
||||
ImGui::PopStyleColor();
|
||||
|
||||
ImGui::SetWindowFontScale(0.7f);
|
||||
ImGui::AlignTextToFramePadding();
|
||||
ImGui::Text(
|
||||
"%s", localization::file_transfer[localization_language_index_].c_str());
|
||||
|
||||
ImGui::SameLine();
|
||||
|
||||
if (ImGui::Button(
|
||||
localization::select_file[localization_language_index_].c_str())) {
|
||||
std::string title = localization::select_file[localization_language_index_];
|
||||
std::string path = OpenFileDialog(title);
|
||||
LOG_INFO("Selected file path: {}", path.c_str());
|
||||
}
|
||||
ImGui::SetWindowFontScale(1.0f);
|
||||
|
||||
ImGui::EndChild();
|
||||
|
||||
return 0;
|
||||
}
|
||||
} // namespace crossdesk
|
||||
Reference in New Issue
Block a user