4个版本 (破坏性更新)
使用旧的Rust 2015
0.4.0 | 2019年2月22日 |
---|---|
0.3.0 | 2018年10月13日 |
0.2.0 | 2018年10月13日 |
0.1.0 | 2018年9月29日 |
#509 in 图形API
44KB
693 行
gfx-gtk
使用Gfx (pre-ll)库渲染到gtk-rs GLArea
的简单桥梁库。
使用[epoxy]进行GL加载,因此不需要像glutin
或winit
这样的GL窗口/加载管理。
以下是一个简短的分步列表,以启动集成
添加Cargo依赖项
[dependencies]
gfx_gtk = "0.3"
导入crate和包
extern crate gfx_gtk;
use gfx_gtk::formats;
use gfx_gtk::GlRenderContext;
选择一些渲染格式和抗锯齿模式
const MSAA: gfx::texture::AaMode = formats::MSAA_4X;
type RenderColorFormat = formats::DefaultRenderColorFormat;
type RenderDepthFormat = formats::DefaultRenderDepthFormat;
编写渲染回调
您需要实现[GlRenderCallback]和[GlPostprocessCallback]特质(后者可以采用默认实现)
struct SimpleRenderCallback {
...
}
impl gfx_gtk::GlRenderCallback<RenderColorFormat, RenderDepthFormat> for SimpleRenderCallback {
fn render(
&mut self,
gfx_context: &mut gfx_gtk::GlGfxContext,
viewport: &gfx_gtk::Viewport,
frame_buffer: &gfx_gtk::GlFrameBuffer<RenderColorFormat>,
depth_buffer: &gfx_gtk::GlDepthBuffer<RenderDepthFormat>,
) -> gfx_gtk::Result<gfx_gtk::GlRenderCallbackStatus> {
gfx_context.encoder.draw(...);
Ok(gfx_gtk::GlRenderCallbackStatus::Continue)
}
}
impl gfx_gtk::GlPostprocessCallback<RenderColorFormat, RenderDepthFormat> for SimpleRenderCallback {}
加载GL函数
gfx_gtk::load();
连接小部件的信号
由于其创建GL上下文的能力,渲染需要由GlArea
小部件驱动。
需要连接realize
、resize
和render
信号。在将闭包附加到GlArea::connect_realize()
之后,在调用make_current()
之后创建[GlRenderContext]和[GlRenderCallback](否则将无法“绑定”到当前GlArea
GL上下文)
let gfx_context: Rc<RefCell<Option<GlRenderContext<RenderColorFormat, RenderDepthFormat>>>> = Rc::new(RefCell::new(None));
let render_callback: Rc<RefCell<Option<SimpleRenderCallback>>> = Rc::new(RefCell::new(None));
let glarea = gtk::GLArea::new();
glarea.connect_realize({
let gfx_context = gfx_context.clone();
let render_callback = render_callback.clone();
move |widget| {
if widget.get_realized() {
widget.make_current();
}
let allocation = widget.get_allocation();
let mut new_context =
gfx_gtk::GlRenderContext::new(
MSAA,
allocation.width,
allocation.height,
None).ok();
if let Some(ref mut new_context) = new_context {
let ref vp = new_context.viewport();
let ref mut ctx = new_context.gfx_context_mut();
*render_callback.borrow_mut() = SimpleRenderCallback::new(ctx, vp).ok();
}
*gfx_context.borrow_mut() = new_context;
}
});
glarea.connect_resize({
let gfx_context = gfx_context.clone();
let render_callback = render_callback.clone();
move |_widget, width, height| {
if let Some(ref mut context) = *gfx_context.borrow_mut() {
if let Some(ref mut render_callback) = *render_callback.borrow_mut() {
context.resize(width, height, Some(render_callback)).ok();
}
}
}
});
glarea.connect_render({
let gfx_context = gfx_context.clone();
let render_callback = render_callback.clone();
move |_widget, _gl_context| {
if let Some(ref mut context) = *gfx_context.borrow_mut() {
if let Some(ref mut render_callback) = *render_callback.borrow_mut() {
context.with_gfx(render_callback);
}
}
Inhibit(false)
}
});
之后,每次Gtk刷新GlArea
内容时,它将调用render_callback
来绘制自己。
请参阅examples/setup.rs中的简单交互式渲染示例。运行它时,使用cargo run --example setup
,它应该看起来像这样
© 2018 Nico Orru https://www.itadinanta.net
依赖关系
~13MB
~326K SLoC