Skip to content

Hacks for usage with stable Rust #30

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ repository = "https://github.com/dhardy/kas"

[features]
# Enables usage of unstable Rust features
nightly = []
nightly = ["kas-macros/nightly"]

[dependencies.kas-macros]
version = "0.1.0-pre.1"
Expand All @@ -27,6 +27,10 @@ version = "0.8"
version = "0.20.0-alpha5"
optional = true

[dependencies]
proc-macro-hack = "0.5"
proc-macro-nested = "0.1"

[workspace]
members = ["kas-macros", "kas-wgpu"]

Expand Down
5 changes: 5 additions & 0 deletions kas-macros/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,14 @@ repository = "https://github.com/dhardy/kas"
[lib]
proc-macro = true

[features]
# Enables usage of unstable Rust features
nightly = []

[dependencies]
quote = "1.0"
proc-macro2 = { version = "1.0", features = ["nightly"] }
proc-macro-hack = "0.5"

[dependencies.syn]
version = "1.0"
Expand Down
5 changes: 5 additions & 0 deletions kas-macros/src/args.rs
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ pub fn read_attrs(ast: &mut DeriveInput) -> Result<Args> {
if core.is_none() {
core = Some(member(i, field.ident.clone()));
} else {
#[cfg(feature = "nightly")]
attr.span()
.unwrap()
.error("multiple fields marked with #[core]")
Expand All @@ -73,6 +74,7 @@ pub fn read_attrs(ast: &mut DeriveInput) -> Result<Args> {
if field.ty != parse_quote! { <Self as kas::LayoutData>::Data }
&& field.ty != parse_quote! { <Self as LayoutData>::Data }
{
#[cfg(feature = "nightly")]
field
.ty
.span()
Expand All @@ -82,6 +84,7 @@ pub fn read_attrs(ast: &mut DeriveInput) -> Result<Args> {
}
layout_data = Some(member(i, field.ident.clone()));
} else {
#[cfg(feature = "nightly")]
attr.span()
.unwrap()
.error("multiple fields marked with #[layout_data]")
Expand All @@ -103,6 +106,7 @@ pub fn read_attrs(ast: &mut DeriveInput) -> Result<Args> {
if widget.is_none() {
widget = Some(syn::parse2(attr.tokens)?);
} else {
#[cfg(feature = "nightly")]
attr.span()
.unwrap()
.error("multiple #[widget(..)] attributes on type")
Expand All @@ -112,6 +116,7 @@ pub fn read_attrs(ast: &mut DeriveInput) -> Result<Args> {
if handler.is_none() {
handler = Some(syn::parse2(attr.tokens)?);
} else {
#[cfg(feature = "nightly")]
attr.span()
.unwrap()
.error("multiple #[handler(..)] attributes on type")
Expand Down
17 changes: 11 additions & 6 deletions kas-macros/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,18 @@
// https://www.apache.org/licenses/LICENSE-2.0

#![recursion_limit = "128"]
#![feature(proc_macro_diagnostic)]
#![cfg_attr(feature = "nightly", feature(proc_macro_diagnostic))]

extern crate proc_macro;

mod args;

use proc_macro2::{Span, TokenStream};
use proc_macro_hack::proc_macro_hack;
use quote::{quote, TokenStreamExt};
use std::fmt::Write;
use syn::punctuated::Punctuated;
#[cfg(feature = "nightly")]
use syn::spanned::Spanned;
use syn::token::Comma;
use syn::{parse_macro_input, parse_quote};
Expand Down Expand Up @@ -201,9 +203,7 @@ pub fn derive(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
/// Macro to create a widget with anonymous type
///
/// See the [`kas::macros`](../kas/macros/index.html) module documentation.
///
/// Currently usage of this macro requires `#![feature(proc_macro_hygiene)]`.
#[proc_macro]
#[proc_macro_hack]
pub fn make_widget(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
let mut find_handler_ty_buf: Vec<(Ident, Type)> = vec![];
// find type of handler's message; return None on error
Expand All @@ -222,16 +222,19 @@ pub fn make_widget(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
for impl_block in impls {
for f in &impl_block.1 {
if f.sig.ident == *handler {
if let Some(x) = x {
if let Some(_x) = x {
#[cfg(feature = "nightly")]
handler
.span()
.unwrap()
.error("multiple methods with this name")
.emit();
x.0.span()
#[cfg(feature = "nightly")]
_x.0.span()
.unwrap()
.error("first method with this name")
.emit();
#[cfg(feature = "nightly")]
f.sig
.ident
.span()
Expand All @@ -241,6 +244,7 @@ pub fn make_widget(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
return None;
}
if f.sig.inputs.len() != 3 {
#[cfg(feature = "nightly")]
f.sig.span()
.unwrap()
.error("handler functions must have signature: fn handler(&mut self, tk: &mut dyn TkWindow, msg: T)")
Expand All @@ -260,6 +264,7 @@ pub fn make_widget(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
find_handler_ty_buf.push((handler.clone(), x.1.clone()));
Some(x.1)
} else {
#[cfg(feature = "nightly")]
handler
.span()
.unwrap()
Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/calculator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,17 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Simple calculator example (lots of buttons, grid layout)
#![feature(proc_macro_hygiene)]
#![recursion_limit = "1024"]

use std::num::ParseFloatError;
use std::str::FromStr;

use kas::class::HasText;
use kas::event::VirtualKeyCode as VK;
use kas::event::{Response, VoidMsg};
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::widget::{EditBox, TextButton, Window};
use kas::TkWindow;
use kas::{make_widget, TkWindow};

#[derive(Clone, Debug, VoidMsg)]
enum Key {
Expand Down
4 changes: 1 addition & 3 deletions kas-wgpu/examples/clock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Clock example (simple periodically updated display)
#![feature(proc_macro_hygiene)]

extern crate chrono;

Expand All @@ -13,9 +12,8 @@ use std::time::Duration;

use kas::class::HasText;
use kas::event::{Callback, VoidMsg};
use kas::macros::make_widget;
use kas::widget::{Label, Window};
use kas::{TkWindow, WidgetCore};
use kas::{make_widget, TkWindow, WidgetCore};

fn main() {
let mut window = Window::new(
Expand Down
1 change: 0 additions & 1 deletion kas-wgpu/examples/clock_expanded.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Clock example, with the make_widget macro expanded
#![feature(proc_macro_hygiene)]

extern crate chrono;

Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/counter.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,13 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Counter example (simple button)
#![feature(proc_macro_hygiene)]
#![recursion_limit = "256"]

use kas::class::HasText;
use kas::event::{VoidMsg, VoidResponse};
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::widget::{Label, TextButton, Window};
use kas::TkWindow;
use kas::{make_widget, TkWindow};

#[derive(Clone, Debug, VoidMsg)]
enum Message {
Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/dynamic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,14 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Dynamic widget example
#![feature(proc_macro_hygiene)]
#![recursion_limit = "256"]

use kas::class::HasText;
use kas::event::{Callback, Response, VoidMsg};
use kas::layout::Vertical;
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::widget::{DynVec, EditBox, Label, ScrollRegion, TextButton, Window};
use kas::TkWindow;
use kas::{make_widget, TkWindow};

#[derive(Clone, Debug, VoidMsg)]
enum Control {
Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/gallery.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,12 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Gallery of all widgets
#![feature(proc_macro_hygiene)]
#![recursion_limit = "512"]

use kas::event::{VoidMsg, VoidResponse};
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::widget::*;
use kas::TkWindow;
use kas::{make_widget, TkWindow};

#[derive(Clone, Debug, VoidMsg)]
enum Item {
Expand Down
4 changes: 2 additions & 2 deletions kas-wgpu/examples/layout.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,10 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Gallery of all widgets
#![feature(proc_macro_hygiene)]
#![recursion_limit = "256"]

use kas::event::VoidMsg;
use kas::macros::make_widget;
use kas::make_widget;
use kas::widget::{CheckBox, EditBox, Label, Window};

fn main() -> Result<(), winit::error::OsError> {
Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/stopwatch.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,16 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Counter example (simple button)
#![feature(proc_macro_hygiene)]
#![recursion_limit = "512"]

use std::fmt::Write;
use std::time::{Duration, Instant};

use kas::class::HasText;
use kas::event::{Callback, Response, VoidMsg};
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::widget::{Label, TextButton, Window};
use kas::TkWindow;
use kas::{make_widget, TkWindow};

#[derive(Clone, Debug, VoidMsg)]
enum Control {
Expand Down
6 changes: 3 additions & 3 deletions kas-wgpu/examples/theme.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,16 @@
// https://www.apache.org/licenses/LICENSE-2.0

//! Custom theme demo
#![feature(proc_macro_hygiene)]
#![recursion_limit = "256"]

use std::cell::Cell;

use kas::draw::Colour;
use kas::event::{VoidMsg, VoidResponse};
use kas::macros::{make_widget, VoidMsg};
use kas::macros::VoidMsg;
use kas::theme::Theme;
use kas::widget::*;
use kas::TkWindow;
use kas::{make_widget, TkWindow};

use kas_wgpu::draw::*;
use kas_wgpu::glyph::Font;
Expand Down
6 changes: 6 additions & 0 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -45,3 +45,9 @@ pub mod macros;
pub use crate::data::*;
pub use crate::toolkit::*;
pub use crate::traits::*;

use proc_macro_hack::proc_macro_hack;

/// See [The `make_widget` macro]: #the-make_widget-macro
#[proc_macro_hack(support_nested)]
pub use kas_macros::make_widget;
12 changes: 2 additions & 10 deletions src/macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,12 +21,6 @@
//! because procedural macros must be defined in a special crate. The
//! `kas-macros` crate should not be used directly.
//!
//! Note further that these macros require gated functionality only available
//! in nightly `rustc` builds:
//! ```
//! #![feature(proc_macro_hygiene)]
//! ```
//!
//! [`make_widget`]: #the-make_widget-macro
//! [`derive(Widget)`]: #the-derivewidget-macro
//! [`derive(VoidMsg)`]: #the-derivevoidmsg-macro
Expand Down Expand Up @@ -215,9 +209,7 @@
//! ### Example
//!
//! ```
//! #![feature(proc_macro_hygiene)]
//!
//! use kas::macros::{make_widget};
//! use kas::make_widget;
//! use kas::widget::TextButton;
//!
//! #[derive(Copy, Clone, Debug)]
Expand Down Expand Up @@ -257,4 +249,4 @@
//! [`Handler`]: crate::event::Handler
//! [`Handler::Msg`]: crate::event::Handler::Msg

pub use kas_macros::{make_widget, VoidMsg, Widget};
pub use kas_macros::{VoidMsg, Widget};