Skip to content

RAprogramm/yew-nav-link

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

46 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

yew-nav-link

Navigation link component for Yew with automatic active state detection.

Crates.io docs.rs Downloads MSRV License: MIT REUSE Codecov Hits-of-Code Hits-of-Code

Table of Contents

Overview

yew-nav-link provides a NavLink component that wraps Yew Router's Link with automatic active state management. When the target route matches the current URL, an active CSS class is applied automatically.

Installation

[dependencies]
yew-nav-link = "0.4"

Requirements

Dependency Version
yew 0.22+
yew-router 0.19+

Examples

Full working examples are available in the examples/ directory:

Example Description
basic Simple navigation with Home, About, Contact pages
bootstrap Integration with Bootstrap 5 navbar
tailwind Sidebar navigation styled with Tailwind CSS
nested-routes Multi-level navigation with partial matching

Running Examples

# Install prerequisites (once)
rustup target add wasm32-unknown-unknown
cargo install trunk

# Run example
cd examples/basic
trunk serve

Open http://127.0.0.1:8080 in your browser.

Usage

Component Syntax

use yew::prelude::*;
use yew_nav_link::NavLink;
use yew_router::prelude::*;

#[derive(Clone, PartialEq, Routable)]
enum Route {
    #[at("/")]
    Home,
    #[at("/about")]
    About,
}

#[component]
fn Navigation() -> Html {
    html! {
        <nav>
            <NavLink<Route> to={Route::Home}>{ "Home" }</NavLink<Route>>
            <NavLink<Route> to={Route::About}>{ "About" }</NavLink<Route>>
        </nav>
    }
}

Function Syntax

For text-only links, use nav_link with explicit Match mode:

use yew::prelude::*;
use yew_nav_link::{nav_link, Match};
use yew_router::prelude::*;

#[derive(Clone, PartialEq, Routable)]
enum Route {
    #[at("/")]
    Home,
    #[at("/docs")]
    Docs,
}

#[component]
fn Menu() -> Html {
    html! {
        <nav>
            { nav_link(Route::Home, "Home", Match::Exact) }
            { nav_link(Route::Docs, "Docs", Match::Partial) }
        </nav>
    }
}

Partial Matching

Use partial prop to keep parent links active on nested routes:

use yew::prelude::*;
use yew_nav_link::NavLink;
use yew_router::prelude::*;

#[derive(Clone, PartialEq, Routable)]
enum Route {
    #[at("/docs")]
    Docs,
    #[at("/docs/api")]
    DocsApi,
}

#[component]
fn Navigation() -> Html {
    html! {
        <nav>
            // Active on /docs, /docs/api, /docs/*
            <NavLink<Route> to={Route::Docs} partial=true>{ "Docs" }</NavLink<Route>>
        </nav>
    }
}

CSS Classes

The component applies these classes to the rendered <a> element:

Class When Applied
nav-link Always
active Route matches current URL

Bootstrap Integration

<ul class="nav nav-pills">
    <li class="nav-item">
        <NavLink<Route> to={Route::Home}>{ "Home" }</NavLink<Route>>
        <!-- Renders: <a class="nav-link active" href="/">Home</a> -->
    </li>
</ul>

Tailwind CSS

.nav-link {
    @apply px-4 py-2 text-gray-600 hover:text-gray-900;
}
.nav-link.active {
    @apply text-blue-600 font-semibold;
}

API Reference

NavLink<R> Component

Prop Type Default Description
to R: Routable required Target route
children Children required Link content
partial bool false Enable prefix matching

Match Enum

Variant Description
Match::Exact Active only on exact path match
Match::Partial Active when current path starts with target

nav_link<R> Function

fn nav_link<R: Routable>(to: R, children: &str, match_mode: Match) -> Html

Creates a NavLink with text content and specified match mode.

Coverage

Code coverage is tracked via Codecov. Target: 95%+ coverage.

Sunburst

The inner-most circle is the entire project, moving away from the center are folders then, finally, a single file. The size and color of each slice represents the number of statements and the coverage, respectively.

Sunburst

Grid

Each block represents a single file in the project. The size and color of each block represents the number of statements and the coverage, respectively.

Grid

Icicle

The top section represents the entire project. Proceeding with folders and finally individual files. The size and color of each slice represents the number of statements and the coverage, respectively.

Icicle

License

Licensed under the MIT License.