document.rs (3888B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5 extern crate euclid; 6 extern crate gleam; 7 extern crate glutin; 8 extern crate webrender; 9 extern crate winit; 10 11 #[path = "common/boilerplate.rs"] 12 mod boilerplate; 13 14 use crate::boilerplate::Example; 15 use euclid::Scale; 16 use webrender::api::*; 17 use webrender::render_api::*; 18 use webrender::api::units::*; 19 20 // This example creates multiple documents overlapping each other with 21 // specified layer indices. 22 23 struct Document { 24 id: DocumentId, 25 pipeline_id: PipelineId, 26 content_rect: LayoutRect, 27 color: ColorF, 28 } 29 30 struct App { 31 documents: Vec<Document>, 32 } 33 34 impl App { 35 fn init( 36 &mut self, 37 api: &mut RenderApi, 38 device_pixel_ratio: f32, 39 ) { 40 let init_data = vec![ 41 ( 42 PipelineId(1, 0), 43 ColorF::new(0.0, 1.0, 0.0, 1.0), 44 DeviceIntPoint::new(0, 0), 45 ), 46 ( 47 PipelineId(2, 0), 48 ColorF::new(1.0, 1.0, 0.0, 1.0), 49 DeviceIntPoint::new(200, 0), 50 ), 51 ( 52 PipelineId(3, 0), 53 ColorF::new(1.0, 0.0, 0.0, 1.0), 54 DeviceIntPoint::new(200, 200), 55 ), 56 ( 57 PipelineId(4, 0), 58 ColorF::new(1.0, 0.0, 1.0, 1.0), 59 DeviceIntPoint::new(0, 200), 60 ), 61 ]; 62 63 for (pipeline_id, color, offset) in init_data { 64 let size = DeviceIntSize::new(250, 250); 65 let bounds = DeviceIntRect::from_origin_and_size(offset, size); 66 67 let document_id = api.add_document(size); 68 let mut txn = Transaction::new(); 69 txn.set_root_pipeline(pipeline_id); 70 api.send_transaction(document_id, txn); 71 72 self.documents.push(Document { 73 id: document_id, 74 pipeline_id, 75 content_rect: LayoutRect::from_size( 76 bounds.size().to_f32() / Scale::new(device_pixel_ratio), 77 ), 78 color, 79 }); 80 } 81 } 82 } 83 84 impl Example for App { 85 fn render( 86 &mut self, 87 api: &mut RenderApi, 88 _base_builder: &mut DisplayListBuilder, 89 _txn: &mut Transaction, 90 _device_size: DeviceIntSize, 91 _pipeline_id: PipelineId, 92 _: DocumentId, 93 ) { 94 if self.documents.is_empty() { 95 // this is the first run, hack around the boilerplate, 96 // which assumes an example only needs one document 97 self.init(api, 1.0); 98 } 99 100 for doc in &self.documents { 101 let space_and_clip = SpaceAndClipInfo::root_scroll(doc.pipeline_id); 102 let mut builder = DisplayListBuilder::new( 103 doc.pipeline_id, 104 ); 105 builder.begin(); 106 let local_rect = LayoutRect::from_size(doc.content_rect.size()); 107 108 builder.push_simple_stacking_context( 109 doc.content_rect.min, 110 space_and_clip.spatial_id, 111 PrimitiveFlags::IS_BACKFACE_VISIBLE, 112 ); 113 builder.push_rect( 114 &CommonItemProperties::new(local_rect, space_and_clip), 115 local_rect, 116 doc.color, 117 ); 118 builder.pop_stacking_context(); 119 120 let mut txn = Transaction::new(); 121 txn.set_display_list( 122 Epoch(0), 123 builder.end(), 124 ); 125 txn.generate_frame(0, true, false, RenderReasons::empty()); 126 api.send_transaction(doc.id, txn); 127 } 128 } 129 } 130 131 fn main() { 132 let mut app = App { 133 documents: Vec::new(), 134 }; 135 boilerplate::main_wrapper(&mut app, None); 136 }