diff --git a/NOTICE b/NOTICE index 9bffbd5b..649c5b8d 100644 --- a/NOTICE +++ b/NOTICE @@ -50,4 +50,13 @@ Spring motion constants (resources/css/tokens/motion.css) From androidx Compose Material 3, tokens/ExpressiveMotionTokens.kt. Copyright The Android Open Source Project. Apache License 2.0. +Material Design 3 documentation (resources/boost/guidelines/material-3.blade.php, +resources/boost/skills/material-3-design/SKILL.md, docs/reference/m3) + Rules, tables and wording condensed from https://m3.material.io (Foundations, Styles, + Components), which Google publishes under the Creative Commons Attribution 4.0 License + except as otherwise noted; the numeric token values from androidx Compose Material 3's + token files. + Copyright Google LLC (CC BY 4.0, https://creativecommons.org/licenses/by/4.0/); + Copyright The Android Open Source Project (Apache License 2.0). + A copy of the Apache License 2.0 is available at https://www.apache.org/licenses/LICENSE-2.0. diff --git a/tests/Feature/BoostResourcesTest.php b/tests/Feature/BoostResourcesTest.php index c4b0be7c..f27c44bf 100644 --- a/tests/Feature/BoostResourcesTest.php +++ b/tests/Feature/BoostResourcesTest.php @@ -28,3 +28,65 @@ it('names every component in the skill', function () { expect($undocumented)->toBeEmpty(); }); + +const GUIDELINE_PATH = __DIR__.'/../../resources/boost/guidelines/material-3.blade.php'; +const DESIGN_SKILL_PATH = __DIR__.'/../../resources/boost/skills/material-3-design/SKILL.md'; + +it('keeps the Material 3 guideline short, verbatim and always on', function () { + $guideline = File::get(GUIDELINE_PATH); + + expect($guideline) + ->toStartWith("@verbatim\n") + ->toContain("\n@endverbatim") + ->toContain("\n## Material 3\n"); + + // Boost inlines every guideline into every session, so this one must stay a page. + expect(substr_count($guideline, "\n"))->toBeLessThan(120); +}); + +it('gives the design skill the frontmatter Boost requires', function () { + $skill = File::get(DESIGN_SKILL_PATH); + + expect($skill) + ->toStartWith("---\n") + ->toContain("\nname: material-3-design\n") + ->toMatch('/\ndescription: \S.+\n/'); +}); + +it('carries every guideline section in the design skill', function () { + preg_match_all('/^### (.+)$/m', File::get(GUIDELINE_PATH), $sections); + preg_match_all('/^## (.+)$/m', File::get(DESIGN_SKILL_PATH), $chapters); + + expect($sections[1])->not->toBeEmpty(); + expect(array_values(array_diff($sections[1], $chapters[1])))->toBe([]); +}); + +it('names every token family and breakpoint in the design skill', function () { + $skill = File::get(DESIGN_SKILL_PATH); + + $families = collect(File::files(__DIR__.'/../../resources/css/tokens')) + ->flatMap(function (SplFileInfo $file): array { + preg_match_all('/--md-(?:sys|ref)-[a-z]+-/', $file->getContents(), $matches); + + return $matches[0]; + }) + ->unique() + ->values(); + + expect($families)->not->toBeEmpty(); + + foreach ($families as $family) { + expect($skill)->toContain($family.'*'); + } + + foreach (['medium', 'expanded', 'large', 'extra-large'] as $breakpoint) { + expect($skill)->toContain("`{$breakpoint}:`"); + } +}); + +it('attributes the design skill to Google', function () { + expect(File::get(DESIGN_SKILL_PATH)) + ->toContain("\n## Attribution\n") + ->toContain('Creative Commons Attribution 4.0') + ->toContain('Apache License 2.0'); +});