├── README.md
├── example
└── simple.html
└── jquery.localStorageTextareas.js
/README.md:
--------------------------------------------------------------------------------
1 | localStorage memory for textareas
2 | =================================
3 |
4 | By Pablo Villalba for [Teambox](http://teambox.com) collaboration software.
5 |
6 | Usage
7 | -----
8 |
9 | Saves textareas, inputs or selects to localStorage when the data-save-id attribute
10 | is defined as a unique string identifier for that textarea.
11 |
12 |
13 |
14 |
15 | First
16 | Second
17 |
18 |
19 | - Typing on an input field will save its value locally every 200 ms.
20 | - Clicking on an empty field will load the saved value if there is one.
21 | - Calling $(selector).loadSavedTextareas() will restore input or textareas saved.
22 |
23 | READ THE CODE to understand how it works, it's not so long :)
24 |
25 | Notes
26 | -----
27 |
28 | - Depends on underscore.js, jQuery 1.7.
29 | - You will need to manually clear localStorage if you need it.
30 |
31 | Licence
32 | -------
33 |
34 | MIT Licence, do whatever you want with it :)
35 |
--------------------------------------------------------------------------------
/example/simple.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | jquery.localStorageTextareas
5 |
6 |
7 |
8 |
9 |
14 |
20 |
21 |
22 | Demo for textareas with localStorage
23 | This textarea has a data-save-id attribute with a unique id.
24 | Edit it and reload the page. When clicking it, the content will be loaded from what you typed before.
25 |
26 | Of course, clicking on it to load it isn't ideal at all. That's why you can call $(document).loadSavedTextareas() to load it when the page is loaded:
27 |
28 | $(document).loadSavedTextareas();
29 |
30 |
31 | Execute this code to load from localStorage
32 |
33 | The textarea below is loaded by calling $("#container").loadSavedTextareas() after the page loads, so you don't need to click on it:
34 |
35 |
36 |
37 |
42 |
43 |
44 |
--------------------------------------------------------------------------------
/jquery.localStorageTextareas.js:
--------------------------------------------------------------------------------
1 | // Saves textareas to localStorage when the data-save-id attribute is defined
2 | // as a unique string identifier for that textarea.
3 | //
4 | //
5 | //
6 | // Typing on a textarea will save its value locally every 200 ms.
7 | // Clicking on an empty textarea will load the saved value if there is one.
8 | // Calling $(selector).loadSavedTextareas() will restore textareas saved.
9 | //
10 | // READ THE CODE to understand how it works, it's not so long :)
11 | //
12 | // Notes:
13 | //
14 | // - Depends on Modernizr.js, underscore.js, jQuery 1.7.
15 | // - You will need to manually clear localStorage if you need it.
16 | //
17 | // By Pablo Villalba, for Teambox 4 (http://teambox.com)
18 |
19 |
20 | (function () {
21 |
22 | // Don't load if localStorage isn't supported
23 | function localStorageSupported() {
24 | try {
25 | return !!localStorage.getItem;
26 | } catch (e) {
27 | return false;
28 | }
29 | }
30 |
31 | if (!localStorageSupported()) {
32 | return;
33 | }
34 |
35 | var saveTextarea, dirty = {};
36 |
37 | function id(el) {
38 | return "textareas-autosave/" + $(el).attr('data-save-id');
39 | }
40 |
41 | // setItem wrapper to fix some localStorage issues in *le* iPad
42 | // More info: http://stackoverflow.com/questions/2603682/
43 | function setkey(key, val) {
44 | localStorage.removeItem(key);
45 | localStorage.setItem(key, val);
46 | }
47 |
48 | // Save text to its unique identifier at most every 200ms
49 | saveTextarea = _.debounce(function (event) {
50 | setkey(id(this), $(this).val());
51 | $(this).attr("data-restored", true);
52 | dirty[id(this)] = true;
53 | }, 200);
54 |
55 | // Load text for the textarea if clicked and it's empty
56 | function loadTextarea(event) {
57 | var _id = id(this)
58 | , msg = "There is a saved version for this content. Would you like to restore the saved version?"
59 | , should_restore;
60 | // Only attempt to restore if there's saved content
61 | // and we haven't restored it yet.
62 | if (localStorage.getItem(_id) && !$(this).attr("data-restored")) {
63 | should_restore =
64 | // Empty..
65 | $(this).val().length === 0 ||
66 | // ..or different that what we have saved (request confirmation)
67 | ($(this).val() !== localStorage.getItem(_id) && confirm(msg));
68 | if (should_restore) {
69 | $(this).val(localStorage.getItem(_id));
70 | $(this).attr("data-restored", true);
71 | dirty[id(this)] = true;
72 | }
73 | }
74 | }
75 |
76 | /**
77 | * Load all textareas on demand
78 | *
79 | * Usage: $(".container").loadSavedTextareas();
80 | *
81 | * @return {jQuery}
82 | */
83 | $.fn.loadSavedTextareas = function () {
84 | var _id = id;
85 | return this.each(function () {
86 | var id = _id;
87 | // Restore input and textarea as text
88 | $(this).find("input[data-save-id],textarea[data-save-id]").each(function () {
89 | var $this = $(this);
90 | if ($this.val().length === 0) {
91 | $this.val(localStorage.getItem(id(this)));
92 | $this.attr("data-restored", true);
93 | dirty[id(this)] = true;
94 | }
95 | });
96 | // Restore select as a value
97 | $(this).find("select[data-save-id]").each(function () {
98 | var saved = localStorage.getItem(id(this));
99 | if (saved) {
100 | $(this).val(saved).attr("data-restored", true);
101 | dirty[id(this)] = true;
102 | }
103 | });
104 | });
105 | };
106 |
107 | /**
108 | * Remove a given textarea
109 | *
110 | * Usage: $("textarea, input, select").clearSavedTextarea();
111 | *
112 | * @return {jQuery}
113 | */
114 | $.fn.clearSavedTextarea = function () {
115 | var _id = id(this);
116 |
117 | if (localStorage.getItem(_id)) {
118 | localStorage.removeItem(_id);
119 | }
120 |
121 | return this;
122 | };
123 |
124 | // Iterate over all textareas to see if they should be cleared
125 | // from the DOM
126 | function resetEmptyTextareas(event) {
127 | $("select[data-save-id],input[data-save-id],textarea[data-save-id]").each(function (i, t) {
128 | var _id = id(t)
129 | , is_saved = localStorage.getItem(_id)
130 | , is_empty = t.value ? t.value.length === 0 : true
131 | , is_dirty = dirty[_id];
132 |
133 | if (is_saved && is_empty && is_dirty) {
134 | localStorage.removeItem(_id);
135 | }
136 | });
137 | }
138 |
139 | // Bind events
140 | $(document).on("change", "select[data-save-id]", saveTextarea);
141 | $(document).on("keyup", "select[data-save-id],input[data-save-id],textarea[data-save-id]", saveTextarea);
142 | $(document).on("click", "select[data-save-id],input[data-save-id],textarea[data-save-id]", loadTextarea);
143 | $(document).ajaxSuccess(resetEmptyTextareas);
144 |
145 | }());
146 |
--------------------------------------------------------------------------------