コード例 #1
0
ファイル: window_manager.c プロジェクト: virajs/egui
/**
 * @brief 初始化窗口管理器图形相关
 *
 * @param framebuffer_path framebuffer设备路径
 * @param top_margin 配置项 屏幕上方留白的像素
 * @param down_margin 配置项 屏幕下方留白的像素
 * @param left_margin 配置项 屏幕左方留白的像素
 * @param right_margin 配置项 屏幕右方留白的像素
 *
 * @return 成功返回0 否则返回-1
 **/
static si_t graph_init(char* framebuffer_path, si_t top_margin, si_t down_margin, si_t left_margin, si_t right_margin)
{       
	struct graphics_device* gd_ptr = NULL;

	/* 初始化屏幕 */
	screen_init(framebuffer_path);
	/* 设置颜色的限制 */
	screen_color_limit();

	/** 
	 * 初始化窗口管理器的图形设备
	 **/
	global_wm.gd_handler = engine_graphics_device_init(0, 0, global_screen.width, global_screen.height, 0,0,0,0,0);
	if(0 == global_wm.gd_handler)
	{
		EGUI_PRINT_ERROR("failed to init window manager graph device.");
		return -1;
	}
	gd_ptr = (struct graphics_device*)global_wm.gd_handler;
	gd_ptr->screen.memory_addr = global_screen.memory_addr;
	gd_ptr->screen.buffer_addr = NULL;
	gd_ptr->screen.video_access_mode = VIDEO_ACCESS_MODE_DIRECT;

	/**
	 * 初始化窗口区域
	 **/
	rectangle_set(&global_wm.work_area,
		0 + left_margin, 0 + top_margin, global_screen.width - left_margin - right_margin, global_screen.height - top_margin - down_margin);

	/** 绘制桌面 **/
	engine_set_color(global_wm.gd_handler, global_wm.backcolor.r, global_wm.backcolor.g, global_wm.backcolor.b, global_wm.backcolor.a);
	engine_fill_rectangle(global_wm.gd_handler, global_wm.work_area.x, global_wm.work_area.y, global_wm.work_area.width, global_wm.work_area.height);

	return 0;
}
コード例 #2
0
ファイル: server_lib.c プロジェクト: puresmw/egui
extern si_t send_widget_resize_message(struct egui_uds* uds_ptr, union message* msg, si_t window_descripter, si_t x_axis, si_t y_axis, si_t x_size, si_t y_size)
{
    union message msg_to_be_sent;
    struct rectangle area = {0};
    copy_message(msg, &msg_to_be_sent);
    rectangle_set(&area, x_axis, y_axis, x_size, y_size);
    message_set_widget_resize(&msg_to_be_sent, window_descripter, &area);
    return comm_send_message(uds_ptr, &msg_to_be_sent);
}
コード例 #3
0
gboolean FloatingWindow::on_title_bar_motion_notify (GdkEventMotion *event)
{
  if (dragging_window) {
    guint layout_width, layout_height;
    gtk_layout_get_size (GTK_LAYOUT (layout), &layout_width, &layout_height);
    gint event_x = event->x_root;
    gint event_y = event->y_root;
    if (previous_root_x >= 0) {
      bool move_box = false;
      if (event_x != previous_root_x) {
        guint new_x = my_gdk_rectangle.x + event_x - previous_root_x;
        // The window does not move beyond the left or right side 
        if (new_x >= 0) {
          if ((new_x + my_gdk_rectangle.width) <= layout_width) {
            my_gdk_rectangle.x = new_x;
            move_box = true;
          }
        }
      }
      if (event_y != previous_root_y) {
        guint new_y = my_gdk_rectangle.y + event_y - previous_root_y;
        // The window does not move beyond the top or bottom.
        if (new_y >= 0) {
          if ((new_y + my_gdk_rectangle.height) <= layout_height) {
            my_gdk_rectangle.y = new_y;
            move_box = true;
          }
        }
      }
      if (move_box) {
        rectangle_set (my_gdk_rectangle);
      }
    }
    previous_root_x = event_x;
    previous_root_y = event_y;
  }
  return false;
}
コード例 #4
0
ファイル: window_info.c プロジェクト: FangKuangKuang/egui
void window_info_resize(struct window_info* win_info_ptr, si_t x, si_t y, si_t w, si_t h)
{
    /* 窗口区域 */
	rectangle_set(&win_info_ptr->area, 
		x - frame_size, y - frame_size - title_bar_size, w + 2 * frame_size, h + 2 * frame_size + title_bar_size);

    /* 用户工作区域 */
	rectangle_set(&win_info_ptr->work_area, x, y, w, h);

    /* 菜单按钮区域 */
	rectangle_set(&win_info_ptr->menu_button_area,
		x, y - title_bar_size, title_bar_size, title_bar_size);

    /* 标题栏区域 */
	rectangle_set(&win_info_ptr->title_bar_area,
		x + title_bar_size, y - title_bar_size, w - 2 * title_bar_size, title_bar_size);

    /* 最小化按钮区域 */
    if(win_info_ptr->minimize_enable == 1)
    {
		rectangle_set(&win_info_ptr->minimize_button_area, 
			x + w - 3 * title_bar_size, y - title_bar_size, title_bar_size, title_bar_size);

        win_info_ptr->title_bar_area.width -= title_bar_size;
    }

    /* 最大化按钮区域 */
    if(win_info_ptr->maximize_enable == 1)
    {
		rectangle_set(&win_info_ptr->maximize_button_area, 
			x + w - 2 * title_bar_size, y - title_bar_size, title_bar_size, title_bar_size);

        win_info_ptr->title_bar_area.width -= title_bar_size;
    }

    /* 退出按钮区域 */
	rectangle_set(&win_info_ptr->close_button_area,
		x + w - title_bar_size, y - title_bar_size, title_bar_size, title_bar_size);
}
コード例 #5
0
void FloatingWindow::display(bool startup)
// Does the bookkeeping necessary for displaying the floating box.
// startup: whether the box is started at program startup.
{
  // Settings.
  extern Settings *settings;

  // The parameters of all the windows.
  WindowData window_parameters(false);

  // Clear the new window's position.
  my_gdk_rectangle.x = 0;
  my_gdk_rectangle.y = 0;
  my_gdk_rectangle.width = 0;
  my_gdk_rectangle.height = 0;

  // At program startup extract the position and size of the window from the general configuration.
  // It does not matter whether the space for the window is already taken up by another window,
  // because the user wishes to use the coordinates that he has set for this window.
  for (unsigned int i = 0; i < window_parameters.widths.size(); i++) {
    if ((window_parameters.ids[i] == window_id) && (window_parameters.titles[i] == title) && startup) {
      my_gdk_rectangle.x = window_parameters.x_positions[i];
      my_gdk_rectangle.y = window_parameters.y_positions[i];
      my_gdk_rectangle.width = window_parameters.widths[i];
      my_gdk_rectangle.height = window_parameters.heights[i];
    }
  }

  // Reject zero width and zero height values on startup.
  if ((my_gdk_rectangle.width == 0) || (my_gdk_rectangle.height == 0))
    startup = false;

  // When a new window needs to be allocated, there are a few steps to be taken.
  if (!startup) {

    // Step 1: The area rectangle where the window should fit in is defined. 
    GdkRectangle area_rectangle;
    area_rectangle.x = 0;
    area_rectangle.y = 0;
    area_rectangle.width = 0;
    area_rectangle.height = 0;
    {
      guint width, height;
      gtk_layout_get_size (GTK_LAYOUT (layout), &width, &height);
      area_rectangle.width = width;
      area_rectangle.height = height;
    }

    // Step 2: An available region is made of that whole area.
    GdkRegion *available_region = gdk_region_rectangle(&area_rectangle);

    // Step 3: The regions of each of the open windows is substracted from the available region.
    for (unsigned int i = 0; i < settings->session.open_floating_windows.size(); i++) {
      FloatingWindow * floating_window = (FloatingWindow *) settings->session.open_floating_windows[i];
      GdkRectangle rectangle = floating_window->rectangle_get();
      GdkRegion *region = gdk_region_rectangle(&rectangle);
      gdk_region_subtract(available_region, region);
      gdk_region_destroy(region);
    }

    // Step 4: The rectangles that the area region consists of are requested,
    // and the biggest suitable rectangle is chosen for the window.
    // A rectangle is considered suitable if it has at least 10% of the width, and 10% of the height of the area rectangle.
    GdkRectangle *gdk_rectangles = NULL;
    gint rectangle_count = 0;
    gdk_region_get_rectangles(available_region, &gdk_rectangles, &rectangle_count);
    for (int i = 0; i < rectangle_count; ++i) {
      GdkRectangle & rectangle = gdk_rectangles[i];
      if (rectangle.width >= (area_rectangle.width / 10)) {
        if (rectangle.height >= (area_rectangle.height / 10)) {
          if ((rectangle.width * rectangle.height) > (my_gdk_rectangle.width * my_gdk_rectangle.height)) {
            my_gdk_rectangle = rectangle;
          }
        }
      }
    }
    g_free(gdk_rectangles);

    // Step 5: The available region is destroyed.
    gdk_region_destroy(available_region);

    // Step 6: If no area big enough is found, then the window that takes most space in the area is chosen, 
    // the longest side is halved, and the new window is put in that freed area.
    if ((my_gdk_rectangle.width == 0) || (my_gdk_rectangle.height == 0)) {
      FloatingWindow * resize_window_pointer = NULL;
      int largest_size = 0;
      for (unsigned int i = 0; i < settings->session.open_floating_windows.size(); i++) {
        FloatingWindow *floating_window = (FloatingWindow *) settings->session.open_floating_windows[i];
        GdkRectangle rectangle = floating_window->rectangle_get ();
        int size = rectangle.width * rectangle.height;
        if (size > largest_size) {
          resize_window_pointer = floating_window;
          largest_size = size;
        }
      }
      if (resize_window_pointer) {
        GdkRectangle resize_window_rectangle = resize_window_pointer->rectangle_get();
        my_gdk_rectangle = resize_window_pointer->rectangle_get();
        if (resize_window_rectangle.width > resize_window_rectangle.height) {
          resize_window_rectangle.width /= 2;
          my_gdk_rectangle.width /= 2;
          my_gdk_rectangle.x += resize_window_rectangle.width;
        } else {
          resize_window_rectangle.height /= 2;
          my_gdk_rectangle.height /= 2;
          my_gdk_rectangle.y += resize_window_rectangle.height;
        }
        resize_window_pointer->rectangle_set (resize_window_rectangle);
      }
    }
  }
  // Add the window to the layout and set its position and size.
  gtk_layout_put (GTK_LAYOUT (layout), vbox_window, my_gdk_rectangle.x, my_gdk_rectangle.y);
  rectangle_set (my_gdk_rectangle);
  // Store a pointer to this window in the Session.
  settings->session.open_floating_windows.push_back(gpointer (this));
}