完善Project面板功能:搜索框、创建文件夹、右键菜单、中文路径支持
This commit is contained in:
@@ -7,50 +7,143 @@
|
||||
namespace UI {
|
||||
|
||||
ProjectPanel::ProjectPanel() : Panel("Project") {
|
||||
ProjectManager::Get().CreateDemoAssets();
|
||||
}
|
||||
|
||||
void ProjectPanel::Initialize(const std::string& projectPath) {
|
||||
ProjectManager::Get().Initialize(projectPath);
|
||||
}
|
||||
|
||||
void ProjectPanel::Render() {
|
||||
ImGui::Begin(m_name.c_str(), &m_isOpen, ImGuiWindowFlags_None);
|
||||
|
||||
ImGui::Text("Assets/");
|
||||
auto& manager = ProjectManager::Get();
|
||||
|
||||
if (manager.CanNavigateBack()) {
|
||||
if (ImGui::Button("<")) {
|
||||
manager.NavigateBack();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
}
|
||||
|
||||
ImGui::Text("%s", manager.GetCurrentPath().c_str());
|
||||
|
||||
ImGui::SameLine();
|
||||
ImGui::TextColored(ImVec4(0.5f, 0.5f, 0.5f, 1.0f), "> Project");
|
||||
float refreshBtnWidth = 60.0f;
|
||||
ImGui::SetCursorPosX(ImGui::GetWindowWidth() - refreshBtnWidth - 80.0f);
|
||||
if (ImGui::Button("Refresh")) {
|
||||
manager.RefreshCurrentFolder();
|
||||
}
|
||||
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("+")) {
|
||||
m_showCreateFolderPopup = true;
|
||||
strcpy_s(m_newFolderName, "NewFolder");
|
||||
}
|
||||
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::PushItemWidth(-1);
|
||||
ImGui::InputTextWithHint("##Search", "Search...", m_searchBuffer, sizeof(m_searchBuffer));
|
||||
ImGui::PopItemWidth();
|
||||
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::BeginChild("AssetList", ImVec2(0, 0), false);
|
||||
|
||||
float buttonWidth = 80.0f;
|
||||
float buttonHeight = 90.0f;
|
||||
float padding = 10.0f;
|
||||
float panelWidth = ImGui::GetContentRegionAvail().x;
|
||||
int columns = (int)(panelWidth / (buttonWidth + padding));
|
||||
if (columns < 1) columns = 1;
|
||||
|
||||
auto& items = ProjectManager::Get().GetItems();
|
||||
auto& items = manager.GetCurrentItems();
|
||||
std::string searchStr = m_searchBuffer;
|
||||
for (int i = 0; i < items.size(); i++) {
|
||||
if (!searchStr.empty()) {
|
||||
if (items[i]->name.find(searchStr) == std::string::npos) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (i > 0 && i % columns != 0) {
|
||||
ImGui::SameLine();
|
||||
}
|
||||
RenderAssetItem(items[i], i);
|
||||
}
|
||||
|
||||
if (ImGui::BeginPopupContextWindow("ProjectContextMenu")) {
|
||||
if (ImGui::MenuItem("Create Folder")) {
|
||||
m_showCreateFolderPopup = true;
|
||||
strcpy_s(m_newFolderName, "NewFolder");
|
||||
}
|
||||
ImGui::Separator();
|
||||
if (ImGui::MenuItem("Refresh")) {
|
||||
manager.RefreshCurrentFolder();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
|
||||
ImGui::EndChild();
|
||||
|
||||
if (m_showCreateFolderPopup) {
|
||||
ImGui::OpenPopup("Create Folder");
|
||||
}
|
||||
|
||||
if (ImGui::BeginPopupModal("Create Folder", nullptr, ImGuiWindowFlags_AlwaysAutoResize)) {
|
||||
ImGui::InputText("Name", m_newFolderName, sizeof(m_newFolderName));
|
||||
ImGui::Separator();
|
||||
if (ImGui::Button("Create", ImVec2(80, 0))) {
|
||||
CreateNewFolder(m_newFolderName);
|
||||
m_showCreateFolderPopup = false;
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::SameLine();
|
||||
if (ImGui::Button("Cancel", ImVec2(80, 0))) {
|
||||
m_showCreateFolderPopup = false;
|
||||
ImGui::CloseCurrentPopup();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
|
||||
ImGui::End();
|
||||
}
|
||||
|
||||
void ProjectPanel::RenderAssetItem(const AssetItem& item, int index) {
|
||||
ImGui::PushID(index);
|
||||
void ProjectPanel::RenderAssetItem(const AssetItemPtr& item, int index) {
|
||||
auto& manager = ProjectManager::Get();
|
||||
bool isSelected = (manager.GetSelectedIndex() == index);
|
||||
|
||||
std::string popupId = "ItemMenu" + std::to_string(index);
|
||||
|
||||
bool isSelected = (ProjectManager::Get().GetSelectedIndex() == index);
|
||||
if (isSelected) {
|
||||
ImGui::PushStyleColor(ImGuiCol_Button, ImVec4(0.40f, 0.40f, 0.40f, 0.50f));
|
||||
}
|
||||
|
||||
ImVec2 buttonSize(80.0f, 90.0f);
|
||||
if (ImGui::Button("##Asset", buttonSize)) {
|
||||
ProjectManager::Get().SetSelectedIndex(index);
|
||||
if (ImGui::Button(("##Asset" + std::to_string(index)).c_str(), buttonSize)) {
|
||||
manager.SetSelectedIndex(index);
|
||||
}
|
||||
|
||||
if (ImGui::IsItemClicked(ImGuiMouseButton_Right)) {
|
||||
manager.SetSelectedIndex(index);
|
||||
ImGui::OpenPopup(popupId.c_str());
|
||||
}
|
||||
|
||||
if (item->isFolder && ImGui::IsItemHovered() && ImGui::IsMouseDoubleClicked(0)) {
|
||||
manager.NavigateToFolder(item);
|
||||
}
|
||||
|
||||
if (ImGui::BeginPopup(popupId.c_str())) {
|
||||
if (item->isFolder) {
|
||||
if (ImGui::MenuItem("Open")) {
|
||||
manager.NavigateToFolder(item);
|
||||
}
|
||||
}
|
||||
ImGui::Separator();
|
||||
if (ImGui::MenuItem("Delete")) {
|
||||
manager.SetSelectedIndex(index);
|
||||
DeleteSelectedItem();
|
||||
}
|
||||
ImGui::EndPopup();
|
||||
}
|
||||
|
||||
if (isSelected) {
|
||||
@@ -58,23 +151,48 @@ void ProjectPanel::RenderAssetItem(const AssetItem& item, int index) {
|
||||
}
|
||||
|
||||
ImVec2 min = ImGui::GetItemRectMin();
|
||||
ImVec2 max = ImGui::GetItemRectMax();
|
||||
ImDrawList* drawList = ImGui::GetWindowDrawList();
|
||||
|
||||
ImU32 iconColor = item.isFolder ? IM_COL32(200, 180, 100, 255) : IM_COL32(100, 150, 200, 255);
|
||||
ImU32 iconColor;
|
||||
if (item->isFolder) {
|
||||
iconColor = IM_COL32(200, 180, 100, 255);
|
||||
} else if (item->type == "Texture") {
|
||||
iconColor = IM_COL32(150, 200, 150, 255);
|
||||
} else if (item->type == "Model") {
|
||||
iconColor = IM_COL32(150, 150, 200, 255);
|
||||
} else if (item->type == "Script") {
|
||||
iconColor = IM_COL32(200, 150, 150, 255);
|
||||
} else if (item->type == "Scene") {
|
||||
iconColor = IM_COL32(200, 200, 150, 255);
|
||||
} else {
|
||||
iconColor = IM_COL32(100, 150, 200, 255);
|
||||
}
|
||||
|
||||
float iconSize = 40.0f;
|
||||
ImVec2 iconMin(min.x + (80.0f - iconSize) * 0.5f, min.y + 10.0f);
|
||||
ImVec2 iconMax(iconMin.x + iconSize, iconMin.y + iconSize);
|
||||
drawList->AddRectFilled(iconMin, iconMax, iconColor, 4.0f);
|
||||
|
||||
ImVec2 textPos(min.x + 5.0f, min.y + 60.0f);
|
||||
ImVec4 textColor = isSelected ? ImVec4(1.0f, 1.0f, 1.0f, 1.0f) : ImVec4(0.8f, 0.8f, 0.8f, 1.0f);
|
||||
ImVec2 textSize = ImGui::CalcTextSize(item.name.c_str());
|
||||
float textOffset = (80.0f - textSize.x) * 0.5f;
|
||||
drawList->AddText(ImVec2(min.x + textOffset, textPos.y), ImGui::GetColorU32(textColor), item.name.c_str());
|
||||
ImVec2 textSize = ImGui::CalcTextSize(item->name.c_str());
|
||||
float textOffset = std::max(0.0f, (80.0f - textSize.x) * 0.5f);
|
||||
|
||||
ImGui::PopID();
|
||||
ImGui::PushClipRect(min, ImVec2(min.x + 80.0f, min.y + 90.0f), true);
|
||||
drawList->AddText(ImVec2(min.x + textOffset, min.y + 60.0f), ImGui::GetColorU32(textColor), item->name.c_str());
|
||||
ImGui::PopClipRect();
|
||||
}
|
||||
|
||||
void ProjectPanel::CreateNewFolder(const std::string& name) {
|
||||
auto& manager = ProjectManager::Get();
|
||||
manager.CreateFolder(name);
|
||||
}
|
||||
|
||||
void ProjectPanel::DeleteSelectedItem() {
|
||||
auto& manager = ProjectManager::Get();
|
||||
int selectedIndex = manager.GetSelectedIndex();
|
||||
if (selectedIndex >= 0) {
|
||||
manager.DeleteItem(selectedIndex);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user