void GroupEditor::drawContents(Renderer2D &out) const { int2 offset = innerOffset(); for(int n = 0; n < m_tile_group->entryCount(); n++) m_tile_group->entryTile(n)->m_temp = n; IRect clip_rect(int2(0, 0), clippedRect().size()); for(int n = 0; n < (int)m_tile_list.size(); n++) { const ui::TileList::Entry &entry = m_tile_list[n]; entry.is_selected = m_mode == mAddRemove? m_tile_group->isValidEntryId(entry.tile->m_temp, entry.tile) : entry.group_id == m_selected_group_id; IRect tile_rect = entry.tile->rect(); int2 pos = entry.pos - tile_rect.min - offset; if(areOverlapping(clip_rect, tile_rect + pos)) entry.tile->draw(out, pos); } DTexture::unbind(); for(int n = 0; n < (int)m_tile_list.size(); n++) { const ui::TileList::Entry &entry = m_tile_list[n]; if(!entry.is_selected) continue; Color col = m_tile_group->isEntryDirty(entry.tile->m_temp)? ColorId::red : ColorId::white; int2 pos = entry.pos - offset; out.addRect(IRect(pos, pos + entry.size), col); } if(m_mode == mModify && m_selected_group_id != -1) { IRect edit_rect(clippedRect().max - int2(280, 250), clippedRect().max - int2(5, 0)); int2 center = edit_rect.center(); out.setViewPos(-center); int2 half_size = edit_rect.size() / 2; out.addFilledRect(IRect(-half_size, half_size), FColor(0.3f, 0.3f, 0.3f)); drawBBox(out, IBox({-9, 0, -9}, {9, 1, 9}), ColorId::white); auto font = res::getFont(WindowStyle::fonts[0]); for(int n = 0; n < TileGroup::Group::side_count; n++) { out.setViewPos(-center - worldToScreen(TileGroup::Group::s_side_offsets[n] * 9)); font->draw(out, float2(0, 0), {ColorId::white}, format("%d", m_tile_group->groupSurface(m_selected_group_id, n))); } out.setViewPos(-center +edit_rect.size() / 2); font->draw(out, float2(0, 0), {ColorId::white}, format("setting surface: %d", m_selected_surface_id)); /* const char *names[] = { "", "snow", "gravel", "dirt", "grass", "mud", "mud_cracked", "sand", "green goo", }; out.setViewPos(-int2(bottom_rect.max.x - 200, bottom_rect.min.y)); for(int n = 0; n < arraySize(names); n++) font->draw(int2(0, 10), ColorId::white, m_selected_surface_id == n? "%d: [%s]\n" : "%d: %s\n", n, names[n]); */ out.setViewPos(-clippedRect().min); } if(m_current_entry) m_font->draw(out, float2(5, height() - 20), {ColorId::white, ColorId::black}, format("%s", m_current_entry->tile->resourceName().c_str())); }
void EntitiesEditor::drawContents(Renderer2D &out) const { m_view.updateVisibility(); SceneRenderer renderer(clippedRect(), m_view.pos()); { vector<int> visible_ids; visible_ids.reserve(1024); m_tile_map.findAll(visible_ids, renderer.targetRect(), Flags::all | Flags::visible); for(int i = 0; i < (int)visible_ids.size(); i++) { auto &object = m_tile_map[visible_ids[i]]; int3 pos(object.bbox.min); object.ptr->addToRender(renderer, pos, Color::white); } visible_ids.clear(); m_entity_map.findAll(visible_ids, renderer.targetRect(), Flags::all | Flags::visible); vector<char> selection_map(m_entity_map.size(), 0); vector<float3> old_positions(m_selected_ids.size()); for(int n = 0; n < (int)m_selected_ids.size(); n++) { selection_map[m_selected_ids[n]] = 1; visible_ids.push_back(m_selected_ids[n]); if(m_is_moving) { auto &object = m_entity_map[m_selected_ids[n]]; old_positions[n] = object.ptr->pos(); object.ptr->setPos(old_positions[n] + float3(m_move_offset)); m_entity_map.update(m_selected_ids[n]); } } sort(visible_ids.begin(), visible_ids.end()); visible_ids.resize(std::unique(visible_ids.begin(), visible_ids.end()) - visible_ids.begin()); for(int n = 0; n < (int)visible_ids.size(); n++) { auto &object = m_entity_map[visible_ids[n]]; float3 old_pos = object.ptr->pos(); bool is_selected = selection_map[visible_ids[n]]; FBox bbox = object.ptr->boundingBox(); if(object.ptr->typeId() == EntityId::trigger) { renderer.addBox(bbox, Color(Color::green, 64), true); renderer.addBox(FBox(bbox.min + float3(0.1, 0.1, 0.1), bbox.max - float3(0.1, 0.1, 0.1)), Color::green); } else { object.ptr->addToRender(renderer); } bool is_colliding = m_tile_map.findAny(bbox) != -1 || m_entity_map.findAny(bbox, visible_ids[n]) != -1; if(is_colliding) renderer.addBox(bbox, Color::red); if(is_selected) { if(!is_colliding) renderer.addBox(bbox, Color::white); FBox overground_box = computeOvergroundBox(bbox); if(!overground_box.isEmpty()) renderer.addBox(overground_box, Color::yellow); } } if(m_is_moving) for(int n = 0; n < (int)m_selected_ids.size(); n++) { auto &object = m_entity_map[m_selected_ids[n]]; object.ptr->setPos(old_positions[n]); m_entity_map.update(m_selected_ids[n]); } } if(m_proto && m_mode == Mode::placing) { m_proto->setPos(m_cursor_pos); m_proto->addToRender(renderer); FBox bbox = m_proto->boundingBox(); bool is_colliding = m_tile_map.findAny(bbox) != -1 || m_entity_map.findAny(bbox) != -1; renderer.addBox(bbox, is_colliding? Color::red : Color::white); if(bbox.max.y == bbox.min.y) bbox.max.y += 1.0f; FBox overground_box = computeOvergroundBox(bbox); if(!overground_box.isEmpty()) renderer.addBox(overground_box, Color::yellow); } renderer.render(); if(m_mode == Mode::selecting && m_is_selecting) out.addRect(m_selection - m_view.pos(), Color::white); out.setScissorRect(clippedRect()); out.setViewPos(-clippedRect().min + m_view.pos()); m_view.drawGrid(out); out.setViewPos(-clippedRect().min); auto font = res::getFont(WindowStyle::fonts[1]); font->draw(out, int2(0, clippedRect().height() - 25), {Color::white, Color::black}, format("Cursor: (%.0f, %.0f, %.0f) Grid: %d Mode: %s\n", m_cursor_pos.x, m_cursor_pos.y, m_cursor_pos.z, m_view.gridHeight(), EntitiesEditorMode::toString(m_mode))); }