Repository: hakimel/Ladda
Branch: master
Commit: c7a9c44c5e9d
Files: 23
Total size: 57.6 KB
Directory structure:
gitextract_hiwuh9bh/
├── .gitattributes
├── .gitignore
├── .npmrc
├── CHANGELOG.md
├── CONTRIBUTING.md
├── Gruntfile.cjs
├── LICENSE
├── README.md
├── css/
│ ├── ladda-themed.scss
│ └── ladda.scss
├── js/
│ ├── ladda.d.ts
│ └── ladda.js
├── package.json
├── rollup.config.js
└── site/
├── bootstrap.html
├── bootstrap3.html
├── bootstrap4.html
├── demo.css
├── form.html
├── form.js
├── index.html
├── index.js
└── rtl.html
================================================
FILE CONTENTS
================================================
================================================
FILE: .gitattributes
================================================
# so website files won't cause project language to be shown as HTML
site/* linguist-documentation
================================================
FILE: .gitignore
================================================
/node_modules/
/dist/
/site/dist/
================================================
FILE: .npmrc
================================================
package-lock=false
================================================
FILE: CHANGELOG.md
================================================
# Changelog
All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [Unreleased]
## [2.0.3] - 2021-12-02
### Fixed
- Deprecated slash as division when using Dart Sass (issue [#109])
## [2.0.2] - 2021-09-01
### Changed
- Set package type to `module` to better support native ES module imports
- Code cleanup and documentation improvements
## [2.0.1] - 2018-05-14
### Added
- Support for reassigning `$spinnerSize` Sass variable (PR [#81])
- Re-included Sass files in the npm package
## [2.0.0] - 2018-05-13
### Added
- Built-in TypeScript definitions
- Support for the `style-src 'self';` Content Security Policy
### Changed
- Rewritten as a native ES6 module using spin.js v4
### Removed
- Deprecated jQuery API
- Deprecated `enable` and `disable` methods
- Bower support
- Support for Internet Explorer 9 (not supported by spin.js v4)
## [1.0.6] - 2018-02-04
### Added
- Support for forms with `novalidate` attribute (issue [#80])
### Fixed
- Protruding outline in Chrome on buttons with a progress bar
## [1.0.5] - 2017-09-24
### Added
- Validation for URL input fields in IE 9
### Fixed
- Detection of required HTML5 inputs in IE 9
- Bug where the `stop()` method would remove a button's disabled state even though Ladda was already stopped (issue [#68])
## [1.0.4] - 2017-08-27
### Fixed
- Incorrect return value for jQuery `isLoading` argument (PR [#62], issue [#65])
Note that the Ladda jQuery API is deprecated - it is recommended to use the plain JavaScript API instead.
## [1.0.3] - 2017-08-27
### Changed
- Code cleanup and performance improvements
### Deprecated
- Undocumented `enable` and `disable` instance methods
## [1.0.2] - 2017-08-27
### Added
- Support for right-to-left text direction (PR [#66])
### Deprecated
- jQuery API
## [1.0.1] - 2017-07-11
### Fixed
- Bug where focus outline protruded outside button in Chrome
### Removed
- Unnecessary `toArray()` function
## [1.0.0] - 2016-03-08
### Added
- `data-spinner-lines` attribute for controlling the number of lines in the spinner (PR [#50])
### Changed
- The `ladda-button` class and `data-style` attribute are now automatically set if missing (PR [#52])
- `ladda-label` now wraps existing elements instead of reinserting them using `innerHTML` (PR [#55])
- `checkValidity` is now used to validate forms where supported (PR [#58])
## [0.9.8] - 2015-04-05
### Added
- `main` field to package.json for easier CommonJS loading (PR [#47])
- Validity check for email inputs (PR [#48])
### Changed
- Updated spin.js to v2.0.2 (PR [#49])
## [0.9.7] - 2015-01-17
### Fixed
- The Ladda theme is now baked into the output ladda.min.css file again. Was broken after upgrading grunt Sass in v0.9.5.
## [0.9.6] - 2015-01-16
### Removed
- Unintended references to non-existing sourcemap files that were introduced in v0.9.5 as part of the grunt Sass upgrade.
## [0.9.5] - 2015-01-16
### Fixed
- Validation of required select, radio, and checkbox inputs (PR [#43])
- The `ladda-spinner` element is no longer created if it already exists (PR [#44])
## [0.9.4] - 2014-06-21
### Added
- `remove()` method to Ladda instances to stop memory leaks (PR [#36])
### Changed
- Updated from spin.js v1.3 to v2.0 (PR [#37])
## [0.9.3] - 2014-04-16
### Added
- jQuery wrapper (PR [#33])
### Fixed
- Overlay effect in Safari
- Missing CommonJS requirement
## [0.9.2] - 2013-12-03
### Fixed
- Spinner height is now calculated when spinning starts as opposed to when Ladda is initialized. This fixes spinner sizing issues with buttons that are initially hidden.
## [0.9.1] - 2013-11-27
### Fixed
- Issue where loading animations did not start for buttons outside of forms. This only affected use through the `Ladda.bind()` method.
## [0.9.0] - 2013-10-23
### Changed
- Ladda now confirms that all `required` fields in its parent form are filled out before starting the spinning animation. Note that this only applies to buttons bound using `Ladda.bind()`.
### Removed
- jQuery dependencies
## [0.8.0] - 2013-09-05
### Added
- `data-spinner-color` attribute for configuring spinner color
### Changed
- Disabled pointer events on spinner element
### Fixed
- Array conversion bug which prevented binding Ladda to a selector
- Default `z-index` value, was `initial` but should be `auto`
## [0.7.0] - 2013-07-19
### Added
- `startAfter(delay)` method
### Changed
- Limit progress value to number between `0` and `1`
### Fixed
- Issue that prevented forms from submitting
- Error that caused IE 8 to blow up on page load (still not supported, though)
## [0.6.0] - 2013-07-07
### Added
- `data-spinner-size` attribute for setting explicit pixel size of spinner
### Changed
- `ladda-label` wrapper is now automatically created if it doesn't exist
## [0.5.2] - 2013-06-27
### Added
- bower.json
### Fixed
- Error when passing element to `Ladda.create()`
## [0.5.1] - 2013-06-19
### Added
- Bootstrap integration example
## [0.5.0] - 2013-06-19
### Changed
- Split visual and functional styles into separate stylesheets for framework compatibility (issue [#20])
- Spinner size is now automatically calculated using JavaScript
## [0.4.2] - 2013-06-14
### Added
- Size options (issue [#15])
- Mint color preset
### Changed
- All settings are now applied via `data-*` attributes
## [0.4.1] - 2013-06-14
### Added
- `enable` and `disable` helper methods
## [0.4.0] - 2013-06-14
### Added
- Common.js / AMD module support
- Grunt build file and minified files in /dist folder
### Changed
- Migrated from plain CSS to Sass
## [0.3.0] - 2013-06-08
### Added
- Built-in progress bars which can be controlled using `setProgress` method
### Changed
- Replaced spinner GIF with spin.js
- `spinner` and `label` classes are now prefixed with `ladda-`
### Removed
- Hardcoded timeout
## [0.2.0] - 2013-06-05
### Added
- Simple JavaScript API
- Instructions in readme
- MIT license
## [0.1.0] - 2013-06-05
- Initial release
[Unreleased]: https://github.com/hakimel/Ladda/compare/2.0.3...HEAD
[2.0.3]: https://github.com/hakimel/Ladda/compare/2.0.2...2.0.3
[2.0.2]: https://github.com/hakimel/Ladda/compare/2.0.1...2.0.2
[2.0.1]: https://github.com/hakimel/Ladda/compare/2.0.0...2.0.1
[2.0.0]: https://github.com/hakimel/Ladda/compare/1.0.6...2.0.0
[1.0.6]: https://github.com/hakimel/Ladda/compare/1.0.5...1.0.6
[1.0.5]: https://github.com/hakimel/Ladda/compare/1.0.4...1.0.5
[1.0.4]: https://github.com/hakimel/Ladda/compare/1.0.3...1.0.4
[1.0.3]: https://github.com/hakimel/Ladda/compare/1.0.2...1.0.3
[1.0.2]: https://github.com/hakimel/Ladda/compare/1.0.1...1.0.2
[1.0.1]: https://github.com/hakimel/Ladda/compare/1.0.0...1.0.1
[1.0.0]: https://github.com/hakimel/Ladda/compare/0.9.8...1.0.0
[0.9.8]: https://github.com/hakimel/Ladda/compare/0.9.7...0.9.8
[0.9.7]: https://github.com/hakimel/Ladda/compare/0.9.6...0.9.7
[0.9.6]: https://github.com/hakimel/Ladda/compare/0.9.5...0.9.6
[0.9.5]: https://github.com/hakimel/Ladda/compare/0.9.4...0.9.5
[0.9.4]: https://github.com/hakimel/Ladda/compare/0.9.3...0.9.4
[0.9.3]: https://github.com/hakimel/Ladda/compare/0.9.2...0.9.3
[0.9.2]: https://github.com/hakimel/Ladda/compare/0.9.1...0.9.2
[0.9.1]: https://github.com/hakimel/Ladda/compare/0.9.0...0.9.1
[0.9.0]: https://github.com/hakimel/Ladda/compare/0.8.0...0.9.0
[0.8.0]: https://github.com/hakimel/Ladda/compare/0.7.0...0.8.0
[0.7.0]: https://github.com/hakimel/Ladda/compare/0.6.0...0.7.0
[0.6.0]: https://github.com/hakimel/Ladda/compare/0.5.2...0.6.0
[0.5.2]: https://github.com/hakimel/Ladda/compare/0.5.1...0.5.2
[0.5.1]: https://github.com/hakimel/Ladda/compare/0.5.0...0.5.1
[0.5.0]: https://github.com/hakimel/Ladda/compare/0.4.2...0.5.0
[0.4.2]: https://github.com/hakimel/Ladda/compare/0.4.1...0.4.2
[0.4.1]: https://github.com/hakimel/Ladda/compare/0.4.0...0.4.1
[0.4.0]: https://github.com/hakimel/Ladda/compare/0.3.0...0.4.0
[0.3.0]: https://github.com/hakimel/Ladda/compare/0.2.0...0.3.0
[0.2.0]: https://github.com/hakimel/Ladda/compare/0.1.0...0.2.0
[0.1.0]: https://github.com/hakimel/Ladda/tree/0.1.0
[#109]: https://github.com/hakimel/Ladda/issues/109
[#81]: https://github.com/hakimel/Ladda/pull/81
[#80]: https://github.com/hakimel/Ladda/issues/80
[#68]: https://github.com/hakimel/Ladda/issues/68
[#66]: https://github.com/hakimel/Ladda/pull/66
[#65]: https://github.com/hakimel/Ladda/issues/65
[#62]: https://github.com/hakimel/Ladda/pull/62
[#58]: https://github.com/hakimel/Ladda/pull/58
[#55]: https://github.com/hakimel/Ladda/pull/55
[#52]: https://github.com/hakimel/Ladda/pull/52
[#50]: https://github.com/hakimel/Ladda/pull/50
[#49]: https://github.com/hakimel/Ladda/pull/49
[#48]: https://github.com/hakimel/Ladda/pull/48
[#47]: https://github.com/hakimel/Ladda/pull/47
[#44]: https://github.com/hakimel/Ladda/pull/44
[#43]: https://github.com/hakimel/Ladda/pull/43
[#37]: https://github.com/hakimel/Ladda/pull/37
[#36]: https://github.com/hakimel/Ladda/pull/36
[#33]: https://github.com/hakimel/Ladda/pull/33
[#20]: https://github.com/hakimel/Ladda/issues/20
[#15]: https://github.com/hakimel/Ladda/issues/15
================================================
FILE: CONTRIBUTING.md
================================================
# Contributing
Clone the repository and run `npm install` to install development dependencies and compile the project.
Then run `npm start` to watch files for changes and start a static file server for viewing the test site.
Open http://localhost:8000/ in your browser to view the site.
================================================
FILE: Gruntfile.cjs
================================================
const sass = require('sass');
module.exports = function (grunt) {
'use strict';
// Project configuration
grunt.initConfig({
sass: {
options: {
implementation: sass,
outputStyle: 'compressed',
},
dist: {
files: {
'dist/ladda.min.css': 'css/ladda-themed.scss',
'dist/ladda-themeless.min.css': 'css/ladda.scss'
}
}
},
jshint: {
options: {
// enforcing
esversion: 6,
curly: true,
eqeqeq: true,
freeze: true,
futurehostile: true,
globals: {
module: false,
console: false,
define: false
},
latedef: "nofunc",
maxparams: 3,
noarg: true,
nocomma: true,
nonbsp: true,
nonew: true,
undef: true,
unused: true,
// environments
browser: true,
node: true,
},
files: [ 'Gruntfile.cjs', 'js/ladda.js' ]
},
connect: {
server: {
options: {
port: 8000,
base: 'site',
}
}
},
copy: {
css: {
files: [
{ src: ['dist/ladda*.min.css'], dest: 'site/' }
]
}
},
watch: {
main: {
files: [ 'Gruntfile.js', 'js/ladda.js' ],
tasks: 'js',
options: {
livereload: true,
},
},
theme: {
files: [ 'css/*.scss' ],
tasks: 'css',
options: {
livereload: true,
},
}
}
});
// Dependencies
grunt.loadNpmTasks('grunt-contrib-jshint');
grunt.loadNpmTasks('grunt-contrib-watch');
grunt.loadNpmTasks('grunt-sass');
grunt.loadNpmTasks('grunt-contrib-connect');
grunt.loadNpmTasks('grunt-contrib-copy');
// Default task
grunt.registerTask('default', ['jshint', 'css']);
// Theme task
grunt.registerTask('css', ['sass', 'copy']);
// Serve presentation locally
grunt.registerTask('serve', ['connect', 'watch']);
};
================================================
FILE: LICENSE
================================================
Copyright (C) 2017 Hakim El Hattab, http://hakim.se
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
================================================
FILE: README.md
================================================
# Ladda
Buttons with built-in loading indicators, effectively bridging the gap between action and feedback.
[Check out the demo page](https://lab.hakim.se/ladda/).
## Installation
`npm install ladda`
### Module bundling
Ladda 2.x is distributed as a standard ES6 module. Since not all browsers/environments support native
ES6 modules, it is recommended to use a bundler such as <a href="https://rollupjs.org/">Rollup</a>,
<a href="https://parceljs.org/">Parcel</a>, or <a href="https://webpack.js.org/">Webpack</a> to create
a production-ready code bundle.
## Usage
### CSS
You will need to include ONE of the two style sheets in the **/dist** directory.
If you want the button styles used on the demo page, use the **ladda.min.css** file.
If you want to have the functional buttons without the visual style (colors, padding, etc.),
use the **ladda-themeless.min.css** file.
### HTML
Below is an example of a button using the `expand-right` animation style.
```html
<button class="ladda-button" data-style="expand-right">Submit</button>
```
When the JS code runs to bind Ladda to the button, the `ladda-button` class
will be automatically added if it doesn't already exist. Additionally, a span
with class `ladda-label` will automatically wrap the button text, resulting
in the following DOM structure:
```html
<button class="ladda-button" data-style="expand-right">
<span class="ladda-label">Submit</span>
</button>
```
Buttons accept the following attributes:
- **data-style**: one of the button styles *[required]*
- expand-left, expand-right, expand-up, expand-down
- contract, contract-overlay
- zoom-in, zoom-out
- slide-left, slide-right, slide-up, slide-down
- **data-color**: green/red/blue/purple/mint
- **data-size**: xs/s/l/xl, defaults to medium
- **data-spinner-size**: pixel dimensions of spinner, defaults to dynamic size based on the button height
- **data-spinner-color**: a hex code or any named CSS color, defaults to `#fff`
- **data-spinner-lines**: the number of lines for the spinner, defaults to `12`
### JavaScript
Start by importing the Ladda module:
```javascript
import * as Ladda from 'ladda';
```
The following approach is recommended for JavaScript control over your buttons:
```javascript
// Create a new instance of ladda for the specified button
var l = Ladda.create(document.querySelector('.my-button'));
// Start loading
l.start();
// Will display a progress bar for 50% of the button width
l.setProgress(0.5);
// Stop loading
l.stop();
// Toggle between loading/not loading states
l.toggle();
// Check the current state
l.isLoading();
// Delete the button's ladda instance
l.remove();
```
To show the loading animation for a form that is submitted to the server
(always resulting in a page reload) the `bind()` method can be used:
```javascript
// Automatically trigger the loading animation on click
Ladda.bind('button[type=submit]');
// Same as the above but automatically stops after two seconds
Ladda.bind('button[type=submit]', {timeout: 2000});
```
Note: when using the `bind()` method on buttons that are inside a form,
loading indicators will not be shown until the form is valid.
All loading animations on the page can be stopped by using:
```javascript
Ladda.stopAll();
```
## Browser support
Ladda has been tested in Firefox, Microsoft Edge, Chrome, and Internet Explorer 11.
It also Should Work™ in Safari and Internet Explorer 10.
## Changelog
<https://github.com/hakimel/Ladda/blob/master/CHANGELOG.md>
## License
MIT
================================================
FILE: css/ladda-themed.scss
================================================
/*!
* Ladda including the default theme.
*/
@import "ladda";
/*************************************
* CONFIG
*/
$green: #2aca76;
$blue: #53b5e6;
$red: #ea8557;
$purple: #9973C2;
$mint: #16a085;
/*************************************
* BUTTON THEME
*/
.ladda-button {
background: #666;
border: 0;
padding: 14px 18px;
font-size: 18px;
cursor: pointer;
color: #fff;
border-radius: 2px;
border: 1px solid transparent;
-webkit-appearance: none;
-webkit-font-smoothing: antialiased;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
&:hover {
border-color: rgba( 0, 0, 0, 0.07 );
background-color: #888;
}
@include buttonColor( 'green', $green );
@include buttonColor( 'blue', $blue );
@include buttonColor( 'red', $red );
@include buttonColor( 'purple', $purple );
@include buttonColor( 'mint', $mint );
&[disabled],
&[data-loading] {
border-color: rgba( 0, 0, 0, 0.07 );
&, &:hover {
cursor: default;
background-color: #999;
}
}
&[data-size=xs] {
padding: 4px 8px;
.ladda-label {
font-size: 0.7em;
}
}
&[data-size=s] {
padding: 6px 10px;
.ladda-label {
font-size: 0.9em;
}
}
&[data-size=l] .ladda-label {
font-size: 1.2em;
}
&[data-size=xl] .ladda-label {
font-size: 1.5em;
}
}
================================================
FILE: css/ladda.scss
================================================
/*!
* Ladda
* http://lab.hakim.se/ladda
* MIT licensed
*
* Copyright (C) 2018 Hakim El Hattab, http://hakim.se
*/
/*************************************
* CONFIG
*/
@use "sass:math";
$spinnerSize: 32px !default;
/*************************************
* MIXINS
*/
@mixin buttonColor( $name, $color ) {
&[data-color=#{$name}] {
background: $color;
&:hover {
background-color: lighten( $color, 5% );
}
}
}
/*************************************
* Opacity animation for spin.js
*/
@keyframes ladda-spinner-line-fade {
0%, 100% {
opacity: 0.22; /* minimum opacity */
}
1% {
opacity: 1;
}
}
/*************************************
* BUTTON BASE
*/
.ladda-button {
position: relative;
}
/* Spinner animation */
.ladda-button .ladda-spinner {
position: absolute;
z-index: 2;
display: inline-block;
width: $spinnerSize;
top: 50%;
margin-top: 0;
opacity: 0;
pointer-events: none;
}
/* Button label */
.ladda-button .ladda-label {
position: relative;
z-index: 3;
}
/* Progress bar */
.ladda-button .ladda-progress {
position: absolute;
width: 0;
height: 100%;
left: 0;
top: 0;
background: rgba( 0, 0, 0, 0.2 );
display: none;
transition: 0.1s linear all;
}
.ladda-button[data-loading] .ladda-progress {
display: block;
}
/*************************************
* EASING
*/
.ladda-button,
.ladda-button .ladda-spinner,
.ladda-button .ladda-label {
transition: 0.3s cubic-bezier(0.175, 0.885, 0.320, 1.275) all;
}
.ladda-button[data-style=zoom-in],
.ladda-button[data-style=zoom-in] .ladda-spinner,
.ladda-button[data-style=zoom-in] .ladda-label,
.ladda-button[data-style=zoom-out],
.ladda-button[data-style=zoom-out] .ladda-spinner,
.ladda-button[data-style=zoom-out] .ladda-label {
transition: 0.3s ease all;
}
/*************************************
* EXPAND RIGHT
*/
.ladda-button[data-style=expand-right] {
.ladda-spinner {
right: math.div($spinnerSize, -2) + 10;
}
&[data-size="s"] .ladda-spinner,
&[data-size="xs"] .ladda-spinner {
right: math.div($spinnerSize, -2) + 4;
}
&[data-loading] {
padding-right: 56px;
.ladda-spinner {
opacity: 1;
}
&[data-size="s"],
&[data-size="xs"] {
padding-right: 40px;
}
}
}
/*************************************
* EXPAND LEFT
*/
.ladda-button[data-style=expand-left] {
.ladda-spinner {
left: $spinnerSize * 0.5 + 10;
}
&[data-size="s"] .ladda-spinner,
&[data-size="xs"] .ladda-spinner {
left: 4px;
}
&[data-loading] {
padding-left: 56px;
.ladda-spinner {
opacity: 1;
}
&[data-size="s"],
&[data-size="xs"] {
padding-left: 40px;
}
}
}
/*************************************
* EXPAND UP
*/
.ladda-button[data-style=expand-up] {
overflow: hidden;
.ladda-spinner {
top: -$spinnerSize;
left: 50%;
margin-left: 0;
}
&[data-loading] {
padding-top: 54px;
.ladda-spinner {
opacity: 1;
top: ($spinnerSize * 0.5) + 10;
margin-top: 0;
}
&[data-size="s"],
&[data-size="xs"] {
padding-top: 32px;
.ladda-spinner {
top: 4px;
}
}
}
}
/*************************************
* EXPAND DOWN
*/
.ladda-button[data-style=expand-down] {
overflow: hidden;
.ladda-spinner {
top: 62px;
left: 50%;
margin-left: 0;
}
&[data-size="s"] .ladda-spinner,
&[data-size="xs"] .ladda-spinner {
top: 40px;
}
&[data-loading] {
padding-bottom: 54px;
.ladda-spinner {
opacity: 1;
}
&[data-size="s"],
&[data-size="xs"] {
padding-bottom: 32px;
}
}
}
/*************************************
* SLIDE LEFT
*/
.ladda-button[data-style=slide-left] {
overflow: hidden;
.ladda-label {
position: relative;
}
.ladda-spinner {
left: 100%;
margin-left: 0;
}
&[data-loading] {
.ladda-label {
opacity: 0;
left: -100%;
}
.ladda-spinner {
opacity: 1;
left: 50%;
}
}
}
/*************************************
* SLIDE RIGHT
*/
.ladda-button[data-style=slide-right] {
overflow: hidden;
.ladda-label {
position: relative;
}
.ladda-spinner {
right: 100%;
margin-left: 0;
left: $spinnerSize * 0.5;
[dir="rtl"] & {
right: auto;
}
}
&[data-loading] {
.ladda-label {
opacity: 0;
left: 100%;
}
.ladda-spinner {
opacity: 1;
left: 50%;
}
}
}
/*************************************
* SLIDE UP
*/
.ladda-button[data-style=slide-up] {
overflow: hidden;
.ladda-label {
position: relative;
}
.ladda-spinner {
left: 50%;
margin-left: 0;
margin-top: 1em;
}
&[data-loading] {
.ladda-label {
opacity: 0;
top: -1em;
}
.ladda-spinner {
opacity: 1;
margin-top: 0;
}
}
}
/*************************************
* SLIDE DOWN
*/
.ladda-button[data-style=slide-down] {
overflow: hidden;
.ladda-label {
position: relative;
}
.ladda-spinner {
left: 50%;
margin-left: 0;
margin-top: -2em;
}
&[data-loading] {
.ladda-label {
opacity: 0;
top: 1em;
}
.ladda-spinner {
opacity: 1;
margin-top: 0;
}
}
}
/*************************************
* ZOOM-OUT
*/
.ladda-button[data-style=zoom-out] {
overflow: hidden;
.ladda-label {
position: relative;
display: inline-block;
}
.ladda-spinner {
left: 50%;
margin-left: $spinnerSize;
transform: scale(2.5);
}
&[data-loading] {
.ladda-label {
opacity: 0;
transform: scale(0.5);
}
.ladda-spinner {
opacity: 1;
margin-left: 0;
transform: none;
}
}
}
/*************************************
* ZOOM-IN
*/
.ladda-button[data-style=zoom-in] {
overflow: hidden;
.ladda-label {
position: relative;
display: inline-block;
}
.ladda-spinner {
left: 50%;
margin-left: math.div($spinnerSize, -2);
transform: scale(0.2);
}
&[data-loading] {
.ladda-label {
opacity: 0;
transform: scale(2.2);
}
.ladda-spinner {
opacity: 1;
margin-left: 0;
transform: none;
}
}
}
/*************************************
* CONTRACT
*/
.ladda-button[data-style=contract] {
overflow: hidden;
width: 100px;
.ladda-spinner {
left: 50%;
margin-left: 0;
}
&[data-loading] {
border-radius: 50%;
width: 52px;
.ladda-label {
opacity: 0;
}
.ladda-spinner {
opacity: 1;
}
}
}
/*************************************
* OVERLAY
*/
.ladda-button[data-style=contract-overlay] {
overflow: hidden;
width: 100px;
box-shadow: 0px 0px 0px 2000px rgba(0,0,0,0);
.ladda-spinner {
left: 50%;
margin-left: 0;
}
&[data-loading] {
border-radius: 50%;
width: 52px;
box-shadow: 0px 0px 0px 2000px rgba(0,0,0,0.8);
.ladda-label {
opacity: 0;
}
.ladda-spinner {
opacity: 1;
}
}
}
[dir="rtl"] .ladda-spinner > div {
left: 25% !important;
}
================================================
FILE: js/ladda.d.ts
================================================
export interface LaddaButton {
start(): LaddaButton,
startAfter(delay: number): LaddaButton,
stop(): LaddaButton,
toggle(): LaddaButton,
setProgress(progress: number): void,
isLoading(): boolean,
remove(): void,
}
export interface BindOptions {
/**
* Number of milliseconds to wait before automatically cancelling the animation.
*/
timeout?: number,
/**
* A function to be called with the Ladda instance when a target button is clicked.
*/
callback?: (instance: LaddaButton) => void,
}
/**
* Creates a new instance of Ladda which wraps the target button element.
*/
export function create(button: HTMLButtonElement): LaddaButton;
/**
* Binds the target buttons to automatically enter the loading state when clicked.
* @param target Either an HTML element or a CSS selector.
*/
export function bind(target: HTMLElement | string, options?: BindOptions): void;
/**
* Stops all current loading animations.
*/
export function stopAll(): void;
================================================
FILE: js/ladda.js
================================================
/*!
* Ladda
* http://lab.hakim.se/ladda
* MIT licensed
*
* Copyright (C) 2018 Hakim El Hattab, http://hakim.se
*/
import {Spinner} from 'spin.js';
// All currently instantiated instances of Ladda
var ALL_INSTANCES = [];
/**
* Creates a new instance of Ladda which wraps the
* target button element.
*
* @return An API object that can be used to control
* the loading animation state.
*/
export function create(button) {
if (typeof button === 'undefined') {
console.warn("Ladda button target must be defined.");
return;
}
// The button must have the class "ladda-button"
if (!button.classList.contains('ladda-button')) {
button.classList.add('ladda-button');
}
// Style is required, default to "expand-right"
if (!button.hasAttribute('data-style')) {
button.setAttribute('data-style', 'expand-right');
}
// The text contents must be wrapped in a ladda-label
// element, create one if it doesn't already exist
if (!button.querySelector('.ladda-label')) {
var laddaLabel = document.createElement('span');
laddaLabel.className = 'ladda-label';
wrapContent(button, laddaLabel);
}
// The spinner component
var spinnerWrapper = button.querySelector('.ladda-spinner');
// Wrapper element for the spinner
if (!spinnerWrapper) {
spinnerWrapper = document.createElement('span');
spinnerWrapper.className = 'ladda-spinner';
}
button.appendChild(spinnerWrapper);
// Timer used to delay starting/stopping
var timer;
var spinner;
var instance = {
/**
* Enter the loading state.
*/
start: function() {
// Create the spinner if it doesn't already exist
if (!spinner) {
spinner = createSpinner(button);
}
button.disabled = true;
button.setAttribute('data-loading', '');
clearTimeout(timer);
spinner.spin(spinnerWrapper);
this.setProgress(0);
return this; // chain
},
/**
* Enter the loading state, after a delay.
*/
startAfter: function(delay) {
clearTimeout(timer);
timer = setTimeout(function() { instance.start(); }, delay);
return this; // chain
},
/**
* Exit the loading state.
*/
stop: function() {
if (instance.isLoading()) {
button.disabled = false;
button.removeAttribute('data-loading');
}
// Kill the animation after a delay to make sure it
// runs for the duration of the button transition
clearTimeout(timer);
if (spinner) {
timer = setTimeout(function() { spinner.stop(); }, 1000);
}
return this; // chain
},
/**
* Toggle the loading state on/off.
*/
toggle: function() {
return this.isLoading() ? this.stop() : this.start();
},
/**
* Sets the width of the visual progress bar inside of
* this Ladda button
*
* @param {number} progress in the range of 0-1
*/
setProgress: function(progress) {
// Cap it
progress = Math.max(Math.min(progress, 1), 0);
var progressElement = button.querySelector('.ladda-progress');
// Remove the progress bar if we're at 0 progress
if (progress === 0 && progressElement && progressElement.parentNode) {
progressElement.parentNode.removeChild(progressElement);
} else {
if (!progressElement) {
progressElement = document.createElement('div');
progressElement.className = 'ladda-progress';
button.appendChild(progressElement);
}
progressElement.style.width = ((progress || 0) * button.offsetWidth) + 'px';
}
},
isLoading: function() {
return button.hasAttribute('data-loading');
},
remove: function() {
clearTimeout(timer);
button.disabled = false;
button.removeAttribute('data-loading');
if (spinner) {
spinner.stop();
spinner = null;
}
ALL_INSTANCES.splice(ALL_INSTANCES.indexOf(instance), 1);
}
};
ALL_INSTANCES.push(instance);
return instance;
}
/**
* Binds the target buttons to automatically enter the
* loading state when clicked.
*
* @param target Either an HTML element or a CSS selector.
* @param options
* - timeout Number of milliseconds to wait before
* automatically cancelling the animation.
* - callback A function to be called with the Ladda
* instance when a target button is clicked.
*/
export function bind(target, options) {
var targets;
if (typeof target === 'string') {
targets = document.querySelectorAll(target);
} else if (typeof target === 'object') {
targets = [target];
} else {
throw new Error('target must be string or object');
}
options = options || {};
for (var i = 0; i < targets.length; i++) {
bindElement(targets[i], options);
}
}
/**
* Stops ALL current loading animations.
*/
export function stopAll() {
for (var i = 0, len = ALL_INSTANCES.length; i < len; i++) {
ALL_INSTANCES[i].stop();
}
}
/**
* Get the first ancestor node from an element, having a
* certain type.
*
* @param elem An HTML element
* @param type an HTML tag type (uppercased)
*
* @return An HTML element
*/
function getAncestorOfTagType(elem, type) {
while (elem.parentNode && elem.tagName !== type) {
elem = elem.parentNode;
}
return (type === elem.tagName) ? elem : undefined;
}
function createSpinner(button) {
var height = button.offsetHeight,
spinnerColor,
spinnerLines;
if (height === 0) {
// We may have an element that is not visible so
// we attempt to get the height in a different way
height = parseFloat(window.getComputedStyle(button).height);
}
// If the button is tall we can afford some padding
if (height > 32) {
height *= 0.8;
}
// Prefer an explicit height if one is defined
if (button.hasAttribute('data-spinner-size')) {
height = parseInt(button.getAttribute('data-spinner-size'), 10);
}
// Allow buttons to specify the color of the spinner element
if (button.hasAttribute('data-spinner-color')) {
spinnerColor = button.getAttribute('data-spinner-color');
}
// Allow buttons to specify the number of lines of the spinner
if (button.hasAttribute('data-spinner-lines')) {
spinnerLines = parseInt(button.getAttribute('data-spinner-lines'), 10);
}
var radius = height * 0.2,
length = radius * 0.6,
width = radius < 7 ? 2 : 3;
return new Spinner({
color: spinnerColor || '#fff',
lines: spinnerLines || 12,
radius: radius,
length: length,
width: width,
animation: 'ladda-spinner-line-fade',
zIndex: 'auto',
top: 'auto',
left: 'auto',
className: ''
});
}
function wrapContent(node, wrapper) {
var r = document.createRange();
r.selectNodeContents(node);
r.surroundContents(wrapper);
node.appendChild(wrapper);
}
function bindElement(element, options) {
if (typeof element.addEventListener !== 'function') {
return;
}
var instance = create(element);
var timeout = -1;
element.addEventListener('click', function() {
// If the button belongs to a form, make sure all the
// fields in that form are filled out
var valid = true;
var form = getAncestorOfTagType(element, 'FORM');
if (typeof form !== 'undefined' && !form.hasAttribute('novalidate')) {
// Modern form validation
if (typeof form.checkValidity === 'function') {
valid = form.checkValidity();
}
}
if (valid) {
// This is asynchronous to avoid an issue where disabling
// the button prevents forms from submitting
instance.startAfter(1);
// Set a loading timeout if one is specified
if (typeof options.timeout === 'number') {
clearTimeout(timeout);
timeout = setTimeout(instance.stop, options.timeout);
}
// Invoke callbacks
if (typeof options.callback === 'function') {
options.callback.apply(null, [instance]);
}
}
}, false);
}
================================================
FILE: package.json
================================================
{
"name": "ladda",
"version": "2.0.3",
"description": "Buttons with built-in loading indicators",
"homepage": "https://lab.hakim.se/ladda/",
"files": [
"css/*.scss",
"dist/*.css",
"js/ladda.d.ts",
"js/ladda.js"
],
"type": "module",
"main": "./js/ladda.js",
"types": "./js/ladda.d.ts",
"scripts": {
"test": "grunt jshint --gruntfile Gruntfile.cjs",
"prepare": "grunt --gruntfile Gruntfile.cjs && rollup -c",
"start": "grunt serve --gruntfile Gruntfile.cjs"
},
"author": "Hakim El Hattab <hakim.elhattab@gmail.com> https://hakim.se",
"contributors": [
"Theodore Brown <theodorejb@outlook.com> https://theodorejb.me"
],
"repository": {
"type": "git",
"url": "git://github.com/hakimel/Ladda.git"
},
"devDependencies": {
"grunt": "^1.4.1",
"grunt-contrib-connect": "^3.0.0",
"grunt-contrib-copy": "^1.0.0",
"grunt-contrib-jshint": "^3.1.1",
"grunt-contrib-watch": "^1.1.0",
"grunt-sass": "^3.1.0",
"rollup": "^2.60.2",
"rollup-plugin-node-resolve": "^5.2.0",
"sass": "^1.44.0"
},
"license": "MIT",
"dependencies": {
"spin.js": "^4.1.1"
}
}
================================================
FILE: rollup.config.js
================================================
import resolve from 'rollup-plugin-node-resolve';
export default [
{
input: 'site/index.js',
output: {
file: 'site/dist/index-bundle.js',
format: 'iife'
},
plugins: [resolve()]
},
{
input: 'site/form.js',
output: {
file: 'site/dist/form-bundle.js',
format: 'iife'
},
plugins: [resolve()]
},
];
================================================
FILE: site/bootstrap.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda: Bootstrap compatibility test</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.0-beta1/dist/css/bootstrap.min.css" rel="stylesheet"
integrity="sha384-giJF6kkoqNQ00vy+HMDP7azOuL0xtbfIcaT9wjKHr8RbDVddVHyTfAAsrekwKmP1" crossorigin="anonymous">
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda-themeless.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda Bootstrap 5 test</h1>
</div>
<section class="button-demo">
<h3>expand-left</h3>
<button class="btn btn-primary ladda-button" data-style="expand-left">Submit</button>
</section>
<section class="button-demo">
<h3>expand-right</h3>
<button class="btn btn-primary ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="button-demo">
<h3>expand-up</h3>
<button class="btn btn-primary ladda-button" data-style="expand-up">Submit</button>
</section>
<section class="button-demo">
<h3>expand-down</h3>
<button class="btn btn-primary ladda-button" data-style="expand-down">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-in</h3>
<button class="btn btn-info ladda-button" data-style="zoom-in" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-out</h3>
<button class="btn btn-info ladda-button" data-style="zoom-out" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-left</h3>
<button class="btn btn-warning ladda-button" data-style="slide-left" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-right</h3>
<button class="btn btn-warning ladda-button" data-style="slide-right" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-up</h3>
<button class="btn btn-warning ladda-button" data-style="slide-up" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-down</h3>
<button class="btn btn-warning ladda-button" data-style="slide-down" data-spinner-color="#000">Submit</button>
</section>
<h3 id="progress">Built-in progress bar</h3>
<section class="progress-demo">
<h3>expand-right</h3>
<button class="btn btn-success ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>contract</h3>
<button class="btn btn-success ladda-button" data-style="contract">Submit</button>
</section>
<h3 id="sizes">Sizes</h3>
<section class="progress-demo">
<h3>Small</h3>
<button class="btn btn-danger btn-sm ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>Large</h3>
<button class="btn btn-danger btn-lg ladda-button" data-style="expand-right">Submit</button>
</section>
<h3>Buttons in forms containing required inputs</h3>
<section>
<form action="https://example.com">
<div class="mb-3">
<input class="form-control" type="text" name="aText" placeholder="Please fill me" required/>
</div>
<div class="mb-3">
<button id="aFormSubmitButton" type="submit" class="btn btn-primary ladda-button" data-style="expand-left">Submit</button>
</div>
</form>
</section>
</article>
<script src="dist/index-bundle.js"></script>
</body>
</html>
================================================
FILE: site/bootstrap3.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda: Bootstrap compatibility test</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/3.4.1/css/bootstrap.min.css"
integrity="sha384-HSMxcRTRxnN+Bdg0JdbxYKrThecOKuH5zCYotlSAcp1+c8xmyTe9GYg1l9a69psu" crossorigin="anonymous">
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda-themeless.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda Bootstrap 3 test</h1>
</div>
<section class="button-demo">
<h3>expand-left</h3>
<button class="btn btn-primary ladda-button" data-style="expand-left">Submit</button>
</section>
<section class="button-demo">
<h3>expand-right</h3>
<button class="btn btn-primary ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="button-demo">
<h3>expand-up</h3>
<button class="btn btn-primary ladda-button" data-style="expand-up">Submit</button>
</section>
<section class="button-demo">
<h3>expand-down</h3>
<button class="btn btn-primary ladda-button" data-style="expand-down">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-in</h3>
<button class="btn btn-info ladda-button" data-style="zoom-in">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-out</h3>
<button class="btn btn-info ladda-button" data-style="zoom-out">Submit</button>
</section>
<section class="button-demo">
<h3>slide-left</h3>
<button class="btn btn-warning ladda-button" data-style="slide-left">Submit</button>
</section>
<section class="button-demo">
<h3>slide-right</h3>
<button class="btn btn-warning ladda-button" data-style="slide-right">Submit</button>
</section>
<section class="button-demo">
<h3>slide-up</h3>
<button class="btn btn-warning ladda-button" data-style="slide-up">Submit</button>
</section>
<section class="button-demo">
<h3>slide-down</h3>
<button class="btn btn-warning ladda-button" data-style="slide-down">Submit</button>
</section>
<h3 id="progress">Built-in progress bar</h3>
<section class="progress-demo">
<h3>expand-right</h3>
<button class="btn btn-success ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>contract</h3>
<button class="btn btn-success ladda-button" data-style="contract">Submit</button>
</section>
<h3 id="sizes">Sizes</h3>
<section class="progress-demo">
<h3>Small</h3>
<button class="btn btn-danger btn-sm ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>Large</h3>
<button class="btn btn-danger btn-lg ladda-button" data-style="expand-right">Submit</button>
</section>
<h3>Buttons in forms containing required inputs</h3>
<section>
<form action="https://example.com">
<div class="form-group">
<input class="form-control" type="text" name="aText" placeholder="Please fill me" required />
</div>
<div class="form-group">
<button id="aFormSubmitButton" type="submit" class="btn btn-primary ladda-button"
data-style="expand-left">Submit</button>
</div>
</form>
</section>
</article>
<script src="dist/index-bundle.js"></script>
</body>
</html>
================================================
FILE: site/bootstrap4.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda: Bootstrap compatibility test</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@4.5.3/dist/css/bootstrap.min.css"
integrity="sha384-TX8t27EcRE3e/ihU7zmQxVncDAy5uIKz4rEkgIXeMed4M0jlfIDPvg6uqKI2xXr2" crossorigin="anonymous">
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda-themeless.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda Bootstrap 4 test</h1>
</div>
<section class="button-demo">
<h3>expand-left</h3>
<button class="btn btn-primary ladda-button" data-style="expand-left">Submit</button>
</section>
<section class="button-demo">
<h3>expand-right</h3>
<button class="btn btn-primary ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="button-demo">
<h3>expand-up</h3>
<button class="btn btn-primary ladda-button" data-style="expand-up">Submit</button>
</section>
<section class="button-demo">
<h3>expand-down</h3>
<button class="btn btn-primary ladda-button" data-style="expand-down">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-in</h3>
<button class="btn btn-info ladda-button" data-style="zoom-in">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-out</h3>
<button class="btn btn-info ladda-button" data-style="zoom-out">Submit</button>
</section>
<section class="button-demo">
<h3>slide-left</h3>
<button class="btn btn-warning ladda-button" data-style="slide-left" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-right</h3>
<button class="btn btn-warning ladda-button" data-style="slide-right" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-up</h3>
<button class="btn btn-warning ladda-button" data-style="slide-up" data-spinner-color="#000">Submit</button>
</section>
<section class="button-demo">
<h3>slide-down</h3>
<button class="btn btn-warning ladda-button" data-style="slide-down" data-spinner-color="#000">Submit</button>
</section>
<h3 id="progress">Built-in progress bar</h3>
<section class="progress-demo">
<h3>expand-right</h3>
<button class="btn btn-success ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>contract</h3>
<button class="btn btn-success ladda-button" data-style="contract">Submit</button>
</section>
<h3 id="sizes">Sizes</h3>
<section class="progress-demo">
<h3>Small</h3>
<button class="btn btn-danger btn-sm ladda-button" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>Large</h3>
<button class="btn btn-danger btn-lg ladda-button" data-style="expand-right">Submit</button>
</section>
<h3>Buttons in forms containing required inputs</h3>
<section>
<form action="https://example.com">
<div class="form-group">
<input class="form-control" type="text" name="aText" placeholder="Please fill me" required />
</div>
<div class="form-group">
<button id="aFormSubmitButton" type="submit" class="btn btn-primary ladda-button"
data-style="expand-left">Submit</button>
</div>
</form>
</section>
</article>
<script src="dist/index-bundle.js"></script>
</body>
</html>
================================================
FILE: site/demo.css
================================================
/* Styles used specifically for the demo page */
body {
background: #f5f5f5;
font-family: monospace;
font-size: 14px;
color: #333333;
}
button {
outline: 0;
}
.examples {
max-width: 670px;
margin: 2em auto;
padding: 4em;
background: #fff;
text-align: center;
}
.examples .intro {
margin-bottom: 3em;
line-height: 1.4em;
font-size: 16px;
text-align: left;
}
.examples .intro h1 {
margin-top: 0;
font-size: 18px;
font-weight: bold;
}
.examples h3 {
font-size: 17px;
}
.examples .outro {
display: block;
text-align: right;
margin-top: 3em;
}
.examples section {
display: inline-block;
width: 24%;
min-width: 160px;
margin-bottom: 2em;
text-align: center;
vertical-align: top;
}
.examples section h3 {
color: #bbb;
font-weight: normal;
}
.sharing {
float: left;
}
.fork {
position: absolute;
top: 0;
right: 0;
border: none;
}
================================================
FILE: site/form.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda: Form test</title>
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda Form Validation</h1>
<p>
This page can be used to test that Ladda does NOT start spinning when submitting an invalid form.
</p>
<form action="https://example.com">
<input type="email" name="email" placeholder="Email address..." style="font-size: 1em; padding: 14px;" required>
<button type="submit" class="ladda-button" data-color="green" data-style="expand-left">Submit</button>
</form>
</div>
</article>
<script src="dist/form-bundle.js"></script>
</body>
</html>
================================================
FILE: site/form.js
================================================
import * as Ladda from '../js/ladda.js';
Ladda.bind('button[type=submit]');
================================================
FILE: site/index.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda</title>
<meta name="author" content="Hakim El Hattab">
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda</h1>
<p>
A UI concept which merges loading indicators into the action that invoked them. Primarily intended for use with forms where
it gives users immediate feedback upon submit rather than leaving them wondering while the browser does its thing. For a
real-world example, check out any of the forms on <a href="http://slides.com">slides.com</a>.
</p>
</div>
<section class="button-demo">
<h3>expand-left</h3>
<button data-color="green" data-style="expand-left">Submit</button>
</section>
<section class="button-demo">
<h3>expand-right</h3>
<button data-color="green" data-style="expand-right">Submit</button>
</section>
<section class="button-demo">
<h3>expand-up</h3>
<button data-color="green" data-style="expand-up">Submit</button>
</section>
<section class="button-demo">
<h3>expand-down</h3>
<button data-color="green" data-style="expand-down">Submit</button>
</section>
<section class="button-demo">
<h3>contract</h3>
<button class="ladda-button" data-color="red" data-style="contract">Submit</button>
</section>
<section class="button-demo">
<h3>contract-overlay</h3>
<button class="ladda-button" data-color="red" data-style="contract-overlay" style="z-index: 10;">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-in</h3>
<button class="ladda-button" data-color="red" data-style="zoom-in">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-out</h3>
<button class="ladda-button" data-color="red" data-style="zoom-out">Submit</button>
</section>
<section class="button-demo">
<h3>slide-left</h3>
<button class="ladda-button" data-color="blue" data-style="slide-left">Submit</button>
</section>
<section class="button-demo">
<h3>slide-right</h3>
<button class="ladda-button" data-color="blue" data-style="slide-right">Submit</button>
</section>
<section class="button-demo">
<h3>slide-up</h3>
<button class="ladda-button" data-color="blue" data-style="slide-up">Submit</button>
</section>
<section class="button-demo">
<h3>slide-down</h3>
<button class="ladda-button" data-color="blue" data-style="slide-down">Submit</button>
</section>
<h3 id="progress">Built-in progress bar</h3>
<section class="progress-demo">
<h3>expand-right</h3>
<button class="ladda-button" data-color="purple" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>contract</h3>
<button class="ladda-button" data-color="purple" data-style="contract">Submit</button>
</section>
<h3 id="sizes">Sizes</h3>
<section class="progress-demo">
<h3>Extra Small</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="xs">Submit</button>
</section>
<section class="progress-demo">
<h3>Small</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="s">Submit</button>
</section>
<section class="progress-demo">
<h3>Large</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="l">Submit</button>
</section>
<section class="progress-demo">
<h3>Extra Large</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="xl">Submit</button>
</section>
<footer>
<small class="sharing">
<a href="http://twitter.com/share" class="twitter-share-button" data-text="Ladda - Buttons with built-in loading indicators by @hakimel" data-url="http://lab.hakim.se/ladda" data-count="small" data-related="hakimel"></a>
</small>
<small class="outro">by <a href="http://hakim.se">Hakim El Hattab</a> / <a href="http://twitter.com/hakimel">@hakimel</a></small>
</footer>
</article>
<script src="dist/index-bundle.js"></script>
<a class="fork" href="https://github.com/hakimel/Ladda"><img width="149" height="149" src="https://github.blog/wp-content/uploads/2008/12/forkme_right_red_aa0000.png?resize=149%2C149" alt="Fork me on GitHub" data-recalc-dims="1"></a>
<script type="text/javascript" src="http://platform.twitter.com/widgets.js"></script>
</body>
</html>
================================================
FILE: site/index.js
================================================
import * as Ladda from '../js/ladda.js';
// Bind normal buttons
Ladda.bind('.button-demo button', { timeout: 2000 });
// Bind progress buttons and simulate loading progress
Ladda.bind('.progress-demo button', {
callback: function (instance) {
var progress = 0;
var interval = setInterval(function () {
progress = Math.min(progress + Math.random() * 0.1, 1);
instance.setProgress(progress);
if (progress === 1) {
instance.stop();
clearInterval(interval);
}
}, 200);
}
});
// You can control loading explicitly using the JavaScript API
// as outlined below:
// var l = Ladda.create( document.querySelector( 'button' ) );
// l.start();
// l.stop();
// l.toggle();
// l.isLoading();
// l.setProgress( 0-1 );
================================================
FILE: site/rtl.html
================================================
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Ladda</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no">
<link rel="stylesheet" href="demo.css">
<link rel="stylesheet" href="dist/ladda.min.css">
</head>
<body>
<article class="examples">
<div class="intro">
<h1>Ladda RTL support</h1>
</div>
<div dir="rtl">
<section class="button-demo">
<h3>expand-left</h3>
<button class="ladda-button" data-color="green" data-style="expand-left">Submit</button>
</section>
<section class="button-demo">
<h3>expand-right</h3>
<button class="ladda-button" data-color="green" data-style="expand-right">Submit</button>
</section>
<section class="button-demo">
<h3>expand-up</h3>
<button class="ladda-button" data-color="green" data-style="expand-up">Submit</button>
</section>
<section class="button-demo">
<h3>expand-down</h3>
<button class="ladda-button" data-color="green" data-style="expand-down">Submit</button>
</section>
<section class="button-demo">
<h3>contract</h3>
<button class="ladda-button" data-color="red" data-style="contract">Submit</button>
</section>
<section class="button-demo">
<h3>contract-overlay</h3>
<button class="ladda-button" data-color="red" data-style="contract-overlay" style="z-index: 10;">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-in</h3>
<button class="ladda-button" data-color="red" data-style="zoom-in">Submit</button>
</section>
<section class="button-demo">
<h3>zoom-out</h3>
<button class="ladda-button" data-color="red" data-style="zoom-out">Submit</button>
</section>
<section class="button-demo">
<h3>slide-left</h3>
<button class="ladda-button" data-color="blue" data-style="slide-left">Submit</button>
</section>
<section class="button-demo">
<h3>slide-right</h3>
<button class="ladda-button" data-color="blue" data-style="slide-right">Submit</button>
</section>
<section class="button-demo">
<h3>slide-up</h3>
<button class="ladda-button" data-color="blue" data-style="slide-up">Submit</button>
</section>
<section class="button-demo">
<h3>slide-down</h3>
<button class="ladda-button" data-color="blue" data-style="slide-down">Submit</button>
</section>
<h3 id="progress">Built-in progress bar</h3>
<section class="progress-demo">
<h3>expand-right</h3>
<button class="ladda-button" data-color="purple" data-style="expand-right">Submit</button>
</section>
<section class="progress-demo">
<h3>contract</h3>
<button class="ladda-button" data-color="purple" data-style="contract">Submit</button>
</section>
<h3 id="sizes">Sizes</h3>
<section class="progress-demo">
<h3>Extra Small</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="xs">Submit</button>
</section>
<section class="progress-demo">
<h3>Small</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="s">Submit</button>
</section>
<section class="progress-demo">
<h3>Large</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="l">Submit</button>
</section>
<section class="progress-demo">
<h3>Extra Large</h3>
<button class="ladda-button" data-color="mint" data-style="expand-right" data-size="xl">Submit</button>
</section>
</div>
</article>
<script src="dist/index-bundle.js"></script>
</body>
</html>
gitextract_hiwuh9bh/
├── .gitattributes
├── .gitignore
├── .npmrc
├── CHANGELOG.md
├── CONTRIBUTING.md
├── Gruntfile.cjs
├── LICENSE
├── README.md
├── css/
│ ├── ladda-themed.scss
│ └── ladda.scss
├── js/
│ ├── ladda.d.ts
│ └── ladda.js
├── package.json
├── rollup.config.js
└── site/
├── bootstrap.html
├── bootstrap3.html
├── bootstrap4.html
├── demo.css
├── form.html
├── form.js
├── index.html
├── index.js
└── rtl.html
SYMBOL INDEX (9 symbols across 2 files)
FILE: js/ladda.d.ts
type LaddaButton (line 1) | interface LaddaButton {
type BindOptions (line 11) | interface BindOptions {
FILE: js/ladda.js
function create (line 21) | function create(button) {
function bind (line 178) | function bind(target, options) {
function stopAll (line 199) | function stopAll() {
function getAncestorOfTagType (line 214) | function getAncestorOfTagType(elem, type) {
function createSpinner (line 222) | function createSpinner(button) {
function wrapContent (line 271) | function wrapContent(node, wrapper) {
function bindElement (line 278) | function bindElement(element, options) {
Condensed preview — 23 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (65K chars).
[
{
"path": ".gitattributes",
"chars": 98,
"preview": "# so website files won't cause project language to be shown as HTML\nsite/* linguist-documentation\n"
},
{
"path": ".gitignore",
"chars": 34,
"preview": "/node_modules/\n/dist/\n/site/dist/\n"
},
{
"path": ".npmrc",
"chars": 19,
"preview": "package-lock=false\n"
},
{
"path": "CHANGELOG.md",
"chars": 9214,
"preview": "# Changelog\nAll notable changes to this project will be documented in this file.\n\nThe format is based on [Keep a Changel"
},
{
"path": "CONTRIBUTING.md",
"chars": 288,
"preview": "# Contributing\n\nClone the repository and run `npm install` to install development dependencies and compile the project.\n"
},
{
"path": "Gruntfile.cjs",
"chars": 1753,
"preview": "const sass = require('sass');\n\nmodule.exports = function (grunt) {\n\t'use strict';\n\n\t// Project configuration\n\tgrunt.init"
},
{
"path": "LICENSE",
"chars": 1075,
"preview": "Copyright (C) 2017 Hakim El Hattab, http://hakim.se\n\nPermission is hereby granted, free of charge, to any person obtaini"
},
{
"path": "README.md",
"chars": 3519,
"preview": "# Ladda\n\nButtons with built-in loading indicators, effectively bridging the gap between action and feedback.\n\n[Check out"
},
{
"path": "css/ladda-themed.scss",
"chars": 1463,
"preview": "/*!\n * Ladda including the default theme.\n */\n\n@import \"ladda\";\n\n/*************************************\n * CONFIG\n */\n\n$"
},
{
"path": "css/ladda.scss",
"chars": 8038,
"preview": "/*!\n * Ladda\n * http://lab.hakim.se/ladda\n * MIT licensed\n *\n * Copyright (C) 2018 Hakim El Hattab, http://hakim.se\n */\n"
},
{
"path": "js/ladda.d.ts",
"chars": 1014,
"preview": "export interface LaddaButton {\n start(): LaddaButton,\n startAfter(delay: number): LaddaButton,\n stop(): LaddaBu"
},
{
"path": "js/ladda.js",
"chars": 8895,
"preview": "/*!\n * Ladda\n * http://lab.hakim.se/ladda\n * MIT licensed\n *\n * Copyright (C) 2018 Hakim El Hattab, http://hakim.se\n */\n"
},
{
"path": "package.json",
"chars": 1157,
"preview": "{\n \"name\": \"ladda\",\n \"version\": \"2.0.3\",\n \"description\": \"Buttons with built-in loading indicators\",\n \"homepage\": \"h"
},
{
"path": "rollup.config.js",
"chars": 423,
"preview": "import resolve from 'rollup-plugin-node-resolve';\n\nexport default [\n {\n input: 'site/index.js',\n output"
},
{
"path": "site/bootstrap.html",
"chars": 3649,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda: Bootstrap compatibility test</title>\n\t"
},
{
"path": "site/bootstrap3.html",
"chars": 3550,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda: Bootstrap compatibility test</title>\n\t"
},
{
"path": "site/bootstrap4.html",
"chars": 3655,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda: Bootstrap compatibility test</title>\n\t"
},
{
"path": "site/demo.css",
"chars": 1110,
"preview": "/* Styles used specifically for the demo page */\n\nbody {\n background: #f5f5f5;\n font-family: monospace;\n font-s"
},
{
"path": "site/form.html",
"chars": 784,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda: Form test</title>\n\n\t\t<link rel=\"styles"
},
{
"path": "site/form.js",
"chars": 77,
"preview": "import * as Ladda from '../js/ladda.js';\n\nLadda.bind('button[type=submit]');\n"
},
{
"path": "site/index.html",
"chars": 4673,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda</title>\n\t\t<meta name=\"author\" content=\""
},
{
"path": "site/index.js",
"chars": 821,
"preview": "import * as Ladda from '../js/ladda.js';\n\n// Bind normal buttons\nLadda.bind('.button-demo button', { timeout: 2000 });\n\n"
},
{
"path": "site/rtl.html",
"chars": 3697,
"preview": "<!doctype html>\n<html lang=\"en\">\n\t<head>\n\t\t<meta charset=\"utf-8\">\n\t\t<title>Ladda</title>\n\t\t<meta name=\"viewport\" content"
}
]
About this extraction
This page contains the full source code of the hakimel/Ladda GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 23 files (57.6 KB), approximately 17.0k tokens, and a symbol index with 9 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.