Version Description
- September 25th, 2019 =
- Adding additional checks to post global before enqueueing assets.
Download this release
Release Info
Developer | fmixell |
Plugin | ![]() |
Version | 1.6.11 |
Comparing to | |
See all releases |
Code changes from version 1.6.10 to 1.6.11
- LICENSE +340 -340
- admin/class.export.php +33 -33
- admin/class.import.php +47 -47
- admin/class.premium.php +120 -120
- admin/class.support.php +110 -110
- admin/class.yikes-woo-generate-html.php +395 -395
- admin/class.yikes-woo-saved-tabs.php +626 -626
- admin/class.yikes-woo-tabs.php +365 -365
- admin/page.premium.php +90 -90
- admin/page.support.php +14 -14
- admin/page.yikes-woo-saved-tabs-single.php +102 -102
- admin/page.yikes-woo-saved-tabs.php +146 -146
- css/dist/lity.min.css +2 -2
- js/lity.min.js +3 -3
- js/premium.js +52 -52
- js/repeatable-custom-tabs-settings.js +219 -219
- js/repeatable-custom-tabs-shared.js +384 -384
- js/twitter-embed.js +16 -16
- public/class.yikes-woo-tabs-display.php +122 -122
- readme.txt +243 -240
- slider/css/lightslider.css +394 -394
- slider/css/lightslider.min.css +2 -2
- slider/js/lightslider.js +1143 -1143
- slider/js/lightslider.min.js +3 -3
- uninstall.php +27 -27
- yikes-inc-easy-custom-woocommerce-product-tabs.php +322 -322
LICENSE
CHANGED
@@ -1,340 +1,340 @@
|
|
1 |
-
GNU GENERAL PUBLIC LICENSE
|
2 |
-
Version 2, June 1991
|
3 |
-
|
4 |
-
Copyright (C) 1989, 1991 Free Software Foundation, Inc., <http://fsf.org/>
|
5 |
-
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
6 |
-
Everyone is permitted to copy and distribute verbatim copies
|
7 |
-
of this license document, but changing it is not allowed.
|
8 |
-
|
9 |
-
Preamble
|
10 |
-
|
11 |
-
The licenses for most software are designed to take away your
|
12 |
-
freedom to share and change it. By contrast, the GNU General Public
|
13 |
-
License is intended to guarantee your freedom to share and change free
|
14 |
-
software--to make sure the software is free for all its users. This
|
15 |
-
General Public License applies to most of the Free Software
|
16 |
-
Foundation's software and to any other program whose authors commit to
|
17 |
-
using it. (Some other Free Software Foundation software is covered by
|
18 |
-
the GNU Lesser General Public License instead.) You can apply it to
|
19 |
-
your programs, too.
|
20 |
-
|
21 |
-
When we speak of free software, we are referring to freedom, not
|
22 |
-
price. Our General Public Licenses are designed to make sure that you
|
23 |
-
have the freedom to distribute copies of free software (and charge for
|
24 |
-
this service if you wish), that you receive source code or can get it
|
25 |
-
if you want it, that you can change the software or use pieces of it
|
26 |
-
in new free programs; and that you know you can do these things.
|
27 |
-
|
28 |
-
To protect your rights, we need to make restrictions that forbid
|
29 |
-
anyone to deny you these rights or to ask you to surrender the rights.
|
30 |
-
These restrictions translate to certain responsibilities for you if you
|
31 |
-
distribute copies of the software, or if you modify it.
|
32 |
-
|
33 |
-
For example, if you distribute copies of such a program, whether
|
34 |
-
gratis or for a fee, you must give the recipients all the rights that
|
35 |
-
you have. You must make sure that they, too, receive or can get the
|
36 |
-
source code. And you must show them these terms so they know their
|
37 |
-
rights.
|
38 |
-
|
39 |
-
We protect your rights with two steps: (1) copyright the software, and
|
40 |
-
(2) offer you this license which gives you legal permission to copy,
|
41 |
-
distribute and/or modify the software.
|
42 |
-
|
43 |
-
Also, for each author's protection and ours, we want to make certain
|
44 |
-
that everyone understands that there is no warranty for this free
|
45 |
-
software. If the software is modified by someone else and passed on, we
|
46 |
-
want its recipients to know that what they have is not the original, so
|
47 |
-
that any problems introduced by others will not reflect on the original
|
48 |
-
authors' reputations.
|
49 |
-
|
50 |
-
Finally, any free program is threatened constantly by software
|
51 |
-
patents. We wish to avoid the danger that redistributors of a free
|
52 |
-
program will individually obtain patent licenses, in effect making the
|
53 |
-
program proprietary. To prevent this, we have made it clear that any
|
54 |
-
patent must be licensed for everyone's free use or not licensed at all.
|
55 |
-
|
56 |
-
The precise terms and conditions for copying, distribution and
|
57 |
-
modification follow.
|
58 |
-
|
59 |
-
GNU GENERAL PUBLIC LICENSE
|
60 |
-
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
61 |
-
|
62 |
-
0. This License applies to any program or other work which contains
|
63 |
-
a notice placed by the copyright holder saying it may be distributed
|
64 |
-
under the terms of this General Public License. The "Program", below,
|
65 |
-
refers to any such program or work, and a "work based on the Program"
|
66 |
-
means either the Program or any derivative work under copyright law:
|
67 |
-
that is to say, a work containing the Program or a portion of it,
|
68 |
-
either verbatim or with modifications and/or translated into another
|
69 |
-
language. (Hereinafter, translation is included without limitation in
|
70 |
-
the term "modification".) Each licensee is addressed as "you".
|
71 |
-
|
72 |
-
Activities other than copying, distribution and modification are not
|
73 |
-
covered by this License; they are outside its scope. The act of
|
74 |
-
running the Program is not restricted, and the output from the Program
|
75 |
-
is covered only if its contents constitute a work based on the
|
76 |
-
Program (independent of having been made by running the Program).
|
77 |
-
Whether that is true depends on what the Program does.
|
78 |
-
|
79 |
-
1. You may copy and distribute verbatim copies of the Program's
|
80 |
-
source code as you receive it, in any medium, provided that you
|
81 |
-
conspicuously and appropriately publish on each copy an appropriate
|
82 |
-
copyright notice and disclaimer of warranty; keep intact all the
|
83 |
-
notices that refer to this License and to the absence of any warranty;
|
84 |
-
and give any other recipients of the Program a copy of this License
|
85 |
-
along with the Program.
|
86 |
-
|
87 |
-
You may charge a fee for the physical act of transferring a copy, and
|
88 |
-
you may at your option offer warranty protection in exchange for a fee.
|
89 |
-
|
90 |
-
2. You may modify your copy or copies of the Program or any portion
|
91 |
-
of it, thus forming a work based on the Program, and copy and
|
92 |
-
distribute such modifications or work under the terms of Section 1
|
93 |
-
above, provided that you also meet all of these conditions:
|
94 |
-
|
95 |
-
a) You must cause the modified files to carry prominent notices
|
96 |
-
stating that you changed the files and the date of any change.
|
97 |
-
|
98 |
-
b) You must cause any work that you distribute or publish, that in
|
99 |
-
whole or in part contains or is derived from the Program or any
|
100 |
-
part thereof, to be licensed as a whole at no charge to all third
|
101 |
-
parties under the terms of this License.
|
102 |
-
|
103 |
-
c) If the modified program normally reads commands interactively
|
104 |
-
when run, you must cause it, when started running for such
|
105 |
-
interactive use in the most ordinary way, to print or display an
|
106 |
-
announcement including an appropriate copyright notice and a
|
107 |
-
notice that there is no warranty (or else, saying that you provide
|
108 |
-
a warranty) and that users may redistribute the program under
|
109 |
-
these conditions, and telling the user how to view a copy of this
|
110 |
-
License. (Exception: if the Program itself is interactive but
|
111 |
-
does not normally print such an announcement, your work based on
|
112 |
-
the Program is not required to print an announcement.)
|
113 |
-
|
114 |
-
These requirements apply to the modified work as a whole. If
|
115 |
-
identifiable sections of that work are not derived from the Program,
|
116 |
-
and can be reasonably considered independent and separate works in
|
117 |
-
themselves, then this License, and its terms, do not apply to those
|
118 |
-
sections when you distribute them as separate works. But when you
|
119 |
-
distribute the same sections as part of a whole which is a work based
|
120 |
-
on the Program, the distribution of the whole must be on the terms of
|
121 |
-
this License, whose permissions for other licensees extend to the
|
122 |
-
entire whole, and thus to each and every part regardless of who wrote it.
|
123 |
-
|
124 |
-
Thus, it is not the intent of this section to claim rights or contest
|
125 |
-
your rights to work written entirely by you; rather, the intent is to
|
126 |
-
exercise the right to control the distribution of derivative or
|
127 |
-
collective works based on the Program.
|
128 |
-
|
129 |
-
In addition, mere aggregation of another work not based on the Program
|
130 |
-
with the Program (or with a work based on the Program) on a volume of
|
131 |
-
a storage or distribution medium does not bring the other work under
|
132 |
-
the scope of this License.
|
133 |
-
|
134 |
-
3. You may copy and distribute the Program (or a work based on it,
|
135 |
-
under Section 2) in object code or executable form under the terms of
|
136 |
-
Sections 1 and 2 above provided that you also do one of the following:
|
137 |
-
|
138 |
-
a) Accompany it with the complete corresponding machine-readable
|
139 |
-
source code, which must be distributed under the terms of Sections
|
140 |
-
1 and 2 above on a medium customarily used for software interchange; or,
|
141 |
-
|
142 |
-
b) Accompany it with a written offer, valid for at least three
|
143 |
-
years, to give any third party, for a charge no more than your
|
144 |
-
cost of physically performing source distribution, a complete
|
145 |
-
machine-readable copy of the corresponding source code, to be
|
146 |
-
distributed under the terms of Sections 1 and 2 above on a medium
|
147 |
-
customarily used for software interchange; or,
|
148 |
-
|
149 |
-
c) Accompany it with the information you received as to the offer
|
150 |
-
to distribute corresponding source code. (This alternative is
|
151 |
-
allowed only for noncommercial distribution and only if you
|
152 |
-
received the program in object code or executable form with such
|
153 |
-
an offer, in accord with Subsection b above.)
|
154 |
-
|
155 |
-
The source code for a work means the preferred form of the work for
|
156 |
-
making modifications to it. For an executable work, complete source
|
157 |
-
code means all the source code for all modules it contains, plus any
|
158 |
-
associated interface definition files, plus the scripts used to
|
159 |
-
control compilation and installation of the executable. However, as a
|
160 |
-
special exception, the source code distributed need not include
|
161 |
-
anything that is normally distributed (in either source or binary
|
162 |
-
form) with the major components (compiler, kernel, and so on) of the
|
163 |
-
operating system on which the executable runs, unless that component
|
164 |
-
itself accompanies the executable.
|
165 |
-
|
166 |
-
If distribution of executable or object code is made by offering
|
167 |
-
access to copy from a designated place, then offering equivalent
|
168 |
-
access to copy the source code from the same place counts as
|
169 |
-
distribution of the source code, even though third parties are not
|
170 |
-
compelled to copy the source along with the object code.
|
171 |
-
|
172 |
-
4. You may not copy, modify, sublicense, or distribute the Program
|
173 |
-
except as expressly provided under this License. Any attempt
|
174 |
-
otherwise to copy, modify, sublicense or distribute the Program is
|
175 |
-
void, and will automatically terminate your rights under this License.
|
176 |
-
However, parties who have received copies, or rights, from you under
|
177 |
-
this License will not have their licenses terminated so long as such
|
178 |
-
parties remain in full compliance.
|
179 |
-
|
180 |
-
5. You are not required to accept this License, since you have not
|
181 |
-
signed it. However, nothing else grants you permission to modify or
|
182 |
-
distribute the Program or its derivative works. These actions are
|
183 |
-
prohibited by law if you do not accept this License. Therefore, by
|
184 |
-
modifying or distributing the Program (or any work based on the
|
185 |
-
Program), you indicate your acceptance of this License to do so, and
|
186 |
-
all its terms and conditions for copying, distributing or modifying
|
187 |
-
the Program or works based on it.
|
188 |
-
|
189 |
-
6. Each time you redistribute the Program (or any work based on the
|
190 |
-
Program), the recipient automatically receives a license from the
|
191 |
-
original licensor to copy, distribute or modify the Program subject to
|
192 |
-
these terms and conditions. You may not impose any further
|
193 |
-
restrictions on the recipients' exercise of the rights granted herein.
|
194 |
-
You are not responsible for enforcing compliance by third parties to
|
195 |
-
this License.
|
196 |
-
|
197 |
-
7. If, as a consequence of a court judgment or allegation of patent
|
198 |
-
infringement or for any other reason (not limited to patent issues),
|
199 |
-
conditions are imposed on you (whether by court order, agreement or
|
200 |
-
otherwise) that contradict the conditions of this License, they do not
|
201 |
-
excuse you from the conditions of this License. If you cannot
|
202 |
-
distribute so as to satisfy simultaneously your obligations under this
|
203 |
-
License and any other pertinent obligations, then as a consequence you
|
204 |
-
may not distribute the Program at all. For example, if a patent
|
205 |
-
license would not permit royalty-free redistribution of the Program by
|
206 |
-
all those who receive copies directly or indirectly through you, then
|
207 |
-
the only way you could satisfy both it and this License would be to
|
208 |
-
refrain entirely from distribution of the Program.
|
209 |
-
|
210 |
-
If any portion of this section is held invalid or unenforceable under
|
211 |
-
any particular circumstance, the balance of the section is intended to
|
212 |
-
apply and the section as a whole is intended to apply in other
|
213 |
-
circumstances.
|
214 |
-
|
215 |
-
It is not the purpose of this section to induce you to infringe any
|
216 |
-
patents or other property right claims or to contest validity of any
|
217 |
-
such claims; this section has the sole purpose of protecting the
|
218 |
-
integrity of the free software distribution system, which is
|
219 |
-
implemented by public license practices. Many people have made
|
220 |
-
generous contributions to the wide range of software distributed
|
221 |
-
through that system in reliance on consistent application of that
|
222 |
-
system; it is up to the author/donor to decide if he or she is willing
|
223 |
-
to distribute software through any other system and a licensee cannot
|
224 |
-
impose that choice.
|
225 |
-
|
226 |
-
This section is intended to make thoroughly clear what is believed to
|
227 |
-
be a consequence of the rest of this License.
|
228 |
-
|
229 |
-
8. If the distribution and/or use of the Program is restricted in
|
230 |
-
certain countries either by patents or by copyrighted interfaces, the
|
231 |
-
original copyright holder who places the Program under this License
|
232 |
-
may add an explicit geographical distribution limitation excluding
|
233 |
-
those countries, so that distribution is permitted only in or among
|
234 |
-
countries not thus excluded. In such case, this License incorporates
|
235 |
-
the limitation as if written in the body of this License.
|
236 |
-
|
237 |
-
9. The Free Software Foundation may publish revised and/or new versions
|
238 |
-
of the General Public License from time to time. Such new versions will
|
239 |
-
be similar in spirit to the present version, but may differ in detail to
|
240 |
-
address new problems or concerns.
|
241 |
-
|
242 |
-
Each version is given a distinguishing version number. If the Program
|
243 |
-
specifies a version number of this License which applies to it and "any
|
244 |
-
later version", you have the option of following the terms and conditions
|
245 |
-
either of that version or of any later version published by the Free
|
246 |
-
Software Foundation. If the Program does not specify a version number of
|
247 |
-
this License, you may choose any version ever published by the Free Software
|
248 |
-
Foundation.
|
249 |
-
|
250 |
-
10. If you wish to incorporate parts of the Program into other free
|
251 |
-
programs whose distribution conditions are different, write to the author
|
252 |
-
to ask for permission. For software which is copyrighted by the Free
|
253 |
-
Software Foundation, write to the Free Software Foundation; we sometimes
|
254 |
-
make exceptions for this. Our decision will be guided by the two goals
|
255 |
-
of preserving the free status of all derivatives of our free software and
|
256 |
-
of promoting the sharing and reuse of software generally.
|
257 |
-
|
258 |
-
NO WARRANTY
|
259 |
-
|
260 |
-
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
261 |
-
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
262 |
-
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
263 |
-
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
264 |
-
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
265 |
-
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
266 |
-
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
267 |
-
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
268 |
-
REPAIR OR CORRECTION.
|
269 |
-
|
270 |
-
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
271 |
-
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
272 |
-
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
273 |
-
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
274 |
-
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
275 |
-
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
276 |
-
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
277 |
-
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
278 |
-
POSSIBILITY OF SUCH DAMAGES.
|
279 |
-
|
280 |
-
END OF TERMS AND CONDITIONS
|
281 |
-
|
282 |
-
How to Apply These Terms to Your New Programs
|
283 |
-
|
284 |
-
If you develop a new program, and you want it to be of the greatest
|
285 |
-
possible use to the public, the best way to achieve this is to make it
|
286 |
-
free software which everyone can redistribute and change under these terms.
|
287 |
-
|
288 |
-
To do so, attach the following notices to the program. It is safest
|
289 |
-
to attach them to the start of each source file to most effectively
|
290 |
-
convey the exclusion of warranty; and each file should have at least
|
291 |
-
the "copyright" line and a pointer to where the full notice is found.
|
292 |
-
|
293 |
-
{description}
|
294 |
-
Copyright (C) {year} {fullname}
|
295 |
-
|
296 |
-
This program is free software; you can redistribute it and/or modify
|
297 |
-
it under the terms of the GNU General Public License as published by
|
298 |
-
the Free Software Foundation; either version 2 of the License, or
|
299 |
-
(at your option) any later version.
|
300 |
-
|
301 |
-
This program is distributed in the hope that it will be useful,
|
302 |
-
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
303 |
-
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
304 |
-
GNU General Public License for more details.
|
305 |
-
|
306 |
-
You should have received a copy of the GNU General Public License along
|
307 |
-
with this program; if not, write to the Free Software Foundation, Inc.,
|
308 |
-
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
309 |
-
|
310 |
-
Also add information on how to contact you by electronic and paper mail.
|
311 |
-
|
312 |
-
If the program is interactive, make it output a short notice like this
|
313 |
-
when it starts in an interactive mode:
|
314 |
-
|
315 |
-
Gnomovision version 69, Copyright (C) year name of author
|
316 |
-
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
317 |
-
This is free software, and you are welcome to redistribute it
|
318 |
-
under certain conditions; type `show c' for details.
|
319 |
-
|
320 |
-
The hypothetical commands `show w' and `show c' should show the appropriate
|
321 |
-
parts of the General Public License. Of course, the commands you use may
|
322 |
-
be called something other than `show w' and `show c'; they could even be
|
323 |
-
mouse-clicks or menu items--whatever suits your program.
|
324 |
-
|
325 |
-
You should also get your employer (if you work as a programmer) or your
|
326 |
-
school, if any, to sign a "copyright disclaimer" for the program, if
|
327 |
-
necessary. Here is a sample; alter the names:
|
328 |
-
|
329 |
-
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
330 |
-
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
331 |
-
|
332 |
-
{signature of Ty Coon}, 1 April 1989
|
333 |
-
Ty Coon, President of Vice
|
334 |
-
|
335 |
-
This General Public License does not permit incorporating your program into
|
336 |
-
proprietary programs. If your program is a subroutine library, you may
|
337 |
-
consider it more useful to permit linking proprietary applications with the
|
338 |
-
library. If this is what you want to do, use the GNU Lesser General
|
339 |
-
Public License instead of this License.
|
340 |
-
|
1 |
+
GNU GENERAL PUBLIC LICENSE
|
2 |
+
Version 2, June 1991
|
3 |
+
|
4 |
+
Copyright (C) 1989, 1991 Free Software Foundation, Inc., <http://fsf.org/>
|
5 |
+
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
|
6 |
+
Everyone is permitted to copy and distribute verbatim copies
|
7 |
+
of this license document, but changing it is not allowed.
|
8 |
+
|
9 |
+
Preamble
|
10 |
+
|
11 |
+
The licenses for most software are designed to take away your
|
12 |
+
freedom to share and change it. By contrast, the GNU General Public
|
13 |
+
License is intended to guarantee your freedom to share and change free
|
14 |
+
software--to make sure the software is free for all its users. This
|
15 |
+
General Public License applies to most of the Free Software
|
16 |
+
Foundation's software and to any other program whose authors commit to
|
17 |
+
using it. (Some other Free Software Foundation software is covered by
|
18 |
+
the GNU Lesser General Public License instead.) You can apply it to
|
19 |
+
your programs, too.
|
20 |
+
|
21 |
+
When we speak of free software, we are referring to freedom, not
|
22 |
+
price. Our General Public Licenses are designed to make sure that you
|
23 |
+
have the freedom to distribute copies of free software (and charge for
|
24 |
+
this service if you wish), that you receive source code or can get it
|
25 |
+
if you want it, that you can change the software or use pieces of it
|
26 |
+
in new free programs; and that you know you can do these things.
|
27 |
+
|
28 |
+
To protect your rights, we need to make restrictions that forbid
|
29 |
+
anyone to deny you these rights or to ask you to surrender the rights.
|
30 |
+
These restrictions translate to certain responsibilities for you if you
|
31 |
+
distribute copies of the software, or if you modify it.
|
32 |
+
|
33 |
+
For example, if you distribute copies of such a program, whether
|
34 |
+
gratis or for a fee, you must give the recipients all the rights that
|
35 |
+
you have. You must make sure that they, too, receive or can get the
|
36 |
+
source code. And you must show them these terms so they know their
|
37 |
+
rights.
|
38 |
+
|
39 |
+
We protect your rights with two steps: (1) copyright the software, and
|
40 |
+
(2) offer you this license which gives you legal permission to copy,
|
41 |
+
distribute and/or modify the software.
|
42 |
+
|
43 |
+
Also, for each author's protection and ours, we want to make certain
|
44 |
+
that everyone understands that there is no warranty for this free
|
45 |
+
software. If the software is modified by someone else and passed on, we
|
46 |
+
want its recipients to know that what they have is not the original, so
|
47 |
+
that any problems introduced by others will not reflect on the original
|
48 |
+
authors' reputations.
|
49 |
+
|
50 |
+
Finally, any free program is threatened constantly by software
|
51 |
+
patents. We wish to avoid the danger that redistributors of a free
|
52 |
+
program will individually obtain patent licenses, in effect making the
|
53 |
+
program proprietary. To prevent this, we have made it clear that any
|
54 |
+
patent must be licensed for everyone's free use or not licensed at all.
|
55 |
+
|
56 |
+
The precise terms and conditions for copying, distribution and
|
57 |
+
modification follow.
|
58 |
+
|
59 |
+
GNU GENERAL PUBLIC LICENSE
|
60 |
+
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
61 |
+
|
62 |
+
0. This License applies to any program or other work which contains
|
63 |
+
a notice placed by the copyright holder saying it may be distributed
|
64 |
+
under the terms of this General Public License. The "Program", below,
|
65 |
+
refers to any such program or work, and a "work based on the Program"
|
66 |
+
means either the Program or any derivative work under copyright law:
|
67 |
+
that is to say, a work containing the Program or a portion of it,
|
68 |
+
either verbatim or with modifications and/or translated into another
|
69 |
+
language. (Hereinafter, translation is included without limitation in
|
70 |
+
the term "modification".) Each licensee is addressed as "you".
|
71 |
+
|
72 |
+
Activities other than copying, distribution and modification are not
|
73 |
+
covered by this License; they are outside its scope. The act of
|
74 |
+
running the Program is not restricted, and the output from the Program
|
75 |
+
is covered only if its contents constitute a work based on the
|
76 |
+
Program (independent of having been made by running the Program).
|
77 |
+
Whether that is true depends on what the Program does.
|
78 |
+
|
79 |
+
1. You may copy and distribute verbatim copies of the Program's
|
80 |
+
source code as you receive it, in any medium, provided that you
|
81 |
+
conspicuously and appropriately publish on each copy an appropriate
|
82 |
+
copyright notice and disclaimer of warranty; keep intact all the
|
83 |
+
notices that refer to this License and to the absence of any warranty;
|
84 |
+
and give any other recipients of the Program a copy of this License
|
85 |
+
along with the Program.
|
86 |
+
|
87 |
+
You may charge a fee for the physical act of transferring a copy, and
|
88 |
+
you may at your option offer warranty protection in exchange for a fee.
|
89 |
+
|
90 |
+
2. You may modify your copy or copies of the Program or any portion
|
91 |
+
of it, thus forming a work based on the Program, and copy and
|
92 |
+
distribute such modifications or work under the terms of Section 1
|
93 |
+
above, provided that you also meet all of these conditions:
|
94 |
+
|
95 |
+
a) You must cause the modified files to carry prominent notices
|
96 |
+
stating that you changed the files and the date of any change.
|
97 |
+
|
98 |
+
b) You must cause any work that you distribute or publish, that in
|
99 |
+
whole or in part contains or is derived from the Program or any
|
100 |
+
part thereof, to be licensed as a whole at no charge to all third
|
101 |
+
parties under the terms of this License.
|
102 |
+
|
103 |
+
c) If the modified program normally reads commands interactively
|
104 |
+
when run, you must cause it, when started running for such
|
105 |
+
interactive use in the most ordinary way, to print or display an
|
106 |
+
announcement including an appropriate copyright notice and a
|
107 |
+
notice that there is no warranty (or else, saying that you provide
|
108 |
+
a warranty) and that users may redistribute the program under
|
109 |
+
these conditions, and telling the user how to view a copy of this
|
110 |
+
License. (Exception: if the Program itself is interactive but
|
111 |
+
does not normally print such an announcement, your work based on
|
112 |
+
the Program is not required to print an announcement.)
|
113 |
+
|
114 |
+
These requirements apply to the modified work as a whole. If
|
115 |
+
identifiable sections of that work are not derived from the Program,
|
116 |
+
and can be reasonably considered independent and separate works in
|
117 |
+
themselves, then this License, and its terms, do not apply to those
|
118 |
+
sections when you distribute them as separate works. But when you
|
119 |
+
distribute the same sections as part of a whole which is a work based
|
120 |
+
on the Program, the distribution of the whole must be on the terms of
|
121 |
+
this License, whose permissions for other licensees extend to the
|
122 |
+
entire whole, and thus to each and every part regardless of who wrote it.
|
123 |
+
|
124 |
+
Thus, it is not the intent of this section to claim rights or contest
|
125 |
+
your rights to work written entirely by you; rather, the intent is to
|
126 |
+
exercise the right to control the distribution of derivative or
|
127 |
+
collective works based on the Program.
|
128 |
+
|
129 |
+
In addition, mere aggregation of another work not based on the Program
|
130 |
+
with the Program (or with a work based on the Program) on a volume of
|
131 |
+
a storage or distribution medium does not bring the other work under
|
132 |
+
the scope of this License.
|
133 |
+
|
134 |
+
3. You may copy and distribute the Program (or a work based on it,
|
135 |
+
under Section 2) in object code or executable form under the terms of
|
136 |
+
Sections 1 and 2 above provided that you also do one of the following:
|
137 |
+
|
138 |
+
a) Accompany it with the complete corresponding machine-readable
|
139 |
+
source code, which must be distributed under the terms of Sections
|
140 |
+
1 and 2 above on a medium customarily used for software interchange; or,
|
141 |
+
|
142 |
+
b) Accompany it with a written offer, valid for at least three
|
143 |
+
years, to give any third party, for a charge no more than your
|
144 |
+
cost of physically performing source distribution, a complete
|
145 |
+
machine-readable copy of the corresponding source code, to be
|
146 |
+
distributed under the terms of Sections 1 and 2 above on a medium
|
147 |
+
customarily used for software interchange; or,
|
148 |
+
|
149 |
+
c) Accompany it with the information you received as to the offer
|
150 |
+
to distribute corresponding source code. (This alternative is
|
151 |
+
allowed only for noncommercial distribution and only if you
|
152 |
+
received the program in object code or executable form with such
|
153 |
+
an offer, in accord with Subsection b above.)
|
154 |
+
|
155 |
+
The source code for a work means the preferred form of the work for
|
156 |
+
making modifications to it. For an executable work, complete source
|
157 |
+
code means all the source code for all modules it contains, plus any
|
158 |
+
associated interface definition files, plus the scripts used to
|
159 |
+
control compilation and installation of the executable. However, as a
|
160 |
+
special exception, the source code distributed need not include
|
161 |
+
anything that is normally distributed (in either source or binary
|
162 |
+
form) with the major components (compiler, kernel, and so on) of the
|
163 |
+
operating system on which the executable runs, unless that component
|
164 |
+
itself accompanies the executable.
|
165 |
+
|
166 |
+
If distribution of executable or object code is made by offering
|
167 |
+
access to copy from a designated place, then offering equivalent
|
168 |
+
access to copy the source code from the same place counts as
|
169 |
+
distribution of the source code, even though third parties are not
|
170 |
+
compelled to copy the source along with the object code.
|
171 |
+
|
172 |
+
4. You may not copy, modify, sublicense, or distribute the Program
|
173 |
+
except as expressly provided under this License. Any attempt
|
174 |
+
otherwise to copy, modify, sublicense or distribute the Program is
|
175 |
+
void, and will automatically terminate your rights under this License.
|
176 |
+
However, parties who have received copies, or rights, from you under
|
177 |
+
this License will not have their licenses terminated so long as such
|
178 |
+
parties remain in full compliance.
|
179 |
+
|
180 |
+
5. You are not required to accept this License, since you have not
|
181 |
+
signed it. However, nothing else grants you permission to modify or
|
182 |
+
distribute the Program or its derivative works. These actions are
|
183 |
+
prohibited by law if you do not accept this License. Therefore, by
|
184 |
+
modifying or distributing the Program (or any work based on the
|
185 |
+
Program), you indicate your acceptance of this License to do so, and
|
186 |
+
all its terms and conditions for copying, distributing or modifying
|
187 |
+
the Program or works based on it.
|
188 |
+
|
189 |
+
6. Each time you redistribute the Program (or any work based on the
|
190 |
+
Program), the recipient automatically receives a license from the
|
191 |
+
original licensor to copy, distribute or modify the Program subject to
|
192 |
+
these terms and conditions. You may not impose any further
|
193 |
+
restrictions on the recipients' exercise of the rights granted herein.
|
194 |
+
You are not responsible for enforcing compliance by third parties to
|
195 |
+
this License.
|
196 |
+
|
197 |
+
7. If, as a consequence of a court judgment or allegation of patent
|
198 |
+
infringement or for any other reason (not limited to patent issues),
|
199 |
+
conditions are imposed on you (whether by court order, agreement or
|
200 |
+
otherwise) that contradict the conditions of this License, they do not
|
201 |
+
excuse you from the conditions of this License. If you cannot
|
202 |
+
distribute so as to satisfy simultaneously your obligations under this
|
203 |
+
License and any other pertinent obligations, then as a consequence you
|
204 |
+
may not distribute the Program at all. For example, if a patent
|
205 |
+
license would not permit royalty-free redistribution of the Program by
|
206 |
+
all those who receive copies directly or indirectly through you, then
|
207 |
+
the only way you could satisfy both it and this License would be to
|
208 |
+
refrain entirely from distribution of the Program.
|
209 |
+
|
210 |
+
If any portion of this section is held invalid or unenforceable under
|
211 |
+
any particular circumstance, the balance of the section is intended to
|
212 |
+
apply and the section as a whole is intended to apply in other
|
213 |
+
circumstances.
|
214 |
+
|
215 |
+
It is not the purpose of this section to induce you to infringe any
|
216 |
+
patents or other property right claims or to contest validity of any
|
217 |
+
such claims; this section has the sole purpose of protecting the
|
218 |
+
integrity of the free software distribution system, which is
|
219 |
+
implemented by public license practices. Many people have made
|
220 |
+
generous contributions to the wide range of software distributed
|
221 |
+
through that system in reliance on consistent application of that
|
222 |
+
system; it is up to the author/donor to decide if he or she is willing
|
223 |
+
to distribute software through any other system and a licensee cannot
|
224 |
+
impose that choice.
|
225 |
+
|
226 |
+
This section is intended to make thoroughly clear what is believed to
|
227 |
+
be a consequence of the rest of this License.
|
228 |
+
|
229 |
+
8. If the distribution and/or use of the Program is restricted in
|
230 |
+
certain countries either by patents or by copyrighted interfaces, the
|
231 |
+
original copyright holder who places the Program under this License
|
232 |
+
may add an explicit geographical distribution limitation excluding
|
233 |
+
those countries, so that distribution is permitted only in or among
|
234 |
+
countries not thus excluded. In such case, this License incorporates
|
235 |
+
the limitation as if written in the body of this License.
|
236 |
+
|
237 |
+
9. The Free Software Foundation may publish revised and/or new versions
|
238 |
+
of the General Public License from time to time. Such new versions will
|
239 |
+
be similar in spirit to the present version, but may differ in detail to
|
240 |
+
address new problems or concerns.
|
241 |
+
|
242 |
+
Each version is given a distinguishing version number. If the Program
|
243 |
+
specifies a version number of this License which applies to it and "any
|
244 |
+
later version", you have the option of following the terms and conditions
|
245 |
+
either of that version or of any later version published by the Free
|
246 |
+
Software Foundation. If the Program does not specify a version number of
|
247 |
+
this License, you may choose any version ever published by the Free Software
|
248 |
+
Foundation.
|
249 |
+
|
250 |
+
10. If you wish to incorporate parts of the Program into other free
|
251 |
+
programs whose distribution conditions are different, write to the author
|
252 |
+
to ask for permission. For software which is copyrighted by the Free
|
253 |
+
Software Foundation, write to the Free Software Foundation; we sometimes
|
254 |
+
make exceptions for this. Our decision will be guided by the two goals
|
255 |
+
of preserving the free status of all derivatives of our free software and
|
256 |
+
of promoting the sharing and reuse of software generally.
|
257 |
+
|
258 |
+
NO WARRANTY
|
259 |
+
|
260 |
+
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
261 |
+
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
262 |
+
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
263 |
+
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
264 |
+
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
265 |
+
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
266 |
+
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
267 |
+
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
268 |
+
REPAIR OR CORRECTION.
|
269 |
+
|
270 |
+
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
271 |
+
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
272 |
+
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
273 |
+
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
274 |
+
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
275 |
+
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
276 |
+
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
277 |
+
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
278 |
+
POSSIBILITY OF SUCH DAMAGES.
|
279 |
+
|
280 |
+
END OF TERMS AND CONDITIONS
|
281 |
+
|
282 |
+
How to Apply These Terms to Your New Programs
|
283 |
+
|
284 |
+
If you develop a new program, and you want it to be of the greatest
|
285 |
+
possible use to the public, the best way to achieve this is to make it
|
286 |
+
free software which everyone can redistribute and change under these terms.
|
287 |
+
|
288 |
+
To do so, attach the following notices to the program. It is safest
|
289 |
+
to attach them to the start of each source file to most effectively
|
290 |
+
convey the exclusion of warranty; and each file should have at least
|
291 |
+
the "copyright" line and a pointer to where the full notice is found.
|
292 |
+
|
293 |
+
{description}
|
294 |
+
Copyright (C) {year} {fullname}
|
295 |
+
|
296 |
+
This program is free software; you can redistribute it and/or modify
|
297 |
+
it under the terms of the GNU General Public License as published by
|
298 |
+
the Free Software Foundation; either version 2 of the License, or
|
299 |
+
(at your option) any later version.
|
300 |
+
|
301 |
+
This program is distributed in the hope that it will be useful,
|
302 |
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
303 |
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
304 |
+
GNU General Public License for more details.
|
305 |
+
|
306 |
+
You should have received a copy of the GNU General Public License along
|
307 |
+
with this program; if not, write to the Free Software Foundation, Inc.,
|
308 |
+
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
309 |
+
|
310 |
+
Also add information on how to contact you by electronic and paper mail.
|
311 |
+
|
312 |
+
If the program is interactive, make it output a short notice like this
|
313 |
+
when it starts in an interactive mode:
|
314 |
+
|
315 |
+
Gnomovision version 69, Copyright (C) year name of author
|
316 |
+
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
317 |
+
This is free software, and you are welcome to redistribute it
|
318 |
+
under certain conditions; type `show c' for details.
|
319 |
+
|
320 |
+
The hypothetical commands `show w' and `show c' should show the appropriate
|
321 |
+
parts of the General Public License. Of course, the commands you use may
|
322 |
+
be called something other than `show w' and `show c'; they could even be
|
323 |
+
mouse-clicks or menu items--whatever suits your program.
|
324 |
+
|
325 |
+
You should also get your employer (if you work as a programmer) or your
|
326 |
+
school, if any, to sign a "copyright disclaimer" for the program, if
|
327 |
+
necessary. Here is a sample; alter the names:
|
328 |
+
|
329 |
+
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
330 |
+
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
331 |
+
|
332 |
+
{signature of Ty Coon}, 1 April 1989
|
333 |
+
Ty Coon, President of Vice
|
334 |
+
|
335 |
+
This General Public License does not permit incorporating your program into
|
336 |
+
proprietary programs. If your program is a subroutine library, you may
|
337 |
+
consider it more useful to permit linking proprietary applications with the
|
338 |
+
library. If this is what you want to do, use the GNU Lesser General
|
339 |
+
Public License instead of this License.
|
340 |
+
|
admin/class.export.php
CHANGED
@@ -1,33 +1,33 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
/**
|
4 |
-
* Class YIKES_Custom_Product_Tabs_Export.
|
5 |
-
*/
|
6 |
-
class YIKES_Custom_Product_Tabs_Export {
|
7 |
-
|
8 |
-
/**
|
9 |
-
* Define our hooks.
|
10 |
-
*/
|
11 |
-
public function __construct() {
|
12 |
-
add_filter( 'woocommerce_product_export_meta_value', array( $this, 'prep_product_tabs_for_export' ), 10, 4 );
|
13 |
-
}
|
14 |
-
|
15 |
-
/**
|
16 |
-
* Prep our tabs for an export.
|
17 |
-
*
|
18 |
-
* @param mixed $meta_value The meta value.
|
19 |
-
* @param object $meta The meta field.
|
20 |
-
* @param WC_Product $product Product being exported.
|
21 |
-
* @param array $row Row data.
|
22 |
-
*/
|
23 |
-
public function prep_product_tabs_for_export( $meta_value, $meta, $product, $row ) {
|
24 |
-
if ( isset( $meta->key ) && $meta->key === 'yikes_woo_products_tabs' ) {
|
25 |
-
if ( is_array( $meta_value ) ) {
|
26 |
-
return serialize( $meta_value );
|
27 |
-
}
|
28 |
-
}
|
29 |
-
return $meta_value;
|
30 |
-
}
|
31 |
-
}
|
32 |
-
|
33 |
-
new YIKES_Custom_Product_Tabs_Export();
|
1 |
+
<?php
|
2 |
+
|
3 |
+
/**
|
4 |
+
* Class YIKES_Custom_Product_Tabs_Export.
|
5 |
+
*/
|
6 |
+
class YIKES_Custom_Product_Tabs_Export {
|
7 |
+
|
8 |
+
/**
|
9 |
+
* Define our hooks.
|
10 |
+
*/
|
11 |
+
public function __construct() {
|
12 |
+
add_filter( 'woocommerce_product_export_meta_value', array( $this, 'prep_product_tabs_for_export' ), 10, 4 );
|
13 |
+
}
|
14 |
+
|
15 |
+
/**
|
16 |
+
* Prep our tabs for an export.
|
17 |
+
*
|
18 |
+
* @param mixed $meta_value The meta value.
|
19 |
+
* @param object $meta The meta field.
|
20 |
+
* @param WC_Product $product Product being exported.
|
21 |
+
* @param array $row Row data.
|
22 |
+
*/
|
23 |
+
public function prep_product_tabs_for_export( $meta_value, $meta, $product, $row ) {
|
24 |
+
if ( isset( $meta->key ) && $meta->key === 'yikes_woo_products_tabs' ) {
|
25 |
+
if ( is_array( $meta_value ) ) {
|
26 |
+
return serialize( $meta_value );
|
27 |
+
}
|
28 |
+
}
|
29 |
+
return $meta_value;
|
30 |
+
}
|
31 |
+
}
|
32 |
+
|
33 |
+
new YIKES_Custom_Product_Tabs_Export();
|
admin/class.import.php
CHANGED
@@ -1,47 +1,47 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
/**
|
4 |
-
* Class YIKES_Custom_Product_Tabs_Import.
|
5 |
-
*/
|
6 |
-
class YIKES_Custom_Product_Tabs_Import {
|
7 |
-
|
8 |
-
/**
|
9 |
-
* Define hooks.
|
10 |
-
*/
|
11 |
-
public function __construct() {
|
12 |
-
add_filter( 'woocommerce_product_importer_formatting_callbacks', array( $this, 'remove_wp_kses_posts_callback_from_import' ), 10, 2 );
|
13 |
-
}
|
14 |
-
|
15 |
-
/**
|
16 |
-
* When importing our meta field via WooCommerce's native import, replace the wp_kses_post sanitization callback with trim().
|
17 |
-
*
|
18 |
-
* The wp_kses_post function gets ran on all meta and this breaks some serialized arrays.
|
19 |
-
*/
|
20 |
-
public function remove_wp_kses_posts_callback_from_import( $callbacks, $importer ) {
|
21 |
-
|
22 |
-
$meta_key = false;
|
23 |
-
|
24 |
-
// Go through the file's keys and look for our meta field.
|
25 |
-
if ( method_exists( $importer, 'get_mapped_keys' ) ) {
|
26 |
-
foreach ( $importer->get_mapped_keys() as $key_number => $field_name ) {
|
27 |
-
if ( $field_name === 'meta:yikes_woo_products_tabs' ) {
|
28 |
-
$meta_key = $key_number;
|
29 |
-
break;
|
30 |
-
}
|
31 |
-
}
|
32 |
-
}
|
33 |
-
|
34 |
-
// Set our meta field's callback to `trim()`.
|
35 |
-
if ( $meta_key !== false ) {
|
36 |
-
foreach ( $callbacks as $key => $callback ) {
|
37 |
-
if ( $key === $meta_key ) {
|
38 |
-
$callbacks[ $key ] = 'trim';
|
39 |
-
}
|
40 |
-
}
|
41 |
-
}
|
42 |
-
|
43 |
-
return $callbacks;
|
44 |
-
}
|
45 |
-
}
|
46 |
-
|
47 |
-
new YIKES_Custom_Product_Tabs_Import();
|
1 |
+
<?php
|
2 |
+
|
3 |
+
/**
|
4 |
+
* Class YIKES_Custom_Product_Tabs_Import.
|
5 |
+
*/
|
6 |
+
class YIKES_Custom_Product_Tabs_Import {
|
7 |
+
|
8 |
+
/**
|
9 |
+
* Define hooks.
|
10 |
+
*/
|
11 |
+
public function __construct() {
|
12 |
+
add_filter( 'woocommerce_product_importer_formatting_callbacks', array( $this, 'remove_wp_kses_posts_callback_from_import' ), 10, 2 );
|
13 |
+
}
|
14 |
+
|
15 |
+
/**
|
16 |
+
* When importing our meta field via WooCommerce's native import, replace the wp_kses_post sanitization callback with trim().
|
17 |
+
*
|
18 |
+
* The wp_kses_post function gets ran on all meta and this breaks some serialized arrays.
|
19 |
+
*/
|
20 |
+
public function remove_wp_kses_posts_callback_from_import( $callbacks, $importer ) {
|
21 |
+
|
22 |
+
$meta_key = false;
|
23 |
+
|
24 |
+
// Go through the file's keys and look for our meta field.
|
25 |
+
if ( method_exists( $importer, 'get_mapped_keys' ) ) {
|
26 |
+
foreach ( $importer->get_mapped_keys() as $key_number => $field_name ) {
|
27 |
+
if ( $field_name === 'meta:yikes_woo_products_tabs' ) {
|
28 |
+
$meta_key = $key_number;
|
29 |
+
break;
|
30 |
+
}
|
31 |
+
}
|
32 |
+
}
|
33 |
+
|
34 |
+
// Set our meta field's callback to `trim()`.
|
35 |
+
if ( $meta_key !== false ) {
|
36 |
+
foreach ( $callbacks as $key => $callback ) {
|
37 |
+
if ( $key === $meta_key ) {
|
38 |
+
$callbacks[ $key ] = 'trim';
|
39 |
+
}
|
40 |
+
}
|
41 |
+
}
|
42 |
+
|
43 |
+
return $callbacks;
|
44 |
+
}
|
45 |
+
}
|
46 |
+
|
47 |
+
new YIKES_Custom_Product_Tabs_Import();
|
admin/class.premium.php
CHANGED
@@ -1,121 +1,121 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
class YIKES_Custom_Product_Tabs_Premium {
|
4 |
-
|
5 |
-
/**
|
6 |
-
* Constructah >:^)
|
7 |
-
*/
|
8 |
-
public function __construct() {
|
9 |
-
|
10 |
-
// Add our custom settings page
|
11 |
-
add_action( 'admin_menu', array( $this, 'register_premium_subpage' ), 30 );
|
12 |
-
|
13 |
-
// Enqueue scripts & styles
|
14 |
-
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_scripts' ), 10, 1 );
|
15 |
-
|
16 |
-
// Display an ad for CPTPRO
|
17 |
-
add_action( 'yikes-woo-saved-tabs-list-ad', array( $this, 'display_cptpro_ad' ), 10 );
|
18 |
-
}
|
19 |
-
|
20 |
-
/**
|
21 |
-
* Enqueue our scripts and styes
|
22 |
-
*
|
23 |
-
* @param string | $page | The slug of the page we're currently on
|
24 |
-
*/
|
25 |
-
public function enqueue_scripts( $page ) {
|
26 |
-
|
27 |
-
if ( $page === 'custom-product-tabs_page_' . YIKES_Custom_Product_Tabs_Premium_Page ) {
|
28 |
-
|
29 |
-
wp_enqueue_style ( 'lightslider-styles', YIKES_Custom_Product_Tabs_URI . 'slider/css/lightslider.min.css' );
|
30 |
-
wp_enqueue_style ( 'repeatable-custom-tabs-styles', YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css' );
|
31 |
-
wp_enqueue_script( 'lightslider-scripts', YIKES_Custom_Product_Tabs_URI . 'slider/js/lightslider.min.js', array( 'jquery' ), YIKES_Custom_Product_Tabs_Version );
|
32 |
-
wp_enqueue_script( 'premium-scripts', YIKES_Custom_Product_Tabs_URI . 'js/premium.min.js', array( 'lightslider-scripts' ), YIKES_Custom_Product_Tabs_Version );
|
33 |
-
wp_enqueue_style ( 'repeatable-custom-tabs-styles' , YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css', '', YIKES_Custom_Product_Tabs_Version, 'all' );
|
34 |
-
}
|
35 |
-
}
|
36 |
-
|
37 |
-
/**
|
38 |
-
* Register our premium page
|
39 |
-
*/
|
40 |
-
public function register_premium_subpage() {
|
41 |
-
|
42 |
-
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
43 |
-
return;
|
44 |
-
}
|
45 |
-
|
46 |
-
// Add our custom settings page
|
47 |
-
add_submenu_page(
|
48 |
-
YIKES_Custom_Product_Tabs_Settings_Page, // Parent menu item slug
|
49 |
-
__( 'Go Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), // Tab title name (HTML title)
|
50 |
-
__( 'Go Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), // Menu page name
|
51 |
-
apply_filters( 'yikes-woo-premium-capability', 'publish_products' ), // Capability required
|
52 |
-
YIKES_Custom_Product_Tabs_Premium_Page, // Page slug (?page=slug-name)
|
53 |
-
array( $this, 'premium_page' ) // Function to generate page
|
54 |
-
);
|
55 |
-
}
|
56 |
-
|
57 |
-
/**
|
58 |
-
* Include our settings page
|
59 |
-
*/
|
60 |
-
public function premium_page() {
|
61 |
-
|
62 |
-
require_once YIKES_Custom_Product_Tabs_Path . 'admin/page.premium.php';
|
63 |
-
}
|
64 |
-
|
65 |
-
/**
|
66 |
-
* Display an ad for CPTPRO on the saved tabs list and saved tabs single pages
|
67 |
-
*/
|
68 |
-
public function display_cptpro_ad() {
|
69 |
-
|
70 |
-
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
71 |
-
return;
|
72 |
-
}
|
73 |
-
|
74 |
-
?>
|
75 |
-
<div class="yikes-woo-all-about-us">
|
76 |
-
<div class="postbox yikes-woo-review-us">
|
77 |
-
|
78 |
-
<h3 class="yikes-woo-review-us-title">Show Us Some Love</h3>
|
79 |
-
<div class="yikes-woo-review-us-body">
|
80 |
-
<div class="yikes-woo-review-us yikes-woo-all-about-us-box" id="yikes-woo-review-us">
|
81 |
-
|
82 |
-
<p><?php _e( 'Leave a review!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?> </p>
|
83 |
-
<p class="star-container">
|
84 |
-
<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs/reviews/?rate=5#new-post" target="_blank">
|
85 |
-
<span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span>
|
86 |
-
</a>
|
87 |
-
</p>
|
88 |
-
</div>
|
89 |
-
|
90 |
-
<div class="yikes-woo-all-about-us-separator"></div>
|
91 |
-
|
92 |
-
<div class="yikes-woo-tweet-us yikes-woo-all-about-us-box" id="yikes-woo-tweet-us">
|
93 |
-
|
94 |
-
<p><?php _e( 'Tweet about us!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></p>
|
95 |
-
<a class="twitter-share-button"
|
96 |
-
href="https://twitter.com/intent/tweet?text=I use Custom Product Tabs for WooCommerce by @yikesinc to help sell products online. Awesome #WordPress #plugins &url=https://wordpress.org/plugins/yikes-inc-easy-custom-woocommerce-product-tabs/"
|
97 |
-
data-size="large">
|
98 |
-
<?php _e( 'Tweet', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></a>
|
99 |
-
</div>
|
100 |
-
|
101 |
-
<p class="yikes-woo-review-us-footer">This plugin made with <span class="dashicons dashicons-heart yikes-love"></span> by <a href="http://www.yikesinc.com" target="_blank" title="YIKES Inc.">YIKES Inc.</a></p>
|
102 |
-
</div><!-- .yikes-woo-review-us-body -->
|
103 |
-
</div>
|
104 |
-
|
105 |
-
<div class="postbox yikes-woo-buy-us yikes-woo-all-about-us-box" id="yikes-woo-buy-us">
|
106 |
-
<h3 class="yikes-woo-buy-us-title">Custom Product Tabs Pro</h3>
|
107 |
-
<div class="yikes-woo-buy-us-body">
|
108 |
-
<h4><?php _e( 'Check out Custom Product Tabs Pro!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?> </h4>
|
109 |
-
<p><?php _e( 'Create global tabs, add tabs to products based on categories or tags, add tab content to search results, and more!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></p>
|
110 |
-
<a class="button button-primary" href="https://yikesplugins.com/plugin/custom-product-tabs-pro/" target="_blank">
|
111 |
-
<?php _e( 'Custom Product Tabs Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
112 |
-
</a>
|
113 |
-
</div><!-- .yikes-woo-buy-us-body -->
|
114 |
-
</div>
|
115 |
-
</div>
|
116 |
-
<?php
|
117 |
-
}
|
118 |
-
|
119 |
-
}
|
120 |
-
|
121 |
new YIKES_Custom_Product_Tabs_Premium();
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class YIKES_Custom_Product_Tabs_Premium {
|
4 |
+
|
5 |
+
/**
|
6 |
+
* Constructah >:^)
|
7 |
+
*/
|
8 |
+
public function __construct() {
|
9 |
+
|
10 |
+
// Add our custom settings page
|
11 |
+
add_action( 'admin_menu', array( $this, 'register_premium_subpage' ), 30 );
|
12 |
+
|
13 |
+
// Enqueue scripts & styles
|
14 |
+
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_scripts' ), 10, 1 );
|
15 |
+
|
16 |
+
// Display an ad for CPTPRO
|
17 |
+
add_action( 'yikes-woo-saved-tabs-list-ad', array( $this, 'display_cptpro_ad' ), 10 );
|
18 |
+
}
|
19 |
+
|
20 |
+
/**
|
21 |
+
* Enqueue our scripts and styes
|
22 |
+
*
|
23 |
+
* @param string | $page | The slug of the page we're currently on
|
24 |
+
*/
|
25 |
+
public function enqueue_scripts( $page ) {
|
26 |
+
|
27 |
+
if ( $page === 'custom-product-tabs_page_' . YIKES_Custom_Product_Tabs_Premium_Page ) {
|
28 |
+
|
29 |
+
wp_enqueue_style ( 'lightslider-styles', YIKES_Custom_Product_Tabs_URI . 'slider/css/lightslider.min.css' );
|
30 |
+
wp_enqueue_style ( 'repeatable-custom-tabs-styles', YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css' );
|
31 |
+
wp_enqueue_script( 'lightslider-scripts', YIKES_Custom_Product_Tabs_URI . 'slider/js/lightslider.min.js', array( 'jquery' ), YIKES_Custom_Product_Tabs_Version );
|
32 |
+
wp_enqueue_script( 'premium-scripts', YIKES_Custom_Product_Tabs_URI . 'js/premium.min.js', array( 'lightslider-scripts' ), YIKES_Custom_Product_Tabs_Version );
|
33 |
+
wp_enqueue_style ( 'repeatable-custom-tabs-styles' , YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css', '', YIKES_Custom_Product_Tabs_Version, 'all' );
|
34 |
+
}
|
35 |
+
}
|
36 |
+
|
37 |
+
/**
|
38 |
+
* Register our premium page
|
39 |
+
*/
|
40 |
+
public function register_premium_subpage() {
|
41 |
+
|
42 |
+
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
43 |
+
return;
|
44 |
+
}
|
45 |
+
|
46 |
+
// Add our custom settings page
|
47 |
+
add_submenu_page(
|
48 |
+
YIKES_Custom_Product_Tabs_Settings_Page, // Parent menu item slug
|
49 |
+
__( 'Go Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), // Tab title name (HTML title)
|
50 |
+
__( 'Go Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), // Menu page name
|
51 |
+
apply_filters( 'yikes-woo-premium-capability', 'publish_products' ), // Capability required
|
52 |
+
YIKES_Custom_Product_Tabs_Premium_Page, // Page slug (?page=slug-name)
|
53 |
+
array( $this, 'premium_page' ) // Function to generate page
|
54 |
+
);
|
55 |
+
}
|
56 |
+
|
57 |
+
/**
|
58 |
+
* Include our settings page
|
59 |
+
*/
|
60 |
+
public function premium_page() {
|
61 |
+
|
62 |
+
require_once YIKES_Custom_Product_Tabs_Path . 'admin/page.premium.php';
|
63 |
+
}
|
64 |
+
|
65 |
+
/**
|
66 |
+
* Display an ad for CPTPRO on the saved tabs list and saved tabs single pages
|
67 |
+
*/
|
68 |
+
public function display_cptpro_ad() {
|
69 |
+
|
70 |
+
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
71 |
+
return;
|
72 |
+
}
|
73 |
+
|
74 |
+
?>
|
75 |
+
<div class="yikes-woo-all-about-us">
|
76 |
+
<div class="postbox yikes-woo-review-us">
|
77 |
+
|
78 |
+
<h3 class="yikes-woo-review-us-title">Show Us Some Love</h3>
|
79 |
+
<div class="yikes-woo-review-us-body">
|
80 |
+
<div class="yikes-woo-review-us yikes-woo-all-about-us-box" id="yikes-woo-review-us">
|
81 |
+
|
82 |
+
<p><?php _e( 'Leave a review!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?> </p>
|
83 |
+
<p class="star-container">
|
84 |
+
<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs/reviews/?rate=5#new-post" target="_blank">
|
85 |
+
<span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span><span class="dashicons dashicons-star-filled"></span>
|
86 |
+
</a>
|
87 |
+
</p>
|
88 |
+
</div>
|
89 |
+
|
90 |
+
<div class="yikes-woo-all-about-us-separator"></div>
|
91 |
+
|
92 |
+
<div class="yikes-woo-tweet-us yikes-woo-all-about-us-box" id="yikes-woo-tweet-us">
|
93 |
+
|
94 |
+
<p><?php _e( 'Tweet about us!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></p>
|
95 |
+
<a class="twitter-share-button"
|
96 |
+
href="https://twitter.com/intent/tweet?text=I use Custom Product Tabs for WooCommerce by @yikesinc to help sell products online. Awesome #WordPress #plugins &url=https://wordpress.org/plugins/yikes-inc-easy-custom-woocommerce-product-tabs/"
|
97 |
+
data-size="large">
|
98 |
+
<?php _e( 'Tweet', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></a>
|
99 |
+
</div>
|
100 |
+
|
101 |
+
<p class="yikes-woo-review-us-footer">This plugin made with <span class="dashicons dashicons-heart yikes-love"></span> by <a href="http://www.yikesinc.com" target="_blank" title="YIKES Inc.">YIKES Inc.</a></p>
|
102 |
+
</div><!-- .yikes-woo-review-us-body -->
|
103 |
+
</div>
|
104 |
+
|
105 |
+
<div class="postbox yikes-woo-buy-us yikes-woo-all-about-us-box" id="yikes-woo-buy-us">
|
106 |
+
<h3 class="yikes-woo-buy-us-title">Custom Product Tabs Pro</h3>
|
107 |
+
<div class="yikes-woo-buy-us-body">
|
108 |
+
<h4><?php _e( 'Check out Custom Product Tabs Pro!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?> </h4>
|
109 |
+
<p><?php _e( 'Create global tabs, add tabs to products based on categories or tags, add tab content to search results, and more!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?></p>
|
110 |
+
<a class="button button-primary" href="https://yikesplugins.com/plugin/custom-product-tabs-pro/" target="_blank">
|
111 |
+
<?php _e( 'Custom Product Tabs Pro', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
112 |
+
</a>
|
113 |
+
</div><!-- .yikes-woo-buy-us-body -->
|
114 |
+
</div>
|
115 |
+
</div>
|
116 |
+
<?php
|
117 |
+
}
|
118 |
+
|
119 |
+
}
|
120 |
+
|
121 |
new YIKES_Custom_Product_Tabs_Premium();
|
admin/class.support.php
CHANGED
@@ -1,111 +1,111 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
class YIKES_Custom_Product_Tabs_Support {
|
4 |
-
|
5 |
-
/**
|
6 |
-
* Constructah >:^)
|
7 |
-
*/
|
8 |
-
public function __construct() {
|
9 |
-
|
10 |
-
// Add our custom settings page
|
11 |
-
add_action( 'admin_menu', array( $this, 'register_support_subpage' ), 20 );
|
12 |
-
|
13 |
-
// Enqueue scripts & styles
|
14 |
-
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_scripts' ), 10, 1 );
|
15 |
-
|
16 |
-
// Add our free support page HTML
|
17 |
-
add_action( 'yikes-woo-support-page-free', array( $this, 'render_support_page' ), 100 );
|
18 |
-
}
|
19 |
-
|
20 |
-
/**
|
21 |
-
* Enqueue our scripts and styes
|
22 |
-
*
|
23 |
-
* @param string | $page | The slug of the page we're currently on
|
24 |
-
*/
|
25 |
-
public function enqueue_scripts( $page ) {
|
26 |
-
|
27 |
-
if ( $page === 'custom-product-tabs_page_' . YIKES_Custom_Product_Tabs_Support_Page ) {
|
28 |
-
|
29 |
-
wp_enqueue_style( 'repeatable-custom-tabs-styles' , YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css', '', YIKES_Custom_Product_Tabs_Version, 'all' );
|
30 |
-
}
|
31 |
-
}
|
32 |
-
|
33 |
-
/**
|
34 |
-
* Register our settings page
|
35 |
-
*/
|
36 |
-
public function register_support_subpage() {
|
37 |
-
|
38 |
-
// Add our custom settings page
|
39 |
-
add_submenu_page(
|
40 |
-
YIKES_Custom_Product_Tabs_Settings_Page, // Parent menu item slug
|
41 |
-
__( 'Support', YIKES_Custom_Product_Tabs_Settings_Page ), // Tab title name (HTML title)
|
42 |
-
__( 'Support', YIKES_Custom_Product_Tabs_Settings_Page ), // Menu page name
|
43 |
-
apply_filters( 'yikes-woo-support-capability', 'publish_products' ), // Capability required
|
44 |
-
YIKES_Custom_Product_Tabs_Support_Page, // Page slug (?page=slug-name)
|
45 |
-
array( $this, 'support_page' ) // Function to generate page
|
46 |
-
);
|
47 |
-
}
|
48 |
-
|
49 |
-
/**
|
50 |
-
* Include our settings page
|
51 |
-
*/
|
52 |
-
public function support_page() {
|
53 |
-
|
54 |
-
require_once YIKES_Custom_Product_Tabs_Path . 'admin/page.support.php';
|
55 |
-
}
|
56 |
-
|
57 |
-
/**
|
58 |
-
* Show our support page HTML
|
59 |
-
*/
|
60 |
-
public function render_support_page() {
|
61 |
-
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
62 |
-
return;
|
63 |
-
}
|
64 |
-
?>
|
65 |
-
<div class="cptpro-settings cptpro-settings-support-help-container">
|
66 |
-
<p>
|
67 |
-
<?php
|
68 |
-
echo sprintf( __( 'Before submitting a support request, please visit our %1sKnowledge Base%2s where we have step-by-step guides and troubleshooting help.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
69 |
-
'<a href="https://yikesplugins.com/support/knowledge-base/product/easy-custom-product-tabs-for-woocommerce/" target="_blank">', '</a>' );
|
70 |
-
?>
|
71 |
-
</p>
|
72 |
-
|
73 |
-
<p>
|
74 |
-
<?php
|
75 |
-
echo sprintf( __( 'Custom Product Tabs Pro users qualify for premium support. Check out %1sCustom Product Tabs Pro%2s!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
76 |
-
'<a href="https://yikesplugins.com/plugin/custom-product-tabs-pro/" target="_blank">', '</a>' );
|
77 |
-
?>
|
78 |
-
</p>
|
79 |
-
|
80 |
-
<hr />
|
81 |
-
|
82 |
-
|
83 |
-
<h1>
|
84 |
-
<span class="dashicons dashicons-wordpress-alt"></span> <?php _e( 'WordPress.org Support Forums', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
85 |
-
</h1>
|
86 |
-
|
87 |
-
<p>
|
88 |
-
<?php
|
89 |
-
echo sprintf( __( 'If you need help with free Custom Product Tabs, please post questions to %1sour support forum on the WordPress Plugin Directory%2s. We aim to respond to support requests within a week.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
90 |
-
'<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">', '</a>' );
|
91 |
-
?>
|
92 |
-
</p>
|
93 |
-
|
94 |
-
<p>
|
95 |
-
<a class="button button-primary" href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">
|
96 |
-
<?php _e( 'Submit a Support Request', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
97 |
-
</a>
|
98 |
-
</p>
|
99 |
-
|
100 |
-
<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">
|
101 |
-
<img src="<?php echo YIKES_Custom_Product_Tabs_URI . 'images/support-screenshot.png' ?>" />
|
102 |
-
</a>
|
103 |
-
|
104 |
-
</div>
|
105 |
-
<?php
|
106 |
-
}
|
107 |
-
|
108 |
-
|
109 |
-
}
|
110 |
-
|
111 |
new YIKES_Custom_Product_Tabs_Support();
|
1 |
+
<?php
|
2 |
+
|
3 |
+
class YIKES_Custom_Product_Tabs_Support {
|
4 |
+
|
5 |
+
/**
|
6 |
+
* Constructah >:^)
|
7 |
+
*/
|
8 |
+
public function __construct() {
|
9 |
+
|
10 |
+
// Add our custom settings page
|
11 |
+
add_action( 'admin_menu', array( $this, 'register_support_subpage' ), 20 );
|
12 |
+
|
13 |
+
// Enqueue scripts & styles
|
14 |
+
add_action( 'admin_enqueue_scripts', array( $this, 'enqueue_scripts' ), 10, 1 );
|
15 |
+
|
16 |
+
// Add our free support page HTML
|
17 |
+
add_action( 'yikes-woo-support-page-free', array( $this, 'render_support_page' ), 100 );
|
18 |
+
}
|
19 |
+
|
20 |
+
/**
|
21 |
+
* Enqueue our scripts and styes
|
22 |
+
*
|
23 |
+
* @param string | $page | The slug of the page we're currently on
|
24 |
+
*/
|
25 |
+
public function enqueue_scripts( $page ) {
|
26 |
+
|
27 |
+
if ( $page === 'custom-product-tabs_page_' . YIKES_Custom_Product_Tabs_Support_Page ) {
|
28 |
+
|
29 |
+
wp_enqueue_style( 'repeatable-custom-tabs-styles' , YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css', '', YIKES_Custom_Product_Tabs_Version, 'all' );
|
30 |
+
}
|
31 |
+
}
|
32 |
+
|
33 |
+
/**
|
34 |
+
* Register our settings page
|
35 |
+
*/
|
36 |
+
public function register_support_subpage() {
|
37 |
+
|
38 |
+
// Add our custom settings page
|
39 |
+
add_submenu_page(
|
40 |
+
YIKES_Custom_Product_Tabs_Settings_Page, // Parent menu item slug
|
41 |
+
__( 'Support', YIKES_Custom_Product_Tabs_Settings_Page ), // Tab title name (HTML title)
|
42 |
+
__( 'Support', YIKES_Custom_Product_Tabs_Settings_Page ), // Menu page name
|
43 |
+
apply_filters( 'yikes-woo-support-capability', 'publish_products' ), // Capability required
|
44 |
+
YIKES_Custom_Product_Tabs_Support_Page, // Page slug (?page=slug-name)
|
45 |
+
array( $this, 'support_page' ) // Function to generate page
|
46 |
+
);
|
47 |
+
}
|
48 |
+
|
49 |
+
/**
|
50 |
+
* Include our settings page
|
51 |
+
*/
|
52 |
+
public function support_page() {
|
53 |
+
|
54 |
+
require_once YIKES_Custom_Product_Tabs_Path . 'admin/page.support.php';
|
55 |
+
}
|
56 |
+
|
57 |
+
/**
|
58 |
+
* Show our support page HTML
|
59 |
+
*/
|
60 |
+
public function render_support_page() {
|
61 |
+
if ( defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ) {
|
62 |
+
return;
|
63 |
+
}
|
64 |
+
?>
|
65 |
+
<div class="cptpro-settings cptpro-settings-support-help-container">
|
66 |
+
<p>
|
67 |
+
<?php
|
68 |
+
echo sprintf( __( 'Before submitting a support request, please visit our %1sKnowledge Base%2s where we have step-by-step guides and troubleshooting help.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
69 |
+
'<a href="https://yikesplugins.com/support/knowledge-base/product/easy-custom-product-tabs-for-woocommerce/" target="_blank">', '</a>' );
|
70 |
+
?>
|
71 |
+
</p>
|
72 |
+
|
73 |
+
<p>
|
74 |
+
<?php
|
75 |
+
echo sprintf( __( 'Custom Product Tabs Pro users qualify for premium support. Check out %1sCustom Product Tabs Pro%2s!', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
76 |
+
'<a href="https://yikesplugins.com/plugin/custom-product-tabs-pro/" target="_blank">', '</a>' );
|
77 |
+
?>
|
78 |
+
</p>
|
79 |
+
|
80 |
+
<hr />
|
81 |
+
|
82 |
+
|
83 |
+
<h1>
|
84 |
+
<span class="dashicons dashicons-wordpress-alt"></span> <?php _e( 'WordPress.org Support Forums', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
85 |
+
</h1>
|
86 |
+
|
87 |
+
<p>
|
88 |
+
<?php
|
89 |
+
echo sprintf( __( 'If you need help with free Custom Product Tabs, please post questions to %1sour support forum on the WordPress Plugin Directory%2s. We aim to respond to support requests within a week.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
90 |
+
'<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">', '</a>' );
|
91 |
+
?>
|
92 |
+
</p>
|
93 |
+
|
94 |
+
<p>
|
95 |
+
<a class="button button-primary" href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">
|
96 |
+
<?php _e( 'Submit a Support Request', 'yikes-inc-easy-custom-woocommerce-product-tabs' ); ?>
|
97 |
+
</a>
|
98 |
+
</p>
|
99 |
+
|
100 |
+
<a href="https://wordpress.org/support/plugin/yikes-inc-easy-custom-woocommerce-product-tabs#new-post" target="_blank">
|
101 |
+
<img src="<?php echo YIKES_Custom_Product_Tabs_URI . 'images/support-screenshot.png' ?>" />
|
102 |
+
</a>
|
103 |
+
|
104 |
+
</div>
|
105 |
+
<?php
|
106 |
+
}
|
107 |
+
|
108 |
+
|
109 |
+
}
|
110 |
+
|
111 |
new YIKES_Custom_Product_Tabs_Support();
|
admin/class.yikes-woo-generate-html.php
CHANGED
@@ -1,396 +1,396 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
if ( ! class_exists( 'Yikes_Woo_Custom_Product_Tabs_HTML' ) ) {
|
4 |
-
class Yikes_Woo_Custom_Product_Tabs_HTML {
|
5 |
-
|
6 |
-
public function __construct() {
|
7 |
-
// empty...
|
8 |
-
}
|
9 |
-
|
10 |
-
/**
|
11 |
-
* Creates all of the HTML required for tabs on the product edit screen
|
12 |
-
*
|
13 |
-
* @since 1.5
|
14 |
-
*/
|
15 |
-
public function generate_html() {
|
16 |
-
global $post;
|
17 |
-
|
18 |
-
// Pull the custom tab data out of the database
|
19 |
-
$tab_data = maybe_unserialize( get_post_meta( $post->ID, 'yikes_woo_products_tabs', true ) );
|
20 |
-
$tab_data = is_array( $tab_data ) ? $tab_data : array();
|
21 |
-
|
22 |
-
// If we don't have tab data, we display things slightly differently
|
23 |
-
$product_has_tabs = true;
|
24 |
-
if ( empty( $tab_data ) ) {
|
25 |
-
$product_has_tabs = false;
|
26 |
-
}
|
27 |
-
|
28 |
-
// Pull the saved array of reusable tabs
|
29 |
-
$reusable_tab_options_array = get_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
30 |
-
|
31 |
-
// Display the custom tab panel
|
32 |
-
echo '<div id="yikes_woocommerce_custom_product_tabs" class="panel wc-metaboxes-wrapper woocommerce_options_panel">';
|
33 |
-
echo '<div class="options_group">';
|
34 |
-
|
35 |
-
echo $this->display_yikes_how_to();
|
36 |
-
|
37 |
-
if ( $product_has_tabs === true ) {
|
38 |
-
|
39 |
-
// Loop through all the tabs and add all components
|
40 |
-
$this->generate_tab_html( $tab_data, $reusable_tab_options_array, $post );
|
41 |
-
}
|
42 |
-
|
43 |
-
// Add duplicate container
|
44 |
-
$this->generate_duplicate_html();
|
45 |
-
|
46 |
-
// Add a Saved Tab // Add Another Tab
|
47 |
-
echo $this->display_yikes_add_tabs_container( $product_has_tabs );
|
48 |
-
|
49 |
-
// Hidden input field holding # of tabs
|
50 |
-
echo $this->display_yikes_number_of_tabs( count( $tab_data ) );
|
51 |
-
|
52 |
-
echo '</div>';
|
53 |
-
echo '</div>';
|
54 |
-
|
55 |
-
}
|
56 |
-
|
57 |
-
/* Generate HTML Functions */
|
58 |
-
|
59 |
-
/**
|
60 |
-
* Generate the duplicate HTML block
|
61 |
-
*
|
62 |
-
* @since 1.5
|
63 |
-
*
|
64 |
-
*/
|
65 |
-
protected function generate_duplicate_html() {
|
66 |
-
|
67 |
-
// duplicate_this_row content
|
68 |
-
echo '<div id="duplicate_this_row">';
|
69 |
-
|
70 |
-
// Tab title input field
|
71 |
-
woocommerce_wp_text_input( array( 'id' => 'hidden_duplicator_row_title' , 'label' => __( 'Tab Title', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'description' => '', 'placeholder' => __( 'Custom Tab Title' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'class' => 'yikes_woo_tabs_title_field yikes_woo_tabs_title_field_duplicate' ) );
|
72 |
-
|
73 |
-
// WYSIWYG Content field
|
74 |
-
$this->display_woocommerce_wp_wysiwyg_input_duplicate();
|
75 |
-
|
76 |
-
// Override Saved Tab checkbox & hidden input fields - Up & Down arrows && Remove Tab button (Duplicate)
|
77 |
-
echo $this->display_yikes_button_holder_container_duplicate();
|
78 |
-
|
79 |
-
echo '</div>';
|
80 |
-
}
|
81 |
-
|
82 |
-
/**
|
83 |
-
* Generate the normal tab HTML block
|
84 |
-
*
|
85 |
-
* @since 1.5
|
86 |
-
*
|
87 |
-
* @param array | $tab_data | Array of tab data
|
88 |
-
* @param array | $reusable_tab_options | Array of saved tab data
|
89 |
-
* @param object| $post | The global $post object
|
90 |
-
*/
|
91 |
-
protected function generate_tab_html( $tab_data, $reusable_tab_options, $post ) {
|
92 |
-
$i = 1;
|
93 |
-
|
94 |
-
// Set up the initial display, by looping
|
95 |
-
foreach ( $tab_data as $tab ) {
|
96 |
-
|
97 |
-
$reusable_tab_flag = false;
|
98 |
-
$reusable_tab_id = '';
|
99 |
-
|
100 |
-
// If $tab is in the array of reusable tabs, set flag
|
101 |
-
if ( isset( $reusable_tab_options ) && isset( $reusable_tab_options[$post->ID] ) ) {
|
102 |
-
|
103 |
-
foreach( $reusable_tab_options[$post->ID] as $id => $reusable_tab_data ) {
|
104 |
-
if ( isset( $reusable_tab_data['tab_id'] ) && isset( $tab['id'] ) && $reusable_tab_data['tab_id'] === $tab['id'] ) {
|
105 |
-
$reusable_tab_flag = true;
|
106 |
-
$reusable_tab_id = $reusable_tab_data['reusable_tab_id'];
|
107 |
-
}
|
108 |
-
}
|
109 |
-
}
|
110 |
-
|
111 |
-
// Tab Title input field
|
112 |
-
$this->display_woocommerce_wp_text_input( $i, $tab );
|
113 |
-
|
114 |
-
// Tab content wysiwyg
|
115 |
-
$this->display_woocommerce_wp_wysiwyg_input( $i, $tab );
|
116 |
-
|
117 |
-
// Override Saved Tab checkbox & hidden input fields, Up & Down arrows, Remove Tab button
|
118 |
-
echo $this->display_yikes_button_holder_container( $i, $reusable_tab_flag, $reusable_tab_id );
|
119 |
-
|
120 |
-
// line separating tabs
|
121 |
-
echo $this->display_yikes_tab_divider( $i, count( $tab_data ) );
|
122 |
-
|
123 |
-
$i++;
|
124 |
-
}
|
125 |
-
}
|
126 |
-
|
127 |
-
/**
|
128 |
-
* Add how-to info HTML to page
|
129 |
-
*
|
130 |
-
* @since 1.5
|
131 |
-
*
|
132 |
-
* @return string HTML
|
133 |
-
*/
|
134 |
-
protected function display_yikes_how_to() {
|
135 |
-
$return_html = '';
|
136 |
-
$return_html .= '<div class="yikes-woo-tabs-hidden-how-to-info">';
|
137 |
-
$return_html .= '<p class="yikes_woo_how_to_info">' . __( "For help using Custom Tabs please visit our <a href='https://yikesplugins.com/support/knowledge-base/product/easy-custom-product-tabs-for-woocommerce/' target='_blank'>Knowledge Base</a>" , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '</p>';
|
138 |
-
$return_html .= '</div>';
|
139 |
-
$return_html .= '<div id="yikes-woo-help-me-icon" class="dashicons dashicons-editor-help yikes-tabs-how-to-toggle" title="' . __( "Help Me!" , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '"></div>';
|
140 |
-
|
141 |
-
return $return_html;
|
142 |
-
}
|
143 |
-
|
144 |
-
/**
|
145 |
-
* Add button holder container HTML to page
|
146 |
-
*
|
147 |
-
* @since 1.5
|
148 |
-
*
|
149 |
-
* @param int $i Counter for tab generating loop
|
150 |
-
* @return string HTML
|
151 |
-
*/
|
152 |
-
protected function display_yikes_button_holder_container( $i, $reusable_tab_flag, $reusable_tab_id ) {
|
153 |
-
$return_html = '';
|
154 |
-
|
155 |
-
$return_html .= '<section class="button-holder" alt="' . $i . '">';
|
156 |
-
|
157 |
-
$return_html .= '<p class="yikes_wc_override_reusable_tab_container" id="_yikes_wc_override_reusable_tab_container_' . $i . '" ';
|
158 |
-
if ( $reusable_tab_flag === true ) {
|
159 |
-
$return_html .= ' data-reusable-tab="true">';
|
160 |
-
} else {
|
161 |
-
$return_html .= ' style="display: none;">';
|
162 |
-
}
|
163 |
-
$return_html .= '<input type="checkbox" class="_yikes_wc_override_reusable_tab" id="_yikes_wc_override_reusable_tab_' . $i . '" data-tab-number="'. $i .'"';
|
164 |
-
$return_html .= 'title="' . __( 'Check this box to override the saved tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '">';
|
165 |
-
$return_html .= '<label id="_yikes_wc_override_reusable_tab_label_' . $i . '" for="_yikes_wc_override_reusable_tab_' . $i . '" class="_yikes_wc_override_reusable_tab_label">';
|
166 |
-
$return_html .= __( ' Override Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
167 |
-
$return_html .= '</label>';
|
168 |
-
$return_html .= '<input type="hidden" name="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '_action" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action"';
|
169 |
-
$return_html .= 'id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '_action" value="none">';
|
170 |
-
$return_html .= '<input type="hidden" name="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id"';
|
171 |
-
$return_html .= 'id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '" value="' . $reusable_tab_id . '">';
|
172 |
-
$return_html .= '</p>';
|
173 |
-
|
174 |
-
$return_html .= '<div class="yikes_wc_move_tab_container">';
|
175 |
-
$return_html .= '<p class="yikes_wc_move_tab">Move tab order</p>';
|
176 |
-
$return_html .= '<span class="dashicons dashicons-arrow-up move-tab-data-up"></span>';
|
177 |
-
$return_html .= '<span class="dashicons dashicons-arrow-down move-tab-data-down"></span>';
|
178 |
-
$return_html .= '</div>';
|
179 |
-
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab"><span class="dashicons dashicons-no-alt"></span>';
|
180 |
-
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
181 |
-
$return_html .= '</a>';
|
182 |
-
$return_html .= '</section>';
|
183 |
-
|
184 |
-
return $return_html;
|
185 |
-
}
|
186 |
-
|
187 |
-
/**
|
188 |
-
* Add tab divider HTML to page
|
189 |
-
*
|
190 |
-
* @since 1.5
|
191 |
-
*
|
192 |
-
* @param int $i Counter for tab generating loop
|
193 |
-
* @param int $tab_count Total # of tabs
|
194 |
-
* @return string HTML
|
195 |
-
*/
|
196 |
-
protected function display_yikes_tab_divider( $i, $tab_count ) {
|
197 |
-
$return_html = '';
|
198 |
-
if ( $i != $tab_count ) {
|
199 |
-
$return_html .= '<div class="yikes-woo-custom-tab-divider"></div>';
|
200 |
-
}
|
201 |
-
|
202 |
-
return $return_html;
|
203 |
-
}
|
204 |
-
|
205 |
-
/**
|
206 |
-
* Call input field generation function and echo HTML to page
|
207 |
-
*
|
208 |
-
* @since 1.5
|
209 |
-
*
|
210 |
-
* @param int $i Counter for tab generating loop
|
211 |
-
* @param array $tab Array of tab data
|
212 |
-
*/
|
213 |
-
protected function display_woocommerce_wp_text_input( $i, $tab ) {
|
214 |
-
|
215 |
-
woocommerce_wp_text_input( array( 'id' => '_yikes_wc_custom_repeatable_product_tabs_tab_title_' . $i , 'label' => __( 'Tab Title', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'description' => '', 'value' => $tab['title'] , 'placeholder' => __( 'Custom Tab Title' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'class' => 'yikes_woo_tabs_title_field') );
|
216 |
-
}
|
217 |
-
|
218 |
-
/**
|
219 |
-
* Call wp_editor wrapped function and echo HTML to page
|
220 |
-
*
|
221 |
-
* @since 1.5
|
222 |
-
*
|
223 |
-
* @param int $i Counter for tab generating loop
|
224 |
-
* @param array $tab Array of tab data
|
225 |
-
*/
|
226 |
-
protected function display_woocommerce_wp_wysiwyg_input( $i, $tab ) {
|
227 |
-
echo '<div class="form-field-tinymce _yikes_wc_custom_repeatable_product_tabs_tab_content_field _yikes_wc_custom_repeatable_product_tabs_tab_content_' . $i . '_field">';
|
228 |
-
$this->woocommerce_wp_wysiwyg_input( array(
|
229 |
-
'id' => '_yikes_wc_custom_repeatable_product_tabs_tab_content_' . $i ,
|
230 |
-
'label' => __( 'Content', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
231 |
-
'placeholder' => __( 'HTML and text to display.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
232 |
-
'value' => $tab['content'],
|
233 |
-
'style' => 'width:100%;min-height:10rem;',
|
234 |
-
'class' => 'yikes_woo_tabs_content_field',
|
235 |
-
'number' => $i
|
236 |
-
) );
|
237 |
-
echo '</div>';
|
238 |
-
}
|
239 |
-
|
240 |
-
/* Hidden Duplicate HTML Section */
|
241 |
-
|
242 |
-
/**
|
243 |
-
* Add duplicate remove tab button HTML to page
|
244 |
-
*
|
245 |
-
* @since 1.5
|
246 |
-
*
|
247 |
-
* @return string HTML
|
248 |
-
*/
|
249 |
-
protected function display_yikes_remove_tab_duplicate() {
|
250 |
-
$return_html = '';
|
251 |
-
|
252 |
-
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab">';
|
253 |
-
$return_html .= '<span class="dashicons dashicons-no-alt"></span>';
|
254 |
-
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
255 |
-
$return_html .= '</a>';
|
256 |
-
|
257 |
-
return $return_html;
|
258 |
-
}
|
259 |
-
|
260 |
-
/**
|
261 |
-
* Call input field generation function and echo HTML to page
|
262 |
-
*
|
263 |
-
* @since 1.5
|
264 |
-
*
|
265 |
-
* @param array $tab Array of tab data
|
266 |
-
*/
|
267 |
-
protected function display_woocommerce_wp_wysiwyg_input_duplicate() {
|
268 |
-
|
269 |
-
$this->woocommerce_wp_textarea_input( array( 'id' => 'hidden_duplicator_row_content' , 'label' => __( 'Content', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'placeholder' => __( 'HTML and text to display.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'style' => 'width:100%; min-height:10rem;' , 'class' => 'yikes_woo_tabs_content_field' ) );
|
270 |
-
}
|
271 |
-
|
272 |
-
/**
|
273 |
-
* Add duplicate button holder container HTML to page
|
274 |
-
*
|
275 |
-
* @since 1.5
|
276 |
-
*
|
277 |
-
* @return string HTML
|
278 |
-
*/
|
279 |
-
protected function display_yikes_button_holder_container_duplicate() {
|
280 |
-
$return_html = '';
|
281 |
-
|
282 |
-
$return_html .= '<section class="button-holder" alt="">';
|
283 |
-
$return_html .= '<p class="yikes_wc_override_reusable_tab_container _yikes_wc_override_reusable_tab_container_duplicate" id="_yikes_wc_override_reusable_tab_container_duplicate" style="display: none;">';
|
284 |
-
$return_html .= '<input type="checkbox" class="_yikes_wc_override_reusable_tab" id="_yikes_wc_override_reusable_tab_duplicate" title="' . __( 'Check this box to override the saved tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '" />';
|
285 |
-
$return_html .= '<label class="_yikes_wc_override_reusable_tab_label_duplicate">' . __( 'Override Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '</label>';
|
286 |
-
$return_html .= '<input type="hidden" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action" id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action_duplicate" value="none">';
|
287 |
-
$return_html .= '<input type="hidden" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id" id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_duplicate" value="">';
|
288 |
-
$return_html .= '</p>';
|
289 |
-
$return_html .= '<div class="yikes_wc_move_tab_container">';
|
290 |
-
$return_html .= '<p class="yikes_wc_move_tab">Move tab order</p>';
|
291 |
-
$return_html .= '<span class="dashicons dashicons-arrow-up move-tab-data-up"></span>';
|
292 |
-
$return_html .= '<span class="dashicons dashicons-arrow-down move-tab-data-down"></span>';
|
293 |
-
$return_html .= '</div>';
|
294 |
-
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab">';
|
295 |
-
$return_html .= '<span class="dashicons dashicons-no-alt"></span>';
|
296 |
-
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
297 |
-
$return_html .= '</a>';
|
298 |
-
$return_html .= '</section>';
|
299 |
-
|
300 |
-
return $return_html;
|
301 |
-
}
|
302 |
-
|
303 |
-
/**
|
304 |
-
* Add hidden input field for number of tabs to page
|
305 |
-
*
|
306 |
-
* @since 1.5
|
307 |
-
*
|
308 |
-
* @return string HTML
|
309 |
-
*/
|
310 |
-
protected function display_yikes_number_of_tabs( $tab_count ) {
|
311 |
-
$return_html = '';
|
312 |
-
|
313 |
-
$return_html .= '<input type="hidden" value="' . $tab_count . '" id="number_of_tabs" name="number_of_tabs" >';
|
314 |
-
|
315 |
-
return $return_html;
|
316 |
-
}
|
317 |
-
|
318 |
-
/**
|
319 |
-
* Add 'Add Another Tab' and 'Add a Saved Tab' buttons to page
|
320 |
-
*
|
321 |
-
* @since 1.5
|
322 |
-
*
|
323 |
-
* @param bool | $product_has_tabs | flag indicating whether the product has any defined tabs
|
324 |
-
* @return string HTML
|
325 |
-
*/
|
326 |
-
protected function display_yikes_add_tabs_container( $product_has_tabs ) {
|
327 |
-
$return_html = '';
|
328 |
-
|
329 |
-
// If we don't have any tabs, then add some classes
|
330 |
-
$classes_to_add = ( $product_has_tabs === false ) ? '_yikes_wc_add_tab_center_new _yikes_wc_add_tab_center' : '';
|
331 |
-
|
332 |
-
$return_html .= '<div class="add_tabs_container ' . $classes_to_add . '">';
|
333 |
-
$return_html .= '<span id="yikes_woo_ajax_save_feedback"></span>';
|
334 |
-
$return_html .= '<a href="#" class="button-secondary _yikes_wc_add_tabs" id="add_another_tab">';
|
335 |
-
$return_html .= '<i class="dashicons dashicons-plus-alt inline-button-dashicons"></i>';
|
336 |
-
$return_html .= __( 'Add a Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
337 |
-
$return_html .= '</a>';
|
338 |
-
$return_html .= '<span class="yikes_wc_apply_reusable_tab_container">';
|
339 |
-
$return_html .= '<span class="button-secondary _yikes_wc_apply_a_saved_tab _yikes_wc_add_tabs" id="_yikes_wc_apply_a_saved_tab">';
|
340 |
-
$return_html .= '<i class="dashicons dashicons-plus-alt inline-button-dashicons"></i>';
|
341 |
-
$return_html .= __( 'Add a Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
342 |
-
$return_html .= '</span>';
|
343 |
-
$return_html .= '</span>';
|
344 |
-
$return_html .= '<input name="save" class="button button-primary" id="yikes_woo_save_custom_tabs" value="Save Tabs" type="button">';
|
345 |
-
$return_html .= '</div>';
|
346 |
-
|
347 |
-
return $return_html;
|
348 |
-
}
|
349 |
-
|
350 |
-
/**
|
351 |
-
* Generates a textarea field for hidden duplicate HTML block
|
352 |
-
*
|
353 |
-
* @param array $field Array of HTML field related values
|
354 |
-
*/
|
355 |
-
private function woocommerce_wp_textarea_input( $field ) {
|
356 |
-
|
357 |
-
if ( ! isset( $field['placeholder'] ) ) $field['placeholder'] = '';
|
358 |
-
if ( ! isset( $field['class'] ) ) $field['class'] = '';
|
359 |
-
if ( ! isset( $field['value'] ) ) $field['value'] = '';
|
360 |
-
|
361 |
-
echo '<p class="form-field-tinymce ' . $field['id'] . '_field"> <textarea class="' . $field['class'] . '" name="' . $field['id'] . '" id="' . $field['id'] . '" placeholder="' . $field['placeholder'] . '" rows="2" cols="20"' . (isset( $field['style'] ) ? ' style="' . $field['style'] . '"' : '') . '>' . $field['value'] . '</textarea> ';
|
362 |
-
|
363 |
-
if ( isset( $field['description'] ) && $field['description'] ) {
|
364 |
-
echo '<span class="description">' . $field['description'] . '</span>';
|
365 |
-
}
|
366 |
-
|
367 |
-
echo '</p>';
|
368 |
-
}
|
369 |
-
|
370 |
-
/**
|
371 |
-
* Wrapper function for wp_editor
|
372 |
-
*
|
373 |
-
* @param array $field Array of HTML field related values
|
374 |
-
*/
|
375 |
-
private function woocommerce_wp_wysiwyg_input( $field ) {
|
376 |
-
|
377 |
-
if ( ! isset( $field['placeholder'] ) ) $field['placeholder'] = '';
|
378 |
-
if ( ! isset( $field['class'] ) ) $field['class'] = '';
|
379 |
-
if ( ! isset( $field['value'] ) ) $field['value'] = '';
|
380 |
-
|
381 |
-
$editor_settings = array(
|
382 |
-
'textarea_name' => $field['id']
|
383 |
-
);
|
384 |
-
|
385 |
-
wp_editor( $field['value'], $field['id'], $editor_settings );
|
386 |
-
|
387 |
-
if ( isset( $field['description'] ) && $field['description'] ) {
|
388 |
-
echo '<span class="description">' . $field['description'] . '</span>';
|
389 |
-
}
|
390 |
-
}
|
391 |
-
|
392 |
-
/* END HTML Functions */
|
393 |
-
}
|
394 |
-
}
|
395 |
-
|
396 |
?>
|
1 |
+
<?php
|
2 |
+
|
3 |
+
if ( ! class_exists( 'Yikes_Woo_Custom_Product_Tabs_HTML' ) ) {
|
4 |
+
class Yikes_Woo_Custom_Product_Tabs_HTML {
|
5 |
+
|
6 |
+
public function __construct() {
|
7 |
+
// empty...
|
8 |
+
}
|
9 |
+
|
10 |
+
/**
|
11 |
+
* Creates all of the HTML required for tabs on the product edit screen
|
12 |
+
*
|
13 |
+
* @since 1.5
|
14 |
+
*/
|
15 |
+
public function generate_html() {
|
16 |
+
global $post;
|
17 |
+
|
18 |
+
// Pull the custom tab data out of the database
|
19 |
+
$tab_data = maybe_unserialize( get_post_meta( $post->ID, 'yikes_woo_products_tabs', true ) );
|
20 |
+
$tab_data = is_array( $tab_data ) ? $tab_data : array();
|
21 |
+
|
22 |
+
// If we don't have tab data, we display things slightly differently
|
23 |
+
$product_has_tabs = true;
|
24 |
+
if ( empty( $tab_data ) ) {
|
25 |
+
$product_has_tabs = false;
|
26 |
+
}
|
27 |
+
|
28 |
+
// Pull the saved array of reusable tabs
|
29 |
+
$reusable_tab_options_array = get_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
30 |
+
|
31 |
+
// Display the custom tab panel
|
32 |
+
echo '<div id="yikes_woocommerce_custom_product_tabs" class="panel wc-metaboxes-wrapper woocommerce_options_panel">';
|
33 |
+
echo '<div class="options_group">';
|
34 |
+
|
35 |
+
echo $this->display_yikes_how_to();
|
36 |
+
|
37 |
+
if ( $product_has_tabs === true ) {
|
38 |
+
|
39 |
+
// Loop through all the tabs and add all components
|
40 |
+
$this->generate_tab_html( $tab_data, $reusable_tab_options_array, $post );
|
41 |
+
}
|
42 |
+
|
43 |
+
// Add duplicate container
|
44 |
+
$this->generate_duplicate_html();
|
45 |
+
|
46 |
+
// Add a Saved Tab // Add Another Tab
|
47 |
+
echo $this->display_yikes_add_tabs_container( $product_has_tabs );
|
48 |
+
|
49 |
+
// Hidden input field holding # of tabs
|
50 |
+
echo $this->display_yikes_number_of_tabs( count( $tab_data ) );
|
51 |
+
|
52 |
+
echo '</div>';
|
53 |
+
echo '</div>';
|
54 |
+
|
55 |
+
}
|
56 |
+
|
57 |
+
/* Generate HTML Functions */
|
58 |
+
|
59 |
+
/**
|
60 |
+
* Generate the duplicate HTML block
|
61 |
+
*
|
62 |
+
* @since 1.5
|
63 |
+
*
|
64 |
+
*/
|
65 |
+
protected function generate_duplicate_html() {
|
66 |
+
|
67 |
+
// duplicate_this_row content
|
68 |
+
echo '<div id="duplicate_this_row">';
|
69 |
+
|
70 |
+
// Tab title input field
|
71 |
+
woocommerce_wp_text_input( array( 'id' => 'hidden_duplicator_row_title' , 'label' => __( 'Tab Title', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'description' => '', 'placeholder' => __( 'Custom Tab Title' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'class' => 'yikes_woo_tabs_title_field yikes_woo_tabs_title_field_duplicate' ) );
|
72 |
+
|
73 |
+
// WYSIWYG Content field
|
74 |
+
$this->display_woocommerce_wp_wysiwyg_input_duplicate();
|
75 |
+
|
76 |
+
// Override Saved Tab checkbox & hidden input fields - Up & Down arrows && Remove Tab button (Duplicate)
|
77 |
+
echo $this->display_yikes_button_holder_container_duplicate();
|
78 |
+
|
79 |
+
echo '</div>';
|
80 |
+
}
|
81 |
+
|
82 |
+
/**
|
83 |
+
* Generate the normal tab HTML block
|
84 |
+
*
|
85 |
+
* @since 1.5
|
86 |
+
*
|
87 |
+
* @param array | $tab_data | Array of tab data
|
88 |
+
* @param array | $reusable_tab_options | Array of saved tab data
|
89 |
+
* @param object| $post | The global $post object
|
90 |
+
*/
|
91 |
+
protected function generate_tab_html( $tab_data, $reusable_tab_options, $post ) {
|
92 |
+
$i = 1;
|
93 |
+
|
94 |
+
// Set up the initial display, by looping
|
95 |
+
foreach ( $tab_data as $tab ) {
|
96 |
+
|
97 |
+
$reusable_tab_flag = false;
|
98 |
+
$reusable_tab_id = '';
|
99 |
+
|
100 |
+
// If $tab is in the array of reusable tabs, set flag
|
101 |
+
if ( isset( $reusable_tab_options ) && isset( $reusable_tab_options[$post->ID] ) ) {
|
102 |
+
|
103 |
+
foreach( $reusable_tab_options[$post->ID] as $id => $reusable_tab_data ) {
|
104 |
+
if ( isset( $reusable_tab_data['tab_id'] ) && isset( $tab['id'] ) && $reusable_tab_data['tab_id'] === $tab['id'] ) {
|
105 |
+
$reusable_tab_flag = true;
|
106 |
+
$reusable_tab_id = $reusable_tab_data['reusable_tab_id'];
|
107 |
+
}
|
108 |
+
}
|
109 |
+
}
|
110 |
+
|
111 |
+
// Tab Title input field
|
112 |
+
$this->display_woocommerce_wp_text_input( $i, $tab );
|
113 |
+
|
114 |
+
// Tab content wysiwyg
|
115 |
+
$this->display_woocommerce_wp_wysiwyg_input( $i, $tab );
|
116 |
+
|
117 |
+
// Override Saved Tab checkbox & hidden input fields, Up & Down arrows, Remove Tab button
|
118 |
+
echo $this->display_yikes_button_holder_container( $i, $reusable_tab_flag, $reusable_tab_id );
|
119 |
+
|
120 |
+
// line separating tabs
|
121 |
+
echo $this->display_yikes_tab_divider( $i, count( $tab_data ) );
|
122 |
+
|
123 |
+
$i++;
|
124 |
+
}
|
125 |
+
}
|
126 |
+
|
127 |
+
/**
|
128 |
+
* Add how-to info HTML to page
|
129 |
+
*
|
130 |
+
* @since 1.5
|
131 |
+
*
|
132 |
+
* @return string HTML
|
133 |
+
*/
|
134 |
+
protected function display_yikes_how_to() {
|
135 |
+
$return_html = '';
|
136 |
+
$return_html .= '<div class="yikes-woo-tabs-hidden-how-to-info">';
|
137 |
+
$return_html .= '<p class="yikes_woo_how_to_info">' . __( "For help using Custom Tabs please visit our <a href='https://yikesplugins.com/support/knowledge-base/product/easy-custom-product-tabs-for-woocommerce/' target='_blank'>Knowledge Base</a>" , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '</p>';
|
138 |
+
$return_html .= '</div>';
|
139 |
+
$return_html .= '<div id="yikes-woo-help-me-icon" class="dashicons dashicons-editor-help yikes-tabs-how-to-toggle" title="' . __( "Help Me!" , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '"></div>';
|
140 |
+
|
141 |
+
return $return_html;
|
142 |
+
}
|
143 |
+
|
144 |
+
/**
|
145 |
+
* Add button holder container HTML to page
|
146 |
+
*
|
147 |
+
* @since 1.5
|
148 |
+
*
|
149 |
+
* @param int $i Counter for tab generating loop
|
150 |
+
* @return string HTML
|
151 |
+
*/
|
152 |
+
protected function display_yikes_button_holder_container( $i, $reusable_tab_flag, $reusable_tab_id ) {
|
153 |
+
$return_html = '';
|
154 |
+
|
155 |
+
$return_html .= '<section class="button-holder" alt="' . $i . '">';
|
156 |
+
|
157 |
+
$return_html .= '<p class="yikes_wc_override_reusable_tab_container" id="_yikes_wc_override_reusable_tab_container_' . $i . '" ';
|
158 |
+
if ( $reusable_tab_flag === true ) {
|
159 |
+
$return_html .= ' data-reusable-tab="true">';
|
160 |
+
} else {
|
161 |
+
$return_html .= ' style="display: none;">';
|
162 |
+
}
|
163 |
+
$return_html .= '<input type="checkbox" class="_yikes_wc_override_reusable_tab" id="_yikes_wc_override_reusable_tab_' . $i . '" data-tab-number="'. $i .'"';
|
164 |
+
$return_html .= 'title="' . __( 'Check this box to override the saved tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '">';
|
165 |
+
$return_html .= '<label id="_yikes_wc_override_reusable_tab_label_' . $i . '" for="_yikes_wc_override_reusable_tab_' . $i . '" class="_yikes_wc_override_reusable_tab_label">';
|
166 |
+
$return_html .= __( ' Override Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
167 |
+
$return_html .= '</label>';
|
168 |
+
$return_html .= '<input type="hidden" name="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '_action" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action"';
|
169 |
+
$return_html .= 'id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '_action" value="none">';
|
170 |
+
$return_html .= '<input type="hidden" name="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id"';
|
171 |
+
$return_html .= 'id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_' . $i . '" value="' . $reusable_tab_id . '">';
|
172 |
+
$return_html .= '</p>';
|
173 |
+
|
174 |
+
$return_html .= '<div class="yikes_wc_move_tab_container">';
|
175 |
+
$return_html .= '<p class="yikes_wc_move_tab">Move tab order</p>';
|
176 |
+
$return_html .= '<span class="dashicons dashicons-arrow-up move-tab-data-up"></span>';
|
177 |
+
$return_html .= '<span class="dashicons dashicons-arrow-down move-tab-data-down"></span>';
|
178 |
+
$return_html .= '</div>';
|
179 |
+
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab"><span class="dashicons dashicons-no-alt"></span>';
|
180 |
+
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
181 |
+
$return_html .= '</a>';
|
182 |
+
$return_html .= '</section>';
|
183 |
+
|
184 |
+
return $return_html;
|
185 |
+
}
|
186 |
+
|
187 |
+
/**
|
188 |
+
* Add tab divider HTML to page
|
189 |
+
*
|
190 |
+
* @since 1.5
|
191 |
+
*
|
192 |
+
* @param int $i Counter for tab generating loop
|
193 |
+
* @param int $tab_count Total # of tabs
|
194 |
+
* @return string HTML
|
195 |
+
*/
|
196 |
+
protected function display_yikes_tab_divider( $i, $tab_count ) {
|
197 |
+
$return_html = '';
|
198 |
+
if ( $i != $tab_count ) {
|
199 |
+
$return_html .= '<div class="yikes-woo-custom-tab-divider"></div>';
|
200 |
+
}
|
201 |
+
|
202 |
+
return $return_html;
|
203 |
+
}
|
204 |
+
|
205 |
+
/**
|
206 |
+
* Call input field generation function and echo HTML to page
|
207 |
+
*
|
208 |
+
* @since 1.5
|
209 |
+
*
|
210 |
+
* @param int $i Counter for tab generating loop
|
211 |
+
* @param array $tab Array of tab data
|
212 |
+
*/
|
213 |
+
protected function display_woocommerce_wp_text_input( $i, $tab ) {
|
214 |
+
|
215 |
+
woocommerce_wp_text_input( array( 'id' => '_yikes_wc_custom_repeatable_product_tabs_tab_title_' . $i , 'label' => __( 'Tab Title', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'description' => '', 'value' => $tab['title'] , 'placeholder' => __( 'Custom Tab Title' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'class' => 'yikes_woo_tabs_title_field') );
|
216 |
+
}
|
217 |
+
|
218 |
+
/**
|
219 |
+
* Call wp_editor wrapped function and echo HTML to page
|
220 |
+
*
|
221 |
+
* @since 1.5
|
222 |
+
*
|
223 |
+
* @param int $i Counter for tab generating loop
|
224 |
+
* @param array $tab Array of tab data
|
225 |
+
*/
|
226 |
+
protected function display_woocommerce_wp_wysiwyg_input( $i, $tab ) {
|
227 |
+
echo '<div class="form-field-tinymce _yikes_wc_custom_repeatable_product_tabs_tab_content_field _yikes_wc_custom_repeatable_product_tabs_tab_content_' . $i . '_field">';
|
228 |
+
$this->woocommerce_wp_wysiwyg_input( array(
|
229 |
+
'id' => '_yikes_wc_custom_repeatable_product_tabs_tab_content_' . $i ,
|
230 |
+
'label' => __( 'Content', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
231 |
+
'placeholder' => __( 'HTML and text to display.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
232 |
+
'value' => $tab['content'],
|
233 |
+
'style' => 'width:100%;min-height:10rem;',
|
234 |
+
'class' => 'yikes_woo_tabs_content_field',
|
235 |
+
'number' => $i
|
236 |
+
) );
|
237 |
+
echo '</div>';
|
238 |
+
}
|
239 |
+
|
240 |
+
/* Hidden Duplicate HTML Section */
|
241 |
+
|
242 |
+
/**
|
243 |
+
* Add duplicate remove tab button HTML to page
|
244 |
+
*
|
245 |
+
* @since 1.5
|
246 |
+
*
|
247 |
+
* @return string HTML
|
248 |
+
*/
|
249 |
+
protected function display_yikes_remove_tab_duplicate() {
|
250 |
+
$return_html = '';
|
251 |
+
|
252 |
+
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab">';
|
253 |
+
$return_html .= '<span class="dashicons dashicons-no-alt"></span>';
|
254 |
+
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
255 |
+
$return_html .= '</a>';
|
256 |
+
|
257 |
+
return $return_html;
|
258 |
+
}
|
259 |
+
|
260 |
+
/**
|
261 |
+
* Call input field generation function and echo HTML to page
|
262 |
+
*
|
263 |
+
* @since 1.5
|
264 |
+
*
|
265 |
+
* @param array $tab Array of tab data
|
266 |
+
*/
|
267 |
+
protected function display_woocommerce_wp_wysiwyg_input_duplicate() {
|
268 |
+
|
269 |
+
$this->woocommerce_wp_textarea_input( array( 'id' => 'hidden_duplicator_row_content' , 'label' => __( 'Content', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'placeholder' => __( 'HTML and text to display.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ), 'style' => 'width:100%; min-height:10rem;' , 'class' => 'yikes_woo_tabs_content_field' ) );
|
270 |
+
}
|
271 |
+
|
272 |
+
/**
|
273 |
+
* Add duplicate button holder container HTML to page
|
274 |
+
*
|
275 |
+
* @since 1.5
|
276 |
+
*
|
277 |
+
* @return string HTML
|
278 |
+
*/
|
279 |
+
protected function display_yikes_button_holder_container_duplicate() {
|
280 |
+
$return_html = '';
|
281 |
+
|
282 |
+
$return_html .= '<section class="button-holder" alt="">';
|
283 |
+
$return_html .= '<p class="yikes_wc_override_reusable_tab_container _yikes_wc_override_reusable_tab_container_duplicate" id="_yikes_wc_override_reusable_tab_container_duplicate" style="display: none;">';
|
284 |
+
$return_html .= '<input type="checkbox" class="_yikes_wc_override_reusable_tab" id="_yikes_wc_override_reusable_tab_duplicate" title="' . __( 'Check this box to override the saved tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '" />';
|
285 |
+
$return_html .= '<label class="_yikes_wc_override_reusable_tab_label_duplicate">' . __( 'Override Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' ) . '</label>';
|
286 |
+
$return_html .= '<input type="hidden" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action" id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_action_duplicate" value="none">';
|
287 |
+
$return_html .= '<input type="hidden" class="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id" id="_yikes_wc_custom_repeatable_product_tabs_saved_tab_id_duplicate" value="">';
|
288 |
+
$return_html .= '</p>';
|
289 |
+
$return_html .= '<div class="yikes_wc_move_tab_container">';
|
290 |
+
$return_html .= '<p class="yikes_wc_move_tab">Move tab order</p>';
|
291 |
+
$return_html .= '<span class="dashicons dashicons-arrow-up move-tab-data-up"></span>';
|
292 |
+
$return_html .= '<span class="dashicons dashicons-arrow-down move-tab-data-down"></span>';
|
293 |
+
$return_html .= '</div>';
|
294 |
+
$return_html .= '<a href="#" onclick="return false;" class="button-secondary remove_this_tab">';
|
295 |
+
$return_html .= '<span class="dashicons dashicons-no-alt"></span>';
|
296 |
+
$return_html .= __( 'Remove Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
297 |
+
$return_html .= '</a>';
|
298 |
+
$return_html .= '</section>';
|
299 |
+
|
300 |
+
return $return_html;
|
301 |
+
}
|
302 |
+
|
303 |
+
/**
|
304 |
+
* Add hidden input field for number of tabs to page
|
305 |
+
*
|
306 |
+
* @since 1.5
|
307 |
+
*
|
308 |
+
* @return string HTML
|
309 |
+
*/
|
310 |
+
protected function display_yikes_number_of_tabs( $tab_count ) {
|
311 |
+
$return_html = '';
|
312 |
+
|
313 |
+
$return_html .= '<input type="hidden" value="' . $tab_count . '" id="number_of_tabs" name="number_of_tabs" >';
|
314 |
+
|
315 |
+
return $return_html;
|
316 |
+
}
|
317 |
+
|
318 |
+
/**
|
319 |
+
* Add 'Add Another Tab' and 'Add a Saved Tab' buttons to page
|
320 |
+
*
|
321 |
+
* @since 1.5
|
322 |
+
*
|
323 |
+
* @param bool | $product_has_tabs | flag indicating whether the product has any defined tabs
|
324 |
+
* @return string HTML
|
325 |
+
*/
|
326 |
+
protected function display_yikes_add_tabs_container( $product_has_tabs ) {
|
327 |
+
$return_html = '';
|
328 |
+
|
329 |
+
// If we don't have any tabs, then add some classes
|
330 |
+
$classes_to_add = ( $product_has_tabs === false ) ? '_yikes_wc_add_tab_center_new _yikes_wc_add_tab_center' : '';
|
331 |
+
|
332 |
+
$return_html .= '<div class="add_tabs_container ' . $classes_to_add . '">';
|
333 |
+
$return_html .= '<span id="yikes_woo_ajax_save_feedback"></span>';
|
334 |
+
$return_html .= '<a href="#" class="button-secondary _yikes_wc_add_tabs" id="add_another_tab">';
|
335 |
+
$return_html .= '<i class="dashicons dashicons-plus-alt inline-button-dashicons"></i>';
|
336 |
+
$return_html .= __( 'Add a Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
337 |
+
$return_html .= '</a>';
|
338 |
+
$return_html .= '<span class="yikes_wc_apply_reusable_tab_container">';
|
339 |
+
$return_html .= '<span class="button-secondary _yikes_wc_apply_a_saved_tab _yikes_wc_add_tabs" id="_yikes_wc_apply_a_saved_tab">';
|
340 |
+
$return_html .= '<i class="dashicons dashicons-plus-alt inline-button-dashicons"></i>';
|
341 |
+
$return_html .= __( 'Add a Saved Tab' , 'yikes-inc-easy-custom-woocommerce-product-tabs' );
|
342 |
+
$return_html .= '</span>';
|
343 |
+
$return_html .= '</span>';
|
344 |
+
$return_html .= '<input name="save" class="button button-primary" id="yikes_woo_save_custom_tabs" value="Save Tabs" type="button">';
|
345 |
+
$return_html .= '</div>';
|
346 |
+
|
347 |
+
return $return_html;
|
348 |
+
}
|
349 |
+
|
350 |
+
/**
|
351 |
+
* Generates a textarea field for hidden duplicate HTML block
|
352 |
+
*
|
353 |
+
* @param array $field Array of HTML field related values
|
354 |
+
*/
|
355 |
+
private function woocommerce_wp_textarea_input( $field ) {
|
356 |
+
|
357 |
+
if ( ! isset( $field['placeholder'] ) ) $field['placeholder'] = '';
|
358 |
+
if ( ! isset( $field['class'] ) ) $field['class'] = '';
|
359 |
+
if ( ! isset( $field['value'] ) ) $field['value'] = '';
|
360 |
+
|
361 |
+
echo '<p class="form-field-tinymce ' . $field['id'] . '_field"> <textarea class="' . $field['class'] . '" name="' . $field['id'] . '" id="' . $field['id'] . '" placeholder="' . $field['placeholder'] . '" rows="2" cols="20"' . (isset( $field['style'] ) ? ' style="' . $field['style'] . '"' : '') . '>' . $field['value'] . '</textarea> ';
|
362 |
+
|
363 |
+
if ( isset( $field['description'] ) && $field['description'] ) {
|
364 |
+
echo '<span class="description">' . $field['description'] . '</span>';
|
365 |
+
}
|
366 |
+
|
367 |
+
echo '</p>';
|
368 |
+
}
|
369 |
+
|
370 |
+
/**
|
371 |
+
* Wrapper function for wp_editor
|
372 |
+
*
|
373 |
+
* @param array $field Array of HTML field related values
|
374 |
+
*/
|
375 |
+
private function woocommerce_wp_wysiwyg_input( $field ) {
|
376 |
+
|
377 |
+
if ( ! isset( $field['placeholder'] ) ) $field['placeholder'] = '';
|
378 |
+
if ( ! isset( $field['class'] ) ) $field['class'] = '';
|
379 |
+
if ( ! isset( $field['value'] ) ) $field['value'] = '';
|
380 |
+
|
381 |
+
$editor_settings = array(
|
382 |
+
'textarea_name' => $field['id']
|
383 |
+
);
|
384 |
+
|
385 |
+
wp_editor( $field['value'], $field['id'], $editor_settings );
|
386 |
+
|
387 |
+
if ( isset( $field['description'] ) && $field['description'] ) {
|
388 |
+
echo '<span class="description">' . $field['description'] . '</span>';
|
389 |
+
}
|
390 |
+
}
|
391 |
+
|
392 |
+
/* END HTML Functions */
|
393 |
+
}
|
394 |
+
}
|
395 |
+
|
396 |
?>
|
admin/class.yikes-woo-saved-tabs.php
CHANGED
@@ -1,627 +1,627 @@
|
|
1 |
-
<?php
|
2 |
-
|
3 |
-
if ( ! class_exists( 'YIKES_Custom_Product_Tabs_Saved_Tabs' ) ) {
|
4 |
-
|
5 |
-
class YIKES_Custom_Product_Tabs_Saved_Tabs {
|
6 |
-
|
7 |
-
public function __construct() {
|
8 |
-
|
9 |
-
// Add our custom settings page
|
10 |
-
add_action( 'admin_menu', array( $this, 'yikes_woo_register_settings_page' ), 10 );
|
11 |
-
|
12 |
-
// Define our options and filters
|
13 |
-
add_action( 'admin_init', array( $this, 'init' ) );
|
14 |
-
}
|
15 |
-
|
16 |
-
public function init() {
|
17 |
-
|
18 |
-
// Add our custom options for saved tabs
|
19 |
-
add_option( 'yikes_woo_reusable_products_tabs', array() );
|
20 |
-
add_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
21 |
-
|
22 |
-
// Enqueue our JS / CSS files
|
23 |
-
add_action( 'admin_enqueue_scripts' , array( $this , 'enqueue_scripts_and_styles' ), 10, 1 );
|
24 |
-
|
25 |
-
// Define our AJAX calls
|
26 |
-
add_action( 'wp_ajax_yikes_woo_save_tab_as_reusable', array( $this, 'yikes_woo_save_tab_as_reusable' ) );
|
27 |
-
add_action( 'wp_ajax_yikes_woo_fetch_reusable_tabs', array( $this, 'yikes_woo_fetch_reusable_tabs' ) );
|
28 |
-
add_action( 'wp_ajax_yikes_woo_fetch_reusable_tab', array( $this, 'yikes_woo_fetch_reusable_tab' ) );
|
29 |
-
add_action( 'wp_ajax_yikes_woo_delete_reusable_tab_handler', array( $this, 'yikes_woo_delete_reusable_tab_handler' ) );
|
30 |
-
|
31 |
-
// Duplicate any saved tabs when a product is duplicated
|
32 |
-
add_filter( 'woocommerce_product_duplicate', array( $this, 'yikes_woo_dupe_saved_tabs_on_product_dupe' ), 11, 2 );
|
33 |
-
|
34 |
-
// Delete any saved tabs when a product is deleted
|
35 |
-
add_action( 'delete_post', array( $this, 'delete_saved_tabs_on_product_delete' ), 10, 1 );
|
36 |
-
}
|
37 |
-
|
38 |
-
/**
|
39 |
-
* Enqueue our scripts and styles
|
40 |
-
*
|
41 |
-
* @param string | $hook | The current page
|
42 |
-
*/
|
43 |
-
public function enqueue_scripts_and_styles( $hook ) {
|
44 |
-
|
45 |
-
if ( $hook === 'toplevel_page_' . YIKES_Custom_Product_Tabs_Settings_Page ) {
|
46 |
-
|
47 |
-
// JavaScript
|
48 |
-
wp_enqueue_script ( 'repeatable-custom-tabs-settings', YIKES_Custom_Product_Tabs_URI . 'js/repeatable-custom-tabs-settings.min.js', array( 'jquery' ), YIKES_Custom_Product_Tabs_Version );
|
49 |
-
wp_localize_script( 'repeatable-custom-tabs-settings', 'repeatable_custom_tabs_settings', array(
|
50 |
-
'loading_gif' => '<img src="' . admin_url( 'images/loading.gif' ) . '" alt="preloader" class="loading-wp-editor-gif-settings" />',
|
51 |
-
'ajaxurl' => admin_url( 'admin-ajax.php' ),
|
52 |
-
'tab_list_page_url' => esc_url_raw( add_query_arg( array( 'page' => YIKES_Custom_Product_Tabs_Settings_Page ), admin_url() ) ),
|
53 |
-
'save_tab_as_reusable_nonce' => wp_create_nonce( 'yikes_woo_save_tab_as_reusable_nonce' ),
|
54 |
-
'delete_reusable_tab_nonce' => wp_create_nonce( 'yikes_woo_delete_reusable_tab_nonce' ),
|
55 |
-
'is_cptpro_enabled' => defined( 'YIKES_Custom_Product_Tabs_Pro_Enabled' ) ? true : false,
|
56 |
-
) );
|
57 |
-
|
58 |
-
wp_enqueue_script ( 'repeatable-custom-tabs-shared', YIKES_Custom_Product_Tabs_URI . 'js/repeatable-custom-tabs-shared.min.js', array( 'jquery' ), YIKES_Custom_Product_Tabs_Version );
|
59 |
-
wp_localize_script( 'repeatable-custom-tabs-shared', 'repeatable_custom_tabs_shared', array(
|
60 |
-
'loading_gif' => '<img src="' . admin_url( 'images/loading.gif' ) . '" alt="preloader" class="loading-wp-editor-gif" />',
|
61 |
-
'ajaxurl' => admin_url( 'admin-ajax.php' ),
|
62 |
-
'get_wp_editor_security_nonce' => wp_create_nonce( 'yikes_woo_get_wp_editor_nonce' ),
|
63 |
-
'get_wp_editor_failure_message' => __( 'Sorry! An error has occurred while trying to retrieve the editor. Please refresh the page and try again.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ),
|
64 |
-
) );
|
65 |
-
|
66 |
-
// Twitter script for our Tweet Us button
|
67 |
-
wp_enqueue_script( 'twitter-button', YIKES_Custom_Product_Tabs_URI . 'js/twitter-embed.js', null, YIKES_Custom_Product_Tabs_Version );
|
68 |
-
|
69 |
-
// CSS
|
70 |
-
wp_enqueue_style( 'repeatable-custom-tabs-styles' , YIKES_Custom_Product_Tabs_URI . 'css/repeatable-custom-tabs.min.css', '', YIKES_Custom_Product_Tabs_Version, 'all' );
|
71 |
-
}
|
72 |
-
|
73 |
-
}
|
74 |
-
|
75 |
-
/* AJAX Functions */
|
76 |
-
|
77 |
-
/**
|
78 |
-
* [AJAX] Save a tab as reusable
|
79 |
-
*
|
80 |
-
* @since 1.5
|
81 |
-
*
|
82 |
-
* @param string | $_POST['tab_title'] | Tab title to save
|
83 |
-
* @param string | $_POST['tab_content'] | Tab content to save
|
84 |
-
* @param string | $_POST['tab_id'] | Optional. Tab ID we're updating
|
85 |
-
* @param string | $_POST['tab_name'] | Tab name to save
|
86 |
-
* @param array | $_POST['taxonomies'] | Optional. Array of taxonomies.
|
87 |
-
*
|
88 |
-
* @return string | JSON response
|
89 |
-
*/
|
90 |
-
public function yikes_woo_save_tab_as_reusable() {
|
91 |
-
|
92 |
-
// Verify the nonce
|
93 |
-
if ( ! check_ajax_referer( 'yikes_woo_save_tab_as_reusable_nonce', 'security_nonce', false ) ) {
|
94 |
-
wp_send_json_error();
|
95 |
-
}
|
96 |
-
|
97 |
-
// Define it now, because we may use this later...
|
98 |
-
$return_redirect_url = '';
|
99 |
-
|
100 |
-
// Get our $_POST vars
|
101 |
-
if ( isset( $_POST['tab_title'] ) && ! empty( $_POST['tab_title'] ) ) {
|
102 |
-
$tab_title = stripslashes( $_POST['tab_title'] );
|
103 |
-
$tab_string_id = urldecode( sanitize_title( $tab_title ) );
|
104 |
-
} else {
|
105 |
-
wp_send_json_error( array( 'reason' => 'no tab title', 'message' => 'Please fill out the tab title before saving.' ) );
|
106 |
-
}
|
107 |
-
|
108 |
-
$tab_content = isset( $_POST['tab_content'] ) && ! empty( $_POST['tab_content'] ) ? $_POST['tab_content'] : '';
|
109 |
-
$tab_id = isset( $_POST['tab_id'] ) && ! empty( $_POST['tab_id'] ) ? $_POST['tab_id'] : '';
|
110 |
-
$tab_name = isset( $_POST['tab_name'] ) ? $_POST['tab_name'] : '';
|
111 |
-
$global_tab = isset( $_POST['global_tab'] ) && $_POST['global_tab'] === 'true' ? true : false;
|
112 |
-
|
113 |
-
// Remove taxonomies if we're using a global tab
|
114 |
-
$taxonomies = isset( $_POST['taxonomies'] ) && ! empty( $_POST['taxonomies'] ) && $global_tab === false ? $_POST['taxonomies'] : array();
|
115 |
-
|
116 |
-
// Get our saved tabs array
|
117 |
-
$yikes_custom_tab_data = get_option( 'yikes_woo_reusable_products_tabs', array() );
|
118 |
-
|
119 |
-
// If the saved tabs array is empty, create a new array and save it (first time we've done this)
|
120 |
-
if ( empty( $yikes_custom_tab_data ) ) {
|
121 |
-
$yikes_custom_tab_options_array = array();
|
122 |
-
$new_tab = array(
|
123 |
-
'tab_title' => $tab_title,
|
124 |
-
'tab_name' => $tab_name,
|
125 |
-
'tab_content' => $tab_content,
|
126 |
-
'tab_id' => 1,
|
127 |
-
'taxonomies' => $taxonomies,
|
128 |
-
'tab_slug' => $tab_string_id,
|
129 |
-
'global_tab' => $global_tab,
|
130 |
-
);
|
131 |
-
|
132 |
-
$yikes_custom_tab_options_array[1] = $new_tab;
|
133 |
-
|
134 |
-
do_action( 'yikes-woo-handle-tab-save', $new_tab, 'new' );
|
135 |
-
|
136 |
-
update_option( 'yikes_woo_reusable_products_tabs', $yikes_custom_tab_options_array );
|
137 |
-
|
138 |
-
// Return redirect URL
|
139 |
-
$return_redirect_url = esc_url_raw( add_query_arg( array( 'page' => YIKES_Custom_Product_Tabs_Settings_Page, 'saved-tab-id' => 1 ), admin_url() ) );
|
140 |
-
|
141 |
-
// Send response
|
142 |
-
wp_send_json_success( array( 'tab_id' => 1, 'redirect' => true, 'redirect_url' => $return_redirect_url ) );
|
143 |
-
} else {
|
144 |
-
|
145 |
-
// this is a new tab and we need to create a unique ID
|
146 |
-
if ( $tab_id === 'new' ) {
|
147 |
-
|
148 |
-
// Get the max ID we have saved
|
149 |
-
foreach ( $yikes_custom_tab_data as $tab_data ) {
|
150 |
-
if ( ! isset( $highest_tab_id ) ) {
|
151 |
-
$highest_tab_id = $tab_data['tab_id'];
|
152 |
-
} else {
|
153 |
-
if ( $tab_data['tab_id'] > $highest_tab_id ) {
|
154 |
-
$highest_tab_id = $tab_data['tab_id'];
|
155 |
-
}
|
156 |
-
}
|
157 |
-
}
|
158 |
-
|
159 |
-
// Add 1 to the max ID
|
160 |
-
$new_tab_id = (int) $highest_tab_id + 1;
|
161 |
-
|
162 |
-
$new_tab = array(
|
163 |
-
'tab_title' => $tab_title,
|
164 |
-
'tab_name' => $tab_name,
|
165 |
-
'tab_content' => $tab_content,
|
166 |
-
'tab_id' => $new_tab_id,
|
167 |
-
'taxonomies' => $taxonomies,
|
168 |
-
'tab_slug' => $tab_string_id,
|
169 |
-
'global_tab' => $global_tab,
|
170 |
-
);
|
171 |
-
|
172 |
-
$yikes_custom_tab_data[$new_tab_id] = $new_tab;
|
173 |
-
|
174 |
-
do_action( 'yikes-woo-handle-tab-save', $new_tab, 'new' );
|
175 |
-
|
176 |
-
update_option( 'yikes_woo_reusable_products_tabs', $yikes_custom_tab_data );
|
177 |
-
|
178 |
-
// Return redirect URL
|
179 |
-
$return_redirect_url = esc_url_raw( add_query_arg( array( 'page' => YIKES_Custom_Product_Tabs_Settings_Page, 'saved-tab-id' => $new_tab_id ), admin_url() ) );
|
180 |
-
|
181 |
-
// Send response
|
182 |
-
wp_send_json_success( array( 'tab_id' => $new_tab_id, 'redirect' => true, 'redirect_url' => $return_redirect_url ) );
|
183 |
-
|
184 |
-
} else {
|
185 |
-
|
186 |
-
// This is an existing tab, so just update it
|
187 |
-
$saved_tab = array(
|
188 |
-
'tab_title' => $tab_title,
|
189 |
-
'tab_name' => $tab_name,
|
190 |
-
'tab_content' => $tab_content,
|
191 |
-
'tab_id' => $tab_id,
|
192 |
-
'taxonomies' => $taxonomies,
|
193 |
-
'tab_slug' => $tab_string_id,
|
194 |
-
'global_tab' => $global_tab,
|
195 |
-
);
|
196 |
-
|
197 |
-
$yikes_custom_tab_data[$tab_id] = $saved_tab;
|
198 |
-
|
199 |
-
do_action( 'yikes-woo-handle-tab-save', $saved_tab, 'existing' );
|
200 |
-
|
201 |
-
update_option( 'yikes_woo_reusable_products_tabs', $yikes_custom_tab_data );
|
202 |
-
|
203 |
-
// Now apply this updated tab's data to custom product tabs that use it
|
204 |
-
|
205 |
-
// Get the array of applied product tabs
|
206 |
-
$reusable_tab_options_array = get_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
207 |
-
|
208 |
-
// Flag so we know we found a post and we should update it
|
209 |
-
$update_post_meta_flag = false;
|
210 |
-
|
211 |
-
// Flag so we know we have to update the yikes_woo_reusable_products_tabs_applied
|
212 |
-
$update_applied_products_array = false;
|
213 |
-
|
214 |
-
foreach( $reusable_tab_options_array as $post_id => $reusable_tab_data ) {
|
215 |
-
|
216 |
-
// Fetch the relevant postmeta field
|
217 |
-
$custom_tab_data = maybe_unserialize( get_post_meta( $post_id, 'yikes_woo_products_tabs', true ) );
|
218 |
-
|
219 |
-
// If we don't have custom tab data then continue
|
220 |
-
if ( empty( $custom_tab_data ) ) {
|
221 |
-
continue;
|
222 |
-
}
|
223 |
-
|
224 |
-
// Loop through $custom_tab_data and find the custom tab that was just updated
|
225 |
-
foreach( $custom_tab_data as $index => $tab ) {
|
226 |
-
if ( isset( $reusable_tab_data[ $tab_id ] ) && $tab['id'] === $reusable_tab_data[ $tab_id ]['tab_id'] ) {
|
227 |
-
$custom_tab_data[$index]['title'] = $tab_title;
|
228 |
-
$custom_tab_data[$index]['name'] = $tab_name;
|
229 |
-
$custom_tab_data[$index]['content'] = $tab_content;
|
230 |
-
$custom_tab_data[$index]['id'] = $tab_string_id;
|
231 |
-
|
232 |
-
// We may need to update the tab_string_id too
|
233 |
-
if ( $tab_string_id !== $tab['id'] ) {
|
234 |
-
$reusable_tab_options_array[$post_id][$tab_id]['tab_id'] = $tab_string_id;
|
235 |
-
$update_applied_products_array = true;
|
236 |
-
}
|
237 |
-
$update_post_meta_flag = true;
|
238 |
-
}
|
239 |
-
}
|
240 |
-
|
241 |
-
// If we updated a tab, save it
|
242 |
-
if ( $update_post_meta_flag === true ) {
|
243 |
-
update_post_meta( $post_id, 'yikes_woo_products_tabs', $custom_tab_data );
|
244 |
-
}
|
245 |
-
}
|
246 |
-
|
247 |
-
// If we updated the tab_string_id in the yikes_woo_reusable_products_tabs_applied array, save it
|
248 |
-
if ( $update_applied_products_array === true ) {
|
249 |
-
update_option( 'yikes_woo_reusable_products_tabs_applied', $reusable_tab_options_array);
|
250 |
-
}
|
251 |
-
}
|
252 |
-
}
|
253 |
-
|
254 |
-
wp_send_json_success( array( 'redirect' => false ) );
|
255 |
-
}
|
256 |
-
|
257 |
-
/**
|
258 |
-
* [AJAX] Fetch a single reusable
|
259 |
-
*
|
260 |
-
* @since 1.5
|
261 |
-
*
|
262 |
-
* @return object success w/ tab data || failure w/ message
|
263 |
-
*/
|
264 |
-
public function yikes_woo_fetch_reusable_tab() {
|
265 |
-
|
266 |
-
// Verify the nonce
|
267 |
-
if ( ! check_ajax_referer( 'yikes_woo_fetch_reusable_tab_nonce', 'security_nonce', false ) ) {
|
268 |
-
wp_send_json_error();
|
269 |
-
}
|
270 |
-
|
271 |
-
$tab_id = isset( $_POST['tab_id'] ) ? filter_var( $_POST['tab_id'], FILTER_SANITIZE_NUMBER_INT ) : '';
|
272 |
-
|
273 |
-
// Get the array of saved tabs
|
274 |
-
$saved_tabs = get_option( 'yikes_woo_reusable_products_tabs' );
|
275 |
-
|
276 |
-
$tab = isset( $saved_tabs[$tab_id] ) ? $saved_tabs[$tab_id] : false;
|
277 |
-
|
278 |
-
if ( $tab !== false ) {
|
279 |
-
|
280 |
-
$tab['tab_content'] = stripslashes( $tab['tab_content'] );
|
281 |
-
|
282 |
-
wp_send_json_success( $tab );
|
283 |
-
} else {
|
284 |
-
wp_send_json_success( array( 'message' => __( 'Could not find the tab. Please try again.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ) ) );
|
285 |
-
}
|
286 |
-
|
287 |
-
// If we get this far, send error
|
288 |
-
wp_send_json_error( array( 'message' => __( 'Uh oh. Something went wrong.', 'yikes-inc-easy-custom-woocommerce-product-tabs' ) ) );
|
289 |
-
}
|
290 |
-
|
291 |
-
/**
|
292 |
-
* [AJAX] Fetch all reusable tabs
|
293 |
-
*
|
294 |
-
* @since 1.5
|
295 |
-
*
|
296 |
-
* @return object success w/ saved_tabs || failure w/ message
|
297 |
-
*/
|
298 |
-
public function yikes_woo_fetch_reusable_tabs() {
|
299 |
-
|
300 |
-
// Verify the nonce
|
301 |
-
if ( ! check_ajax_referer( 'yikes_woo_fetch_reusable_tabs_nonce', 'security_nonce', false ) ) {
|
302 |
-
wp_send_json_error();
|
303 |
-
}
|
304 |
-
|
305 |
-
// Get the array of saved tabs
|
306 |
-
$saved_tabs = get_option( 'yikes_woo_reusable_products_tabs' );
|
307 |
-
|
308 |
-
$fetch_tab_content = isset( $_POST['fetch_tab_content'] ) ? filter_var( $_POST['fetch_tab_content'], FILTER_VALIDATE_BOOLEAN ) : false;
|
309 |
-
|
310 |
-
// We don't need to pass the content back, and it could be a LOT, so let's just remove it
|
311 |
-
if ( $fetch_tab_content === false && ! empty( $saved_tabs ) ) {
|
312 |
-
foreach( $saved_tabs as $key => $tab ) {
|
313 |
-
unset( $saved_tabs[$key]['tab_content'] );
|
314 |
-
}
|
315 |
-
}
|
316 |
-
|
317 |
-
if ( ! empty( $saved_tabs ) ) {
|
318 |
-
wp_send_json_success( json_encode( $saved_tabs ) );
|
319 |
-
} else {
|
320 |
-
wp_send_json_success( array( 'message' => 'No saved tabs were found.' ) );
|
321 |
-
}
|
322 |
-
|
323 |
-
// If we get this far, send error
|
324 |
-
wp_send_json_error( array( 'message' => 'Uh oh. Something went wrong.' ) );
|
325 |
-
}
|
326 |
-
|
327 |
-
/**
|
328 |
-
* [AJAX] Delete a reusable tab
|
329 |
-
*
|
330 |
-
* @since 1.5
|
331 |
-
*
|
332 |
-
* @param string $_POST['tab_id']
|
333 |
-
* @return object success w/ saved_tabs || failure w/ message
|
334 |
-
*/
|
335 |
-
public function yikes_woo_delete_reusable_tab_handler() {
|
336 |
-
|
337 |
-
// Verify the nonce
|
338 |
-
if ( ! check_ajax_referer( 'yikes_woo_delete_reusable_tab_nonce', 'security_nonce', false ) ) {
|
339 |
-
wp_send_json_error();
|
340 |
-
}
|
341 |
-
|
342 |
-
// Get our tab_id
|
343 |
-
if ( isset( $_POST['tab_id'] ) && ! empty( $_POST['tab_id'] ) ) {
|
344 |
-
|
345 |
-
$tab_ids = $_POST['tab_id'];
|
346 |
-
|
347 |
-
// if $tab_ids isn't an array, turn it into one
|
348 |
-
if ( ! is_array( $tab_ids ) ) {
|
349 |
-
$tab_ids = array( $tab_ids );
|
350 |
-
}
|
351 |
-
|
352 |
-
// Set this up before we use it
|
353 |
-
$return_vars = array();
|
354 |
-
|
355 |
-
foreach( $tab_ids as $tab_id ) {
|
356 |
-
|
357 |
-
// Delete the tab, store the return values in $return_vars
|
358 |
-
$return_vars = $this->yikes_woo_delete_reusable_tab( $tab_id );
|
359 |
-
|
360 |
-
// Make sure $return_vars is what we think it is, and check if our delete failed
|
361 |
-
if ( is_array( $return_vars ) && isset( $return_vars['success'] ) && $return_vars['success'] === false ) {
|
362 |
-
|
363 |
-
// If something failed, let's return
|
364 |
-
wp_send_json_error( $return_vars );
|
365 |
-
}
|
366 |
-
}
|
367 |
-
} else {
|
368 |
-
|
369 |
-
// Fail if we don't have a tab_id
|
370 |
-
wp_send_json_error( array( 'reason' => 'no tab id' ) );
|
371 |
-
}
|
372 |
-
|
373 |
-
// Make sure $return_vars is what we think it is, and check if our delete was successful
|
374 |
-
if ( is_array( $return_vars ) && isset( $return_vars['success'] ) && $return_vars['success'] === true ) {
|
375 |
-
|
376 |
-
// If nothing failed, let's return
|
377 |
-
wp_send_json_success( $return_vars );
|
378 |
-
}
|
379 |
-
|
380 |
-
// We shouldn't have gotten this far, but if we did let's return failure
|
381 |
-
wp_send_json_error();
|
382 |
-
}
|
383 |
-
|
384 |
-
/* End AJAX Functions */
|
385 |
-
|
386 |
-
/* AJAX Helper Functions */
|
387 |
-
|
388 |
-
/**
|
389 |
-
* Delete a saved tab from the options array and delete the tab from the product's tabs array
|
390 |
-
*
|
391 |
-
* @since 1.5
|
392 |
-
*
|
393 |
-
* @param int | $tab_id | unique identifier of a tab
|
394 |
-
* @return array | $response | array of data signifying success, message, reason, and other needed data
|
395 |
-
*/
|
396 |
-
protected function yikes_woo_delete_reusable_tab( $tab_id ) {
|
397 |
-
|
398 |
-
// The following code will remove the tab from our array of saved tabs
|
399 |
-
|
400 |
-
// Fetch all saved tabs
|
401 |
-
$saved_tabs = get_option( 'yikes_woo_reusable_products_tabs' );
|
402 |
-
|
403 |
-
// Check some stuff, then remove the tab from our array of saved tabs
|
404 |
-
if ( ! empty( $saved_tabs ) ) {
|
405 |
-
if ( isset( $saved_tabs[$tab_id] ) ) {
|
406 |
-
unset( $saved_tabs[$tab_id] );
|
407 |
-
update_option( 'yikes_woo_reusable_products_tabs', $saved_tabs );
|
408 |
-
} else {
|
409 |
-
$response = array(
|
410 |
-
'success' => false,
|
411 |
-
'tab_id' => $tab_id,
|
412 |
-
'message' => 'No saved tab with id ' . $tab_id . ' found!',
|
413 |
-
'reason' => 'no saved tab found'
|
414 |
-
);
|
415 |
-
return $response;
|
416 |
-
}
|
417 |
-
} else {
|
418 |
-
$response = array(
|
419 |
-
'success' => false,
|
420 |
-
'tab_id' => $tab_id,
|
421 |
-
'message' => 'No saved tabs found!',
|
422 |
-
'reason' => 'no saved tabs found'
|
423 |
-
);
|
424 |
-
return $response;
|
425 |
-
}
|
426 |
-
|
427 |
-
// The following code will remove the tab from our array of applied tabs and postmeta
|
428 |
-
|
429 |
-
// Fetch all applied tabs
|
430 |
-
$applied_tabs = get_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
431 |
-
|
432 |
-
// Set a flag so we know if we need to update the database
|
433 |
-
$unset_applied_tabs_flag = false;
|
434 |
-
|
435 |
-
if ( ! empty( $applied_tabs ) ) {
|
436 |
-
|
437 |
-
// Run through all the applied tabs and remove the ones with this ID
|
438 |
-
foreach( $applied_tabs as $post_id => $applied_tabs_array ) {
|
439 |
-
|
440 |
-
// If this ID is set, unset the array
|
441 |
-
if ( isset( $applied_tabs_array[$tab_id] ) ) {
|
442 |
-
|
443 |
-
// Now we also need to remove this entry from our postmeta
|
444 |
-
$post_tabs = maybe_unserialize( get_post_meta( $post_id, 'yikes_woo_products_tabs', true ) );
|
445 |
-
|
446 |
-
// Make sure it exists
|
447 |
-
if ( ! empty( $post_tabs ) ) {
|
448 |
-
foreach ( $post_tabs as $index => $post_tab ) {
|
449 |
-
if ( $applied_tabs[$post_id][$tab_id]['tab_id'] === $post_tab['id'] ) {
|
450 |
-
unset( $post_tabs[$index] );
|
451 |
-
update_post_meta( $post_id, 'yikes_woo_products_tabs', $post_tabs );
|
452 |
-
}
|
453 |
-
}
|
454 |
-
}
|
455 |
-
|
456 |
-
// Unset the array of our applied saved tabs
|
457 |
-
unset( $applied_tabs[ $post_id ][ $tab_id ] );
|
458 |
-
|
459 |
-
// If that was the only saved tab for this product, unset the product's array key
|
460 |
-
if ( empty( $applied_tabs[ $post_id ] ) ) {
|
461 |
-
unset( $applied_tabs[ $post_id ] );
|
462 |
-
}
|
463 |
-
$unset_applied_tabs_flag = true;
|
464 |
-
}
|
465 |
-
}
|
466 |
-
|
467 |
-
// If we unset an applied tab, update the database
|
468 |
-
if ( $unset_applied_tabs_flag === true ) {
|
469 |
-
update_option( 'yikes_woo_reusable_products_tabs_applied', $applied_tabs );
|
470 |
-
}
|
471 |
-
}
|
472 |
-
|
473 |
-
// If we're on the single tab edit screen, we want to redirect back to tab list so let's return a var
|
474 |
-
$return_redirect_url = esc_url_raw( add_query_arg( array( 'page' => YIKES_Custom_Product_Tabs_Settings_Page, 'delete-success' => true ), admin_url() ) );
|
475 |
-
|
476 |
-
$response = array(
|
477 |
-
'success' => true,
|
478 |
-
'tab_id' => $tab_id,
|
479 |
-
'message' => 'Tab successfully deleted!',
|
480 |
-
'reason' => 'tab successfully deleted',
|
481 |
-
'redirect_url' => $return_redirect_url
|
482 |
-
);
|
483 |
-
|
484 |
-
return $response;
|
485 |
-
}
|
486 |
-
|
487 |
-
/* End AJAX Helper Functions */
|
488 |
-
|
489 |
-
|
490 |
-
/* Plugin Settings Page */
|
491 |
-
|
492 |
-
/**
|
493 |
-
* Register our settings page
|
494 |
-
*
|
495 |
-
* @since 1.5
|
496 |
-
*
|
497 |
-
*/
|
498 |
-
public function yikes_woo_register_settings_page() {
|
499 |
-
|
500 |
-
// Add our custom settings page
|
501 |
-
add_menu_page(
|
502 |
-
apply_filters( 'yikes-woo-settings-menu-title', __( 'Custom Product Tabs', 'yikes-inc-easy-custom-woocommerce-product-tabs' ) ), // Tab title name (HTML title)
|
503 |
-
apply_filters( 'yikes-woo-settings-menu-title', __( 'Custom Product Tabs', 'yikes-inc-easy-custom-woocommerce-product-tabs' ) ), // Menu page name
|
504 |
-
apply_filters( 'yikes-woo-settings-menu-capability', 'publish_products' ), // Capability required
|
505 |
-
YIKES_Custom_Product_Tabs_Settings_Page, // Page slug (?page=slug-name)
|
506 |
-
array( $this, 'generate_yikes_settings_page' ), // Function to generate page
|
507 |
-
'dashicons-exerpt-view', // Icon
|
508 |
-
apply_filters( 'yikes-woo-settings-menu-priority', 100 ) // Position
|
509 |
-
);
|
510 |
-
}
|
511 |
-
|
512 |
-
/**
|
513 |
-
* Include our settings page
|
514 |
-
*
|
515 |
-
* @since 1.5
|
516 |
-
*
|
517 |
-
*/
|
518 |
-
public function generate_yikes_settings_page() {
|
519 |
-
|
520 |
-
// Get our saved tabs array
|
521 |
-
$yikes_custom_tab_data = get_option( 'yikes_woo_reusable_products_tabs', array() );
|
522 |
-
|
523 |
-
// New tab URL - used to supply the 'Add Tab' href
|
524 |
-
$new_tab_url = esc_url( add_query_arg( array( 'saved-tab-id' => 'new' ), '?page=' . YIKES_Custom_Product_Tabs_Settings_Page ), admin_url() );
|
525 |
-
|
526 |
-
// If saved_tab_id is set, we should show the single saved tab // add new tab page
|
527 |
-
if ( isset( $_GET['saved-tab-id'] ) && ! empty( $_GET['saved-tab-id'] ) ) {
|
528 |
-
|
529 |
-
// Are we trying to add a new tab?
|
530 |
-
$new_tab = ( $_GET['saved-tab-id'] === 'new' ) ? true : false;
|
531 |
-
|
532 |
-
// Sanitize saved_tab_id
|
533 |
-
$saved_tab_id = filter_var( $_GET['saved-tab-id'], FILTER_SANITIZE_NUMBER_INT );
|
534 |
-
|
535 |
-
// Get the tab
|
536 |
-
$tab = isset( $yikes_custom_tab_data[$saved_tab_id] ) ? $yikes_custom_tab_data[$saved_tab_id] : array();
|
537 |
-
|
538 |
-
// Redirect URL
|
539 |
-
$redirect = esc_url_raw( add_query_arg( array( 'page' => YIKES_Custom_Product_Tabs_Settings_Page ), admin_url() ) );
|
540 |
-
|
541 |
-
require_once( YIKES_Custom_Product_Tabs_Path . 'admin/page.yikes-woo-saved-tabs-single.php' );
|
542 |
-
|
543 |
-
} else {
|
544 |
-
$delete_message_display = 'display: none;';
|
545 |
-
|
546 |
-
// Check if our $_GET variable 'delete-success' is set so we can display a nice success message
|
547 |
-
if ( isset( $_GET['delete-success'] ) && $_GET['delete-success'] === '1' ) {
|
548 |
-
$delete_message_display = '';
|
549 |
-
}
|
550 |
-
|
551 |
-
// Show tab table list
|
552 |
-
require_once( YIKES_Custom_Product_Tabs_Path . 'admin/page.yikes-woo-saved-tabs.php' );
|
553 |
-
}
|
554 |
-
}
|
555 |
-
|
556 |
-
/* End Plugin Settings Page */
|
557 |
-
|
558 |
-
/* Misc. */
|
559 |
-
|
560 |
-
/**
|
561 |
-
* When a WooCommere product is duplicated, check for and duplicate the saved tabs.
|
562 |
-
*
|
563 |
-
* @param object | $duplicated_product | The new, duplicated product
|
564 |
-
* @param object | $original_product | The original product
|
565 |
-
*/
|
566 |
-
public function yikes_woo_dupe_saved_tabs_on_product_dupe( $duplicate_product, $original_product ) {
|
567 |
-
|
568 |
-
// First, let's grab our applied saved tab options array
|
569 |
-
$saved_tabs_array = get_option( 'yikes_woo_reusable_products_tabs_applied' );
|
570 |
-
|
571 |
-
// Grab the old post's ID
|
572 |
-
$old_post_id = method_exists( $original_product, 'get_id' ) === true ? $original_product->get_id() : $original_product->ID;
|
573 |
-
|
574 |
-
// (1) Make sure we have a non-empty array of saved tabs,
|
575 |
-
// (2) Makre sure we have the ID of the old post, and then
|
576 |
-
// (3) Check for the old post's saved tabs. (If we don't find any, do nothing)
|
577 |
-
if ( ! empty( $saved_tabs_array ) && is_array( $saved_tabs_array ) && ! empty( $old_post_id ) && isset( $saved_tabs_array[$old_post_id] ) ) {
|
578 |
-
|
579 |
-
// Grab the new post's ID
|
580 |
-
$new_post_id = method_exists( $duplicate_product, 'get_id' ) === true ? $duplicate_product->get_id() : $duplicate_product->ID;
|
581 |
-
|
582 |
-
// Loop through the $saved_tabs_array and update the post_id item
|
583 |
-
$new_products_saved_tabs = $saved_tabs_array[$old_post_id];
|
584 |
-
foreach ( $new_products_saved_tabs as $saved_tab_id => $saved_tab ) {
|
585 |
-
$new_products_saved_tabs[$saved_tab_id]['post_id'] = $new_post_id;
|
586 |
-
}
|
587 |
-
|
588 |
-
// Add the old post's saved tabs, with the new post's ID as the key
|
589 |
-
$saved_tabs_array[$new_post_id] = $new_products_saved_tabs;
|
590 |
-
|
591 |
-
// Update the saved tab's option
|
592 |
-
update_option( 'yikes_woo_reusable_products_tabs_applied', $saved_tabs_array );
|
593 |
-
}
|
594 |
-
}
|
595 |
-
|
596 |
-
/**
|
597 |
-
* When a WooCommerce product is deleted, delete any saved tabs from the saved tabs option
|
598 |
-
*
|
599 |
-
* @param int | $post_id
|
600 |
-
*/
|
601 |
-
public function delete_saved_tabs_on_product_delete( $post_id ) {
|
602 |
-
|
603 |
-
$post = get_post( $post_id );
|
604 |
-
|
605 |
-
if ( $post->post_type !== 'product' ) {
|
606 |
-
return;
|
607 |
-
}
|
608 |
-
|
609 |
-
// Get our saved tabs option
|
610 |
-
$saved_tabs = get_option( 'yikes_woo_reusable_products_tabs_applied' );
|
611 |
-
|
612 |
-
if ( empty( $saved_tabs ) ) {
|
613 |
-
return;
|
614 |
-
}
|
615 |
-
|
616 |
-
if ( ! empty( $saved_tabs[ $post_id ] ) ) {
|
617 |
-
unset( $saved_tabs[ $post_id ] );
|
618 |
-
update_option( 'yikes_woo_reusable_products_tabs_applied', $saved_tabs );
|
619 |
-
}
|
620 |
-
}
|
621 |
-
|
622 |
-
/* End Misc. */
|
623 |
-
|
624 |
-
}
|
625 |
-
|
626 |
-
new YIKES_Custom_Product_Tabs_Saved_Tabs();
|
627 |
}
|
1 |
+
<?php
|
2 |
+
|
3 |
+
if ( ! class_exists( 'YIKES_Custom_Product_Tabs_Saved_Tabs' ) ) {
|
4 |
+
|
5 |
+
class YIKES_Custom_Product_Tabs_Saved_Tabs {
|
6 |
+
|
7 |
+
public function __construct() {
|
8 |
+
|
9 |
+
// Add our custom settings page
|
10 |
+
add_action( 'admin_menu', array( $this, 'yikes_woo_register_settings_page' ), 10 );
|
11 |
+
|
12 |
+
// Define our options and filters
|
13 |
+
add_action( 'admin_init', array( $this, 'init' ) );
|
14 |
+
}
|
15 |
+
|
16 |
+
public function init() {
|
17 |
+
|
18 |
+
// Add our custom options for saved tabs
|
19 |
+
add_option( 'yikes_woo_reusable_products_tabs', array() );
|
20 |
+
add_option( 'yikes_woo_reusable_products_tabs_applied', array() );
|
21 |
+
|
22 |
+
// Enqueue our JS / CSS files
|
23 |
+
add_action( 'admin_enqueue_scripts' , array( $this , 'enqueue_scripts_and_styles' ), 10, 1 );
|
24 |
+
|
25 |
+
// Define our AJAX calls
|
26 |
+
add_action( 'wp_ajax_yikes_woo_save_tab_as_reusable', array( $this, 'yikes_woo_save_tab_as_reusable' ) );
|
27 |
+
add_action( 'wp_ajax_yikes_woo_fetch_reusable_tabs', array( $this, 'yikes_woo_fetch_reusable_tabs' ) );
|
28 |
+
add_action( 'wp_ajax_yikes_woo_fetch_reusable_tab', array( $this, 'yikes_woo_fetch_reusable_tab' ) );
|
29 |
+
add_action( 'wp_ajax_yikes_woo_delete_reusable_tab_handler', array( $this, 'yikes_woo_delete_reusable_tab_handler' ) );
|
30 |
+
|
31 |
+
// Duplicate any saved tabs when a product is duplicated
|
32 |
+
add_filter( 'woocommerce_product_duplicate', array( $this, 'yikes_woo_dupe_saved_tabs_on_product_dupe' ), 11, 2 );
|
33 |
+
|
34 |
+
// Delete any saved tabs when a product is deleted
|
35 |
+
add_action( 'delete_post', array( $this, 'delete_saved_tabs_on_product_delete' ), 10, 1 );
|
36 |
+
}
|
37 |
+
|
38 |
+
/**
|
39 |
+
* Enqueue our scripts and styles
|
40 |
+
*
|
41 |
+
* @param string | $hook | The current page
|
42 |
+
*/
|
43 |
+
public function enqueue_scripts_and_styles( $hook ) {
|
44 |
+
|
45 |
+
if ( $hook === 'toplevel_page_' . YIKES_Custom_Product_Tabs_Settings_Page ) {
|
46 |
+
|
47 |
+
// JavaScript
|