1#![doc(html_root_url = "https://docs.rs/impl_sim/0.3.0")]
2use proc_macro::TokenStream;
6use proc_macro2::TokenStream as PM2TS;
7use proc_macro2::TokenTree;
8use quote::{quote, ToTokens}; use syn; #[proc_macro]
15pub fn impl_sim_fn(item: TokenStream) -> TokenStream {
16 let ts: PM2TS = item.into();
17 let tk = match ts.into_iter().next().unwrap() {
18 TokenTree::Ident(t) => Some(t), _ => None };
21 let f = &tk.unwrap();
22 let s = &f.to_string();
23 match s.as_str() {
24 "draw_geom" => {
25 quote! {
26 fn #f(&self, geom: dGeomID,
28 pos: Option<*const dReal>, rot: Option<*const dReal>, ws: i32) {
29 ostatln!(concat!("called ", #s));
30 self.super_get().#f(geom, pos, rot, ws);
31 }
32 }
33 },
34 "near_callback" => {
35 quote! {
36 fn #f(&mut self, dat: *mut c_void, o1: dGeomID, o2: dGeomID) {
38 ostatln!(concat!("called ", #s));
39 self.super_mut().#f(dat, o1, o2);
40 }
41 }
42 },
43 "step_callback" => {
44 quote! {
45 fn #f(&mut self, pause: i32) {
47 ostatln!(concat!("called ", #s));
48 self.super_mut().#f(pause);
49 }
50 }
51 },
52 "command_callback" => {
53 quote! {
54 fn #f(&mut self, cmd: i32) {
56 ostatln!(concat!("called ", #s));
57 self.super_mut().#f(cmd);
58 }
59 }
60 },
61 _ => {
62 quote! {
63 fn #f(&mut self) {
65 ostatln!(concat!("called ", #s));
66 self.super_mut().#f();
67 }
68 }
69 }
70 }.into()
71}
72
73#[proc_macro_attribute]
75pub fn impl_sim_derive(attr: TokenStream, item: TokenStream) -> TokenStream {
76 let mut ast = syn::parse_macro_input!(item as syn::ItemImpl);
77 let ts: PM2TS = attr.into();
78 for tt in ts {
79 match tt {
80 TokenTree::Ident(f) => { ast.items.push(syn::parse_quote! {
82 impl_sim_fn!(#f);
83 });
84 },
85 _ => {} }
87 }
88 ast.into_token_stream().into()
89}