Compare commits
428 Commits
Author | SHA1 | Date | |
---|---|---|---|
8800799234 | |||
5d8d9567c7 | |||
5bddc79576 | |||
e2f23df829 | |||
43fbbca050 | |||
5109bc3922 | |||
65b4aeffc8 | |||
7361613bba | |||
a8f33d9a7e | |||
c497a72aab | |||
d0f55a1d1b | |||
3b92caf677 | |||
d3c64810a8 | |||
f85a169248 | |||
2dd08c6820 | |||
d7609f48d4 | |||
1d02c688a2 | |||
37c58c6aa4 | |||
4abd034880 | |||
e8c7584b9b | |||
be3eb0a7ff | |||
eee01ee3f1 | |||
56ad9a8976 | |||
20d0ed1aac | |||
f42b61a49e | |||
5e152e920e | |||
0d26b62416 | |||
8e60b2b317 | |||
cae46d9acd | |||
bfad5509c1 | |||
3ae7b436de | |||
30b2eda29f | |||
a519eff231 | |||
fe2ab08a49 | |||
9b914a471b | |||
74f008517b | |||
ba45ee7e35 | |||
a5543d9d78 | |||
3c2ef4b8ee | |||
07417391be | |||
e00d43e506 | |||
c4f285afca | |||
c70097085e | |||
ca6bde8a64 | |||
a1ba783264 | |||
e77d00b179 | |||
b683ae0bc1 | |||
f658fd7776 | |||
1a08155f54 | |||
a3b3e1f8df | |||
87aca7c667 | |||
a7a8cd2be4 | |||
819d4dc17a | |||
6e94db24a2 | |||
5bf532a750 | |||
c63b7d9b91 | |||
a8052c118a | |||
1ad0dce425 | |||
2228f60e2a | |||
99a007fb70 | |||
5e5caab4da | |||
caa0623112 | |||
a05f9bf97b | |||
7202d9dca1 | |||
655dac458a | |||
0e487d2c54 | |||
d2d1657cb2 | |||
3bf800b51d | |||
9910072e72 | |||
8695d147e8 | |||
042d47b027 | |||
a27823ebc5 | |||
1aee4489da | |||
e4a37c3c2d | |||
ea2a91d15e | |||
72193fefae | |||
7e60155bdc | |||
7eae7dde11 | |||
d70c6ce453 | |||
3337637a8b | |||
69ca597f24 | |||
6f20a402f6 | |||
19c7efc9ef | |||
6c25fab6d6 | |||
a45a7a7616 | |||
3053e21910 | |||
699017532e | |||
7465398d17 | |||
ef410fb877 | |||
f154687c53 | |||
b773263fa4 | |||
9870f62984 | |||
1f6430c278 | |||
4018ca4a65 | |||
1342389602 | |||
368f7004c0 | |||
d33cc9d2b8 | |||
e9be62c2d3 | |||
f2733624e4 | |||
46121d74a8 | |||
cb430673f8 | |||
8852f6a3f4 | |||
56e55c072a | |||
77e60d708a | |||
27fbc25bf9 | |||
a91929682f | |||
d45c510ab3 | |||
57366e972a | |||
cbd1ae929e | |||
884f476598 | |||
55296d52ec | |||
8fb4d2e78f | |||
840473aae5 | |||
5d5b61b76f | |||
0e2a67c203 | |||
aaed5add52 | |||
f616ef4d6c | |||
083a6fd3a3 | |||
9a1ec60750 | |||
bd67f5fd36 | |||
ed2a2a6fa8 | |||
6a28fdcac2 | |||
fda1828637 | |||
ebcc094b4d | |||
51cde55217 | |||
23dff7403d | |||
de164f918c | |||
84840c5261 | |||
16b9e0d467 | |||
3c75e7b0bc | |||
c41d5894d0 | |||
1f76f0d98f | |||
e859c090c8 | |||
42528ab309 | |||
d761867a7d | |||
6996615999 | |||
3450a6fc97 | |||
554dbb8dda | |||
d13aa67a07 | |||
1f9c956637 | |||
59d09866a1 | |||
f8ade27a6c | |||
313bcddba1 | |||
fd64702eaa | |||
e2884ac625 | |||
9ce9cb929f | |||
52d33d7fe8 | |||
2ee33b2fc2 | |||
b107be3241 | |||
76148d0a85 | |||
61a7f99e42 | |||
62e3ca8a80 | |||
d431efb288 | |||
adf6485b7d | |||
170fd7f051 | |||
e7ddfc3d29 | |||
b08b53e9c0 | |||
570529a8d8 | |||
5505ffc783 | |||
6e5fc6ad6b | |||
e731b261ab | |||
955f24e71a | |||
89ebc6051a | |||
79fff7b65d | |||
7864e08900 | |||
878cdf46e6 | |||
131d341744 | |||
513062b15d | |||
4926267e36 | |||
aa4d78b1c9 | |||
8d7289e8ba | |||
eb768ff1ee | |||
8afe7f5d97 | |||
97fb5cf66f | |||
8ea4a219e2 | |||
0e08e58288 | |||
dc52ba0d93 | |||
dc569672a9 | |||
159e946093 | |||
3d2a433df1 | |||
fe0476e1c0 | |||
ea552508b4 | |||
dee2ff810c | |||
63ed835d64 | |||
fbf58f23fc | |||
b6f62bd9bc | |||
88ef454844 | |||
3572df6c0c | |||
714e6e013f | |||
91568cbeb6 | |||
393c89b21f | |||
0b491b7943 | |||
e5d7f66561 | |||
b7a7f40cde | |||
a267c7524c | |||
20b59d11a7 | |||
94c7e2a5c0 | |||
d603d99a04 | |||
e7ffe4d694 | |||
018d7bce77 | |||
64c40d5a1c | |||
7e49328d5e | |||
b50b636371 | |||
ec3bb5b95c | |||
6b2503fb36 | |||
e71d47f983 | |||
085d4f566a | |||
29b249de6e | |||
883ae5b0e4 | |||
d78990cda3 | |||
e5b5a8df37 | |||
2ea2db66ec | |||
7b76ddefd5 | |||
6c56ac8509 | |||
dc074bcb14 | |||
0193644b18 | |||
66de11ecd4 | |||
1238b1711d | |||
0061a9daf9 | |||
52a55d3bd1 | |||
7d686eb1d1 | |||
962188bdb8 | |||
72c3f763ec | |||
44c5d8490f | |||
fb85623b86 | |||
d7bf6addf1 | |||
adea1e9be1 | |||
4f77ca31a3 | |||
087f2ebcdd | |||
3d2a63f319 | |||
54dd3b621a | |||
7fea134109 | |||
fcf4bd12d9 | |||
6694555592 | |||
e6eb3d691e | |||
00f2d418cc | |||
c63f218edd | |||
fae849bbfc | |||
2a253ccb8d | |||
ff55e55ad2 | |||
d798ec446d | |||
56b4038073 | |||
076a55f1fb | |||
10eca98dc3 | |||
37aec3ee4f | |||
dc7c629e3b | |||
e4f16eda49 | |||
bf15bda84f | |||
8472a837e8 | |||
fc326131ae | |||
a19753205f | |||
ee404e3b84 | |||
f1918ac953 | |||
d399ddf6b6 | |||
3f06448f37 | |||
83d84e67d6 | |||
46c42c1bb4 | |||
944bf67190 | |||
7cac061a73 | |||
17764b708f | |||
2e0f4dfb19 | |||
7f5bc8681c | |||
bfcb85f744 | |||
cb9aaf120e | |||
97a9465db3 | |||
8dfaf9ba32 | |||
89d0da93d3 | |||
c9cbfb4317 | |||
a8ccfec5c6 | |||
d8609c9e84 | |||
5461c975d4 | |||
11298bc101 | |||
c42cf2f622 | |||
c9f1d38baa | |||
3d78d6bbe9 | |||
2b4288f301 | |||
09a2dd231a | |||
3fd4ef9985 | |||
05979965ba | |||
e625a7602a | |||
a0c41ad7ab | |||
7163747eb9 | |||
c30e2b6cf3 | |||
e9eae92ba9 | |||
0fd6fa8879 | |||
52ca6eac18 | |||
28776b8558 | |||
588ad3eab7 | |||
d791538086 | |||
62173e7996 | |||
0acdcd1ca7 | |||
f39a2c8dda | |||
b648852ef5 | |||
6e45892118 | |||
cd145c51f7 | |||
2c12d9ee2d | |||
5fe28623f1 | |||
3086b3cfc2 | |||
5fd29872ff | |||
732c8a314f | |||
23c650bfa6 | |||
f5ced785e0 | |||
4dc9004303 | |||
893c6bd72b | |||
2ac32484e1 | |||
b31e8ce5f2 | |||
4270e4c315 | |||
4b13395b0c | |||
2e67029ef5 | |||
257517b9a9 | |||
88ee64e15d | |||
c2030e9a86 | |||
16111a99fb | |||
543b3e5a91 | |||
e33b60065e | |||
3bcfadd2ab | |||
4729583d8d | |||
aa3f457595 | |||
3ad490f840 | |||
eb27ed65ae | |||
d543f62c5b | |||
4e6f7a05de | |||
5d467115ad | |||
6858b266fe | |||
852b1a4c08 | |||
b2324db7b4 | |||
e8c85e2a54 | |||
a4ac74c84a | |||
4e378484ea | |||
c55be70b2c | |||
70898790f5 | |||
bfdb535f5b | |||
996e6b16e7 | |||
0217e21753 | |||
f6f79d42e1 | |||
4bbd26b098 | |||
028179af37 | |||
87283bf838 | |||
c680badaa2 | |||
df4a936e43 | |||
e27946ebcc | |||
13e64c012f | |||
f69302be48 | |||
16edfc16ea | |||
229a9c8102 | |||
490091a7e2 | |||
5f58e5ca82 | |||
16beda530a | |||
f1b373924f | |||
6a73c463cb | |||
0271675cd0 | |||
b7555aa640 | |||
fa9ef6e5bd | |||
1c97b004ca | |||
f0ab42adf1 | |||
165d8358d4 | |||
6bd6e74bcb | |||
b23df9e0a4 | |||
7b12affb77 | |||
8c8c01aa75 | |||
0150e699a2 | |||
e6943e2638 | |||
6f80dcb1de | |||
60ed294302 | |||
e8017b58f5 | |||
c79bf7d337 | |||
ac268c1ec9 | |||
1ef131fa2d | |||
1873007550 | |||
fa2ccb51c9 | |||
8f87d654af | |||
dee6e9fbad | |||
ef90264316 | |||
70bf4be723 | |||
07ef727654 | |||
a346e5be29 | |||
5ce1eadde7 | |||
8a4d5395b1 | |||
b5feed0f46 | |||
11f9579101 | |||
c6000c959a | |||
19e67ea2b0 | |||
0f6619e25d | |||
daf747d3be | |||
7393b1f2cf | |||
efe861a9ba | |||
2c358ab179 | |||
ca157fc91d | |||
1fbe5d7bc6 | |||
71c031ccf9 | |||
6449b7ccca | |||
6a956472fe | |||
d6af88d667 | |||
b9184a202f | |||
f898746967 | |||
68165b7b78 | |||
bb8591a67b | |||
bda71ae78e | |||
abd4f6cac2 | |||
87e6cc2a4f | |||
dde598eb64 | |||
0c4407f43a | |||
b6c864e7a1 | |||
3d9dc6465d | |||
9a6fec094a | |||
61af224d7d | |||
9b41641e97 | |||
4e2e9f6f8f | |||
c29dc8b4c7 | |||
98a3c6b156 | |||
69c540288b | |||
651c9f5692 | |||
9ad3778cf7 | |||
c90e0e9f64 | |||
cb1730c4e2 | |||
3dd8a973fd | |||
c3ea088fca | |||
a11d6d7868 | |||
a596add838 | |||
7e7103ddab | |||
0064970ed7 | |||
9d93f3ea95 | |||
ff2a3cd19e | |||
8419d95ea1 | |||
4ad317ac7b | |||
7cccebbf2c | |||
e4f76ee9eb | |||
26241afb86 |
@ -1,6 +1,4 @@
|
|||||||
Listen 8080
|
<VirtualHost *:80>
|
||||||
|
|
||||||
<VirtualHost *:8080>
|
|
||||||
UseCanonicalName Off
|
UseCanonicalName Off
|
||||||
ServerName mailpoet.loc
|
ServerName mailpoet.loc
|
||||||
DocumentRoot /home/circleci/mailpoet/wordpress
|
DocumentRoot /home/circleci/mailpoet/wordpress
|
||||||
@ -8,6 +6,9 @@ Listen 8080
|
|||||||
LogLevel notice
|
LogLevel notice
|
||||||
|
|
||||||
<Directory /home/circleci/mailpoet/wordpress>
|
<Directory /home/circleci/mailpoet/wordpress>
|
||||||
|
Options Indexes FollowSymLinks
|
||||||
|
AllowOverride All
|
||||||
|
RewriteEngine On
|
||||||
Require all granted
|
Require all granted
|
||||||
</Directory>
|
</Directory>
|
||||||
</VirtualHost>
|
</VirtualHost>
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
version: 2
|
version: 2
|
||||||
jobs:
|
jobs:
|
||||||
qa_js_php5:
|
qa_js_security_php5:
|
||||||
working_directory: /home/circleci/mailpoet
|
working_directory: /home/circleci/mailpoet
|
||||||
docker:
|
docker:
|
||||||
- image: circleci/php:5.6.30-apache-browsers
|
- image: circleci/php:5.6.30-apache-browsers
|
||||||
@ -38,6 +38,10 @@ jobs:
|
|||||||
command: |
|
command: |
|
||||||
mkdir test-results/mocha
|
mkdir test-results/mocha
|
||||||
./do t:j test-results/mocha/junit.xml
|
./do t:j test-results/mocha/junit.xml
|
||||||
|
- run:
|
||||||
|
name: "Composer security check"
|
||||||
|
command: |
|
||||||
|
./do s:composer
|
||||||
- run:
|
- run:
|
||||||
name: "PHP Unit tests"
|
name: "PHP Unit tests"
|
||||||
command: |
|
command: |
|
||||||
@ -81,6 +85,7 @@ jobs:
|
|||||||
curl -sS https://getcomposer.org/installer | php
|
curl -sS https://getcomposer.org/installer | php
|
||||||
php composer.phar install
|
php composer.phar install
|
||||||
./do install
|
./do install
|
||||||
|
./do compile:all --env production
|
||||||
- save_cache:
|
- save_cache:
|
||||||
key: composer-{{ checksum "composer.json" }}-{{ checksum "composer.lock" }}
|
key: composer-{{ checksum "composer.json" }}-{{ checksum "composer.lock" }}
|
||||||
paths:
|
paths:
|
||||||
@ -94,9 +99,52 @@ jobs:
|
|||||||
command: |
|
command: |
|
||||||
docker-compose run codeception --steps --debug -vvv --html --xml
|
docker-compose run codeception --steps --debug -vvv --html --xml
|
||||||
- store_artifacts:
|
- store_artifacts:
|
||||||
path: ~/mailpoet/tests/acceptance-tests/_output
|
path: tests/_output
|
||||||
- store_test_results:
|
- store_test_results:
|
||||||
path: ~/mailpoet/tests/acceptance-tests/_output
|
path: tests/_output
|
||||||
|
acceptance_tests_multisite:
|
||||||
|
working_directory: /home/circleci/mailpoet
|
||||||
|
machine: true
|
||||||
|
steps:
|
||||||
|
- checkout
|
||||||
|
- run:
|
||||||
|
name: "Set up virtual host"
|
||||||
|
command: echo 127.0.0.1 mailpoet.loc | sudo tee -a /etc/hosts
|
||||||
|
- restore_cache:
|
||||||
|
key: composer-{{ checksum "composer.json" }}-{{ checksum "composer.lock" }}
|
||||||
|
- restore_cache:
|
||||||
|
key: npm-{{ checksum "package.json" }}
|
||||||
|
- run:
|
||||||
|
name: "Set up test environment"
|
||||||
|
command: |
|
||||||
|
sudo apt-get update
|
||||||
|
sudo apt-get install circleci-php-5.6.23
|
||||||
|
sudo rm /usr/bin/php
|
||||||
|
sudo ln -s /opt/circleci/php/5.6.23/bin/php /usr/bin/php
|
||||||
|
# Install NodeJS+NPM
|
||||||
|
curl -sL https://deb.nodesource.com/setup_6.x | sudo -E bash -
|
||||||
|
sudo apt-get install nodejs build-essential
|
||||||
|
# install plugin dependencies
|
||||||
|
curl -sS https://getcomposer.org/installer | php
|
||||||
|
php composer.phar install
|
||||||
|
./do install
|
||||||
|
./do compile:all --env production
|
||||||
|
- save_cache:
|
||||||
|
key: composer-{{ checksum "composer.json" }}-{{ checksum "composer.lock" }}
|
||||||
|
paths:
|
||||||
|
- vendor
|
||||||
|
- save_cache:
|
||||||
|
key: npm-{{ checksum "package.json" }}
|
||||||
|
paths:
|
||||||
|
- node_modules
|
||||||
|
- run:
|
||||||
|
name: Run acceptance tests
|
||||||
|
command: |
|
||||||
|
docker-compose run -e MULTISITE=1 codeception --steps --debug -vvv --html --xml
|
||||||
|
- store_artifacts:
|
||||||
|
path: tests/_output
|
||||||
|
- store_test_results:
|
||||||
|
path: tests/_output
|
||||||
php7:
|
php7:
|
||||||
working_directory: /home/circleci/mailpoet
|
working_directory: /home/circleci/mailpoet
|
||||||
docker:
|
docker:
|
||||||
@ -119,7 +167,38 @@ jobs:
|
|||||||
- run:
|
- run:
|
||||||
name: "PHP Unit tests"
|
name: "PHP Unit tests"
|
||||||
command: |
|
command: |
|
||||||
WP_TEST_PATH="/home/circleci/mailpoet/wordpress" ./do t:u --xml
|
./do t:u --xml
|
||||||
|
- store_test_results:
|
||||||
|
path: tests/_output
|
||||||
|
- store_artifacts:
|
||||||
|
path: tests/_output
|
||||||
|
destination: codeception
|
||||||
|
- store_artifacts:
|
||||||
|
path: /tmp/fake-mailer/
|
||||||
|
destination: fake-mailer
|
||||||
|
php7_multisite:
|
||||||
|
working_directory: /home/circleci/mailpoet
|
||||||
|
docker:
|
||||||
|
- image: circleci/php:7.1-apache-browsers
|
||||||
|
- image: circleci/mysql:5.7
|
||||||
|
environment:
|
||||||
|
TZ: /usr/share/zoneinfo/Etc/UTC
|
||||||
|
steps:
|
||||||
|
- checkout
|
||||||
|
- run:
|
||||||
|
name: "Set up virtual host"
|
||||||
|
command: echo 127.0.0.1 mailpoet.loc | sudo tee -a /etc/hosts
|
||||||
|
- restore_cache:
|
||||||
|
key: composer-{{ checksum "composer.json" }}-{{ checksum "composer.lock" }}
|
||||||
|
- restore_cache:
|
||||||
|
key: npm-{{ checksum "package.json" }}
|
||||||
|
- run:
|
||||||
|
name: "Set up test environment"
|
||||||
|
command: source ./.circleci/setup.bash && setup php7_multisite
|
||||||
|
- run:
|
||||||
|
name: "PHP Unit tests"
|
||||||
|
command: |
|
||||||
|
./do t:multisite-unit --xml
|
||||||
- store_test_results:
|
- store_test_results:
|
||||||
path: tests/_output
|
path: tests/_output
|
||||||
- store_artifacts:
|
- store_artifacts:
|
||||||
@ -132,6 +211,8 @@ workflows:
|
|||||||
version: 2
|
version: 2
|
||||||
build_and_test:
|
build_and_test:
|
||||||
jobs:
|
jobs:
|
||||||
- qa_js_php5
|
- qa_js_security_php5
|
||||||
- php7
|
- php7
|
||||||
|
- php7_multisite
|
||||||
- acceptance_tests
|
- acceptance_tests
|
||||||
|
- acceptance_tests_multisite
|
@ -2,11 +2,16 @@
|
|||||||
|
|
||||||
function setup {
|
function setup {
|
||||||
local version=$1
|
local version=$1
|
||||||
|
local wp_cli_wordpress_path="--path=wordpress"
|
||||||
|
local wp_cli_allow_root="--allow-root"
|
||||||
|
|
||||||
# install PHP dependencies for WordPress
|
# install PHP dependencies for WordPress
|
||||||
if [[ $version == "php7" ]]; then
|
if [[ $version == "php7" ]] || [[ $version == "php7_multisite" ]]; then
|
||||||
echo "deb http://packages.dotdeb.org jessie all" | sudo tee -a /etc/apt/sources.list.d/dotdeb.list
|
echo "deb http://packages.dotdeb.org jessie all" | sudo tee -a /etc/apt/sources.list.d/dotdeb.list
|
||||||
echo "deb-src http://packages.dotdeb.org jessie all" | sudo tee -a /etc/apt/sources.list.d/dotdeb.list
|
echo "deb-src http://packages.dotdeb.org jessie all" | sudo tee -a /etc/apt/sources.list.d/dotdeb.list
|
||||||
wget -qO - http://www.dotdeb.org/dotdeb.gpg | sudo apt-key add -
|
wget -qO - http://www.dotdeb.org/dotdeb.gpg | sudo apt-key add -
|
||||||
|
# ref: https://github.com/docker-library/php/pull/542
|
||||||
|
sudo rm /etc/apt/preferences.d/no-debian-php
|
||||||
sudo apt-get update
|
sudo apt-get update
|
||||||
sudo apt-get install mysql-client php7.0-mysql zlib1g-dev
|
sudo apt-get install mysql-client php7.0-mysql zlib1g-dev
|
||||||
sudo docker-php-ext-install mysqli pdo pdo_mysql zip
|
sudo docker-php-ext-install mysqli pdo pdo_mysql zip
|
||||||
@ -15,34 +20,66 @@ function setup {
|
|||||||
sudo apt-get install mysql-client php5-mysql zlib1g-dev
|
sudo apt-get install mysql-client php5-mysql zlib1g-dev
|
||||||
sudo docker-php-ext-install mysql mysqli pdo pdo_mysql zip
|
sudo docker-php-ext-install mysql mysqli pdo pdo_mysql zip
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# Add a fake sendmail mailer
|
# Add a fake sendmail mailer
|
||||||
sudo cp ./.circleci/fake-sendmail.php /usr/local/bin/
|
sudo cp ./.circleci/fake-sendmail.php /usr/local/bin/
|
||||||
|
|
||||||
# configure Apache
|
# configure Apache
|
||||||
sudo cp ./.circleci/mailpoet_php.ini /usr/local/etc/php/conf.d/
|
sudo cp ./.circleci/mailpoet_php.ini /usr/local/etc/php/conf.d/
|
||||||
sudo cp ./.circleci/apache/mailpoet.loc.conf /etc/apache2/sites-available
|
sudo cp ./.circleci/apache/mailpoet.loc.conf /etc/apache2/sites-available
|
||||||
|
sudo a2dissite 000-default.conf
|
||||||
sudo a2ensite mailpoet.loc
|
sudo a2ensite mailpoet.loc
|
||||||
sudo a2enmod rewrite
|
sudo a2enmod rewrite
|
||||||
sudo service apache2 restart
|
sudo service apache2 restart
|
||||||
|
|
||||||
# Install NodeJS+NPM
|
# Install NodeJS+NPM
|
||||||
curl -sL https://deb.nodesource.com/setup_6.x | sudo -E bash -
|
curl -sL https://deb.nodesource.com/setup_6.x | sudo -E bash -
|
||||||
sudo apt-get install nodejs build-essential
|
sudo apt-get install nodejs build-essential
|
||||||
|
|
||||||
# install plugin dependencies
|
# install plugin dependencies
|
||||||
curl -sS https://getcomposer.org/installer | php
|
curl -sS https://getcomposer.org/installer | php
|
||||||
./composer.phar install
|
./composer.phar install
|
||||||
./do install
|
./do install
|
||||||
# Set up Wordpress
|
|
||||||
|
# Set up WordPress
|
||||||
mysql -h 127.0.0.1 -u root -e "create database wordpress"
|
mysql -h 127.0.0.1 -u root -e "create database wordpress"
|
||||||
curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar
|
curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar
|
||||||
chmod +x wp-cli.phar
|
chmod +x wp-cli.phar
|
||||||
./wp-cli.phar core download --allow-root --path=wordpress
|
sudo mv wp-cli.phar /usr/local/bin/wp
|
||||||
|
wp core download $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
|
||||||
# Generate `wp-config.php` file with debugging enabled
|
# Generate `wp-config.php` file with debugging enabled
|
||||||
echo "define(\"WP_DEBUG\", true);" | ./wp-cli.phar core config --allow-root --dbname=wordpress --dbuser=root --dbhost=127.0.0.1 --path=wordpress --extra-php
|
echo "define(\"WP_DEBUG\", true);" | wp core config --dbname=wordpress --dbuser=root --dbhost=127.0.0.1 --extra-php $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
|
||||||
|
# Change default table prefix
|
||||||
|
sed -i "s/\$table_prefix = 'wp_';/\$table_prefix = 'mp_';/" ./wordpress/wp-config.php
|
||||||
|
|
||||||
# Install WordPress
|
# Install WordPress
|
||||||
./wp-cli.phar core install --allow-root --admin_name=admin --admin_password=admin --admin_email=admin@mailpoet.loc --url=http://mailpoet.loc:8080 --title=WordPress --path=wordpress
|
if [[ $version == "php7_multisite" ]]; then
|
||||||
|
# Configure multisite environment
|
||||||
|
wp core multisite-install --admin_name=admin --admin_password=admin --admin_email=admin@mailpoet.loc --url=http://mailpoet.loc --title="WordPress MultiSite" $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
cp ./.circleci/wordpress/.htaccess ./wordpress/
|
||||||
|
|
||||||
|
# Add a second blog
|
||||||
|
wp site create --slug=php7_multisite $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
echo "WP_TEST_MULTISITE_SLUG=php7_multisite" >> .env
|
||||||
|
echo "WP_TEST_PATH_MULTISITE=/home/circleci/mailpoet/wordpress" >> .env
|
||||||
|
echo "HTTP_HOST=mailpoet.loc" >> .env
|
||||||
|
|
||||||
|
# Add a third dummy blog
|
||||||
|
wp site create --slug=dummy_multisite $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
else
|
||||||
|
wp core install --admin_name=admin --admin_password=admin --admin_email=admin@mailpoet.loc --url=http://mailpoet.loc --title="WordPress Single" $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
echo "WP_TEST_PATH=/home/circleci/mailpoet/wordpress" >> .env
|
||||||
|
fi
|
||||||
|
|
||||||
# Softlink plugin to plugin path
|
# Softlink plugin to plugin path
|
||||||
ln -s ../../.. wordpress/wp-content/plugins/mailpoet
|
ln -s ../../.. wordpress/wp-content/plugins/mailpoet
|
||||||
./wp-cli.phar plugin activate mailpoet --path=wordpress
|
|
||||||
# Create .env file with correct path to WP installation
|
# Activate plugin
|
||||||
# TODO: Remove this line after PR gets merged and CircleCI env variables change
|
if [[ $version == "php7_multisite" ]]; then
|
||||||
echo "WP_TEST_PATH=\"/home/circleci/mailpoet/wordpress\"" > .env
|
wp plugin activate mailpoet --url=http://mailpoet.loc/php7_multisite/ $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
}
|
else
|
||||||
|
wp plugin activate mailpoet $wp_cli_wordpress_path $wp_cli_allow_root
|
||||||
|
fi
|
||||||
|
}
|
12
.circleci/wordpress/.htaccess
Normal file
12
.circleci/wordpress/.htaccess
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
RewriteEngine On
|
||||||
|
RewriteBase /
|
||||||
|
RewriteRule ^index\.php$ - [L]
|
||||||
|
|
||||||
|
RewriteRule ^([_0-9a-zA-Z-]+/)?wp-admin$ $1wp-admin/ [R=301,L]
|
||||||
|
|
||||||
|
RewriteCond %{REQUEST_FILENAME} -f [OR]
|
||||||
|
RewriteCond %{REQUEST_FILENAME} -d
|
||||||
|
RewriteRule ^ - [L]
|
||||||
|
RewriteRule ^([_0-9a-zA-Z-]+/)?(wp-(content|admin|includes).*) $2 [L]
|
||||||
|
RewriteRule ^([_0-9a-zA-Z-]+/)?(.*\.php)$ $2 [L]
|
||||||
|
RewriteRule . index.php [L]
|
@ -1,4 +1,6 @@
|
|||||||
WP_TEST_PATH="/var/www/wordpress"
|
WP_TEST_PATH="/var/www/wordpress"
|
||||||
|
WP_TEST_PATH_MULTISITE="/var/www/wordpress"
|
||||||
|
WP_TEST_MULTISITE_SLUG=""
|
||||||
WP_TEST_ENABLE_NETWORK_TESTS="true"
|
WP_TEST_ENABLE_NETWORK_TESTS="true"
|
||||||
WP_TEST_IMPORT_MAILCHIMP_API=""
|
WP_TEST_IMPORT_MAILCHIMP_API=""
|
||||||
WP_TEST_IMPORT_MAILCHIMP_LISTS="" // (separated with comma)
|
WP_TEST_IMPORT_MAILCHIMP_LISTS="" // (separated with comma)
|
||||||
@ -16,4 +18,5 @@ WP_TEST_MAILER_SMTP_LOGIN=""
|
|||||||
WP_TEST_MAILER_SMTP_PASSWORD=""
|
WP_TEST_MAILER_SMTP_PASSWORD=""
|
||||||
WP_SVN_USERNAME=""
|
WP_SVN_USERNAME=""
|
||||||
WP_SVN_PASSWORD=""
|
WP_SVN_PASSWORD=""
|
||||||
WP_TRANSIFEX_API_TOKEN=""
|
WP_TRANSIFEX_API_TOKEN=""
|
||||||
|
HTTP_HOST="" // URL of your site (used for multisite env and equals to DOMAIN_CURRENT_SITE from wp-config.php)
|
@ -8,11 +8,13 @@
|
|||||||
"ecmaVersion": 5
|
"ecmaVersion": 5
|
||||||
},
|
},
|
||||||
"rules": {
|
"rules": {
|
||||||
|
// Exceptions
|
||||||
|
"no-underscore-dangle": 0, // Backbone uses underscores, we cannot remove them
|
||||||
|
// Temporary
|
||||||
"import/no-amd": 0,
|
"import/no-amd": 0,
|
||||||
"prefer-arrow-callback": 0,
|
"prefer-arrow-callback": 0,
|
||||||
"radix": 0,
|
"radix": 0,
|
||||||
"no-alert": 0,
|
"no-alert": 0,
|
||||||
"block-scoped-var": 0,
|
|
||||||
"guard-for-in": 0,
|
"guard-for-in": 0,
|
||||||
"no-prototype-builtins": 0,
|
"no-prototype-builtins": 0,
|
||||||
"no-restricted-syntax": 0,
|
"no-restricted-syntax": 0,
|
||||||
@ -38,25 +40,7 @@
|
|||||||
"global-require": 0,
|
"global-require": 0,
|
||||||
"no-throw-literal": 0,
|
"no-throw-literal": 0,
|
||||||
"no-extra-bind": 0,
|
"no-extra-bind": 0,
|
||||||
"one-var-declaration-per-line": 0,
|
|
||||||
"consistent-return": 0,
|
|
||||||
"no-shadow": 0,
|
|
||||||
"no-underscore-dangle": 0,
|
|
||||||
"brace-style": 0,
|
"brace-style": 0,
|
||||||
"no-else-return": 0,
|
"space-infix-ops": 0
|
||||||
"no-use-before-define": 0,
|
|
||||||
"one-var": 0,
|
|
||||||
"camelcase": 0,
|
|
||||||
"padded-blocks": 0,
|
|
||||||
"strict": 0,
|
|
||||||
"vars-on-top": 0,
|
|
||||||
"no-var": 0,
|
|
||||||
"no-unused-vars": 0,
|
|
||||||
"object-shorthand": 0,
|
|
||||||
"new-parens": 0,
|
|
||||||
"eol-last": 0,
|
|
||||||
"dot-notation": 0,
|
|
||||||
"prefer-template": 0,
|
|
||||||
"func-names": 0
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -14,7 +14,11 @@
|
|||||||
"import/resolver": "webpack"
|
"import/resolver": "webpack"
|
||||||
},
|
},
|
||||||
"rules": {
|
"rules": {
|
||||||
|
// Exceptions
|
||||||
"comma-dangle": ["error", "always-multiline"],
|
"comma-dangle": ["error", "always-multiline"],
|
||||||
|
"no-script-url": 0,
|
||||||
|
"import/extensions": 0, // we wouldn't be able to import jQuery without this line
|
||||||
|
// Temporary
|
||||||
"import/no-amd": 0,
|
"import/no-amd": 0,
|
||||||
"react/no-multi-comp": 0,
|
"react/no-multi-comp": 0,
|
||||||
"react/sort-comp": 0,
|
"react/sort-comp": 0,
|
||||||
@ -37,35 +41,8 @@
|
|||||||
"jsx-a11y/alt-text": 0,
|
"jsx-a11y/alt-text": 0,
|
||||||
"func-names": 0,
|
"func-names": 0,
|
||||||
"object-shorthand": 0,
|
"object-shorthand": 0,
|
||||||
"no-bitwise": 0,
|
"space-unary-ops": 0,
|
||||||
"arrow-body-style": 0,
|
"space-infix-ops": 0,
|
||||||
"prefer-template": 0,
|
"no-irregular-whitespace": 0
|
||||||
"default-case": 0,
|
|
||||||
"array-callback-return": 0,
|
|
||||||
"consistent-return": 0,
|
|
||||||
"import/extensions": 0,
|
|
||||||
"import/no-extraneous-dependencies": 0,
|
|
||||||
"camelcase": 0,
|
|
||||||
"eqeqeq": 0,
|
|
||||||
"no-lonely-if": 0,
|
|
||||||
"block-scoped-var": 0,
|
|
||||||
"no-extra-bind": 0,
|
|
||||||
"class-methods-use-this": 0,
|
|
||||||
"no-case-declarations": 0,
|
|
||||||
"no-else-return": 0,
|
|
||||||
"max-len": 0,
|
|
||||||
"no-useless-concat": 0,
|
|
||||||
"no-sequences": 0,
|
|
||||||
"no-extra-boolean-cast": 0,
|
|
||||||
"dot-notation": 0,
|
|
||||||
"no-shadow": 0,
|
|
||||||
"one-var": 0,
|
|
||||||
"no-alert": 0,
|
|
||||||
"one-var-declaration-per-line": 0,
|
|
||||||
"no-script-url": 0,
|
|
||||||
"wrap-iife": 0,
|
|
||||||
"vars-on-top": 0,
|
|
||||||
"padded-blocks": 0,
|
|
||||||
"no-underscore-dangle": 0
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -8,25 +8,9 @@
|
|||||||
"ecmaVersion": 6
|
"ecmaVersion": 6
|
||||||
},
|
},
|
||||||
"rules": {
|
"rules": {
|
||||||
"import/no-amd": 0,
|
// Exceptions
|
||||||
"one-var": 0,
|
|
||||||
"no-whitespace-before-property": 0,
|
|
||||||
"global-require": 0,
|
|
||||||
"keyword-spacing": 0,
|
|
||||||
"no-bitwise": 0,
|
|
||||||
"no-spaced-func": 0,
|
|
||||||
"func-call-spacing": 0,
|
|
||||||
"max-len": 0,
|
|
||||||
"space-unary-ops": 0,
|
|
||||||
"no-unused-vars": 0,
|
|
||||||
"no-underscore-dangle": 0,
|
|
||||||
"no-shadow": 0,
|
|
||||||
"padded-blocks": 0,
|
|
||||||
"vars-on-top": 0,
|
|
||||||
"space-before-blocks": 0,
|
|
||||||
"object-curly-spacing": 0,
|
|
||||||
"one-var-declaration-per-line": 0,
|
|
||||||
"func-names": 0,
|
"func-names": 0,
|
||||||
"space-before-function-paren": 0
|
// Temporary
|
||||||
|
"no-underscore-dangle": 0
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
4
.gitignore
vendored
4
.gitignore
vendored
@ -2,6 +2,7 @@
|
|||||||
TODO
|
TODO
|
||||||
composer.phar
|
composer.phar
|
||||||
/vendor
|
/vendor
|
||||||
|
/vendor_backup
|
||||||
tests/_output/*
|
tests/_output/*
|
||||||
tests/_support/_generated/*
|
tests/_support/_generated/*
|
||||||
node_modules
|
node_modules
|
||||||
@ -20,4 +21,5 @@ assets/js/*.json
|
|||||||
.vagrant
|
.vagrant
|
||||||
lang
|
lang
|
||||||
.mp_svn
|
.mp_svn
|
||||||
/nbproject/
|
/nbproject/
|
||||||
|
tests/_data/acceptanceGenerated.sql
|
54
RoboFile.php
54
RoboFile.php
@ -153,17 +153,30 @@ class RoboFile extends \Robo\Tasks {
|
|||||||
return $this->_exec('./tasks/transifex_init.sh');
|
return $this->_exec('./tasks/transifex_init.sh');
|
||||||
}
|
}
|
||||||
|
|
||||||
function testUnit($opts=['file' => null, 'xml' => false]) {
|
function testUnit($opts=['file' => null, 'xml' => false, 'multisite' => false]) {
|
||||||
$this->loadEnv();
|
$this->loadEnv();
|
||||||
|
|
||||||
$command = 'vendor/bin/codecept run unit -c codeception.unit.yml -f '.(($opts['file']) ? $opts['file'] : '');
|
$command = 'vendor/bin/codecept run unit -c codeception.unit.yml';
|
||||||
|
|
||||||
|
if($opts['multisite']) {
|
||||||
|
$command = 'MULTISITE=true ' . $command;
|
||||||
|
}
|
||||||
|
|
||||||
|
if($opts['file']) {
|
||||||
|
$command .= ' -f ' . $opts['file'];
|
||||||
|
}
|
||||||
|
|
||||||
if($opts['xml']) {
|
if($opts['xml']) {
|
||||||
$command .= ' --xml';
|
$command .= ' --xml';
|
||||||
}
|
}
|
||||||
|
|
||||||
return $this->_exec($command);
|
return $this->_exec($command);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function testMultisiteUnit($opts=['file' => null, 'xml' => false, 'multisite' => true]) {
|
||||||
|
return $this->testUnit($opts);
|
||||||
|
}
|
||||||
|
|
||||||
function testCoverage($opts=['file' => null, 'xml' => false]) {
|
function testCoverage($opts=['file' => null, 'xml' => false]) {
|
||||||
$this->loadEnv();
|
$this->loadEnv();
|
||||||
$command = join(' ', array(
|
$command = join(' ', array(
|
||||||
@ -198,6 +211,10 @@ class RoboFile extends \Robo\Tasks {
|
|||||||
return $this->_exec($command);
|
return $this->_exec($command);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function securityComposer() {
|
||||||
|
return $this->_exec('vendor/bin/security-checker security:check --format=simple');
|
||||||
|
}
|
||||||
|
|
||||||
function testDebug($opts=['file' => null, 'xml' => false]) {
|
function testDebug($opts=['file' => null, 'xml' => false]) {
|
||||||
$this->loadEnv();
|
$this->loadEnv();
|
||||||
$this->_exec('vendor/bin/codecept build -c codeception.unit.yml');
|
$this->_exec('vendor/bin/codecept build -c codeception.unit.yml');
|
||||||
@ -214,6 +231,14 @@ class RoboFile extends \Robo\Tasks {
|
|||||||
return $this->_exec('COMPOSE_HTTP_TIMEOUT=200 docker-compose run codeception --steps --debug -vvv');
|
return $this->_exec('COMPOSE_HTTP_TIMEOUT=200 docker-compose run codeception --steps --debug -vvv');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function testAcceptanceMultisite() {
|
||||||
|
return $this->_exec('COMPOSE_HTTP_TIMEOUT=200 docker-compose run -e MULTISITE=1 codeception --steps --debug -vvv');
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteDocker() {
|
||||||
|
return $this->_exec('docker-compose down -v --remove-orphans --rmi all');
|
||||||
|
}
|
||||||
|
|
||||||
function testFailed() {
|
function testFailed() {
|
||||||
$this->loadEnv();
|
$this->loadEnv();
|
||||||
$this->_exec('vendor/bin/codecept build -c codeception.unit.yml');
|
$this->_exec('vendor/bin/codecept build -c codeception.unit.yml');
|
||||||
@ -289,15 +314,16 @@ class RoboFile extends \Robo\Tasks {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function svnPublish($opts = ['force' => false]) {
|
function svnPublish($opts = ['force' => false]) {
|
||||||
$this->loadWPFunctions();
|
$this->loadEnv();
|
||||||
|
|
||||||
$svn_dir = ".mp_svn";
|
$svn_dir = ".mp_svn";
|
||||||
$plugin_data = get_plugin_data('mailpoet.php', false, false);
|
$plugin_version = $this->getPluginVersion('mailpoet.php');
|
||||||
$plugin_version = $plugin_data['Version'];
|
$plugin_dist_name = 'mailpoet';
|
||||||
$plugin_dist_name = sanitize_title_with_dashes($plugin_data['Name']);
|
|
||||||
$plugin_dist_name = explode('-', $plugin_dist_name);
|
|
||||||
$plugin_dist_name = $plugin_dist_name[0];
|
|
||||||
$plugin_dist_file = $plugin_dist_name . '.zip';
|
$plugin_dist_file = $plugin_dist_name . '.zip';
|
||||||
|
|
||||||
|
if(!$plugin_version) {
|
||||||
|
throw new \Exception('Could not parse plugin version, check the plugin header');
|
||||||
|
}
|
||||||
$this->say('Publishing version: ' . $plugin_version);
|
$this->say('Publishing version: ' . $plugin_version);
|
||||||
|
|
||||||
// Sanity checks
|
// Sanity checks
|
||||||
@ -416,13 +442,9 @@ class RoboFile extends \Robo\Tasks {
|
|||||||
$dotenv->load();
|
$dotenv->load();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function loadWPFunctions() {
|
protected function getPluginVersion($file) {
|
||||||
$this->loadEnv();
|
$data = file_get_contents($file);
|
||||||
define('ABSPATH', getenv('WP_TEST_PATH') . '/');
|
preg_match('/^[ \t*]*Version:(.*)$/mi', $data, $m);
|
||||||
define('WPINC', 'wp-includes');
|
return !empty($m[1]) ? trim($m[1]) : false;
|
||||||
require_once(ABSPATH . WPINC . '/functions.php');
|
|
||||||
require_once(ABSPATH . WPINC . '/formatting.php');
|
|
||||||
require_once(ABSPATH . WPINC . '/plugin.php');
|
|
||||||
require_once(ABSPATH . 'wp-admin/includes/plugin.php');
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -13,3 +13,6 @@ Style for Members plugin
|
|||||||
width: 20px;
|
width: 20px;
|
||||||
font-size: 20px;
|
font-size: 20px;
|
||||||
margin-right: 3px;
|
margin-right: 3px;
|
||||||
|
|
||||||
|
#wpbody
|
||||||
|
padding-bottom: 20px;
|
||||||
|
@ -27,3 +27,7 @@
|
|||||||
@require 'pages_custom'
|
@require 'pages_custom'
|
||||||
|
|
||||||
@require 'mp2migrator'
|
@require 'mp2migrator'
|
||||||
|
|
||||||
|
@require '../../../node_modules/react-confirm-alert/src/react-confirm-alert.css'
|
||||||
|
|
||||||
|
@require 'newsletter_templates'
|
@ -163,6 +163,7 @@ $master-column-tool-width = 24px
|
|||||||
|
|
||||||
.mailpoet_delete_block_confirm
|
.mailpoet_delete_block_confirm
|
||||||
color: $warning-text-color
|
color: $warning-text-color
|
||||||
|
float: right
|
||||||
|
|
||||||
&:hover
|
&:hover
|
||||||
color: $warning-text-color
|
color: $warning-text-color
|
||||||
@ -170,6 +171,7 @@ $master-column-tool-width = 24px
|
|||||||
|
|
||||||
.mailpoet_delete_block_cancel
|
.mailpoet_delete_block_cancel
|
||||||
color: $warning-alternate-text-color
|
color: $warning-alternate-text-color
|
||||||
|
float: right
|
||||||
|
|
||||||
&:hover
|
&:hover
|
||||||
color: $warning-alternate-text-color
|
color: $warning-alternate-text-color
|
||||||
|
@ -21,6 +21,8 @@ $block-text-line-height = $text-line-height
|
|||||||
left: 0
|
left: 0
|
||||||
pointer-events: none
|
pointer-events: none
|
||||||
border: 1px solid $transparent-color
|
border: 1px solid $transparent-color
|
||||||
|
-webkit-transition: 0.3s;
|
||||||
|
transition: 0.3s;
|
||||||
|
|
||||||
&:hover > .mailpoet_block_highlight
|
&:hover > .mailpoet_block_highlight
|
||||||
border: 1px dashed $block-hover-highlight-color
|
border: 1px dashed $block-hover-highlight-color
|
||||||
|
7
assets/css/src/newsletter_templates.styl
Normal file
7
assets/css/src/newsletter_templates.styl
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
@require 'newsletter_editor/variables'
|
||||||
|
|
||||||
|
.mailpoet_template_iframe
|
||||||
|
position: absolute
|
||||||
|
z-index: -9999
|
||||||
|
width: $newsletter-width
|
||||||
|
max-width: $newsletter-width
|
@ -1,10 +1,10 @@
|
|||||||
define('admin', [
|
define('admin', [
|
||||||
'jquery'
|
'jquery'
|
||||||
],
|
],
|
||||||
function (jQuery) {
|
function admin(jQuery) {
|
||||||
jQuery(function ($) {
|
jQuery(function adminDomReady($) {
|
||||||
// dom ready
|
// dom ready
|
||||||
$(function () {
|
$(function domReady() {
|
||||||
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -2,17 +2,16 @@ function requestFailed(errorMessage, xhr) {
|
|||||||
if (xhr.responseJSON) {
|
if (xhr.responseJSON) {
|
||||||
return xhr.responseJSON;
|
return xhr.responseJSON;
|
||||||
}
|
}
|
||||||
var message = errorMessage.replace('%d', xhr.status);
|
|
||||||
return {
|
return {
|
||||||
errors: [
|
errors: [
|
||||||
{
|
{
|
||||||
message: message
|
message: errorMessage.replace('%d', xhr.status)
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
define('ajax', ['mailpoet', 'jquery', 'underscore'], function (mp, jQuery, _) {
|
define('ajax', ['mailpoet', 'jquery', 'underscore'], function ajax(mp, jQuery, _) {
|
||||||
var MailPoet = mp;
|
var MailPoet = mp;
|
||||||
|
|
||||||
MailPoet.Ajax = {
|
MailPoet.Ajax = {
|
||||||
@ -26,10 +25,10 @@ define('ajax', ['mailpoet', 'jquery', 'underscore'], function (mp, jQuery, _) {
|
|||||||
token: null,
|
token: null,
|
||||||
data: {}
|
data: {}
|
||||||
},
|
},
|
||||||
post: function (options) {
|
post: function post(options) {
|
||||||
return this.request('post', options);
|
return this.request('post', options);
|
||||||
},
|
},
|
||||||
init: function (options) {
|
init: function init(options) {
|
||||||
// merge options
|
// merge options
|
||||||
this.options = jQuery.extend({}, this.defaults, options);
|
this.options = jQuery.extend({}, this.defaults, options);
|
||||||
|
|
||||||
@ -43,7 +42,7 @@ define('ajax', ['mailpoet', 'jquery', 'underscore'], function (mp, jQuery, _) {
|
|||||||
this.options.token = window.mailpoet_token;
|
this.options.token = window.mailpoet_token;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
getParams: function () {
|
getParams: function getParams() {
|
||||||
return {
|
return {
|
||||||
action: 'mailpoet',
|
action: 'mailpoet',
|
||||||
api_version: this.options.api_version,
|
api_version: this.options.api_version,
|
||||||
@ -53,27 +52,29 @@ define('ajax', ['mailpoet', 'jquery', 'underscore'], function (mp, jQuery, _) {
|
|||||||
data: this.options.data || {}
|
data: this.options.data || {}
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
request: function (method, options) {
|
request: function request(method, options) {
|
||||||
// set options
|
var params;
|
||||||
|
var deferred;
|
||||||
|
// set options
|
||||||
this.init(options);
|
this.init(options);
|
||||||
|
|
||||||
// set request params
|
// set request params
|
||||||
var params = this.getParams();
|
params = this.getParams();
|
||||||
|
|
||||||
// remove null values from the data object
|
// remove null values from the data object
|
||||||
if (_.isObject(params.data)) {
|
if (_.isObject(params.data)) {
|
||||||
params.data = _.pick(params.data, function (value) {
|
params.data = _.pick(params.data, function isNotNull(value) {
|
||||||
return (value !== null);
|
return (value !== null);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// ajax request
|
// ajax request
|
||||||
var deferred = jQuery.post(
|
deferred = jQuery.post(
|
||||||
this.options.url,
|
this.options.url,
|
||||||
params,
|
params,
|
||||||
null,
|
null,
|
||||||
'json'
|
'json'
|
||||||
).then(function (data) {
|
).then(function resultHandler(data) {
|
||||||
return data;
|
return data;
|
||||||
}, _.partial(requestFailed, MailPoet.I18n.t('ajaxFailedErrorMessage')));
|
}, _.partial(requestFailed, MailPoet.I18n.t('ajaxFailedErrorMessage')));
|
||||||
|
|
||||||
|
@ -31,12 +31,12 @@ function exportMixpanel(mp) {
|
|||||||
if (window.mailpoet_analytics_enabled) {
|
if (window.mailpoet_analytics_enabled) {
|
||||||
MailPoet.trackEvent = track;
|
MailPoet.trackEvent = track;
|
||||||
} else {
|
} else {
|
||||||
MailPoet.trackEvent = function () {};
|
MailPoet.trackEvent = function emptyFunction() {};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function trackCachedEvents() {
|
function trackCachedEvents() {
|
||||||
eventsCache.map(function (event) {
|
eventsCache.map(function trackIfEnabled(event) {
|
||||||
if (window.mailpoet_analytics_enabled || event.forced) {
|
if (window.mailpoet_analytics_enabled || event.forced) {
|
||||||
window.mixpanel.track(event.name, event.data);
|
window.mixpanel.track(event.name, event.data);
|
||||||
}
|
}
|
||||||
@ -53,7 +53,7 @@ function cacheEvent(forced, name, data) {
|
|||||||
|
|
||||||
define(
|
define(
|
||||||
['mailpoet', 'underscore'],
|
['mailpoet', 'underscore'],
|
||||||
function (mp, _) {
|
function analyticsEvent(mp, _) {
|
||||||
var MailPoet = mp;
|
var MailPoet = mp;
|
||||||
|
|
||||||
function initializeMixpanelWhenLoaded() {
|
function initializeMixpanelWhenLoaded() {
|
||||||
|
@ -3,7 +3,7 @@ define('date',
|
|||||||
'mailpoet',
|
'mailpoet',
|
||||||
'jquery',
|
'jquery',
|
||||||
'moment'
|
'moment'
|
||||||
], function (
|
], function ( // eslint-disable-line func-names
|
||||||
mp,
|
mp,
|
||||||
jQuery,
|
jQuery,
|
||||||
Moment
|
Moment
|
||||||
@ -19,7 +19,7 @@ define('date',
|
|||||||
offset: 0,
|
offset: 0,
|
||||||
format: 'F, d Y H:i:s'
|
format: 'F, d Y H:i:s'
|
||||||
},
|
},
|
||||||
init: function (opts) {
|
init: function init(opts) {
|
||||||
var options = opts || {};
|
var options = opts || {};
|
||||||
|
|
||||||
// set UTC offset
|
// set UTC offset
|
||||||
@ -41,37 +41,43 @@ define('date',
|
|||||||
|
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
format: function (date, opts) {
|
format: function format(date, opts) {
|
||||||
var options = opts || {};
|
var options = opts || {};
|
||||||
|
var momentDate;
|
||||||
this.init(options);
|
this.init(options);
|
||||||
|
|
||||||
var momentDate = Moment(date, this.convertFormat(options.parseFormat));
|
momentDate = Moment(date, this.convertFormat(options.parseFormat));
|
||||||
if (options.offset === 0) momentDate = momentDate.utc();
|
if (options.offset === 0) momentDate = momentDate.utc();
|
||||||
return momentDate.format(this.convertFormat(this.options.format));
|
return momentDate.format(this.convertFormat(this.options.format));
|
||||||
},
|
},
|
||||||
toDate: function (date, opts) {
|
toDate: function toDate(date, opts) {
|
||||||
var options = opts || {};
|
var options = opts || {};
|
||||||
this.init(options);
|
this.init(options);
|
||||||
|
|
||||||
return Moment(date, this.convertFormat(options.parseFormat)).toDate();
|
return Moment(date, this.convertFormat(options.parseFormat)).toDate();
|
||||||
},
|
},
|
||||||
short: function (date) {
|
short: function short(date) {
|
||||||
return this.format(date, {
|
return this.format(date, {
|
||||||
format: 'F, j Y'
|
format: 'F, j Y'
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
full: function (date) {
|
full: function full(date) {
|
||||||
return this.format(date, {
|
return this.format(date, {
|
||||||
format: 'F, j Y H:i:s'
|
format: 'F, j Y H:i:s'
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
time: function (date) {
|
time: function time(date) {
|
||||||
return this.format(date, {
|
return this.format(date, {
|
||||||
format: 'H:i:s'
|
format: 'H:i:s'
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
convertFormat: function (format) {
|
convertFormat: function convertFormat(format) {
|
||||||
var format_mappings = {
|
var replacements;
|
||||||
|
var convertedFormat;
|
||||||
|
var escapeToken;
|
||||||
|
var index;
|
||||||
|
var token;
|
||||||
|
var formatMappings = {
|
||||||
date: {
|
date: {
|
||||||
d: 'DD',
|
d: 'DD',
|
||||||
D: 'ddd',
|
D: 'ddd',
|
||||||
@ -140,12 +146,11 @@ define('date',
|
|||||||
|
|
||||||
if (!format || format.length <= 0) return format;
|
if (!format || format.length <= 0) return format;
|
||||||
|
|
||||||
var replacements = format_mappings['date'];
|
replacements = formatMappings.date;
|
||||||
|
convertedFormat = [];
|
||||||
|
escapeToken = false;
|
||||||
|
|
||||||
var convertedFormat = [];
|
for (index = 0, token = ''; format.charAt(index); index += 1) {
|
||||||
var escapeToken = false;
|
|
||||||
|
|
||||||
for (var index = 0, token = ''; format.charAt(index); index += 1) {
|
|
||||||
token = format.charAt(index);
|
token = format.charAt(index);
|
||||||
if (escapeToken === true) {
|
if (escapeToken === true) {
|
||||||
convertedFormat.push('[' + token + ']');
|
convertedFormat.push('[' + token + ']');
|
||||||
|
@ -16,25 +16,23 @@ define([
|
|||||||
|
|
||||||
// isChecked will be true only if the value is "1"
|
// isChecked will be true only if the value is "1"
|
||||||
// it will be false in case value is "0" or empty
|
// it will be false in case value is "0" or empty
|
||||||
const isChecked = !!(~~(this.props.item[this.props.field.name]));
|
const isChecked = !!(Number(this.props.item[this.props.field.name]));
|
||||||
const options = Object.keys(this.props.field.values).map(
|
const options = Object.keys(this.props.field.values).map(
|
||||||
(value, index) => {
|
(value, index) => (
|
||||||
return (
|
<p key={`checkbox-${index}`}>
|
||||||
<p key={'checkbox-' + index}>
|
<label>
|
||||||
<label>
|
<input
|
||||||
<input
|
ref="checkbox"
|
||||||
ref="checkbox"
|
type="checkbox"
|
||||||
type="checkbox"
|
value="1"
|
||||||
value="1"
|
checked={isChecked}
|
||||||
checked={isChecked}
|
onChange={this.onValueChange}
|
||||||
onChange={this.onValueChange}
|
name={this.props.field.name}
|
||||||
name={this.props.field.name}
|
|
||||||
/>
|
/>
|
||||||
{ this.props.field.values[value] }
|
{ this.props.field.values[value] }
|
||||||
</label>
|
</label>
|
||||||
</p>
|
</p>
|
||||||
);
|
)
|
||||||
}
|
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
@ -167,6 +167,11 @@ define([
|
|||||||
year: this.state.year,
|
year: this.state.year,
|
||||||
};
|
};
|
||||||
break;
|
break;
|
||||||
|
default:
|
||||||
|
value = {
|
||||||
|
value: 'invalid type',
|
||||||
|
};
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return value;
|
return value;
|
||||||
@ -181,7 +186,7 @@ define([
|
|||||||
field = matches[1];
|
field = matches[1];
|
||||||
property = matches[2];
|
property = matches[2];
|
||||||
|
|
||||||
const value = ~~(e.target.value);
|
const value = Number(e.target.value);
|
||||||
|
|
||||||
this.setState({
|
this.setState({
|
||||||
[`${property}`]: value,
|
[`${property}`]: value,
|
||||||
@ -233,6 +238,9 @@ define([
|
|||||||
day={this.state.day}
|
day={this.state.day}
|
||||||
placeholder={this.props.field.day_placeholder}
|
placeholder={this.props.field.day_placeholder}
|
||||||
/>);
|
/>);
|
||||||
|
|
||||||
|
default:
|
||||||
|
return <div>Invalid date type</div>;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -32,7 +32,7 @@ define([
|
|||||||
let field = false;
|
let field = false;
|
||||||
let dataField = data.field;
|
let dataField = data.field;
|
||||||
|
|
||||||
if (data.field['field'] !== undefined) {
|
if (data.field.field !== undefined) {
|
||||||
dataField = jQuery.merge(dataField, data.field.field);
|
dataField = jQuery.merge(dataField, data.field.field);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -68,36 +68,37 @@ define([
|
|||||||
case 'reactComponent':
|
case 'reactComponent':
|
||||||
field = (<data.field.component {...data} />);
|
field = (<data.field.component {...data} />);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
field = 'invalid';
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (inline === true) {
|
if (inline === true) {
|
||||||
return (
|
return (
|
||||||
<span key={'field-' + (data.index || 0)}>
|
<span key={`field-${data.index || 0}`}>
|
||||||
{ field }
|
{ field }
|
||||||
{ description }
|
{ description }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else {
|
|
||||||
return (
|
|
||||||
<div key={'field-' + (data.index || 0)}>
|
|
||||||
{ field }
|
|
||||||
{ description }
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
return (
|
||||||
|
<div key={`field-${data.index || 0}`}>
|
||||||
|
{ field }
|
||||||
|
{ description }
|
||||||
|
</div>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
let field = false;
|
let field = false;
|
||||||
|
|
||||||
if (this.props.field['fields'] !== undefined) {
|
if (this.props.field.fields !== undefined) {
|
||||||
field = this.props.field.fields.map((subfield, index) => {
|
field = this.props.field.fields.map((subfield, index) => this.renderField({
|
||||||
return this.renderField({
|
index: index,
|
||||||
index: index,
|
field: subfield,
|
||||||
field: subfield,
|
item: this.props.item,
|
||||||
item: this.props.item,
|
onValueChange: this.props.onValueChange || false,
|
||||||
onValueChange: this.props.onValueChange || false,
|
}));
|
||||||
});
|
|
||||||
});
|
|
||||||
} else {
|
} else {
|
||||||
field = this.renderField(this.props);
|
field = this.renderField(this.props);
|
||||||
}
|
}
|
||||||
@ -110,10 +111,10 @@ define([
|
|||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<tr>
|
<tr className={`form-field-row-${this.props.field.name}`}>
|
||||||
<th scope="row">
|
<th scope="row">
|
||||||
<label
|
<label
|
||||||
htmlFor={'field_' + this.props.field.name}
|
htmlFor={`field_${this.props.field.name}`}
|
||||||
>
|
>
|
||||||
{ this.props.field.label }
|
{ this.props.field.label }
|
||||||
{ tip }
|
{ tip }
|
||||||
|
@ -10,23 +10,21 @@ define([
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const selected_value = this.props.item[this.props.field.name];
|
const selectedValue = this.props.item[this.props.field.name];
|
||||||
const options = Object.keys(this.props.field.values).map(
|
const options = Object.keys(this.props.field.values).map(
|
||||||
(value, index) => {
|
(value, index) => (
|
||||||
return (
|
<p key={`radio-${index}`}>
|
||||||
<p key={'radio-' + index}>
|
<label>
|
||||||
<label>
|
<input
|
||||||
<input
|
type="radio"
|
||||||
type="radio"
|
checked={selectedValue === value}
|
||||||
checked={selected_value === value}
|
value={value}
|
||||||
value={value}
|
onChange={this.props.onValueChange}
|
||||||
onChange={this.props.onValueChange}
|
name={this.props.field.name} />
|
||||||
name={this.props.field.name} />
|
{ this.props.field.values[value] }
|
||||||
{ this.props.field.values[value] }
|
</label>
|
||||||
</label>
|
</p>
|
||||||
</p>
|
)
|
||||||
);
|
|
||||||
}
|
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
@ -17,7 +17,7 @@ const FormFieldSelect = React.createClass({
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (this.props.field['filter'] !== undefined) {
|
if (this.props.field.filter !== undefined) {
|
||||||
filter = this.props.field.filter;
|
filter = this.props.field.filter;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -41,27 +41,25 @@ const FormFieldSelect = React.createClass({
|
|||||||
keys = Object.keys(this.props.field.values);
|
keys = Object.keys(this.props.field.values);
|
||||||
}
|
}
|
||||||
|
|
||||||
const options = keys.map(
|
const options = keys
|
||||||
(value, index) => {
|
.filter((value) => {
|
||||||
|
if (filter === false) return true;
|
||||||
if (filter !== false && filter(this.props.item, value) === false) {
|
return filter(this.props.item, value);
|
||||||
return;
|
})
|
||||||
}
|
.map(
|
||||||
|
(value, index) => (
|
||||||
return (
|
|
||||||
<option
|
<option
|
||||||
key={'option-' + index}
|
key={`option-${index}`}
|
||||||
value={value}>
|
value={value}>
|
||||||
{ this.props.field.values[value] }
|
{ this.props.field.values[value] }
|
||||||
</option>
|
</option>
|
||||||
);
|
)
|
||||||
}
|
);
|
||||||
);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<select
|
<select
|
||||||
name={this.props.field.name}
|
name={this.props.field.name}
|
||||||
id={'field_' + this.props.field.name}
|
id={`field_${this.props.field.name}`}
|
||||||
value={this.props.item[this.props.field.name]}
|
value={this.props.item[this.props.field.name]}
|
||||||
onChange={this.props.onValueChange}
|
onChange={this.props.onValueChange}
|
||||||
{...this.props.field.validation}
|
{...this.props.field.validation}
|
||||||
|
@ -26,7 +26,7 @@ define([
|
|||||||
return (this.state.select2 === true);
|
return (this.state.select2 === true);
|
||||||
},
|
},
|
||||||
componentDidMount: function () {
|
componentDidMount: function () {
|
||||||
if (this.allowMultipleValues()) {
|
if (this.allowMultipleValues() || this.props.field.forceSelect2) {
|
||||||
this.setupSelect2();
|
this.setupSelect2();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -35,19 +35,19 @@ define([
|
|||||||
(this.props.item !== undefined && prevProps.item !== undefined)
|
(this.props.item !== undefined && prevProps.item !== undefined)
|
||||||
&& (this.props.item.id !== prevProps.item.id)
|
&& (this.props.item.id !== prevProps.item.id)
|
||||||
) {
|
) {
|
||||||
jQuery('#' + this.refs.select.id)
|
jQuery(`#${this.refs.select.id}`)
|
||||||
.val(this.getSelectedValues())
|
.val(this.getSelectedValues())
|
||||||
.trigger('change');
|
.trigger('change');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
componentWillUnmount: function () {
|
componentWillUnmount: function () {
|
||||||
if (this.allowMultipleValues()) {
|
if (this.allowMultipleValues() || this.props.field.forceSelect2) {
|
||||||
this.destroySelect2();
|
this.destroySelect2();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
destroySelect2: function () {
|
destroySelect2: function () {
|
||||||
if (this.isSelect2Initialized()) {
|
if (this.isSelect2Initialized()) {
|
||||||
jQuery('#' + this.refs.select.id).select2('destroy');
|
jQuery(`#${this.refs.select.id}`).select2('destroy');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
setupSelect2: function () {
|
setupSelect2: function () {
|
||||||
@ -55,18 +55,15 @@ define([
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const select2 = jQuery('#' + this.refs.select.id).select2({
|
const select2 = jQuery(`#${this.refs.select.id}`).select2({
|
||||||
width: (this.props.width || ''),
|
width: (this.props.width || ''),
|
||||||
templateResult: function (item) {
|
templateResult: function (item) {
|
||||||
if (item.element && item.element.selected) {
|
if (item.element && item.element.selected) {
|
||||||
return null;
|
return null;
|
||||||
} else {
|
} else if (item.title) {
|
||||||
if (item.title) {
|
return item.title;
|
||||||
return item.title;
|
|
||||||
} else {
|
|
||||||
return item.text;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
return item.text;
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -86,14 +83,12 @@ define([
|
|||||||
this.setState({ select2: true });
|
this.setState({ select2: true });
|
||||||
},
|
},
|
||||||
getSelectedValues: function () {
|
getSelectedValues: function () {
|
||||||
if (this.props.field['selected'] !== undefined) {
|
if (this.props.field.selected !== undefined) {
|
||||||
return this.props.field['selected'](this.props.item);
|
return this.props.field.selected(this.props.item);
|
||||||
} else if (this.props.item !== undefined && this.props.field.name !== undefined) {
|
} else if (this.props.item !== undefined && this.props.field.name !== undefined) {
|
||||||
if (this.allowMultipleValues()) {
|
if (this.allowMultipleValues()) {
|
||||||
if (Array.isArray(this.props.item[this.props.field.name])) {
|
if (Array.isArray(this.props.item[this.props.field.name])) {
|
||||||
return this.props.item[this.props.field.name].map((item) => {
|
return this.props.item[this.props.field.name].map(item => item.id);
|
||||||
return item.id;
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
return this.props.item[this.props.field.name];
|
return this.props.item[this.props.field.name];
|
||||||
@ -102,11 +97,15 @@ define([
|
|||||||
return null;
|
return null;
|
||||||
},
|
},
|
||||||
loadCachedItems: function () {
|
loadCachedItems: function () {
|
||||||
if (typeof (window['mailpoet_' + this.props.field.endpoint]) !== 'undefined') {
|
let items;
|
||||||
let items = window['mailpoet_' + this.props.field.endpoint];
|
if (typeof (window[`mailpoet_${this.props.field.endpoint}`]) !== 'undefined') {
|
||||||
|
items = window[`mailpoet_${this.props.field.endpoint}`];
|
||||||
|
} else if (this.props.field.values !== undefined) {
|
||||||
|
items = this.props.field.values;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Array.isArray(items)) {
|
||||||
if (this.props.field['filter'] !== undefined) {
|
if (this.props.field.filter !== undefined) {
|
||||||
items = items.filter(this.props.field.filter);
|
items = items.filter(this.props.field.filter);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -119,7 +118,7 @@ define([
|
|||||||
let value;
|
let value;
|
||||||
if (this.props.onValueChange !== undefined) {
|
if (this.props.onValueChange !== undefined) {
|
||||||
if (this.props.field.multiple) {
|
if (this.props.field.multiple) {
|
||||||
value = jQuery('#' + this.refs.select.id).val();
|
value = jQuery(`#${this.refs.select.id}`).val();
|
||||||
} else {
|
} else {
|
||||||
value = e.target.value;
|
value = e.target.value;
|
||||||
}
|
}
|
||||||
@ -133,19 +132,19 @@ define([
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
getLabel: function (item) {
|
getLabel: function (item) {
|
||||||
if (this.props.field['getLabel'] !== undefined) {
|
if (this.props.field.getLabel !== undefined) {
|
||||||
return this.props.field.getLabel(item, this.props.item);
|
return this.props.field.getLabel(item, this.props.item);
|
||||||
}
|
}
|
||||||
return item.name;
|
return item.name;
|
||||||
},
|
},
|
||||||
getSearchLabel: function (item) {
|
getSearchLabel: function (item) {
|
||||||
if (this.props.field['getSearchLabel'] !== undefined) {
|
if (this.props.field.getSearchLabel !== undefined) {
|
||||||
return this.props.field.getSearchLabel(item, this.props.item);
|
return this.props.field.getSearchLabel(item, this.props.item);
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
},
|
},
|
||||||
getValue: function (item) {
|
getValue: function (item) {
|
||||||
if (this.props.field['getValue'] !== undefined) {
|
if (this.props.field.getValue !== undefined) {
|
||||||
return this.props.field.getValue(item, this.props.item);
|
return this.props.field.getValue(item, this.props.item);
|
||||||
}
|
}
|
||||||
return item.id;
|
return item.id;
|
||||||
@ -154,11 +153,18 @@ define([
|
|||||||
// this function may be used to transform the placeholder value into
|
// this function may be used to transform the placeholder value into
|
||||||
// desired value.
|
// desired value.
|
||||||
transformChangedValue: function (value) {
|
transformChangedValue: function (value) {
|
||||||
if (typeof this.props.field['transformChangedValue'] === 'function') {
|
if (typeof this.props.field.transformChangedValue === 'function') {
|
||||||
return this.props.field.transformChangedValue.call(this, value);
|
return this.props.field.transformChangedValue.call(this, value);
|
||||||
} else {
|
|
||||||
return value;
|
|
||||||
}
|
}
|
||||||
|
return value;
|
||||||
|
},
|
||||||
|
insertEmptyOption: function () {
|
||||||
|
// https://select2.org/placeholders
|
||||||
|
// For single selects only, in order for the placeholder value to appear,
|
||||||
|
// we must have a blank <option> as the first option in the <select> control.
|
||||||
|
if (this.allowMultipleValues()) return undefined;
|
||||||
|
if (this.props.field.placeholder) return (<option />);
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const options = this.state.items.map((item, index) => {
|
const options = this.state.items.map((item, index) => {
|
||||||
@ -168,7 +174,7 @@ define([
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<option
|
<option
|
||||||
key={'option-' + index}
|
key={`option-${index}`}
|
||||||
value={value}
|
value={value}
|
||||||
title={searchLabel}
|
title={searchLabel}
|
||||||
>
|
>
|
||||||
@ -186,7 +192,10 @@ define([
|
|||||||
multiple={this.props.field.multiple}
|
multiple={this.props.field.multiple}
|
||||||
defaultValue={this.getSelectedValues()}
|
defaultValue={this.getSelectedValues()}
|
||||||
{...this.props.field.validation}
|
{...this.props.field.validation}
|
||||||
>{ options }</select>
|
>
|
||||||
|
{ this.insertEmptyOption() }
|
||||||
|
{ options }
|
||||||
|
</select>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
@ -11,7 +11,7 @@ const FormFieldText = React.createClass({
|
|||||||
<input
|
<input
|
||||||
type="text"
|
type="text"
|
||||||
disabled={
|
disabled={
|
||||||
(this.props.field['disabled'] !== undefined)
|
(this.props.field.disabled !== undefined)
|
||||||
? this.props.field.disabled(this.props.item)
|
? this.props.field.disabled(this.props.item)
|
||||||
: false
|
: false
|
||||||
}
|
}
|
||||||
@ -22,7 +22,7 @@ const FormFieldText = React.createClass({
|
|||||||
: false
|
: false
|
||||||
}
|
}
|
||||||
name={this.props.field.name}
|
name={this.props.field.name}
|
||||||
id={'field_' + this.props.field.name}
|
id={`field_${this.props.field.name}`}
|
||||||
value={value}
|
value={value}
|
||||||
placeholder={this.props.field.placeholder}
|
placeholder={this.props.field.placeholder}
|
||||||
onChange={this.props.onValueChange}
|
onChange={this.props.onValueChange}
|
||||||
|
@ -11,7 +11,7 @@ define([
|
|||||||
type="text"
|
type="text"
|
||||||
className="regular-text"
|
className="regular-text"
|
||||||
name={this.props.field.name}
|
name={this.props.field.name}
|
||||||
id={'field_' + this.props.field.name}
|
id={`field_${this.props.field.name}`}
|
||||||
value={this.props.item[this.props.field.name]}
|
value={this.props.item[this.props.field.name]}
|
||||||
placeholder={this.props.field.placeholder}
|
placeholder={this.props.field.placeholder}
|
||||||
defaultValue={this.props.field.defaultValue}
|
defaultValue={this.props.field.defaultValue}
|
||||||
|
@ -15,7 +15,6 @@ define(
|
|||||||
FormField,
|
FormField,
|
||||||
jQuery
|
jQuery
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const Form = React.createClass({
|
const Form = React.createClass({
|
||||||
contextTypes: {
|
contextTypes: {
|
||||||
router: React.PropTypes.object.isRequired,
|
router: React.PropTypes.object.isRequired,
|
||||||
@ -44,7 +43,7 @@ define(
|
|||||||
this.loadItem(this.props.params.id);
|
this.loadItem(this.props.params.id);
|
||||||
} else {
|
} else {
|
||||||
this.setState({
|
this.setState({
|
||||||
item: jQuery('.mailpoet_form').serializeObject(),
|
item: jQuery('.mailpoet_form').mailpoetSerializeObject(),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -58,8 +57,6 @@ define(
|
|||||||
if (props.item === undefined) {
|
if (props.item === undefined) {
|
||||||
this.refs.form.reset();
|
this.refs.form.reset();
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
this.loadItem(props.params.id);
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
loadItem: function (id) {
|
loadItem: function (id) {
|
||||||
@ -77,6 +74,9 @@ define(
|
|||||||
loading: false,
|
loading: false,
|
||||||
item: response.data,
|
item: response.data,
|
||||||
});
|
});
|
||||||
|
if (typeof this.props.onItemLoad === 'function') {
|
||||||
|
this.props.onItemLoad(response.data);
|
||||||
|
}
|
||||||
}).fail(() => {
|
}).fail(() => {
|
||||||
this.setState({
|
this.setState({
|
||||||
loading: false,
|
loading: false,
|
||||||
@ -100,9 +100,9 @@ define(
|
|||||||
|
|
||||||
// only get values from displayed fields
|
// only get values from displayed fields
|
||||||
const item = {};
|
const item = {};
|
||||||
this.props.fields.map((field) => {
|
this.props.fields.forEach((field) => {
|
||||||
if (field['fields'] !== undefined) {
|
if (field.fields !== undefined) {
|
||||||
field.fields.map((subfield) => {
|
field.fields.forEach((subfield) => {
|
||||||
item[subfield.name] = this.state.item[subfield.name];
|
item[subfield.name] = this.state.item[subfield.name];
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
@ -142,28 +142,25 @@ define(
|
|||||||
handleValueChange: function (e) {
|
handleValueChange: function (e) {
|
||||||
if (this.props.onChange) {
|
if (this.props.onChange) {
|
||||||
return this.props.onChange(e);
|
return this.props.onChange(e);
|
||||||
} else {
|
|
||||||
const item = this.state.item;
|
|
||||||
const field = e.target.name;
|
|
||||||
|
|
||||||
item[field] = e.target.value;
|
|
||||||
|
|
||||||
this.setState({
|
|
||||||
item: item,
|
|
||||||
});
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
const item = this.state.item;
|
||||||
|
const field = e.target.name;
|
||||||
|
|
||||||
|
item[field] = e.target.value;
|
||||||
|
|
||||||
|
this.setState({
|
||||||
|
item: item,
|
||||||
|
});
|
||||||
|
return true;
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
let errors;
|
let errors;
|
||||||
if (this.getErrors() !== undefined) {
|
if (this.getErrors() !== undefined) {
|
||||||
errors = this.getErrors().map((error, index) => {
|
errors = this.getErrors().map((error, index) => (
|
||||||
return (
|
<p key={`error-${index}`} className="mailpoet_error">
|
||||||
<p key={'error-' + index} className="mailpoet_error">
|
{ error.message }
|
||||||
{ error.message }
|
</p>
|
||||||
</p>
|
));
|
||||||
);
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const formClasses = classNames(
|
const formClasses = classNames(
|
||||||
@ -197,7 +194,7 @@ define(
|
|||||||
field={field}
|
field={field}
|
||||||
item={this.getValues()}
|
item={this.getValues()}
|
||||||
onValueChange={onValueChange}
|
onValueChange={onValueChange}
|
||||||
key={'field-' + i} />
|
key={`field-${i}`} />
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/*
|
/*
|
||||||
* name: MailPoet Form Editor
|
* name: MailPoet Form Editor
|
||||||
* author: Jonathan Labreuille
|
* author: Jonathan Labreuille
|
||||||
@ -7,6 +8,31 @@
|
|||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
|
var Observable;
|
||||||
|
var WysijaHistory;
|
||||||
|
var WysijaForm;
|
||||||
|
|
||||||
|
/* LOGGING */
|
||||||
|
function info(value) {
|
||||||
|
if (WysijaForm.options.debug === false) return;
|
||||||
|
|
||||||
|
if (!(window.console && console.log)) {
|
||||||
|
(function () {
|
||||||
|
var noop = function () {};
|
||||||
|
var methods = ['assert', 'clear', 'count', 'debug', 'dir', 'dirxml', 'error', 'exception', 'group', 'groupCollapsed', 'groupEnd', 'info', 'log', 'markTimeline', 'profile', 'profileEnd', 'markTimeline', 'table', 'time', 'timeEnd', 'timeStamp', 'trace', 'warn'];
|
||||||
|
var length = methods.length;
|
||||||
|
var console = {};
|
||||||
|
window.console = {};
|
||||||
|
while (length--) {
|
||||||
|
console[methods[length]] = noop;
|
||||||
|
}
|
||||||
|
}());
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
console.log('[DEBUG] ' + value);
|
||||||
|
} catch (e) {}
|
||||||
|
}
|
||||||
|
|
||||||
Event.cacheDelegated = {};
|
Event.cacheDelegated = {};
|
||||||
Object.extend(document, (function () {
|
Object.extend(document, (function () {
|
||||||
var cache = Event.cacheDelegated;
|
var cache = Event.cacheDelegated;
|
||||||
@ -30,18 +56,21 @@ Object.extend(document, (function () {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function destroyWrapper(selector, eventName, handler) {
|
function destroyWrapper(selector, eventName, handler) {
|
||||||
|
var wrapper;
|
||||||
var c = getCacheForSelector(selector);
|
var c = getCacheForSelector(selector);
|
||||||
if (!c[eventName]) return false;
|
if (!c[eventName]) return false;
|
||||||
var wrapper = findWrapper(selector, eventName, handler);
|
wrapper = findWrapper(selector, eventName, handler);
|
||||||
c[eventName] = c[eventName].without(wrapper);
|
c[eventName] = c[eventName].without(wrapper);
|
||||||
return wrapper;
|
return wrapper;
|
||||||
}
|
}
|
||||||
|
|
||||||
function createWrapper(selector, eventName, handler, context) {
|
function createWrapper(selector, eventName, handler, context) {
|
||||||
var wrapper, c = getWrappersForSelector(selector, eventName);
|
var wrapper;
|
||||||
|
var element;
|
||||||
|
var c = getWrappersForSelector(selector, eventName);
|
||||||
if (c.pluck('handler').include(handler)) return false;
|
if (c.pluck('handler').include(handler)) return false;
|
||||||
wrapper = function (event) {
|
wrapper = function (event) {
|
||||||
var element = event.findElement(selector);
|
element = event.findElement(selector);
|
||||||
if (element) handler.call(context || element, event, element);
|
if (element) handler.call(context || element, event, element);
|
||||||
};
|
};
|
||||||
wrapper.handler = handler;
|
wrapper.handler = handler;
|
||||||
@ -49,31 +78,32 @@ Object.extend(document, (function () {
|
|||||||
return wrapper;
|
return wrapper;
|
||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
delegate: function (selector, eventName, handler, context) {
|
delegate: function (selector, eventName) {
|
||||||
var wrapper = createWrapper.apply(null, arguments);
|
var wrapper = createWrapper.apply(null, arguments);
|
||||||
if (wrapper) document.observe(eventName, wrapper);
|
if (wrapper) document.observe(eventName, wrapper);
|
||||||
return document;
|
return document;
|
||||||
},
|
},
|
||||||
stopDelegating: function (selector, eventName, handler) {
|
stopDelegating: function (selector, eventName) {
|
||||||
var length = arguments.length;
|
var length = arguments.length;
|
||||||
|
var wrapper;
|
||||||
switch (length) {
|
switch (length) {
|
||||||
case 2:
|
case 2:
|
||||||
getWrappersForSelector(selector, eventName).each(function (wrapper) {
|
getWrappersForSelector(selector, eventName).each(function (selectorWrapper) {
|
||||||
document.stopDelegating(selector, eventName, wrapper.handler);
|
document.stopDelegating(selector, eventName, selectorWrapper.handler);
|
||||||
});
|
});
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
Object.keys(getCacheForSelector(selector)).each(function (eventName) {
|
Object.keys(getCacheForSelector(selector)).each(function (event) {
|
||||||
document.stopDelegating(selector, eventName);
|
document.stopDelegating(selector, event);
|
||||||
});
|
});
|
||||||
break;
|
break;
|
||||||
case 0:
|
case 0:
|
||||||
Object.keys(cache).each(function (selector) {
|
Object.keys(cache).each(function (cacheSelector) {
|
||||||
document.stopDelegating(selector);
|
document.stopDelegating(cacheSelector);
|
||||||
});
|
});
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
var wrapper = destroyWrapper.apply(null, arguments);
|
wrapper = destroyWrapper.apply(null, arguments);
|
||||||
if (wrapper) document.stopObserving(eventName, wrapper);
|
if (wrapper) document.stopObserving(eventName, wrapper);
|
||||||
}
|
}
|
||||||
return document;
|
return document;
|
||||||
@ -81,16 +111,22 @@ Object.extend(document, (function () {
|
|||||||
};
|
};
|
||||||
})());
|
})());
|
||||||
|
|
||||||
var Observable = (function () {
|
Observable = (function () {
|
||||||
function getEventName(nameA, namespace) {
|
function getEventName(nameA, namespace) {
|
||||||
var name = nameA.substring(2);
|
var name = nameA.substring(2);
|
||||||
if (namespace) name = namespace + ':' + name;
|
if (namespace) name = namespace + ':' + name;
|
||||||
return name.underscore().split('_').join(':');
|
return name.underscore().split('_').join(':');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getWrapper(handler, klass) {
|
||||||
|
return function (event) {
|
||||||
|
return handler.call(new klass(this), event, event.memo);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
function getHandlers(klass) {
|
function getHandlers(klass) {
|
||||||
var proto = klass.prototype,
|
var proto = klass.prototype;
|
||||||
namespace = proto.namespace;
|
var namespace = proto.namespace;
|
||||||
return Object.keys(proto).grep(/^on/).inject(window.$H(), function (handlers, name) {
|
return Object.keys(proto).grep(/^on/).inject(window.$H(), function (handlers, name) {
|
||||||
if (name === 'onDomLoaded') return handlers;
|
if (name === 'onDomLoaded') return handlers;
|
||||||
handlers.set(getEventName(name, namespace), getWrapper(proto[name], klass));
|
handlers.set(getEventName(name, namespace), getWrapper(proto[name], klass));
|
||||||
@ -98,12 +134,6 @@ var Observable = (function () {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function getWrapper(handler, klass) {
|
|
||||||
return function (event) {
|
|
||||||
return handler.call(new klass(this), event, event.memo);
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
function onDomLoad(selector, klass) {
|
function onDomLoad(selector, klass) {
|
||||||
window.$$(selector).each(function (element) {
|
window.$$(selector).each(function (element) {
|
||||||
new klass(element).onDomLoaded();
|
new klass(element).onDomLoaded();
|
||||||
@ -111,9 +141,9 @@ var Observable = (function () {
|
|||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
observe: function (selector) {
|
observe: function (selector) {
|
||||||
|
var klass = this;
|
||||||
if (!this.handlers) this.handlers = {};
|
if (!this.handlers) this.handlers = {};
|
||||||
if (this.handlers[selector]) return;
|
if (this.handlers[selector]) return;
|
||||||
var klass = this;
|
|
||||||
if (this.prototype.onDomLoaded) {
|
if (this.prototype.onDomLoaded) {
|
||||||
if (document.loaded) {
|
if (document.loaded) {
|
||||||
onDomLoad(selector, klass);
|
onDomLoad(selector, klass);
|
||||||
@ -146,10 +176,11 @@ Object.extend(window.Droppables, {
|
|||||||
return proceed(drop);
|
return proceed(drop);
|
||||||
}),
|
}),
|
||||||
show: function (point, element) {
|
show: function (point, element) {
|
||||||
|
var drop;
|
||||||
|
var affected = [];
|
||||||
if (!this.drops.length) return;
|
if (!this.drops.length) return;
|
||||||
var drop, affected = [];
|
this.drops.each(function (dropsDrop) {
|
||||||
this.drops.each(function (drop) {
|
if (window.Droppables.isAffected(point, element, dropsDrop)) affected.push(dropsDrop);
|
||||||
if (window.Droppables.isAffected(point, element, drop)) affected.push(drop);
|
|
||||||
});
|
});
|
||||||
if (affected.length > 0) drop = window.Droppables.findDeepestChild(affected);
|
if (affected.length > 0) drop = window.Droppables.findDeepestChild(affected);
|
||||||
if (this.last_active && this.last_active !== drop) this.deactivate(this.last_active, element);
|
if (this.last_active && this.last_active !== drop) this.deactivate(this.last_active, element);
|
||||||
@ -159,13 +190,13 @@ Object.extend(window.Droppables, {
|
|||||||
if (drop !== this.last_active) window.Droppables.activate(drop, element);
|
if (drop !== this.last_active) window.Droppables.activate(drop, element);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
displayArea: function (draggable) {
|
displayArea: function () {
|
||||||
if (!this.drops.length) return;
|
if (!this.drops.length) return;
|
||||||
|
|
||||||
// hide controls when displaying drop areas.
|
// hide controls when displaying drop areas.
|
||||||
WysijaForm.hideBlockControls();
|
WysijaForm.hideBlockControls();
|
||||||
|
|
||||||
this.drops.each(function (drop, iterator) {
|
this.drops.each(function (drop) {
|
||||||
if (drop.element.hasClassName('block_placeholder')) {
|
if (drop.element.hasClassName('block_placeholder')) {
|
||||||
drop.element.addClassName('active');
|
drop.element.addClassName('active');
|
||||||
}
|
}
|
||||||
@ -173,7 +204,7 @@ Object.extend(window.Droppables, {
|
|||||||
},
|
},
|
||||||
hideArea: function () {
|
hideArea: function () {
|
||||||
if (!this.drops.length) return;
|
if (!this.drops.length) return;
|
||||||
this.drops.each(function (drop, iterator) {
|
this.drops.each(function (drop) {
|
||||||
if (drop.element.hasClassName('block_placeholder')) {
|
if (drop.element.hasClassName('block_placeholder')) {
|
||||||
drop.element.removeClassName('active');
|
drop.element.removeClassName('active');
|
||||||
} else if (drop.element.hasClassName('image_placeholder')) {
|
} else if (drop.element.hasClassName('image_placeholder')) {
|
||||||
@ -195,7 +226,7 @@ Object.extend(window.Droppables, {
|
|||||||
- set a maximum number of items to be stored
|
- set a maximum number of items to be stored
|
||||||
|
|
||||||
*/
|
*/
|
||||||
var WysijaHistory = {
|
WysijaHistory = {
|
||||||
container: 'mailpoet_form_history',
|
container: 'mailpoet_form_history',
|
||||||
size: 30,
|
size: 30,
|
||||||
enqueue: function (element) {
|
enqueue: function (element) {
|
||||||
@ -239,7 +270,7 @@ var WysijaHistory = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/* MailPoet Form */
|
/* MailPoet Form */
|
||||||
var WysijaForm = {
|
WysijaForm = {
|
||||||
version: '0.7',
|
version: '0.7',
|
||||||
options: {
|
options: {
|
||||||
container: 'mailpoet_form_container',
|
container: 'mailpoet_form_container',
|
||||||
@ -276,8 +307,8 @@ var WysijaForm = {
|
|||||||
return str.replace(/&/g, '&').replace(/>/g, '>').replace(/</g, '<').replace(/"/g, '"');
|
return str.replace(/&/g, '&').replace(/>/g, '>').replace(/</g, '<').replace(/"/g, '"');
|
||||||
// ": fix for FileMerge because the previous line fucks up its syntax coloring
|
// ": fix for FileMerge because the previous line fucks up its syntax coloring
|
||||||
},
|
},
|
||||||
loading: function (is_loading) {
|
loading: function (isLoading) {
|
||||||
if (is_loading) {
|
if (isLoading) {
|
||||||
window.$(WysijaForm.options.editor).addClassName('loading');
|
window.$(WysijaForm.options.editor).addClassName('loading');
|
||||||
window.$(WysijaForm.options.toolbar).addClassName('loading');
|
window.$(WysijaForm.options.toolbar).addClassName('loading');
|
||||||
} else {
|
} else {
|
||||||
@ -292,6 +323,7 @@ var WysijaForm = {
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
load: function (data) {
|
load: function (data) {
|
||||||
|
var settingsElements;
|
||||||
if (data === undefined) return;
|
if (data === undefined) return;
|
||||||
|
|
||||||
// load body
|
// load body
|
||||||
@ -302,8 +334,8 @@ var WysijaForm = {
|
|||||||
});
|
});
|
||||||
|
|
||||||
// load settings
|
// load settings
|
||||||
var settings_elements = window.$('mailpoet_form_settings').getElements();
|
settingsElements = window.$('mailpoet_form_settings').getElements();
|
||||||
settings_elements.each(function (setting) {
|
settingsElements.each(function (setting) {
|
||||||
// skip lists
|
// skip lists
|
||||||
if (setting.name === 'segments') {
|
if (setting.name === 'segments') {
|
||||||
return true;
|
return true;
|
||||||
@ -320,30 +352,31 @@ var WysijaForm = {
|
|||||||
setting.setValue(data.settings[setting.name]);
|
setting.setValue(data.settings[setting.name]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
save: function () {
|
save: function () {
|
||||||
var position = 1,
|
var position = 1;
|
||||||
data = {
|
var data = {
|
||||||
name: window.$F('mailpoet_form_name'),
|
name: window.$F('mailpoet_form_name'),
|
||||||
settings: window.$('mailpoet_form_settings').serialize(true),
|
settings: window.$('mailpoet_form_settings').serialize(true),
|
||||||
body: [],
|
body: [],
|
||||||
styles: (window.MailPoet.CodeEditor !== undefined) ? window.MailPoet.CodeEditor.getValue() : null
|
styles: (window.MailPoet.CodeEditor !== undefined) ? window.MailPoet.CodeEditor.getValue() : null
|
||||||
};
|
};
|
||||||
// body
|
// body
|
||||||
WysijaForm.getBlocks().each(function (b) {
|
WysijaForm.getBlocks().each(function (b) {
|
||||||
var block_data = (typeof (b.block['save']) === 'function') ? b.block.save() : null;
|
var blockData = (typeof (b.block.save) === 'function') ? b.block.save() : null;
|
||||||
|
|
||||||
if (block_data !== null) {
|
if (blockData !== null) {
|
||||||
// set block position
|
// set block position
|
||||||
block_data['position'] = position;
|
blockData.position = position;
|
||||||
|
|
||||||
// increment position
|
// increment position
|
||||||
position++;
|
position++;
|
||||||
|
|
||||||
// add block data to body
|
// add block data to body
|
||||||
data['body'].push(block_data);
|
data.body.push(blockData);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -401,6 +434,7 @@ var WysijaForm = {
|
|||||||
return data;
|
return data;
|
||||||
},
|
},
|
||||||
toggleWidgets: function () {
|
toggleWidgets: function () {
|
||||||
|
var hasSegmentSelection;
|
||||||
window.$$('a[wysija_unique="1"]').invoke('removeClassName', 'disabled');
|
window.$$('a[wysija_unique="1"]').invoke('removeClassName', 'disabled');
|
||||||
|
|
||||||
// loop through each unique field already inserted in the editor and disable its toolbar equivalent
|
// loop through each unique field already inserted in the editor and disable its toolbar equivalent
|
||||||
@ -411,7 +445,7 @@ var WysijaForm = {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var hasSegmentSelection = WysijaForm.hasSegmentSelection();
|
hasSegmentSelection = WysijaForm.hasSegmentSelection();
|
||||||
|
|
||||||
if (hasSegmentSelection) {
|
if (hasSegmentSelection) {
|
||||||
window.$('mailpoet_form_segments').writeAttribute('required', false).disable();
|
window.$('mailpoet_form_segments').writeAttribute('required', false).disable();
|
||||||
@ -425,9 +459,10 @@ var WysijaForm = {
|
|||||||
return (window.$$('#' + WysijaForm.options.editor + ' [wysija_id="segments"]').length > 0);
|
return (window.$$('#' + WysijaForm.options.editor + ' [wysija_id="segments"]').length > 0);
|
||||||
},
|
},
|
||||||
isSegmentSelectionValid: function () {
|
isSegmentSelectionValid: function () {
|
||||||
var segment_selection = window.$$('#' + WysijaForm.options.editor + ' [wysija_id="segments"]')[0];
|
var segmentSelection = window.$$('#' + WysijaForm.options.editor + ' [wysija_id="segments"]')[0];
|
||||||
if (segment_selection !== undefined) {
|
var block;
|
||||||
var block = WysijaForm.get(segment_selection).block.getData();
|
if (segmentSelection !== undefined) {
|
||||||
|
block = WysijaForm.get(segmentSelection).block.getData();
|
||||||
return (
|
return (
|
||||||
(block.params.values !== undefined)
|
(block.params.values !== undefined)
|
||||||
&&
|
&&
|
||||||
@ -437,14 +472,16 @@ var WysijaForm = {
|
|||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
setBlockPositions: function (event, target) {
|
setBlockPositions: function (event, target) {
|
||||||
|
var index = 1;
|
||||||
|
var blockPlaceholder;
|
||||||
|
var previousPlaceholder;
|
||||||
// release dragging lock
|
// release dragging lock
|
||||||
WysijaForm.locks.dragging = false;
|
WysijaForm.locks.dragging = false;
|
||||||
|
|
||||||
var index = 1;
|
|
||||||
WysijaForm.getBlocks().each(function (container) {
|
WysijaForm.getBlocks().each(function (container) {
|
||||||
container.setPosition(index++);
|
container.setPosition(index++);
|
||||||
// remove z-index value to avoid issues when resizing images
|
// remove z-index value to avoid issues when resizing images
|
||||||
if (container['block'] !== undefined) {
|
if (container.block !== undefined) {
|
||||||
container.block.element.setStyle({
|
container.block.element.setStyle({
|
||||||
zIndex: ''
|
zIndex: ''
|
||||||
});
|
});
|
||||||
@ -453,19 +490,19 @@ var WysijaForm = {
|
|||||||
|
|
||||||
if (target !== undefined) {
|
if (target !== undefined) {
|
||||||
// get placeholders (previous placeholder matches the placeholder linked to the next block)
|
// get placeholders (previous placeholder matches the placeholder linked to the next block)
|
||||||
var block_placeholder = window.$(target.element.readAttribute('wysija_placeholder')),
|
blockPlaceholder = window.$(target.element.readAttribute('wysija_placeholder'));
|
||||||
previous_placeholder = target.element.previous('.block_placeholder');
|
previousPlaceholder = target.element.previous('.block_placeholder');
|
||||||
|
|
||||||
if (block_placeholder !== null) {
|
if (blockPlaceholder !== null) {
|
||||||
// put block placeholder before the current block
|
// put block placeholder before the current block
|
||||||
target.element.insert({
|
target.element.insert({
|
||||||
before: block_placeholder
|
before: blockPlaceholder
|
||||||
});
|
});
|
||||||
|
|
||||||
// if the next block is a wysija_block, insert previous placeholder
|
// if the next block is a wysija_block, insert previous placeholder
|
||||||
if (target.element.next() !== undefined && target.element.next().hasClassName('mailpoet_form_block') && previous_placeholder !== undefined) {
|
if (target.element.next() !== undefined && target.element.next().hasClassName('mailpoet_form_block') && previousPlaceholder !== undefined) {
|
||||||
target.element.insert({
|
target.element.insert({
|
||||||
after: previous_placeholder
|
after: previousPlaceholder
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -479,23 +516,17 @@ var WysijaForm = {
|
|||||||
},
|
},
|
||||||
setSettingsPosition: function () {
|
setSettingsPosition: function () {
|
||||||
// get viewport offsets and dimensions
|
// get viewport offsets and dimensions
|
||||||
var viewportHeight = document.viewport.getHeight(),
|
var viewportHeight = document.viewport.getHeight();
|
||||||
blockPadding = 5;
|
|
||||||
|
|
||||||
window.$(WysijaForm.options.container).select('.wysija_settings').each(function (element) {
|
window.$(WysijaForm.options.container).select('.wysija_settings').each(function (element) {
|
||||||
// get parent dimensions and position
|
// get parent dimensions and position
|
||||||
var parentDim = element.up('.mailpoet_form_block').getDimensions(),
|
var parentDim = element.up('.mailpoet_form_block').getDimensions();
|
||||||
parentPos = element.up('.mailpoet_form_block').cumulativeOffset(),
|
var parentPos = element.up('.mailpoet_form_block').cumulativeOffset();
|
||||||
is_visible = (parentPos.top <= (WysijaForm.scroll.top + viewportHeight)),
|
var isVisible = (parentPos.top <= (WysijaForm.scroll.top + viewportHeight));
|
||||||
buttonMargin = 5,
|
var buttonMargin = 5;
|
||||||
relativeTop = buttonMargin;
|
var relativeTop = buttonMargin;
|
||||||
|
|
||||||
if (is_visible) {
|
|
||||||
// desired position is set to center of viewport
|
|
||||||
var absoluteTop = parseInt(WysijaForm.scroll.top + ((viewportHeight / 2) - (element.getHeight() / 2)), 10),
|
|
||||||
parentTop = parseInt(parentPos.top - blockPadding, 10),
|
|
||||||
parentBottom = parseInt(parentPos.top + parentDim.height - blockPadding, 10);
|
|
||||||
|
|
||||||
|
if (isVisible) {
|
||||||
// always center
|
// always center
|
||||||
relativeTop = parseInt((parentDim.height / 2) - (element.getHeight() / 2), 10);
|
relativeTop = parseInt((parentDim.height / 2) - (element.getHeight() / 2), 10);
|
||||||
}
|
}
|
||||||
@ -516,12 +547,12 @@ var WysijaForm = {
|
|||||||
if (WysijaForm.toolbar.left === null) WysijaForm.toolbar.left = parseInt(window.$(WysijaForm.options.container).positionedOffset().left);
|
if (WysijaForm.toolbar.left === null) WysijaForm.toolbar.left = parseInt(window.$(WysijaForm.options.container).positionedOffset().left);
|
||||||
}
|
}
|
||||||
if (WysijaForm.toolbar.x === null) WysijaForm.toolbar.x = parseInt(WysijaForm.toolbar.left + window.$(WysijaForm.options.container).getDimensions().width + 15);
|
if (WysijaForm.toolbar.x === null) WysijaForm.toolbar.x = parseInt(WysijaForm.toolbar.left + window.$(WysijaForm.options.container).getDimensions().width + 15);
|
||||||
|
|
||||||
},
|
},
|
||||||
setToolbarPosition: function () {
|
setToolbarPosition: function () {
|
||||||
|
var position;
|
||||||
WysijaForm.initToolbarPosition();
|
WysijaForm.initToolbarPosition();
|
||||||
|
|
||||||
var position = {
|
position = {
|
||||||
top: WysijaForm.toolbar.y + 'px',
|
top: WysijaForm.toolbar.y + 'px',
|
||||||
visibility: 'visible'
|
visibility: 'visible'
|
||||||
};
|
};
|
||||||
@ -573,10 +604,8 @@ var WysijaForm = {
|
|||||||
},
|
},
|
||||||
hideControls: function () {
|
hideControls: function () {
|
||||||
try {
|
try {
|
||||||
return WysijaForm.getBlocks().invoke('hideControls');
|
WysijaForm.getBlocks().invoke('hideControls');
|
||||||
} catch (e) {
|
} catch (e) {}
|
||||||
return;
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
hideTools: function () {
|
hideTools: function () {
|
||||||
window.$$('.wysija_tools').invoke('hide');
|
window.$$('.wysija_tools').invoke('hide');
|
||||||
@ -585,10 +614,12 @@ var WysijaForm = {
|
|||||||
instances: {},
|
instances: {},
|
||||||
get: function (element, typ) {
|
get: function (element, typ) {
|
||||||
var type = typ;
|
var type = typ;
|
||||||
|
var id;
|
||||||
|
var instance;
|
||||||
if (type === undefined) type = 'block';
|
if (type === undefined) type = 'block';
|
||||||
// identify element
|
// identify element
|
||||||
var id = element.identify();
|
id = element.identify();
|
||||||
var instance = WysijaForm.instances[id] || new WysijaForm[type.capitalize().camelize()](id);
|
instance = WysijaForm.instances[id] || new WysijaForm[type.capitalize().camelize()](id);
|
||||||
|
|
||||||
WysijaForm.instances[id] = instance;
|
WysijaForm.instances[id] = instance;
|
||||||
return instance;
|
return instance;
|
||||||
@ -636,8 +667,8 @@ var WysijaForm = {
|
|||||||
},
|
},
|
||||||
encodeURIComponent: function (str) {
|
encodeURIComponent: function (str) {
|
||||||
// check if it's a url and if so, prevent encoding of protocol
|
// check if it's a url and if so, prevent encoding of protocol
|
||||||
var regexp = new RegExp(/^http[s]?:\/\//),
|
var regexp = new RegExp(/^http[s]?:\/\//);
|
||||||
protocol = regexp.exec(str);
|
var protocol = regexp.exec(str);
|
||||||
|
|
||||||
if (protocol === null) {
|
if (protocol === null) {
|
||||||
// this is not a url so encode the whole thing
|
// this is not a url so encode the whole thing
|
||||||
@ -646,6 +677,7 @@ var WysijaForm = {
|
|||||||
// this is a url, so do not encode the protocol
|
// this is a url, so do not encode the protocol
|
||||||
return encodeURI(str).replace(/[!'()*]/g, escape);
|
return encodeURI(str).replace(/[!'()*]/g, escape);
|
||||||
}
|
}
|
||||||
|
return str;
|
||||||
},
|
},
|
||||||
updateBlock: function (field) {
|
updateBlock: function (field) {
|
||||||
var hasUpdated = false;
|
var hasUpdated = false;
|
||||||
@ -680,13 +712,13 @@ WysijaForm.DraggableItem = window.Class.create({
|
|||||||
},
|
},
|
||||||
STYLES: new window.Template('position: absolute; top: #{top}px; left: #{left}px;'),
|
STYLES: new window.Template('position: absolute; top: #{top}px; left: #{left}px;'),
|
||||||
cloneElement: function () {
|
cloneElement: function () {
|
||||||
var clone = this.element.clone(),
|
var clone = this.element.clone();
|
||||||
offset = this.element.cumulativeOffset(),
|
var offset = this.element.cumulativeOffset();
|
||||||
list = this.getList(),
|
var list = this.getList();
|
||||||
styles = this.STYLES.evaluate({
|
var styles = this.STYLES.evaluate({
|
||||||
top: offset.top - list.scrollTop,
|
top: offset.top - list.scrollTop,
|
||||||
left: offset.left - list.scrollLeft
|
left: offset.left - list.scrollLeft
|
||||||
});
|
});
|
||||||
clone.setStyle(styles);
|
clone.setStyle(styles);
|
||||||
|
|
||||||
clone.addClassName('mailpoet_form_widget');
|
clone.addClassName('mailpoet_form_widget');
|
||||||
@ -743,7 +775,7 @@ WysijaForm.Block = window.Class.create({
|
|||||||
this.block.makeBlockDroppable();
|
this.block.makeBlockDroppable();
|
||||||
|
|
||||||
// setup events
|
// setup events
|
||||||
if (this.block['setup'] !== undefined) {
|
if (this.block.setup !== undefined) {
|
||||||
this.block.setup();
|
this.block.setup();
|
||||||
}
|
}
|
||||||
return this;
|
return this;
|
||||||
@ -752,13 +784,13 @@ WysijaForm.Block = window.Class.create({
|
|||||||
this.element.writeAttribute('wysija_position', position);
|
this.element.writeAttribute('wysija_position', position);
|
||||||
},
|
},
|
||||||
hideControls: function () {
|
hideControls: function () {
|
||||||
if (this['getControls']) {
|
if (this.getControls) {
|
||||||
this.element.removeClassName('hover');
|
this.element.removeClassName('hover');
|
||||||
this.getControls().hide();
|
this.getControls().hide();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
showControls: function () {
|
showControls: function () {
|
||||||
if (this['getControls']) {
|
if (this.getControls) {
|
||||||
this.element.addClassName('hover');
|
this.element.addClassName('hover');
|
||||||
try {
|
try {
|
||||||
this.getControls().show();
|
this.getControls().show();
|
||||||
@ -767,27 +799,28 @@ WysijaForm.Block = window.Class.create({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
makeBlockDroppable: function () {
|
makeBlockDroppable: function () {
|
||||||
|
var blockPlaceholder;
|
||||||
if (this.isBlockDroppableEnabled() === false) {
|
if (this.isBlockDroppableEnabled() === false) {
|
||||||
var block_placeholder = this.getBlockDroppable();
|
blockPlaceholder = this.getBlockDroppable();
|
||||||
window.Droppables.add(block_placeholder.identify(), WysijaForm.blockDropOptions);
|
window.Droppables.add(blockPlaceholder.identify(), WysijaForm.blockDropOptions);
|
||||||
block_placeholder.addClassName('enabled');
|
blockPlaceholder.addClassName('enabled');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
removeBlockDroppable: function () {
|
removeBlockDroppable: function () {
|
||||||
|
var blockPlaceholder;
|
||||||
if (this.isBlockDroppableEnabled()) {
|
if (this.isBlockDroppableEnabled()) {
|
||||||
var block_placeholder = this.getBlockDroppable();
|
blockPlaceholder = this.getBlockDroppable();
|
||||||
window.Droppables.remove(block_placeholder.identify());
|
window.Droppables.remove(blockPlaceholder.identify());
|
||||||
block_placeholder.removeClassName('enabled');
|
blockPlaceholder.removeClassName('enabled');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
isBlockDroppableEnabled: function () {
|
isBlockDroppableEnabled: function () {
|
||||||
// if the block_placeholder does not exist, create it
|
// if the block_placeholder does not exist, create it
|
||||||
var block_placeholder = this.getBlockDroppable();
|
var blockPlaceholder = this.getBlockDroppable();
|
||||||
if (block_placeholder === null) {
|
if (blockPlaceholder === null) {
|
||||||
return this.createBlockDroppable().hasClassName('enabled');
|
return this.createBlockDroppable().hasClassName('enabled');
|
||||||
} else {
|
|
||||||
return block_placeholder.hasClassName('enabled');
|
|
||||||
}
|
}
|
||||||
|
return blockPlaceholder.hasClassName('enabled');
|
||||||
},
|
},
|
||||||
createBlockDroppable: function () {
|
createBlockDroppable: function () {
|
||||||
info('block -> createBlockDroppable');
|
info('block -> createBlockDroppable');
|
||||||
@ -799,14 +832,14 @@ WysijaForm.Block = window.Class.create({
|
|||||||
getBlockDroppable: function () {
|
getBlockDroppable: function () {
|
||||||
if (this.element.previous() === undefined || this.element.previous().hasClassName('block_placeholder') === false) {
|
if (this.element.previous() === undefined || this.element.previous().hasClassName('block_placeholder') === false) {
|
||||||
return null;
|
return null;
|
||||||
} else {
|
|
||||||
return this.element.previous();
|
|
||||||
}
|
}
|
||||||
|
return this.element.previous();
|
||||||
},
|
},
|
||||||
getControls: function () {
|
getControls: function () {
|
||||||
return this.element.down('.wysija_controls');
|
return this.element.down('.wysija_controls');
|
||||||
},
|
},
|
||||||
setupControls: function () {
|
setupControls: function () {
|
||||||
|
var block;
|
||||||
// enable controls
|
// enable controls
|
||||||
this.controls = this.getControls();
|
this.controls = this.getControls();
|
||||||
|
|
||||||
@ -857,9 +890,8 @@ WysijaForm.Block = window.Class.create({
|
|||||||
if (this.settingsButton !== null) {
|
if (this.settingsButton !== null) {
|
||||||
this.settingsButton.observe('click', function (event) {
|
this.settingsButton.observe('click', function (event) {
|
||||||
// TODO: refactor
|
// TODO: refactor
|
||||||
var block = window.$(event.target).up('.mailpoet_form_block') || null;
|
block = window.$(event.target).up('.mailpoet_form_block') || null;
|
||||||
if (block !== null) {
|
if (block !== null) {
|
||||||
var field = WysijaForm.getFieldData(block);
|
|
||||||
this.editSettings();
|
this.editSettings();
|
||||||
}
|
}
|
||||||
}.bind(this));
|
}.bind(this));
|
||||||
@ -905,21 +937,26 @@ WysijaForm.Block = window.Class.create({
|
|||||||
/* Invoked on item dropped */
|
/* Invoked on item dropped */
|
||||||
WysijaForm.Block.create = function (createBlock, target) {
|
WysijaForm.Block.create = function (createBlock, target) {
|
||||||
var block = createBlock;
|
var block = createBlock;
|
||||||
|
var body;
|
||||||
|
var blockTemplate;
|
||||||
|
var template;
|
||||||
|
var output;
|
||||||
|
var settingsSegments;
|
||||||
if (window.$('form_template_' + block.type) === null) {
|
if (window.$('form_template_' + block.type) === null) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
var body = window.$(WysijaForm.options.body),
|
body = window.$(WysijaForm.options.body);
|
||||||
block_template = window.Handlebars.compile(window.$('form_template_block').innerHTML),
|
blockTemplate = window.Handlebars.compile(window.$('form_template_block').innerHTML);
|
||||||
template = window.Handlebars.compile(window.$('form_template_' + block.type).innerHTML),
|
template = window.Handlebars.compile(window.$('form_template_' + block.type).innerHTML);
|
||||||
output = '';
|
output = '';
|
||||||
|
|
||||||
if (block.type === 'segment') {
|
if (block.type === 'segment') {
|
||||||
if (block.params.values === undefined) {
|
if (block.params.values === undefined) {
|
||||||
var settings_segments = window.jQuery('#mailpoet_form_segments').val();
|
settingsSegments = window.jQuery('#mailpoet_form_segments').val();
|
||||||
if (settings_segments !== null && settings_segments.length > 0) {
|
if (settingsSegments !== null && settingsSegments.length > 0) {
|
||||||
block.params.values = window.mailpoet_segments.filter(function (segment) {
|
block.params.values = window.mailpoet_segments.filter(function (segment) {
|
||||||
return (settings_segments.indexOf(segment.id) !== -1);
|
return (settingsSegments.indexOf(segment.id) !== -1);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -927,7 +964,7 @@ WysijaForm.Block.create = function (createBlock, target) {
|
|||||||
|
|
||||||
// set block template (depending on the block type)
|
// set block template (depending on the block type)
|
||||||
block.template = template(block);
|
block.template = template(block);
|
||||||
output = block_template(block);
|
output = blockTemplate(block);
|
||||||
|
|
||||||
// check if the new block is unique and if there's already an instance
|
// check if the new block is unique and if there's already an instance
|
||||||
// of it in the history. If so, remove its former instance from the history
|
// of it in the history. If so, remove its former instance from the history
|
||||||
@ -936,14 +973,13 @@ WysijaForm.Block.create = function (createBlock, target) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// if the drop target was the bottom placeholder
|
// if the drop target was the bottom placeholder
|
||||||
var element = null;
|
|
||||||
if (target.identify() === 'block_placeholder') {
|
if (target.identify() === 'block_placeholder') {
|
||||||
// insert block at the bottom
|
// insert block at the bottom
|
||||||
element = body.insert(output);
|
body.insert(output);
|
||||||
// block = body.childElements().last();
|
// block = body.childElements().last();
|
||||||
} else {
|
} else {
|
||||||
// insert block before the drop target
|
// insert block before the drop target
|
||||||
element = target.insert({
|
target.insert({
|
||||||
before: output
|
before: output
|
||||||
});
|
});
|
||||||
// block = target.previous('.mailpoet_form_block');
|
// block = target.previous('.mailpoet_form_block');
|
||||||
@ -956,6 +992,7 @@ WysijaForm.Block.create = function (createBlock, target) {
|
|||||||
|
|
||||||
// position settings
|
// position settings
|
||||||
WysijaForm.setSettingsPosition();
|
WysijaForm.setSettingsPosition();
|
||||||
|
return true;
|
||||||
};
|
};
|
||||||
|
|
||||||
document.observe('wjfe:item:drop', function (event) {
|
document.observe('wjfe:item:drop', function (event) {
|
||||||
@ -984,8 +1021,8 @@ WysijaForm.Widget = window.Class.create(WysijaForm.Block, {
|
|||||||
this.setupControls();
|
this.setupControls();
|
||||||
},
|
},
|
||||||
save: function () {
|
save: function () {
|
||||||
info('widget -> save');
|
|
||||||
var data = this.getData();
|
var data = this.getData();
|
||||||
|
info('widget -> save');
|
||||||
|
|
||||||
if (data.element !== undefined) {
|
if (data.element !== undefined) {
|
||||||
delete data.element;
|
delete data.element;
|
||||||
@ -994,11 +1031,11 @@ WysijaForm.Widget = window.Class.create(WysijaForm.Block, {
|
|||||||
return data;
|
return data;
|
||||||
},
|
},
|
||||||
setData: function (data) {
|
setData: function (data) {
|
||||||
var current_data = this.getData(),
|
var currentData = this.getData();
|
||||||
params = window.$H(current_data.params).merge(data.params).toObject();
|
var params = window.$H(currentData.params).merge(data.params).toObject();
|
||||||
|
|
||||||
// update type if it changed
|
// update type if it changed
|
||||||
if (data.type !== undefined && data.type !== current_data.type) {
|
if (data.type !== undefined && data.type !== currentData.type) {
|
||||||
this.element.writeAttribute('wysija_type', data.type);
|
this.element.writeAttribute('wysija_type', data.type);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1020,16 +1057,20 @@ WysijaForm.Widget = window.Class.create(WysijaForm.Block, {
|
|||||||
this.removeBlock();
|
this.removeBlock();
|
||||||
},
|
},
|
||||||
redraw: function (data) {
|
redraw: function (data) {
|
||||||
|
var options;
|
||||||
|
var blockTemplate;
|
||||||
|
var template;
|
||||||
|
var params;
|
||||||
// set parameters
|
// set parameters
|
||||||
this.setData(data);
|
this.setData(data);
|
||||||
var options = this.getData();
|
options = this.getData();
|
||||||
// redraw block
|
// redraw block
|
||||||
var block_template = window.Handlebars.compile(window.$('form_template_block').innerHTML),
|
blockTemplate = window.Handlebars.compile(window.$('form_template_block').innerHTML);
|
||||||
template = window.Handlebars.compile(window.$('form_template_' + options.type).innerHTML),
|
template = window.Handlebars.compile(window.$('form_template_' + options.type).innerHTML);
|
||||||
data = window.$H(options).merge({
|
params = window.$H(options).merge({
|
||||||
template: template(options)
|
template: template(options)
|
||||||
}).toObject();
|
}).toObject();
|
||||||
this.element.replace(block_template(data));
|
this.element.replace(blockTemplate(params));
|
||||||
|
|
||||||
WysijaForm.init();
|
WysijaForm.init();
|
||||||
},
|
},
|
||||||
@ -1039,7 +1080,7 @@ WysijaForm.Widget = window.Class.create(WysijaForm.Block, {
|
|||||||
template: window.jQuery('#form_template_field_settings').html(),
|
template: window.jQuery('#form_template_field_settings').html(),
|
||||||
data: this.getData(),
|
data: this.getData(),
|
||||||
onSuccess: function () {
|
onSuccess: function () {
|
||||||
var data = window.jQuery('#form_field_settings').serializeObject();
|
var data = window.jQuery('#form_field_settings').mailpoetSerializeObject();
|
||||||
this.redraw(data);
|
this.redraw(data);
|
||||||
}.bind(this)
|
}.bind(this)
|
||||||
});
|
});
|
||||||
@ -1052,25 +1093,4 @@ WysijaForm.Widget = window.Class.create(WysijaForm.Block, {
|
|||||||
/* When dom is loaded, initialize WysijaForm */
|
/* When dom is loaded, initialize WysijaForm */
|
||||||
document.observe('dom:loaded', WysijaForm.init);
|
document.observe('dom:loaded', WysijaForm.init);
|
||||||
|
|
||||||
/* LOGGING */
|
|
||||||
function info(value) {
|
|
||||||
if (WysijaForm.options.debug === false) return;
|
|
||||||
|
|
||||||
if (!(window.console && console.log)) {
|
|
||||||
(function () {
|
|
||||||
var noop = function () {};
|
|
||||||
var methods = ['assert', 'clear', 'count', 'debug', 'dir', 'dirxml', 'error', 'exception', 'group', 'groupCollapsed', 'groupEnd', 'info', 'log', 'markTimeline', 'profile', 'profileEnd', 'markTimeline', 'table', 'time', 'timeEnd', 'timeStamp', 'trace', 'warn'];
|
|
||||||
var length = methods.length;
|
|
||||||
window.console = {};
|
|
||||||
var console = {};
|
|
||||||
while (length--) {
|
|
||||||
console[methods[length]] = noop;
|
|
||||||
}
|
|
||||||
}());
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
console.log('[DEBUG] ' + value);
|
|
||||||
} catch (e) {}
|
|
||||||
}
|
|
||||||
|
|
||||||
module.exports = WysijaForm;
|
module.exports = WysijaForm;
|
||||||
|
@ -27,7 +27,7 @@ const columns = [
|
|||||||
|
|
||||||
const messages = {
|
const messages = {
|
||||||
onTrash: (response) => {
|
onTrash: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -42,7 +42,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onDelete: (response) => {
|
onDelete: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -57,7 +57,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onRestore: (response) => {
|
onRestore: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -73,7 +73,7 @@ const messages = {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
const bulk_actions = [
|
const bulkActions = [
|
||||||
{
|
{
|
||||||
name: 'trash',
|
name: 'trash',
|
||||||
label: MailPoet.I18n.t('moveToTrash'),
|
label: MailPoet.I18n.t('moveToTrash'),
|
||||||
@ -81,7 +81,7 @@ const bulk_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const item_actions = [
|
const itemActions = [
|
||||||
{
|
{
|
||||||
name: 'edit',
|
name: 'edit',
|
||||||
label: MailPoet.I18n.t('edit'),
|
label: MailPoet.I18n.t('edit'),
|
||||||
@ -110,7 +110,7 @@ const item_actions = [
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -133,32 +133,31 @@ const FormList = React.createClass({
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
renderItem(form, actions) {
|
renderItem(form, actions) {
|
||||||
const row_classes = classNames(
|
const rowClasses = classNames(
|
||||||
'manage-column',
|
'manage-column',
|
||||||
'column-primary',
|
'column-primary',
|
||||||
'has-row-actions'
|
'has-row-actions'
|
||||||
);
|
);
|
||||||
|
|
||||||
let segments = window.mailpoet_segments.filter((segment) => {
|
let segments = window.mailpoet_segments
|
||||||
return (jQuery.inArray(segment.id, form.segments) !== -1);
|
.filter(segment => (jQuery.inArray(segment.id, form.segments) !== -1))
|
||||||
}).map((segment) => {
|
.map(segment => segment.name)
|
||||||
return segment.name;
|
.join(', ');
|
||||||
}).join(', ');
|
|
||||||
|
|
||||||
if (form.settings.segments_selected_by === 'user') {
|
if (form.settings.segments_selected_by === 'user') {
|
||||||
segments = MailPoet.I18n.t('userChoice') + ' ' + segments;
|
segments = `${MailPoet.I18n.t('userChoice')} ${segments}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<td className={row_classes}>
|
<td className={rowClasses}>
|
||||||
<strong>
|
<strong>
|
||||||
<a
|
<a
|
||||||
className="row-title"
|
className="row-title"
|
||||||
@ -199,8 +198,8 @@ const FormList = React.createClass({
|
|||||||
endpoint="forms"
|
endpoint="forms"
|
||||||
onRenderItem={this.renderItem}
|
onRenderItem={this.renderItem}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
item_actions={item_actions}
|
item_actions={itemActions}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -1,34 +1,35 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
||||||
// Handlebars helpers
|
// Handlebars helpers
|
||||||
Handlebars.registerHelper('concat', function () {
|
Handlebars.registerHelper('concat', function () {
|
||||||
var size = (arguments.length - 1),
|
var size = (arguments.length - 1);
|
||||||
output = '';
|
var output = '';
|
||||||
for (var i = 0; i < size; i++) {
|
var i;
|
||||||
|
for (i = 0; i < size; i++) {
|
||||||
output += arguments[i];
|
output += arguments[i];
|
||||||
}
|
}
|
||||||
return output;
|
return output;
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('number_format', function (value, block) {
|
Handlebars.registerHelper('number_format', function (value) {
|
||||||
return Number(value).toLocaleString();
|
return Number(value).toLocaleString();
|
||||||
});
|
});
|
||||||
Handlebars.registerHelper('date_format', function (timestamp, block) {
|
Handlebars.registerHelper('date_format', function (timestamp, block) {
|
||||||
|
var f;
|
||||||
if (window.moment) {
|
if (window.moment) {
|
||||||
if (timestamp === undefined || isNaN(timestamp) || timestamp <= 0) {
|
if (timestamp === undefined || isNaN(timestamp) || timestamp <= 0) {
|
||||||
return;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
// set date format
|
// set date format
|
||||||
var f = block.hash.format || 'MMM Do, YYYY';
|
f = block.hash.format || 'MMM Do, YYYY';
|
||||||
// check if we passed a timestamp
|
// check if we passed a timestamp
|
||||||
if (parseInt(timestamp, 10) == timestamp) {
|
if (parseInt(timestamp, 10) == timestamp) {
|
||||||
return window.moment.unix(timestamp).format(f);
|
return window.moment.unix(timestamp).format(f);
|
||||||
} else {
|
|
||||||
return window.moment.utc(timestamp).format(f);
|
|
||||||
}
|
}
|
||||||
} else {
|
return window.moment.utc(timestamp).format(f);
|
||||||
return timestamp;
|
|
||||||
}
|
}
|
||||||
|
return timestamp;
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('cycle', function (value, block) {
|
Handlebars.registerHelper('cycle', function (value, block) {
|
||||||
@ -59,25 +60,24 @@ define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
|||||||
case '||':
|
case '||':
|
||||||
return (v1 || v2) ? options.fn(this) : options.inverse(this);
|
return (v1 || v2) ? options.fn(this) : options.inverse(this);
|
||||||
case 'in':
|
case 'in':
|
||||||
var values = v2.split(',');
|
|
||||||
return (v2.indexOf(v1) !== -1) ? options.fn(this) : options.inverse(this);
|
return (v2.indexOf(v1) !== -1) ? options.fn(this) : options.inverse(this);
|
||||||
default:
|
default:
|
||||||
return options.inverse(this);
|
return options.inverse(this);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('nl2br', function (value, block) {
|
Handlebars.registerHelper('nl2br', function (value) {
|
||||||
return value.gsub('\n', '<br />');
|
return value.gsub('\n', '<br />');
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('json_encode', function (value, block) {
|
Handlebars.registerHelper('json_encode', function (value) {
|
||||||
return JSON.stringify(value);
|
return JSON.stringify(value);
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('json_decode', function (value, block) {
|
Handlebars.registerHelper('json_decode', function (value) {
|
||||||
return JSON.parse(value);
|
return JSON.parse(value);
|
||||||
});
|
});
|
||||||
Handlebars.registerHelper('url', function (value, block) {
|
Handlebars.registerHelper('url', function (value) {
|
||||||
var url = window.location.protocol + '//' + window.location.host + window.location.pathname;
|
var url = window.location.protocol + '//' + window.location.host + window.location.pathname;
|
||||||
|
|
||||||
return url + value;
|
return url + value;
|
||||||
@ -86,20 +86,20 @@ define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
|||||||
var mailtoMatchingRegex = /^mailto\:/i;
|
var mailtoMatchingRegex = /^mailto\:/i;
|
||||||
if (typeof value === 'string' && value.match(mailtoMatchingRegex)) {
|
if (typeof value === 'string' && value.match(mailtoMatchingRegex)) {
|
||||||
return value.replace(mailtoMatchingRegex, '');
|
return value.replace(mailtoMatchingRegex, '');
|
||||||
} else {
|
|
||||||
return value;
|
|
||||||
}
|
}
|
||||||
|
return value;
|
||||||
});
|
});
|
||||||
Handlebars.registerHelper('lookup', function (obj, field, options) {
|
Handlebars.registerHelper('lookup', function (obj, field) {
|
||||||
return obj && obj[field];
|
return obj && obj[field];
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
Handlebars.registerHelper('rsa_key', function (value, block) {
|
Handlebars.registerHelper('rsa_key', function (value) {
|
||||||
// extract all lines into an array
|
var lines;
|
||||||
|
// extract all lines into an array
|
||||||
if (value === undefined) return '';
|
if (value === undefined) return '';
|
||||||
|
|
||||||
var lines = value.trim().split('\n');
|
lines = value.trim().split('\n');
|
||||||
|
|
||||||
// remove header & footer
|
// remove header & footer
|
||||||
lines.shift();
|
lines.shift();
|
||||||
@ -109,7 +109,7 @@ define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
|||||||
return lines.join('');
|
return lines.join('');
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('trim', function (value, block) {
|
Handlebars.registerHelper('trim', function (value) {
|
||||||
if (value === null || value === undefined) return '';
|
if (value === null || value === undefined) return '';
|
||||||
return value.trim();
|
return value.trim();
|
||||||
});
|
});
|
||||||
@ -126,15 +126,14 @@ define('handlebars_helpers', ['handlebars'], function (Handlebars) {
|
|||||||
*/
|
*/
|
||||||
Handlebars.registerHelper('ellipsis', function (str, limit, append) {
|
Handlebars.registerHelper('ellipsis', function (str, limit, append) {
|
||||||
var strAppend = append;
|
var strAppend = append;
|
||||||
|
var sanitized = str.replace(/(<([^>]+)>)/g, '');
|
||||||
if (strAppend === undefined) {
|
if (strAppend === undefined) {
|
||||||
strAppend = '';
|
strAppend = '';
|
||||||
}
|
}
|
||||||
var sanitized = str.replace(/(<([^>]+)>)/g, '');
|
|
||||||
if (sanitized.length > limit) {
|
if (sanitized.length > limit) {
|
||||||
return sanitized.substr(0, limit - strAppend.length) + strAppend;
|
return sanitized.substr(0, limit - strAppend.length) + strAppend;
|
||||||
} else {
|
|
||||||
return sanitized;
|
|
||||||
}
|
}
|
||||||
|
return sanitized;
|
||||||
});
|
});
|
||||||
|
|
||||||
Handlebars.registerHelper('getNumber', function (string) {
|
Handlebars.registerHelper('getNumber', function (string) {
|
||||||
|
@ -1,12 +1,11 @@
|
|||||||
define('helpTooltip', ['mailpoet', 'react', 'react-dom', 'help-tooltip.jsx'],
|
define('helpTooltip', ['mailpoet', 'react', 'react-dom', 'help-tooltip.jsx'],
|
||||||
function (mp, React, ReactDOM, TooltipComponent) {
|
function helpTooltip(mp, React, ReactDOM, TooltipComponent) {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var MailPoet = mp;
|
var MailPoet = mp;
|
||||||
|
|
||||||
MailPoet.helpTooltip = {
|
MailPoet.helpTooltip = {
|
||||||
show: function (domContainerNode, opts) {
|
show: function show(domContainerNode, opts) {
|
||||||
|
|
||||||
ReactDOM.render(React.createElement(
|
ReactDOM.render(React.createElement(
|
||||||
TooltipComponent, {
|
TooltipComponent, {
|
||||||
tooltip: opts.tooltip,
|
tooltip: opts.tooltip,
|
||||||
@ -16,7 +15,6 @@ define('helpTooltip', ['mailpoet', 'react', 'react-dom', 'help-tooltip.jsx'],
|
|||||||
), domContainerNode);
|
), domContainerNode);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -3,8 +3,9 @@ import ReactDOM from 'react-dom';
|
|||||||
import { Router, Route, IndexRedirect, useRouterHistory } from 'react-router';
|
import { Router, Route, IndexRedirect, useRouterHistory } from 'react-router';
|
||||||
import { createHashHistory } from 'history';
|
import { createHashHistory } from 'history';
|
||||||
|
|
||||||
import KnowledgeBase from 'help/knowledge_base.jsx';
|
import SystemStatus from 'help/system_status.jsx';
|
||||||
import SystemInfo from 'help/system_info.jsx';
|
import SystemInfo from 'help/system_info.jsx';
|
||||||
|
import KnowledgeBase from 'help/knowledge_base.jsx';
|
||||||
|
|
||||||
const history = useRouterHistory(createHashHistory)({ queryKey: false });
|
const history = useRouterHistory(createHashHistory)({ queryKey: false });
|
||||||
|
|
||||||
@ -17,16 +18,15 @@ const App = React.createClass({
|
|||||||
const container = document.getElementById('help_container');
|
const container = document.getElementById('help_container');
|
||||||
|
|
||||||
if (container) {
|
if (container) {
|
||||||
|
|
||||||
ReactDOM.render((
|
ReactDOM.render((
|
||||||
<Router history={history}>
|
<Router history={history}>
|
||||||
<Route path="/" component={App}>
|
<Route path="/" component={App}>
|
||||||
<IndexRedirect to="knowledgeBase" />
|
<IndexRedirect to="systemStatus" />
|
||||||
{/* Pages */}
|
{/* Pages */}
|
||||||
<Route path="knowledgeBase(/)**" params={{ tab: 'knowledgeBase' }} component={KnowledgeBase} />
|
<Route path="systemStatus(/)**" params={{ tab: 'systemStatus' }} component={SystemStatus} />
|
||||||
<Route path="systemInfo(/)**" params={{ tab: 'systemInfo' }} component={SystemInfo} />
|
<Route path="systemInfo(/)**" params={{ tab: 'systemInfo' }} component={SystemInfo} />
|
||||||
|
<Route path="knowledgeBase(/)**" params={{ tab: 'knowledgeBase' }} component={KnowledgeBase} />
|
||||||
</Route>
|
</Route>
|
||||||
</Router>
|
</Router>
|
||||||
), container);
|
), container);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -4,7 +4,6 @@ import MailPoet from 'mailpoet';
|
|||||||
import Tabs from './tabs.jsx';
|
import Tabs from './tabs.jsx';
|
||||||
|
|
||||||
function KnowledgeBase() {
|
function KnowledgeBase() {
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
|
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import MailPoet from 'mailpoet';
|
import MailPoet from 'mailpoet';
|
||||||
import _ from 'underscore';
|
import _ from 'underscore';
|
||||||
|
|
||||||
import Tabs from './tabs.jsx';
|
import Tabs from './tabs.jsx';
|
||||||
|
|
||||||
function handleFocus(event) {
|
function handleFocus(event) {
|
||||||
@ -10,9 +9,7 @@ function handleFocus(event) {
|
|||||||
|
|
||||||
function printData(data) {
|
function printData(data) {
|
||||||
if (_.isObject(data)) {
|
if (_.isObject(data)) {
|
||||||
const printableData = Object.keys(data).map((key) => {
|
const printableData = Object.keys(data).map(key => `${key}: ${data[key]}`);
|
||||||
return `${key}: ${data[key]}`;
|
|
||||||
});
|
|
||||||
|
|
||||||
return (<textarea
|
return (<textarea
|
||||||
readOnly={true}
|
readOnly={true}
|
||||||
@ -23,25 +20,24 @@ function printData(data) {
|
|||||||
height: '400px',
|
height: '400px',
|
||||||
}}
|
}}
|
||||||
/>);
|
/>);
|
||||||
} else {
|
|
||||||
return (<p>{MailPoet.I18n.t('systemInfoDataError')}</p>);
|
|
||||||
}
|
}
|
||||||
|
return (<p>{MailPoet.I18n.t('systemInfoDataError')}</p>);
|
||||||
}
|
}
|
||||||
|
|
||||||
function KnowledgeBase() {
|
function SystemInfo() {
|
||||||
const data = window.help_scout_data;
|
const systemInfoData = window.systemInfoData;
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
|
|
||||||
<Tabs tab="systemInfo" />
|
<Tabs tab="systemInfo" />
|
||||||
|
|
||||||
<div className="mailpoet_notice notice inline notice-success" style={{ marginTop: '1em' }}>
|
<div className="mailpoet_notice notice inline" style={{ marginTop: '1em' }}>
|
||||||
<p>{MailPoet.I18n.t('systemInfoIntro')}</p>
|
<p>{MailPoet.I18n.t('systemInfoIntro')}</p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{printData(data)}
|
{printData(systemInfoData)}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
module.exports = KnowledgeBase;
|
module.exports = SystemInfo;
|
||||||
|
71
assets/js/src/help/system_status.jsx
Normal file
71
assets/js/src/help/system_status.jsx
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
import MailPoet from 'mailpoet';
|
||||||
|
import React from 'react';
|
||||||
|
import ReactStringReplace from 'react-string-replace';
|
||||||
|
import Tabs from './tabs.jsx';
|
||||||
|
|
||||||
|
function renderStatusMessage(status, error, link) {
|
||||||
|
const noticeType = (status) ? 'success' : 'error';
|
||||||
|
let noticeMessage = (status) ?
|
||||||
|
MailPoet.I18n.t('systemStatusConnectionSuccessful') :
|
||||||
|
`${MailPoet.I18n.t('systemStatusConnectionUnsuccessful')} ${error}`;
|
||||||
|
|
||||||
|
if (link) {
|
||||||
|
noticeMessage = ReactStringReplace(
|
||||||
|
noticeMessage,
|
||||||
|
/\[link\](.*?)\[\/link\]/g,
|
||||||
|
match => (
|
||||||
|
<a href={`${link}`} key="kb-link">{ match }</a>
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className={`mailpoet_notice notice inline notice-${noticeType}`} style={{ marginTop: '1em' }}>
|
||||||
|
<p>{noticeMessage}</p>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function renderCronSection(data) {
|
||||||
|
const status = data.cron.isReachable;
|
||||||
|
const url = data.cron.url;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<h2>{MailPoet.I18n.t('systemStatusCronTitle')}</h2>
|
||||||
|
<p>
|
||||||
|
<a href={url} target="_blank">{url}</a>
|
||||||
|
</p>
|
||||||
|
{renderStatusMessage(status, MailPoet.I18n.t('systemStatusCronConnectionUnsuccessfulInfo'), '//beta.docs.mailpoet.com/article/231-sending-does-not-work')}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function renderMSSSection(data) {
|
||||||
|
if (!data.mss.enabled) return undefined;
|
||||||
|
|
||||||
|
const status = data.mss.enabled.isReachable;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<h2>{MailPoet.I18n.t('systemStatusMSSTitle')}</h2>
|
||||||
|
{renderStatusMessage(status, MailPoet.I18n.t('systemStatusMSSConnectionUnsuccessfulInfo'), false)}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
function SystemStatus() {
|
||||||
|
const systemStatusData = window.systemStatusData;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<Tabs tab="systemStatus" />
|
||||||
|
<div className="mailpoet_notice notice inline" style={{ marginTop: '1em' }}>
|
||||||
|
<p>{systemStatusData.mss.enabled ? MailPoet.I18n.t('systemStatusIntroCronMSS') : MailPoet.I18n.t('systemStatusIntroCron')}</p>
|
||||||
|
</div>
|
||||||
|
{renderCronSection(systemStatusData)}
|
||||||
|
{renderMSSSection(systemStatusData)}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
module.exports = SystemStatus;
|
@ -5,19 +5,23 @@ import MailPoet from 'mailpoet';
|
|||||||
|
|
||||||
const tabs = [
|
const tabs = [
|
||||||
{
|
{
|
||||||
name: 'knowledgeBase',
|
name: 'systemStatus',
|
||||||
label: MailPoet.I18n.t('tabKnowledgeBaseTitle'),
|
label: MailPoet.I18n.t('tabSystemStatusTitle'),
|
||||||
link: '/knowledgeBase',
|
link: '/systemStatus',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'systemInfo',
|
name: 'systemInfo',
|
||||||
label: MailPoet.I18n.t('tabSystemInfoTitle'),
|
label: MailPoet.I18n.t('tabSystemInfoTitle'),
|
||||||
link: '/systemInfo',
|
link: '/systemInfo',
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: 'knowledgeBase',
|
||||||
|
label: MailPoet.I18n.t('tabKnowledgeBaseTitle'),
|
||||||
|
link: '/knowledgeBase',
|
||||||
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
function Tabs(props) {
|
function Tabs(props) {
|
||||||
|
|
||||||
const tabLinks = tabs.map((tab, index) => {
|
const tabLinks = tabs.map((tab, index) => {
|
||||||
const tabClasses = classNames(
|
const tabClasses = classNames(
|
||||||
'nav-tab',
|
'nav-tab',
|
||||||
@ -26,7 +30,7 @@ function Tabs(props) {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Link
|
<Link
|
||||||
key={'tab-' + index}
|
key={`tab-${index}`}
|
||||||
className={tabClasses}
|
className={tabClasses}
|
||||||
to={tab.link}
|
to={tab.link}
|
||||||
>{ tab.label }</Link>
|
>{ tab.label }</Link>
|
||||||
@ -41,6 +45,6 @@ function Tabs(props) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Tabs.propTypes = { tab: React.PropTypes.string };
|
Tabs.propTypes = { tab: React.PropTypes.string };
|
||||||
Tabs.defaultProps = { tab: 'knowledgeBase' };
|
Tabs.defaultProps = { tab: 'systemStatus' };
|
||||||
|
|
||||||
module.exports = Tabs;
|
module.exports = Tabs;
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
define('i18n',
|
define('i18n',
|
||||||
[
|
[
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (
|
], function i18n(
|
||||||
mp
|
mp
|
||||||
) {
|
) {
|
||||||
'use strict';
|
'use strict';
|
||||||
@ -11,15 +11,14 @@ define('i18n',
|
|||||||
var translations = {};
|
var translations = {};
|
||||||
|
|
||||||
MailPoet.I18n = {
|
MailPoet.I18n = {
|
||||||
add: function (key, value) {
|
add: function add(key, value) {
|
||||||
translations[key] = value;
|
translations[key] = value;
|
||||||
},
|
},
|
||||||
t: function (key) {
|
t: function t(key) {
|
||||||
return translations[key] || 'TRANSLATION "%$1s" NOT FOUND'.replace('%$1s', key);
|
return translations[key] || 'TRANSLATION "%$1s" NOT FOUND'.replace('%$1s', key);
|
||||||
},
|
},
|
||||||
all: function () {
|
all: function all() {
|
||||||
return translations;
|
return translations;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
});
|
});
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
define('iframe', ['mailpoet'], function (mp) {
|
define('iframe', ['mailpoet'], function iframeModule(mp) {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var MailPoet = mp;
|
var MailPoet = mp;
|
||||||
MailPoet.Iframe = {
|
MailPoet.Iframe = {
|
||||||
marginY: 20,
|
marginY: 20,
|
||||||
autoSize: function (iframe) {
|
autoSize: function autoSize(iframe) {
|
||||||
if (!iframe) return;
|
if (!iframe) return;
|
||||||
|
|
||||||
this.setSize(
|
this.setSize(
|
||||||
@ -12,7 +12,7 @@ define('iframe', ['mailpoet'], function (mp) {
|
|||||||
iframe.contentWindow.document.body.scrollHeight
|
iframe.contentWindow.document.body.scrollHeight
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
setSize: function (sizeIframe, i) {
|
setSize: function setSize(sizeIframe, i) {
|
||||||
var iframe = sizeIframe;
|
var iframe = sizeIframe;
|
||||||
if (!iframe) return;
|
if (!iframe) return;
|
||||||
|
|
||||||
|
@ -2,7 +2,7 @@ define(
|
|||||||
[
|
[
|
||||||
'jquery'
|
'jquery'
|
||||||
],
|
],
|
||||||
function (
|
function ( // eslint-disable-line func-names
|
||||||
jQuery
|
jQuery
|
||||||
) {
|
) {
|
||||||
var $ = jQuery;
|
var $ = jQuery;
|
||||||
@ -23,47 +23,47 @@ define(
|
|||||||
* Dual licensed under the MIT and GPL licenses.
|
* Dual licensed under the MIT and GPL licenses.
|
||||||
* http://benalman.com/about/license/
|
* http://benalman.com/about/license/
|
||||||
*/
|
*/
|
||||||
$.fn.serializeObject = function (coerce) {
|
$.fn.mailpoetSerializeObject = function (coerce) { // eslint-disable-line func-names
|
||||||
var obj = {},
|
var obj = {};
|
||||||
coerce_types = { true: !0, false: !1, null: null };
|
var coerceTypes = { true: !0, false: !1, null: null };
|
||||||
|
|
||||||
// Iterate over all name=value pairs.
|
// Iterate over all name=value pairs.
|
||||||
$.each(this.serializeArray(), function (j, v) {
|
$.each(this.serializeArray(), function (j, v) { // eslint-disable-line func-names
|
||||||
var key = v.name,
|
var key = v.name;
|
||||||
val = v.value,
|
var val = v.value;
|
||||||
cur = obj,
|
var cur = obj;
|
||||||
i = 0,
|
var i = 0;
|
||||||
|
|
||||||
// If key is more complex than 'foo', like 'a[]' or 'a[b][c]', split it
|
// If key is more complex than 'foo', like 'a[]' or 'a[b][c]', split it
|
||||||
// into its component parts.
|
// into its component parts.
|
||||||
keys = key.split(']['),
|
var keys = key.split('][');
|
||||||
keys_last = keys.length - 1;
|
var keysLast = keys.length - 1;
|
||||||
|
|
||||||
// If the first keys part contains [ and the last ends with ], then []
|
// If the first keys part contains [ and the last ends with ], then []
|
||||||
// are correctly balanced.
|
// are correctly balanced.
|
||||||
if (/\[/.test(keys[0]) && /\]$/.test(keys[keys_last])) {
|
if (/\[/.test(keys[0]) && /\]$/.test(keys[keysLast])) {
|
||||||
// Remove the trailing ] from the last keys part.
|
// Remove the trailing ] from the last keys part.
|
||||||
keys[keys_last] = keys[keys_last].replace(/\]$/, '');
|
keys[keysLast] = keys[keysLast].replace(/\]$/, '');
|
||||||
|
|
||||||
// Split first keys part into two parts on the [ and add them back onto
|
// Split first keys part into two parts on the [ and add them back onto
|
||||||
// the beginning of the keys array.
|
// the beginning of the keys array.
|
||||||
keys = keys.shift().split('[').concat(keys);
|
keys = keys.shift().split('[').concat(keys);
|
||||||
|
|
||||||
keys_last = keys.length - 1;
|
keysLast = keys.length - 1;
|
||||||
} else {
|
} else {
|
||||||
// Basic 'foo' style key.
|
// Basic 'foo' style key.
|
||||||
keys_last = 0;
|
keysLast = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Coerce values.
|
// Coerce values.
|
||||||
if (coerce) {
|
if (coerce) {
|
||||||
val = val && !isNaN(val) ? +val // number
|
val = val && !isNaN(val) ? +val // number
|
||||||
: val === 'undefined' ? undefined // undefined
|
: val === 'undefined' ? undefined // undefined
|
||||||
: coerce_types[val] !== undefined ? coerce_types[val] // true, false, null
|
: coerceTypes[val] !== undefined ? coerceTypes[val] // true, false, null
|
||||||
: val; // string
|
: val; // string
|
||||||
}
|
}
|
||||||
|
|
||||||
if (keys_last) {
|
if (keysLast) {
|
||||||
// Complex key, build deep object structure based on a few rules:
|
// Complex key, build deep object structure based on a few rules:
|
||||||
// * The 'cur' pointer starts at the object top-level.
|
// * The 'cur' pointer starts at the object top-level.
|
||||||
// * [] = array push (n is set to array length), [n] = array if n is
|
// * [] = array push (n is set to array length), [n] = array if n is
|
||||||
@ -73,14 +73,13 @@ define(
|
|||||||
// object or array based on the type of the next keys part.
|
// object or array based on the type of the next keys part.
|
||||||
// * Move the 'cur' pointer to the next level.
|
// * Move the 'cur' pointer to the next level.
|
||||||
// * Rinse & repeat.
|
// * Rinse & repeat.
|
||||||
for (; i <= keys_last; i++) {
|
for (; i <= keysLast; i++) {
|
||||||
key = keys[i] === '' ? cur.length : keys[i];
|
key = keys[i] === '' ? cur.length : keys[i];
|
||||||
cur[key] = i < keys_last
|
cur[key] = i < keysLast
|
||||||
? cur[key] || (keys[i + 1] && isNaN(keys[i + 1]) ? {} : [])
|
? cur[key] || (keys[i + 1] && isNaN(keys[i + 1]) ? {} : [])
|
||||||
: val;
|
: val;
|
||||||
cur = cur[key];
|
cur = cur[key];
|
||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
// Simple key, even simpler rules, since only scalars and shallow
|
// Simple key, even simpler rules, since only scalars and shallow
|
||||||
// arrays are allowed.
|
// arrays are allowed.
|
||||||
@ -88,12 +87,10 @@ define(
|
|||||||
if ($.isArray(obj[key])) {
|
if ($.isArray(obj[key])) {
|
||||||
// val is already an array, so push on the next value.
|
// val is already an array, so push on the next value.
|
||||||
obj[key].push(val);
|
obj[key].push(val);
|
||||||
|
|
||||||
} else if (obj[key] !== undefined) {
|
} else if (obj[key] !== undefined) {
|
||||||
// val isn't an array, but since a second value has been specified,
|
// val isn't an array, but since a second value has been specified,
|
||||||
// convert val into an array.
|
// convert val into an array.
|
||||||
obj[key] = [obj[key], val];
|
obj[key] = [obj[key], val];
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
// val is a scalar.
|
// val is a scalar.
|
||||||
obj[key] = val;
|
obj[key] = val;
|
||||||
@ -106,4 +103,4 @@ define(
|
|||||||
|
|
||||||
return $;
|
return $;
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
@ -21,7 +21,7 @@ define([
|
|||||||
const action = this.getSelectedAction();
|
const action = this.getSelectedAction();
|
||||||
|
|
||||||
// action on select callback
|
// action on select callback
|
||||||
if (action !== null && action['onSelect'] !== undefined) {
|
if (action !== null && action.onSelect !== undefined) {
|
||||||
this.setState({
|
this.setState({
|
||||||
extra: action.onSelect(e),
|
extra: action.onSelect(e),
|
||||||
});
|
});
|
||||||
@ -37,23 +37,23 @@ define([
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const selected_ids = (this.props.selection !== 'all')
|
const selectedIds = (this.props.selection !== 'all')
|
||||||
? this.props.selected_ids
|
? this.props.selected_ids
|
||||||
: [];
|
: [];
|
||||||
|
|
||||||
const data = (action['getData'] !== undefined)
|
const data = (action.getData !== undefined)
|
||||||
? action.getData()
|
? action.getData()
|
||||||
: {};
|
: {};
|
||||||
|
|
||||||
data.action = this.state.action;
|
data.action = this.state.action;
|
||||||
|
|
||||||
let onSuccess = function () {};
|
let onSuccess = function () {};
|
||||||
if (action['onSuccess'] !== undefined) {
|
if (action.onSuccess !== undefined) {
|
||||||
onSuccess = action.onSuccess;
|
onSuccess = action.onSuccess;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.action) {
|
if (data.action) {
|
||||||
const promise = this.props.onBulkAction(selected_ids, data);
|
const promise = this.props.onBulkAction(selectedIds, data);
|
||||||
if (promise !== false) {
|
if (promise !== false) {
|
||||||
promise.then(onSuccess);
|
promise.then(onSuccess);
|
||||||
}
|
}
|
||||||
@ -65,11 +65,9 @@ define([
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
getSelectedAction: function () {
|
getSelectedAction: function () {
|
||||||
const selected_action = this.refs.action.value;
|
const selectedAction = this.refs.action.value;
|
||||||
if (selected_action.length > 0) {
|
if (selectedAction.length > 0) {
|
||||||
const action = this.props.bulk_actions.filter((action) => {
|
const action = this.props.bulk_actions.filter(act => (act.name === selectedAction));
|
||||||
return (action.name === selected_action);
|
|
||||||
});
|
|
||||||
|
|
||||||
if (action.length > 0) {
|
if (action.length > 0) {
|
||||||
return action[0];
|
return action[0];
|
||||||
@ -97,14 +95,12 @@ define([
|
|||||||
onChange={this.handleChangeAction}
|
onChange={this.handleChangeAction}
|
||||||
>
|
>
|
||||||
<option value="">{MailPoet.I18n.t('bulkActions')}</option>
|
<option value="">{MailPoet.I18n.t('bulkActions')}</option>
|
||||||
{ this.props.bulk_actions.map((action, index) => {
|
{ this.props.bulk_actions.map((action, index) => (
|
||||||
return (
|
<option
|
||||||
<option
|
value={action.name}
|
||||||
value={action.name}
|
key={`action-${index}`}
|
||||||
key={'action-' + index}
|
|
||||||
>{ action.label }</option>
|
>{ action.label }</option>
|
||||||
);
|
)) }
|
||||||
}) }
|
|
||||||
</select>
|
</select>
|
||||||
<input
|
<input
|
||||||
onClick={this.handleApplyAction}
|
onClick={this.handleApplyAction}
|
||||||
|
@ -11,8 +11,8 @@ define([
|
|||||||
const ListingFilters = React.createClass({
|
const ListingFilters = React.createClass({
|
||||||
handleFilterAction: function () {
|
handleFilterAction: function () {
|
||||||
const filters = {};
|
const filters = {};
|
||||||
this.getAvailableFilters().map((filter, i) => {
|
this.getAvailableFilters().forEach((filter, i) => {
|
||||||
filters[this.refs['filter-' + i].name] = this.refs['filter-' + i].value;
|
filters[this.refs[`filter-${i}`].name] = this.refs[`filter-${i}`].value;
|
||||||
});
|
});
|
||||||
if (this.props.onBeforeSelectFilter) {
|
if (this.props.onBeforeSelectFilter) {
|
||||||
this.props.onBeforeSelectFilter(filters);
|
this.props.onBeforeSelectFilter(filters);
|
||||||
@ -24,23 +24,21 @@ define([
|
|||||||
},
|
},
|
||||||
getAvailableFilters: function () {
|
getAvailableFilters: function () {
|
||||||
const filters = this.props.filters;
|
const filters = this.props.filters;
|
||||||
return Object.keys(filters).filter((filter) => {
|
return Object.keys(filters).filter(filter => !(
|
||||||
return !(
|
|
||||||
filters[filter].length === 0
|
filters[filter].length === 0
|
||||||
|| (
|
|| (
|
||||||
filters[filter].length === 1
|
filters[filter].length === 1
|
||||||
&& !filters[filter][0].value
|
&& !filters[filter][0].value
|
||||||
)
|
)
|
||||||
);
|
));
|
||||||
});
|
|
||||||
},
|
},
|
||||||
componentDidUpdate: function () {
|
componentDidUpdate: function () {
|
||||||
const selected_filters = this.props.filter;
|
const selectedFilters = this.props.filter;
|
||||||
this.getAvailableFilters().map(
|
this.getAvailableFilters().forEach(
|
||||||
(filter, i) => {
|
(filter, i) => {
|
||||||
if (selected_filters[filter] !== undefined && selected_filters[filter]) {
|
if (selectedFilters[filter] !== undefined && selectedFilters[filter]) {
|
||||||
jQuery(this.refs['filter-' + i])
|
jQuery(this.refs[`filter-${i}`])
|
||||||
.val(selected_filters[filter])
|
.val(selectedFilters[filter])
|
||||||
.trigger('change');
|
.trigger('change');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -48,29 +46,25 @@ define([
|
|||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const filters = this.props.filters;
|
const filters = this.props.filters;
|
||||||
const available_filters = this.getAvailableFilters()
|
const availableFilters = this.getAvailableFilters()
|
||||||
.map((filter, i) => {
|
.map((filter, i) => (
|
||||||
return (
|
<select
|
||||||
<select
|
ref={`filter-${i}`}
|
||||||
ref={`filter-${i}`}
|
key={`filter-${i}`}
|
||||||
key={`filter-${i}`}
|
name={filter}
|
||||||
name={filter}
|
|
||||||
>
|
>
|
||||||
{ filters[filter].map((option, j) => {
|
{ filters[filter].map((option, j) => (
|
||||||
return (
|
<option
|
||||||
<option
|
value={option.value}
|
||||||
value={option.value}
|
key={`filter-option-${j}`}
|
||||||
key={'filter-option-' + j}
|
|
||||||
>{ option.label }</option>
|
>{ option.label }</option>
|
||||||
);
|
)) }
|
||||||
}) }
|
</select>
|
||||||
</select>
|
));
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
let button;
|
let button;
|
||||||
|
|
||||||
if (available_filters.length > 0) {
|
if (availableFilters.length > 0) {
|
||||||
button = (
|
button = (
|
||||||
<input
|
<input
|
||||||
id="post-query-submit"
|
id="post-query-submit"
|
||||||
@ -81,9 +75,9 @@ define([
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
let empty_trash;
|
let emptyTrash;
|
||||||
if (this.props.group === 'trash') {
|
if (this.props.group === 'trash') {
|
||||||
empty_trash = (
|
emptyTrash = (
|
||||||
<input
|
<input
|
||||||
onClick={this.handleEmptyTrash}
|
onClick={this.handleEmptyTrash}
|
||||||
type="submit"
|
type="submit"
|
||||||
@ -95,9 +89,9 @@ define([
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div className="alignleft actions actions">
|
<div className="alignleft actions actions">
|
||||||
{ available_filters }
|
{ availableFilters }
|
||||||
{ button }
|
{ button }
|
||||||
{ empty_trash }
|
{ emptyTrash }
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
@ -1,5 +1,4 @@
|
|||||||
define(['react', 'classnames'], (React, classNames) => {
|
define(['react', 'classnames'], (React, classNames) => {
|
||||||
|
|
||||||
const ListingGroups = React.createClass({
|
const ListingGroups = React.createClass({
|
||||||
handleSelect: function (group) {
|
handleSelect: function (group) {
|
||||||
return this.props.onSelectGroup(group);
|
return this.props.onSelectGroup(group);
|
||||||
@ -21,7 +20,8 @@ define(['react', 'classnames'], (React, classNames) => {
|
|||||||
href="javascript:;"
|
href="javascript:;"
|
||||||
className={classes}
|
className={classes}
|
||||||
onClick={this.handleSelect.bind(this, group.name)} >
|
onClick={this.handleSelect.bind(this, group.name)} >
|
||||||
{group.label} <span className="count">({ group.count.toLocaleString() })</span>
|
{group.label}
|
||||||
|
<span className="count">({ parseInt(group.count, 10).toLocaleString() })</span>
|
||||||
</a>
|
</a>
|
||||||
</li>
|
</li>
|
||||||
);
|
);
|
||||||
|
@ -19,7 +19,7 @@ const ListingHeader = React.createClass({
|
|||||||
<ListingColumn
|
<ListingColumn
|
||||||
onSort={this.props.onSort}
|
onSort={this.props.onSort}
|
||||||
sort_by={this.props.sort_by}
|
sort_by={this.props.sort_by}
|
||||||
key={'column-' + index}
|
key={`column-${index}`}
|
||||||
column={renderColumn} />
|
column={renderColumn} />
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -54,9 +54,9 @@ const ListingHeader = React.createClass({
|
|||||||
|
|
||||||
const ListingColumn = React.createClass({
|
const ListingColumn = React.createClass({
|
||||||
handleSort: function () {
|
handleSort: function () {
|
||||||
const sort_by = this.props.column.name;
|
const sortBy = this.props.column.name;
|
||||||
const sort_order = (this.props.column.sorted === 'asc') ? 'desc' : 'asc';
|
const sortOrder = (this.props.column.sorted === 'asc') ? 'desc' : 'asc';
|
||||||
this.props.onSort(sort_by, sort_order);
|
this.props.onSort(sortBy, sortOrder);
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const classes = classNames(
|
const classes = classNames(
|
||||||
|
@ -44,7 +44,7 @@ const ListingItem = React.createClass({
|
|||||||
checkbox = (
|
checkbox = (
|
||||||
<th className="check-column" scope="row">
|
<th className="check-column" scope="row">
|
||||||
<label className="screen-reader-text">{
|
<label className="screen-reader-text">{
|
||||||
'Select ' + this.props.item[this.props.columns[0].name]
|
`Select ${this.props.item[this.props.columns[0].name]}`
|
||||||
}</label>
|
}</label>
|
||||||
<input
|
<input
|
||||||
type="checkbox"
|
type="checkbox"
|
||||||
@ -58,24 +58,20 @@ const ListingItem = React.createClass({
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const custom_actions = this.props.item_actions;
|
const customActions = this.props.item_actions;
|
||||||
let item_actions = false;
|
let itemActions = false;
|
||||||
|
|
||||||
if (custom_actions.length > 0) {
|
if (customActions.length > 0) {
|
||||||
let is_first = true;
|
let isFirst = true;
|
||||||
item_actions = custom_actions.map((action, index) => {
|
itemActions = customActions
|
||||||
if (action.display !== undefined) {
|
.filter(action => action.display === undefined || action.display(this.props.item))
|
||||||
if (action.display(this.props.item) === false) {
|
.map((action, index) => {
|
||||||
return;
|
let customAction = null;
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
let custom_action = null;
|
|
||||||
|
|
||||||
if (action.name === 'trash') {
|
if (action.name === 'trash') {
|
||||||
custom_action = (
|
customAction = (
|
||||||
<span key={'action-' + index} className="trash">
|
<span key={`action-${index}`} className="trash">
|
||||||
{(!is_first) ? ' | ' : ''}
|
{(!isFirst) ? ' | ' : ''}
|
||||||
<a
|
<a
|
||||||
href="javascript:;"
|
href="javascript:;"
|
||||||
onClick={this.handleTrashItem.bind(
|
onClick={this.handleTrashItem.bind(
|
||||||
@ -87,27 +83,27 @@ const ListingItem = React.createClass({
|
|||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else if (action.refresh) {
|
} else if (action.refresh) {
|
||||||
custom_action = (
|
customAction = (
|
||||||
<span
|
<span
|
||||||
onClick={this.props.onRefreshItems}
|
onClick={this.props.onRefreshItems}
|
||||||
key={'action-' + index} className={action.name}>
|
key={`action-${index}`} className={action.name}>
|
||||||
{(!is_first) ? ' | ' : ''}
|
{(!isFirst) ? ' | ' : ''}
|
||||||
{ action.link(this.props.item) }
|
{ action.link(this.props.item) }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else if (action.link) {
|
} else if (action.link) {
|
||||||
custom_action = (
|
customAction = (
|
||||||
<span
|
<span
|
||||||
key={'action-' + index} className={action.name}>
|
key={`action-${index}`} className={action.name}>
|
||||||
{(!is_first) ? ' | ' : ''}
|
{(!isFirst) ? ' | ' : ''}
|
||||||
{ action.link(this.props.item) }
|
{ action.link(this.props.item) }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
custom_action = (
|
customAction = (
|
||||||
<span
|
<span
|
||||||
key={'action-' + index} className={action.name}>
|
key={`action-${index}`} className={action.name}>
|
||||||
{(!is_first) ? ' | ' : ''}
|
{(!isFirst) ? ' | ' : ''}
|
||||||
<a href="javascript:;" onClick={
|
<a href="javascript:;" onClick={
|
||||||
(action.onClick !== undefined)
|
(action.onClick !== undefined)
|
||||||
? action.onClick.bind(null,
|
? action.onClick.bind(null,
|
||||||
@ -120,14 +116,14 @@ const ListingItem = React.createClass({
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (custom_action !== null && is_first === true) {
|
if (customAction !== null && isFirst === true) {
|
||||||
is_first = false;
|
isFirst = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return custom_action;
|
return customAction;
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
item_actions = (
|
itemActions = (
|
||||||
<span className="edit">
|
<span className="edit">
|
||||||
<Link to={`/edit/${this.props.item.id}`}>{MailPoet.I18n.t('edit')}</Link>
|
<Link to={`/edit/${this.props.item.id}`}>{MailPoet.I18n.t('edit')}</Link>
|
||||||
</span>
|
</span>
|
||||||
@ -172,7 +168,7 @@ const ListingItem = React.createClass({
|
|||||||
actions = (
|
actions = (
|
||||||
<div>
|
<div>
|
||||||
<div className="row-actions">
|
<div className="row-actions">
|
||||||
{ item_actions }
|
{ itemActions }
|
||||||
</div>
|
</div>
|
||||||
<button
|
<button
|
||||||
onClick={this.handleToggleItem.bind(null, this.props.item.id)}
|
onClick={this.handleToggleItem.bind(null, this.props.item.id)}
|
||||||
@ -183,10 +179,10 @@ const ListingItem = React.createClass({
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const row_classes = classNames({ 'is-expanded': this.state.expanded });
|
const rowClasses = classNames({ 'is-expanded': this.state.expanded });
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<tr className={row_classes}>
|
<tr className={rowClasses} data-automation-id={`listing_item_${this.props.item.id}`}>
|
||||||
{ checkbox }
|
{ checkbox }
|
||||||
{ this.props.onRenderItem(this.props.item, actions) }
|
{ this.props.onRenderItem(this.props.item, actions) }
|
||||||
</tr>
|
</tr>
|
||||||
@ -223,24 +219,24 @@ const ListingItems = React.createClass({
|
|||||||
</tr>
|
</tr>
|
||||||
</tbody>
|
</tbody>
|
||||||
);
|
);
|
||||||
} else {
|
}
|
||||||
const select_all_classes = classNames(
|
const selectAllClasses = classNames(
|
||||||
'mailpoet_select_all',
|
'mailpoet_select_all',
|
||||||
{ mailpoet_hidden: (
|
{ mailpoet_hidden: (
|
||||||
this.props.selection === false
|
this.props.selection === false
|
||||||
|| (this.props.count <= this.props.limit)
|
|| (this.props.count <= this.props.limit)
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr className={select_all_classes}>
|
<tr className={selectAllClasses}>
|
||||||
<td colSpan={
|
<td colSpan={
|
||||||
this.props.columns.length
|
this.props.columns.length
|
||||||
+ (this.props.is_selectable ? 1 : 0)
|
+ (this.props.is_selectable ? 1 : 0)
|
||||||
}>
|
}>
|
||||||
{
|
{
|
||||||
(this.props.selection !== 'all')
|
(this.props.selection !== 'all')
|
||||||
? MailPoet.I18n.t('selectAllLabel')
|
? MailPoet.I18n.t('selectAllLabel')
|
||||||
: MailPoet.I18n.t('selectedAllLabel').replace(
|
: MailPoet.I18n.t('selectedAllLabel').replace(
|
||||||
@ -249,41 +245,40 @@ const ListingItems = React.createClass({
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
<a
|
<a
|
||||||
onClick={this.props.onSelectAll}
|
onClick={this.props.onSelectAll}
|
||||||
href="javascript:;">{
|
href="javascript:;">{
|
||||||
(this.props.selection !== 'all')
|
(this.props.selection !== 'all')
|
||||||
? MailPoet.I18n.t('selectAllLink')
|
? MailPoet.I18n.t('selectAllLink')
|
||||||
: MailPoet.I18n.t('clearSelection')
|
: MailPoet.I18n.t('clearSelection')
|
||||||
}</a>
|
}</a>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
||||||
{this.props.items.map((item, index) => {
|
{this.props.items.map((item, index) => {
|
||||||
const renderItem = item;
|
const renderItem = item;
|
||||||
renderItem.id = parseInt(item.id, 10);
|
renderItem.id = parseInt(item.id, 10);
|
||||||
renderItem.selected = (this.props.selected_ids.indexOf(renderItem.id) !== -1);
|
renderItem.selected = (this.props.selected_ids.indexOf(renderItem.id) !== -1);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<ListingItem
|
<ListingItem
|
||||||
columns={this.props.columns}
|
columns={this.props.columns}
|
||||||
onSelectItem={this.props.onSelectItem}
|
onSelectItem={this.props.onSelectItem}
|
||||||
onRenderItem={this.props.onRenderItem}
|
onRenderItem={this.props.onRenderItem}
|
||||||
onDeleteItem={this.props.onDeleteItem}
|
onDeleteItem={this.props.onDeleteItem}
|
||||||
onRestoreItem={this.props.onRestoreItem}
|
onRestoreItem={this.props.onRestoreItem}
|
||||||
onTrashItem={this.props.onTrashItem}
|
onTrashItem={this.props.onTrashItem}
|
||||||
onRefreshItems={this.props.onRefreshItems}
|
onRefreshItems={this.props.onRefreshItems}
|
||||||
selection={this.props.selection}
|
selection={this.props.selection}
|
||||||
is_selectable={this.props.is_selectable}
|
is_selectable={this.props.is_selectable}
|
||||||
item_actions={this.props.item_actions}
|
item_actions={this.props.item_actions}
|
||||||
group={this.props.group}
|
group={this.props.group}
|
||||||
key={`item-${renderItem.id}-${index}`}
|
key={`item-${renderItem.id}-${index}`}
|
||||||
item={renderItem} />
|
item={renderItem} />
|
||||||
);
|
);
|
||||||
})}
|
})}
|
||||||
</tbody>
|
</tbody>
|
||||||
);
|
);
|
||||||
}
|
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -319,16 +314,15 @@ const Listing = React.createClass({
|
|||||||
const state = this.getInitialState();
|
const state = this.getInitialState();
|
||||||
// check for url params
|
// check for url params
|
||||||
if (params.splat) {
|
if (params.splat) {
|
||||||
params.splat.split('/').map((param) => {
|
params.splat.split('/').forEach((param) => {
|
||||||
const [key, value] = this.getParam(param);
|
const [key, value] = this.getParam(param);
|
||||||
|
const filters = {};
|
||||||
switch (key) {
|
switch (key) {
|
||||||
case 'filter':
|
case 'filter':
|
||||||
const filters = {};
|
value.split('&').forEach((pair) => {
|
||||||
value.split('&').map((pair) => {
|
|
||||||
const [k, v] = pair.split('=');
|
const [k, v] = pair.split('=');
|
||||||
filters[k] = v;
|
filters[k] = v;
|
||||||
}
|
});
|
||||||
);
|
|
||||||
|
|
||||||
state.filter = filters;
|
state.filter = filters;
|
||||||
break;
|
break;
|
||||||
@ -340,7 +334,7 @@ const Listing = React.createClass({
|
|||||||
|
|
||||||
// limit per page
|
// limit per page
|
||||||
if (this.props.limit !== undefined) {
|
if (this.props.limit !== undefined) {
|
||||||
state.limit = Math.abs(~~this.props.limit);
|
state.limit = Math.abs(Number(this.props.limit));
|
||||||
}
|
}
|
||||||
|
|
||||||
// sort by
|
// sort by
|
||||||
@ -371,8 +365,7 @@ const Listing = React.createClass({
|
|||||||
setParams: function () {
|
setParams: function () {
|
||||||
if (this.props.location) {
|
if (this.props.location) {
|
||||||
const params = Object.keys(this.state)
|
const params = Object.keys(this.state)
|
||||||
.filter((key) => {
|
.filter(key => (
|
||||||
return (
|
|
||||||
[
|
[
|
||||||
'group',
|
'group',
|
||||||
'filter',
|
'filter',
|
||||||
@ -381,8 +374,7 @@ const Listing = React.createClass({
|
|||||||
'sort_by',
|
'sort_by',
|
||||||
'sort_order',
|
'sort_order',
|
||||||
].indexOf(key) !== -1
|
].indexOf(key) !== -1
|
||||||
);
|
))
|
||||||
})
|
|
||||||
.map((key) => {
|
.map((key) => {
|
||||||
let value = this.state[key];
|
let value = this.state[key];
|
||||||
if (value === Object(value)) {
|
if (value === Object(value)) {
|
||||||
@ -390,12 +382,13 @@ const Listing = React.createClass({
|
|||||||
} else if (value === Boolean(value)) {
|
} else if (value === Boolean(value)) {
|
||||||
value = value.toString();
|
value = value.toString();
|
||||||
}
|
}
|
||||||
|
return {
|
||||||
if (value !== '' && value !== null) {
|
key,
|
||||||
return `${key}[${value}]`;
|
value,
|
||||||
}
|
};
|
||||||
})
|
})
|
||||||
.filter((key) => { return (key !== undefined); })
|
.filter(({ value }) => value !== '' && value !== null)
|
||||||
|
.map(({ key, value }) => `${key}[${value}]`)
|
||||||
.join('/');
|
.join('/');
|
||||||
|
|
||||||
// set url
|
// set url
|
||||||
@ -407,24 +400,23 @@ const Listing = React.createClass({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
getUrlWithParams: function (params) {
|
getUrlWithParams: function (params) {
|
||||||
let base_url = (this.props.base_url !== undefined)
|
let baseUrl = (this.props.base_url !== undefined)
|
||||||
? this.props.base_url
|
? this.props.base_url
|
||||||
: null;
|
: null;
|
||||||
|
|
||||||
if (base_url !== null) {
|
if (baseUrl !== null) {
|
||||||
base_url = this.setBaseUrlParams(base_url);
|
baseUrl = this.setBaseUrlParams(baseUrl);
|
||||||
return `/${base_url}/${params}`;
|
return `/${baseUrl}/${params}`;
|
||||||
} else {
|
|
||||||
return `/${params}`;
|
|
||||||
}
|
}
|
||||||
|
return `/${params}`;
|
||||||
},
|
},
|
||||||
setBaseUrlParams: function (base_url) {
|
setBaseUrlParams: function (baseUrl) {
|
||||||
let ret = base_url;
|
let ret = baseUrl;
|
||||||
if (ret.indexOf(':') !== -1) {
|
if (ret.indexOf(':') !== -1) {
|
||||||
const params = this.getParams();
|
const params = this.getParams();
|
||||||
Object.keys(params).map((key) => {
|
Object.keys(params).forEach((key) => {
|
||||||
if (ret.indexOf(':' + key) !== -1) {
|
if (ret.indexOf(`:${key}`) !== -1) {
|
||||||
ret = ret.replace(':' + key, params[key]);
|
ret = ret.replace(`:${key}`, params[key]);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -491,7 +483,7 @@ const Listing = React.createClass({
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -514,14 +506,14 @@ const Listing = React.createClass({
|
|||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
if (
|
if (
|
||||||
this.props.messages !== undefined
|
this.props.messages !== undefined
|
||||||
&& this.props.messages['onRestore'] !== undefined
|
&& this.props.messages.onRestore !== undefined
|
||||||
) {
|
) {
|
||||||
this.props.messages.onRestore(response);
|
this.props.messages.onRestore(response);
|
||||||
}
|
}
|
||||||
this.getItems();
|
this.getItems();
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -542,14 +534,14 @@ const Listing = React.createClass({
|
|||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
if (
|
if (
|
||||||
this.props.messages !== undefined
|
this.props.messages !== undefined
|
||||||
&& this.props.messages['onTrash'] !== undefined
|
&& this.props.messages.onTrash !== undefined
|
||||||
) {
|
) {
|
||||||
this.props.messages.onTrash(response);
|
this.props.messages.onTrash(response);
|
||||||
}
|
}
|
||||||
this.getItems();
|
this.getItems();
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -570,14 +562,14 @@ const Listing = React.createClass({
|
|||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
if (
|
if (
|
||||||
this.props.messages !== undefined
|
this.props.messages !== undefined
|
||||||
&& this.props.messages['onDelete'] !== undefined
|
&& this.props.messages.onDelete !== undefined
|
||||||
) {
|
) {
|
||||||
this.props.messages.onDelete(response);
|
this.props.messages.onDelete(response);
|
||||||
}
|
}
|
||||||
this.getItems();
|
this.getItems();
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
@ -594,16 +586,16 @@ const Listing = React.createClass({
|
|||||||
this.handleGroup('all');
|
this.handleGroup('all');
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
handleBulkAction: function (selected_ids, params) {
|
handleBulkAction: function (selectedIds, params) {
|
||||||
if (
|
if (
|
||||||
this.state.selection === false
|
this.state.selection === false
|
||||||
&& this.state.selected_ids.length === 0
|
&& this.state.selected_ids.length === 0
|
||||||
&& selected_ids !== 'all'
|
&& selectedIds !== 'all'
|
||||||
) {
|
) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -619,8 +611,8 @@ const Listing = React.createClass({
|
|||||||
group: this.state.group,
|
group: this.state.group,
|
||||||
search: this.state.search,
|
search: this.state.search,
|
||||||
};
|
};
|
||||||
if (selected_ids !== 'all') {
|
if (selectedIds !== 'all') {
|
||||||
data.listing.selection = selected_ids;
|
data.listing.selection = selectedIds;
|
||||||
}
|
}
|
||||||
|
|
||||||
return MailPoet.Ajax.post({
|
return MailPoet.Ajax.post({
|
||||||
@ -633,7 +625,7 @@ const Listing = React.createClass({
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -649,20 +641,20 @@ const Listing = React.createClass({
|
|||||||
this.setParams();
|
this.setParams();
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
handleSort: function (sort_by, sort_order = 'asc') {
|
handleSort: function (sortBy, sortOrder = 'asc') {
|
||||||
this.setState({
|
this.setState({
|
||||||
sort_by: sort_by,
|
sort_by: sortBy,
|
||||||
sort_order: (sort_order === 'asc') ? 'asc' : 'desc',
|
sort_order: (sortOrder === 'asc') ? 'asc' : 'desc',
|
||||||
}, () => {
|
}, () => {
|
||||||
this.setParams();
|
this.setParams();
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
handleSelectItem: function (id, is_checked) {
|
handleSelectItem: function (id, isChecked) {
|
||||||
let selected_ids = this.state.selected_ids,
|
let selectedIds = this.state.selected_ids;
|
||||||
selection = false;
|
let selection = false;
|
||||||
|
|
||||||
if (is_checked) {
|
if (isChecked) {
|
||||||
selected_ids = jQuery.merge(selected_ids, [id]);
|
selectedIds = jQuery.merge(selectedIds, [id]);
|
||||||
// check whether all items on the page are selected
|
// check whether all items on the page are selected
|
||||||
if (
|
if (
|
||||||
jQuery('tbody .check-column :checkbox:not(:checked)').length === 0
|
jQuery('tbody .check-column :checkbox:not(:checked)').length === 0
|
||||||
@ -670,24 +662,22 @@ const Listing = React.createClass({
|
|||||||
selection = 'page';
|
selection = 'page';
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
selected_ids.splice(selected_ids.indexOf(id), 1);
|
selectedIds.splice(selectedIds.indexOf(id), 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.setState({
|
this.setState({
|
||||||
selection: selection,
|
selection: selection,
|
||||||
selected_ids: selected_ids,
|
selected_ids: selectedIds,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
handleSelectItems: function (is_checked) {
|
handleSelectItems: function (isChecked) {
|
||||||
if (is_checked === false) {
|
if (isChecked === false) {
|
||||||
this.clearSelection();
|
this.clearSelection();
|
||||||
} else {
|
} else {
|
||||||
const selected_ids = this.state.items.map((item) => {
|
const selectedIds = this.state.items.map(item => Number(item.id));
|
||||||
return ~~item.id;
|
|
||||||
});
|
|
||||||
|
|
||||||
this.setState({
|
this.setState({
|
||||||
selected_ids: selected_ids,
|
selected_ids: selectedIds,
|
||||||
selection: 'page',
|
selection: 'page',
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -747,20 +737,20 @@ const Listing = React.createClass({
|
|||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const items = this.state.items;
|
const items = this.state.items;
|
||||||
const sort_by = this.state.sort_by;
|
const sortBy = this.state.sort_by;
|
||||||
const sort_order = this.state.sort_order;
|
const sortOrder = this.state.sort_order;
|
||||||
|
|
||||||
// columns
|
// columns
|
||||||
let columns = this.props.columns || [];
|
let columns = this.props.columns || [];
|
||||||
columns = columns.filter((column) => {
|
columns = columns.filter(
|
||||||
return (column.display === undefined || !!(column.display) === true);
|
column => (column.display === undefined || !!(column.display) === true)
|
||||||
});
|
);
|
||||||
|
|
||||||
// bulk actions
|
// bulk actions
|
||||||
let bulk_actions = this.props.bulk_actions || [];
|
let bulkActions = this.props.bulk_actions || [];
|
||||||
|
|
||||||
if (this.state.group === 'trash' && bulk_actions.length > 0) {
|
if (this.state.group === 'trash' && bulkActions.length > 0) {
|
||||||
bulk_actions = [
|
bulkActions = [
|
||||||
{
|
{
|
||||||
name: 'restore',
|
name: 'restore',
|
||||||
label: MailPoet.I18n.t('restore'),
|
label: MailPoet.I18n.t('restore'),
|
||||||
@ -775,9 +765,9 @@ const Listing = React.createClass({
|
|||||||
}
|
}
|
||||||
|
|
||||||
// item actions
|
// item actions
|
||||||
const item_actions = this.props.item_actions || [];
|
const itemActions = this.props.item_actions || [];
|
||||||
|
|
||||||
const table_classes = classNames(
|
const tableClasses = classNames(
|
||||||
'mailpoet_listing_table',
|
'mailpoet_listing_table',
|
||||||
'wp-list-table',
|
'wp-list-table',
|
||||||
'widefat',
|
'widefat',
|
||||||
@ -822,7 +812,7 @@ const Listing = React.createClass({
|
|||||||
<div className="tablenav top clearfix">
|
<div className="tablenav top clearfix">
|
||||||
<ListingBulkActions
|
<ListingBulkActions
|
||||||
count={this.state.count}
|
count={this.state.count}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
selection={this.state.selection}
|
selection={this.state.selection}
|
||||||
selected_ids={this.state.selected_ids}
|
selected_ids={this.state.selected_ids}
|
||||||
onBulkAction={this.handleBulkAction} />
|
onBulkAction={this.handleBulkAction} />
|
||||||
@ -840,16 +830,16 @@ const Listing = React.createClass({
|
|||||||
limit={this.state.limit}
|
limit={this.state.limit}
|
||||||
onSetPage={this.handleSetPage} />
|
onSetPage={this.handleSetPage} />
|
||||||
</div>
|
</div>
|
||||||
<table className={table_classes}>
|
<table className={tableClasses}>
|
||||||
<thead>
|
<thead>
|
||||||
<ListingHeader
|
<ListingHeader
|
||||||
onSort={this.handleSort}
|
onSort={this.handleSort}
|
||||||
onSelectItems={this.handleSelectItems}
|
onSelectItems={this.handleSelectItems}
|
||||||
selection={this.state.selection}
|
selection={this.state.selection}
|
||||||
sort_by={sort_by}
|
sort_by={sortBy}
|
||||||
sort_order={sort_order}
|
sort_order={sortOrder}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
is_selectable={bulk_actions.length > 0} />
|
is_selectable={bulkActions.length > 0} />
|
||||||
</thead>
|
</thead>
|
||||||
|
|
||||||
<ListingItems
|
<ListingItems
|
||||||
@ -859,7 +849,7 @@ const Listing = React.createClass({
|
|||||||
onTrashItem={this.handleTrashItem}
|
onTrashItem={this.handleTrashItem}
|
||||||
onRefreshItems={this.handleRefreshItems}
|
onRefreshItems={this.handleRefreshItems}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
is_selectable={bulk_actions.length > 0}
|
is_selectable={bulkActions.length > 0}
|
||||||
onSelectItem={this.handleSelectItem}
|
onSelectItem={this.handleSelectItem}
|
||||||
onSelectAll={this.handleSelectAll}
|
onSelectAll={this.handleSelectAll}
|
||||||
selection={this.state.selection}
|
selection={this.state.selection}
|
||||||
@ -868,7 +858,7 @@ const Listing = React.createClass({
|
|||||||
group={this.state.group}
|
group={this.state.group}
|
||||||
count={this.state.count}
|
count={this.state.count}
|
||||||
limit={this.state.limit}
|
limit={this.state.limit}
|
||||||
item_actions={item_actions}
|
item_actions={itemActions}
|
||||||
messages={messages}
|
messages={messages}
|
||||||
items={items} />
|
items={items} />
|
||||||
|
|
||||||
@ -877,17 +867,17 @@ const Listing = React.createClass({
|
|||||||
onSort={this.handleSort}
|
onSort={this.handleSort}
|
||||||
onSelectItems={this.handleSelectItems}
|
onSelectItems={this.handleSelectItems}
|
||||||
selection={this.state.selection}
|
selection={this.state.selection}
|
||||||
sort_by={sort_by}
|
sort_by={sortBy}
|
||||||
sort_order={sort_order}
|
sort_order={sortOrder}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
is_selectable={bulk_actions.length > 0} />
|
is_selectable={bulkActions.length > 0} />
|
||||||
</tfoot>
|
</tfoot>
|
||||||
|
|
||||||
</table>
|
</table>
|
||||||
<div className="tablenav bottom">
|
<div className="tablenav bottom">
|
||||||
<ListingBulkActions
|
<ListingBulkActions
|
||||||
count={this.state.count}
|
count={this.state.count}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
selection={this.state.selection}
|
selection={this.state.selection}
|
||||||
selected_ids={this.state.selected_ids}
|
selected_ids={this.state.selected_ids}
|
||||||
onBulkAction={this.handleBulkAction} />
|
onBulkAction={this.handleBulkAction} />
|
||||||
|
@ -7,7 +7,6 @@ define([
|
|||||||
classNames,
|
classNames,
|
||||||
MailPoet
|
MailPoet
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const ListingPages = React.createClass({
|
const ListingPages = React.createClass({
|
||||||
getInitialState: function () {
|
getInitialState: function () {
|
||||||
return {
|
return {
|
||||||
@ -38,7 +37,7 @@ define([
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
constrainPage: function (page) {
|
constrainPage: function (page) {
|
||||||
return Math.min(Math.max(1, Math.abs(~~page)), this.getLastPage());
|
return Math.min(Math.max(1, Math.abs(Number(page))), this.getLastPage());
|
||||||
},
|
},
|
||||||
handleSetManualPage: function (e) {
|
handleSetManualPage: function (e) {
|
||||||
if (e.which === 13) {
|
if (e.which === 13) {
|
||||||
@ -59,125 +58,125 @@ define([
|
|||||||
render: function () {
|
render: function () {
|
||||||
if (this.props.count === 0) {
|
if (this.props.count === 0) {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
}
|
||||||
let pagination = false;
|
let pagination = false;
|
||||||
let firstPage = (
|
let firstPage = (
|
||||||
<span aria-hidden="true" className="tablenav-pages-navspan">«</span>
|
<span aria-hidden="true" className="tablenav-pages-navspan">«</span>
|
||||||
);
|
);
|
||||||
let previousPage = (
|
let previousPage = (
|
||||||
<span aria-hidden="true" className="tablenav-pages-navspan">‹</span>
|
<span aria-hidden="true" className="tablenav-pages-navspan">‹</span>
|
||||||
);
|
);
|
||||||
let nextPage = (
|
let nextPage = (
|
||||||
<span aria-hidden="true" className="tablenav-pages-navspan">›</span>
|
<span aria-hidden="true" className="tablenav-pages-navspan">›</span>
|
||||||
);
|
);
|
||||||
let lastPage = (
|
let lastPage = (
|
||||||
<span aria-hidden="true" className="tablenav-pages-navspan">»</span>
|
<span aria-hidden="true" className="tablenav-pages-navspan">»</span>
|
||||||
);
|
);
|
||||||
|
|
||||||
if (this.props.limit > 0 && this.props.count > this.props.limit) {
|
if (this.props.limit > 0 && this.props.count > this.props.limit) {
|
||||||
if (this.props.page > 1) {
|
if (this.props.page > 1) {
|
||||||
previousPage = (
|
previousPage = (
|
||||||
<a href="javascript:;"
|
<a href="javascript:;"
|
||||||
onClick={this.setPreviousPage}
|
onClick={this.setPreviousPage}
|
||||||
className="prev-page">
|
className="prev-page">
|
||||||
<span className="screen-reader-text">{MailPoet.I18n.t('previousPage')}</span>
|
<span className="screen-reader-text">{MailPoet.I18n.t('previousPage')}</span>
|
||||||
<span aria-hidden="true">‹</span>
|
<span aria-hidden="true">‹</span>
|
||||||
</a>
|
</a>
|
||||||
);
|
);
|
||||||
}
|
|
||||||
|
|
||||||
if (this.props.page > 2) {
|
|
||||||
firstPage = (
|
|
||||||
<a href="javascript:;"
|
|
||||||
onClick={this.setFirstPage}
|
|
||||||
className="first-page">
|
|
||||||
<span className="screen-reader-text">{MailPoet.I18n.t('firstPage')}</span>
|
|
||||||
<span aria-hidden="true">«</span>
|
|
||||||
</a>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.props.page < this.getLastPage()) {
|
|
||||||
nextPage = (
|
|
||||||
<a href="javascript:;"
|
|
||||||
onClick={this.setNextPage}
|
|
||||||
className="next-page">
|
|
||||||
<span className="screen-reader-text">{MailPoet.I18n.t('nextPage')}</span>
|
|
||||||
<span aria-hidden="true">›</span>
|
|
||||||
</a>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.props.page < this.getLastPage() - 1) {
|
|
||||||
lastPage = (
|
|
||||||
<a href="javascript:;"
|
|
||||||
onClick={this.setLastPage}
|
|
||||||
className="last-page">
|
|
||||||
<span className="screen-reader-text">{MailPoet.I18n.t('lastPage')}</span>
|
|
||||||
<span aria-hidden="true">»</span>
|
|
||||||
</a>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
let pageValue = this.props.page;
|
|
||||||
if (this.state.page !== null) {
|
|
||||||
pageValue = this.state.page;
|
|
||||||
}
|
|
||||||
|
|
||||||
pagination = (
|
|
||||||
<span className="pagination-links">
|
|
||||||
{firstPage}
|
|
||||||
|
|
||||||
{previousPage}
|
|
||||||
|
|
||||||
<span className="paging-input">
|
|
||||||
<label
|
|
||||||
className="screen-reader-text"
|
|
||||||
htmlFor="current-page-selector">{MailPoet.I18n.t('currentPage')}</label>
|
|
||||||
<input
|
|
||||||
type="text"
|
|
||||||
onChange={this.handleChangeManualPage}
|
|
||||||
onKeyUp={this.handleSetManualPage}
|
|
||||||
onBlur={this.handleBlurManualPage}
|
|
||||||
aria-describedby="table-paging"
|
|
||||||
size="2"
|
|
||||||
ref="page"
|
|
||||||
value={pageValue}
|
|
||||||
name="paged"
|
|
||||||
id="current-page-selector"
|
|
||||||
className="current-page" />
|
|
||||||
{MailPoet.I18n.t('pageOutOf')}
|
|
||||||
<span className="total-pages">
|
|
||||||
{Math.ceil(this.props.count / this.props.limit).toLocaleString()}
|
|
||||||
</span>
|
|
||||||
</span>
|
|
||||||
|
|
||||||
{nextPage}
|
|
||||||
|
|
||||||
{lastPage}
|
|
||||||
</span>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const classes = classNames(
|
if (this.props.page > 2) {
|
||||||
|
firstPage = (
|
||||||
|
<a href="javascript:;"
|
||||||
|
onClick={this.setFirstPage}
|
||||||
|
className="first-page">
|
||||||
|
<span className="screen-reader-text">{MailPoet.I18n.t('firstPage')}</span>
|
||||||
|
<span aria-hidden="true">«</span>
|
||||||
|
</a>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.props.page < this.getLastPage()) {
|
||||||
|
nextPage = (
|
||||||
|
<a href="javascript:;"
|
||||||
|
onClick={this.setNextPage}
|
||||||
|
className="next-page">
|
||||||
|
<span className="screen-reader-text">{MailPoet.I18n.t('nextPage')}</span>
|
||||||
|
<span aria-hidden="true">›</span>
|
||||||
|
</a>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.props.page < this.getLastPage() - 1) {
|
||||||
|
lastPage = (
|
||||||
|
<a href="javascript:;"
|
||||||
|
onClick={this.setLastPage}
|
||||||
|
className="last-page">
|
||||||
|
<span className="screen-reader-text">{MailPoet.I18n.t('lastPage')}</span>
|
||||||
|
<span aria-hidden="true">»</span>
|
||||||
|
</a>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
let pageValue = this.props.page;
|
||||||
|
if (this.state.page !== null) {
|
||||||
|
pageValue = this.state.page;
|
||||||
|
}
|
||||||
|
|
||||||
|
pagination = (
|
||||||
|
<span className="pagination-links">
|
||||||
|
{firstPage}
|
||||||
|
|
||||||
|
{previousPage}
|
||||||
|
|
||||||
|
<span className="paging-input">
|
||||||
|
<label
|
||||||
|
className="screen-reader-text"
|
||||||
|
htmlFor="current-page-selector">{MailPoet.I18n.t('currentPage')}</label>
|
||||||
|
<input
|
||||||
|
type="text"
|
||||||
|
onChange={this.handleChangeManualPage}
|
||||||
|
onKeyUp={this.handleSetManualPage}
|
||||||
|
onBlur={this.handleBlurManualPage}
|
||||||
|
aria-describedby="table-paging"
|
||||||
|
size="2"
|
||||||
|
ref="page"
|
||||||
|
value={pageValue}
|
||||||
|
name="paged"
|
||||||
|
id="current-page-selector"
|
||||||
|
className="current-page" />
|
||||||
|
{MailPoet.I18n.t('pageOutOf')}
|
||||||
|
<span className="total-pages">
|
||||||
|
{Math.ceil(this.props.count / this.props.limit).toLocaleString()}
|
||||||
|
</span>
|
||||||
|
</span>
|
||||||
|
|
||||||
|
{nextPage}
|
||||||
|
|
||||||
|
{lastPage}
|
||||||
|
</span>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
const classes = classNames(
|
||||||
'tablenav-pages',
|
'tablenav-pages',
|
||||||
{ 'one-page': (this.props.count <= this.props.limit) }
|
{ 'one-page': (this.props.count <= this.props.limit) }
|
||||||
);
|
);
|
||||||
|
|
||||||
let numberOfItemsLabel;
|
let numberOfItemsLabel;
|
||||||
if (this.props.count == 1) {
|
if (Number(this.props.count) === 1) {
|
||||||
numberOfItemsLabel = MailPoet.I18n.t('numberOfItemsSingular');
|
numberOfItemsLabel = MailPoet.I18n.t('numberOfItemsSingular');
|
||||||
} else {
|
} else {
|
||||||
numberOfItemsLabel = MailPoet.I18n.t('numberOfItemsMultiple')
|
numberOfItemsLabel = MailPoet.I18n.t('numberOfItemsMultiple')
|
||||||
.replace('%$1d', this.props.count.toLocaleString());
|
.replace('%$1d', parseInt(this.props.count, 10).toLocaleString());
|
||||||
}
|
|
||||||
return (
|
|
||||||
<div className={classes}>
|
|
||||||
<span className="displaying-num">{ numberOfItemsLabel }</span>
|
|
||||||
{ pagination }
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div className={classes}>
|
||||||
|
<span className="displaying-num">{ numberOfItemsLabel }</span>
|
||||||
|
{ pagination }
|
||||||
|
</div>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -5,12 +5,11 @@ define([
|
|||||||
MailPoet,
|
MailPoet,
|
||||||
React
|
React
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const ListingSearch = React.createClass({
|
const ListingSearch = React.createClass({
|
||||||
handleSearch: function (e) {
|
handleSearch: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
this.props.onSearch(
|
this.props.onSearch(
|
||||||
this.refs.search.value
|
this.refs.search.value.trim()
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
componentWillReceiveProps: function (nextProps) {
|
componentWillReceiveProps: function (nextProps) {
|
||||||
@ -19,27 +18,26 @@ define([
|
|||||||
render: function () {
|
render: function () {
|
||||||
if (this.props.search === false) {
|
if (this.props.search === false) {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
|
||||||
return (
|
|
||||||
<form name="search" onSubmit={this.handleSearch}>
|
|
||||||
<p className="search-box">
|
|
||||||
<label htmlFor="search_input" className="screen-reader-text">
|
|
||||||
{MailPoet.I18n.t('searchLabel')}
|
|
||||||
</label>
|
|
||||||
<input
|
|
||||||
type="search"
|
|
||||||
id="search_input"
|
|
||||||
ref="search"
|
|
||||||
name="s"
|
|
||||||
defaultValue={this.props.search} />
|
|
||||||
<input
|
|
||||||
type="submit"
|
|
||||||
defaultValue={MailPoet.I18n.t('searchLabel')}
|
|
||||||
className="button" />
|
|
||||||
</p>
|
|
||||||
</form>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
return (
|
||||||
|
<form name="search" onSubmit={this.handleSearch}>
|
||||||
|
<p className="search-box">
|
||||||
|
<label htmlFor="search_input" className="screen-reader-text">
|
||||||
|
{MailPoet.I18n.t('searchLabel')}
|
||||||
|
</label>
|
||||||
|
<input
|
||||||
|
type="search"
|
||||||
|
id="search_input"
|
||||||
|
ref="search"
|
||||||
|
name="s"
|
||||||
|
defaultValue={this.props.search} />
|
||||||
|
<input
|
||||||
|
type="submit"
|
||||||
|
defaultValue={MailPoet.I18n.t('searchLabel')}
|
||||||
|
className="button" />
|
||||||
|
</p>
|
||||||
|
</form>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
define('mailpoet', [], function () {
|
define('mailpoet', [], function mailpoet() {
|
||||||
// A placeholder for MailPoet object
|
// A placeholder for MailPoet object
|
||||||
var MailPoet = {};
|
var MailPoet = {};
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define('modal', ['mailpoet', 'jquery'],
|
define('modal', ['mailpoet', 'jquery'],
|
||||||
function (mp, jQuery) {
|
function (mp, jQuery) {
|
||||||
'use strict';
|
'use strict';
|
||||||
@ -111,11 +112,11 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
compileTemplate: function (template) {
|
compileTemplate: function (template) {
|
||||||
if (this.renderer === 'html') {
|
if (this.renderer === 'html') {
|
||||||
return function () { return template; };
|
return function () { return template; };
|
||||||
} else {
|
|
||||||
return window.Handlebars.compile(template);
|
|
||||||
}
|
}
|
||||||
|
return window.Handlebars.compile(template);
|
||||||
},
|
},
|
||||||
init: function (options) {
|
init: function (options) {
|
||||||
|
var modal;
|
||||||
if (this.initialized === true) {
|
if (this.initialized === true) {
|
||||||
this.close();
|
this.close();
|
||||||
}
|
}
|
||||||
@ -134,7 +135,7 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
if (this.options.type !== null) {
|
if (this.options.type !== null) {
|
||||||
// insert modal depending on its type
|
// insert modal depending on its type
|
||||||
if (this.options.type === 'popup') {
|
if (this.options.type === 'popup') {
|
||||||
var modal = this.compileTemplate(
|
modal = this.compileTemplate(
|
||||||
this.templates[this.options.type]
|
this.templates[this.options.type]
|
||||||
);
|
);
|
||||||
// create modal
|
// create modal
|
||||||
@ -178,7 +179,7 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
|
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
initOverlay: function (toggle) {
|
initOverlay: function () {
|
||||||
if (jQuery('#mailpoet_modal_overlay').length === 0) {
|
if (jQuery('#mailpoet_modal_overlay').length === 0) {
|
||||||
// insert overlay into the DOM
|
// insert overlay into the DOM
|
||||||
jQuery('body').append(this.templates.overlay);
|
jQuery('body').append(this.templates.overlay);
|
||||||
@ -214,6 +215,7 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
jQuery(document).on('keyup.mailpoet_modal', function (e) {
|
jQuery(document).on('keyup.mailpoet_modal', function (e) {
|
||||||
if (this.opened === false) { return false; }
|
if (this.opened === false) { return false; }
|
||||||
if (e.keyCode === 27) { this.cancel(); }
|
if (e.keyCode === 27) { this.cancel(); }
|
||||||
|
return true;
|
||||||
}.bind(this));
|
}.bind(this));
|
||||||
|
|
||||||
// make sure the popup is repositioned when the window is resized
|
// make sure the popup is repositioned when the window is resized
|
||||||
@ -253,7 +255,7 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
|
|
||||||
// add sub panel wrapper
|
// add sub panel wrapper
|
||||||
jQuery('#mailpoet_' + this.options.type)
|
jQuery('#mailpoet_' + this.options.type)
|
||||||
.append(this.templates['subpanel']);
|
.append(this.templates.subpanel);
|
||||||
|
|
||||||
// add sub panel content
|
// add sub panel content
|
||||||
jQuery('.mailpoet_' + this.options.type + '_body').last()
|
jQuery('.mailpoet_' + this.options.type + '_body').last()
|
||||||
@ -343,20 +345,21 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
setPosition: function () {
|
setPosition: function () {
|
||||||
|
var screenWidth;
|
||||||
|
var screenHeight;
|
||||||
|
var modalWidth;
|
||||||
|
var modalHeight;
|
||||||
switch (this.options.type) {
|
switch (this.options.type) {
|
||||||
case 'popup':
|
case 'popup':
|
||||||
var screenWidth = jQuery(window).width(),
|
screenWidth = jQuery(window).width();
|
||||||
screenHeight = jQuery(window).height(),
|
screenHeight = jQuery(window).height();
|
||||||
modalWidth = jQuery('.mailpoet_' + this.options.type + '_wrapper').width(),
|
modalWidth = jQuery('.mailpoet_'+ this.options.type +'_wrapper').width();
|
||||||
modalHeight = jQuery('.mailpoet_' + this.options.type + '_wrapper').height();
|
modalHeight = jQuery('.mailpoet_'+ this.options.type +'_wrapper').height();
|
||||||
|
|
||||||
var top = Math.max(48, parseInt((screenHeight / 2) - (modalHeight / 2))),
|
// set position of popup depending on screen dimensions.
|
||||||
left = Math.max(0, parseInt((screenWidth / 2) - (modalWidth / 2)));
|
|
||||||
|
|
||||||
// set position of popup depending on screen dimensions.
|
|
||||||
jQuery('#mailpoet_popup').css({
|
jQuery('#mailpoet_popup').css({
|
||||||
top: top,
|
top: Math.max(48, parseInt((screenHeight / 2) - (modalHeight / 2))),
|
||||||
left: left
|
left: Math.max(0, parseInt((screenWidth / 2) - (modalWidth / 2)))
|
||||||
});
|
});
|
||||||
break;
|
break;
|
||||||
case 'panel':
|
case 'panel':
|
||||||
@ -384,9 +387,6 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
// remember the previously focused element
|
// remember the previously focused element
|
||||||
this.prevFocus = jQuery(':focus');
|
this.prevFocus = jQuery(':focus');
|
||||||
|
|
||||||
// add a flag on the body so that we can prevent scrolling
|
|
||||||
jQuery('body').addClass('mailpoet_modal_opened');
|
|
||||||
|
|
||||||
// show popup
|
// show popup
|
||||||
jQuery('#mailpoet_' + this.options.type).show();
|
jQuery('#mailpoet_' + this.options.type).show();
|
||||||
|
|
||||||
@ -436,7 +436,7 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
.removeClass('mailpoet_modal_highlight');
|
.removeClass('mailpoet_modal_highlight');
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
hideModal: function (callback) {
|
hideModal: function () {
|
||||||
// set modal as closed
|
// set modal as closed
|
||||||
this.opened = false;
|
this.opened = false;
|
||||||
|
|
||||||
@ -446,12 +446,9 @@ define('modal', ['mailpoet', 'jquery'],
|
|||||||
// remove class on highlighted elements
|
// remove class on highlighted elements
|
||||||
this.highlightOff();
|
this.highlightOff();
|
||||||
|
|
||||||
// remove class from body to let it be scrollable
|
|
||||||
jQuery('body').removeClass('mailpoet_modal_opened');
|
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
showOverlay: function (force) {
|
showOverlay: function () {
|
||||||
jQuery('#mailpoet_modal_overlay').show();
|
jQuery('#mailpoet_modal_overlay').show();
|
||||||
return this;
|
return this;
|
||||||
},
|
},
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define('mp2migrator', ['mailpoet', 'jquery'], function (mp, jQuery) {
|
define('mp2migrator', ['mailpoet', 'jquery'], function (mp, jQuery) {
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
@ -41,7 +42,6 @@ define('mp2migrator', ['mailpoet', 'jquery'], function (mp, jQuery) {
|
|||||||
jQuery('#upgrade-completed').show();
|
jQuery('#upgrade-completed').show();
|
||||||
}
|
}
|
||||||
jQuery('#logger').append(row + '<br />\n');
|
jQuery('#logger').append(row + '<br />\n');
|
||||||
|
|
||||||
});
|
});
|
||||||
jQuery('#logger').append('<span class="error_msg">' + MailPoet.MP2Migrator.fatal_error + '</span>' + '<br />\n');
|
jQuery('#logger').append('<span class="error_msg">' + MailPoet.MP2Migrator.fatal_error + '</span>' + '<br />\n');
|
||||||
}).always(function () {
|
}).always(function () {
|
||||||
@ -206,5 +206,4 @@ define('mp2migrator', ['mailpoet', 'jquery'], function (mp, jQuery) {
|
|||||||
// Update the display
|
// Update the display
|
||||||
MailPoet.MP2Migrator.updateDisplay();
|
MailPoet.MP2Migrator.updateDisplay();
|
||||||
});
|
});
|
||||||
|
|
||||||
});
|
});
|
||||||
|
@ -1,12 +1,8 @@
|
|||||||
define([
|
define([
|
||||||
'backbone',
|
'backbone',
|
||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'backbone.radio',
|
'backbone.radio'
|
||||||
'jquery',
|
], function (Backbone, Marionette, BackboneRadio) { // eslint-disable-line func-names
|
||||||
'underscore',
|
|
||||||
'handlebars',
|
|
||||||
'handlebars_helpers'
|
|
||||||
], function (Backbone, Marionette, BackboneRadio, jQuery, _, Handlebars) {
|
|
||||||
var Radio = BackboneRadio;
|
var Radio = BackboneRadio;
|
||||||
|
|
||||||
var AppView = Marionette.View.extend({
|
var AppView = Marionette.View.extend({
|
||||||
@ -23,12 +19,12 @@ define([
|
|||||||
var EditorApplication = Marionette.Application.extend({
|
var EditorApplication = Marionette.Application.extend({
|
||||||
region: '#mailpoet_editor',
|
region: '#mailpoet_editor',
|
||||||
|
|
||||||
onStart: function () {
|
onStart: function () { // eslint-disable-line func-names
|
||||||
this._appView = new AppView();
|
this._appView = new AppView();
|
||||||
this.showView(this._appView);
|
this.showView(this._appView);
|
||||||
},
|
},
|
||||||
|
|
||||||
getChannel: function (channel) {
|
getChannel: function (channel) { // eslint-disable-line func-names
|
||||||
if (channel === undefined) {
|
if (channel === undefined) {
|
||||||
return Radio.channel('global');
|
return Radio.channel('global');
|
||||||
}
|
}
|
||||||
@ -40,5 +36,4 @@ define([
|
|||||||
window.EditorApplication = app;
|
window.EditorApplication = app;
|
||||||
|
|
||||||
return app;
|
return app;
|
||||||
|
|
||||||
});
|
});
|
||||||
|
@ -6,10 +6,10 @@
|
|||||||
*/
|
*/
|
||||||
define([
|
define([
|
||||||
'backbone.marionette'
|
'backbone.marionette'
|
||||||
], function (BackboneMarionette) {
|
], function (BackboneMarionette) { // eslint-disable-line func-names
|
||||||
var Marionette = BackboneMarionette;
|
var Marionette = BackboneMarionette;
|
||||||
var BehaviorsLookup = {};
|
var BehaviorsLookup = {};
|
||||||
Marionette.Behaviors.behaviorsLookup = function () {
|
Marionette.Behaviors.behaviorsLookup = function () { // eslint-disable-line func-names
|
||||||
return BehaviorsLookup;
|
return BehaviorsLookup;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -8,16 +8,16 @@ define([
|
|||||||
'newsletter_editor/behaviors/BehaviorsLookup',
|
'newsletter_editor/behaviors/BehaviorsLookup',
|
||||||
'mailpoet',
|
'mailpoet',
|
||||||
'spectrum'
|
'spectrum'
|
||||||
], function (Marionette, BehaviorsLookup, MailPoet, Spectrum) {
|
], function (Marionette, BehaviorsLookup, MailPoet) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.ColorPickerBehavior = Marionette.Behavior.extend({
|
BL.ColorPickerBehavior = Marionette.Behavior.extend({
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
var that = this,
|
var that = this;
|
||||||
preferredFormat = 'hex6';
|
var preferredFormat = 'hex6';
|
||||||
this.view.$('.mailpoet_color').each(function () {
|
this.view.$('.mailpoet_color').each(function () { // eslint-disable-line func-names
|
||||||
var $input = that.view.$(this);
|
var $input = that.view.$(this);
|
||||||
var updateColorInput = function (color) {
|
var updateColorInput = function (color) { // eslint-disable-line func-names
|
||||||
if (color && color.getAlpha() > 0) {
|
if (color && color.getAlpha() > 0) {
|
||||||
$input.val(color.toString(preferredFormat));
|
$input.val(color.toString(preferredFormat));
|
||||||
} else {
|
} else {
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* ContainerDropZoneBehavior
|
* ContainerDropZoneBehavior
|
||||||
*
|
*
|
||||||
@ -25,11 +25,11 @@ define([
|
|||||||
this.addDropZone();
|
this.addDropZone();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
addDropZone: function (_event) {
|
addDropZone: function () {
|
||||||
var that = this,
|
var that = this;
|
||||||
view = this.view,
|
var view = this.view;
|
||||||
domElement = that.$el.get(0),
|
var domElement = that.$el.get(0);
|
||||||
acceptableElementSelector;
|
var acceptableElementSelector;
|
||||||
|
|
||||||
// TODO: Extract this limitation code to be controlled from containers
|
// TODO: Extract this limitation code to be controlled from containers
|
||||||
if (this.view.renderOptions.depth === 0) {
|
if (this.view.renderOptions.depth === 0) {
|
||||||
@ -47,11 +47,11 @@ define([
|
|||||||
interact(domElement).dropzone({
|
interact(domElement).dropzone({
|
||||||
accept: acceptableElementSelector,
|
accept: acceptableElementSelector,
|
||||||
overlap: 'pointer', // Mouse pointer denotes location of a droppable
|
overlap: 'pointer', // Mouse pointer denotes location of a droppable
|
||||||
ondragenter: function (event) {
|
ondragenter: function () {
|
||||||
// 1. Visually mark block as active for dropping
|
// 1. Visually mark block as active for dropping
|
||||||
view.$el.addClass('mailpoet_drop_active');
|
view.$el.addClass('mailpoet_drop_active');
|
||||||
},
|
},
|
||||||
ondragleave: function (event) {
|
ondragleave: function () {
|
||||||
// 1. Remove visual markings of active dropping container
|
// 1. Remove visual markings of active dropping container
|
||||||
// 2. Remove visual markings of drop position visualization
|
// 2. Remove visual markings of drop position visualization
|
||||||
that.cleanup();
|
that.cleanup();
|
||||||
@ -63,20 +63,26 @@ define([
|
|||||||
// 3b. If insertion is special, compute position (which side) and which cell the insertion belongs to
|
// 3b. If insertion is special, compute position (which side) and which cell the insertion belongs to
|
||||||
// 4. If insertion at that position is not visualized, display position visualization there, remove other visualizations from this container
|
// 4. If insertion at that position is not visualized, display position visualization there, remove other visualizations from this container
|
||||||
var dropPosition = that.getDropPosition(
|
var dropPosition = that.getDropPosition(
|
||||||
event.dragmove.pageX,
|
event.dragmove.pageX,
|
||||||
event.dragmove.pageY,
|
event.dragmove.pageY,
|
||||||
view.$el,
|
view.$el,
|
||||||
view.model.get('orientation'),
|
view.model.get('orientation'),
|
||||||
view.model.get('blocks').length
|
view.model.get('blocks').length
|
||||||
),
|
);
|
||||||
element = view.$el,
|
var element = view.$el;
|
||||||
markerWidth = '',
|
var markerWidth = '';
|
||||||
markerHeight = '',
|
var markerHeight = '';
|
||||||
containerOffset = element.offset(),
|
var containerOffset = element.offset();
|
||||||
viewCollection = that.getCollection(),
|
var viewCollection = that.getCollection();
|
||||||
marker, targetModel, targetView, targetElement,
|
var marker;
|
||||||
topOffset, leftOffset, isLastBlockInsertion,
|
var targetModel;
|
||||||
$targetBlock, margin;
|
var targetView;
|
||||||
|
var targetElement;
|
||||||
|
var topOffset;
|
||||||
|
var leftOffset;
|
||||||
|
var isLastBlockInsertion;
|
||||||
|
var $targetBlock;
|
||||||
|
var margin;
|
||||||
|
|
||||||
if (dropPosition === undefined) return;
|
if (dropPosition === undefined) return;
|
||||||
|
|
||||||
@ -178,15 +184,19 @@ define([
|
|||||||
// 4. Perform cleanup actions
|
// 4. Perform cleanup actions
|
||||||
|
|
||||||
var dropPosition = that.getDropPosition(
|
var dropPosition = that.getDropPosition(
|
||||||
event.dragEvent.pageX,
|
event.dragEvent.pageX,
|
||||||
event.dragEvent.pageY,
|
event.dragEvent.pageY,
|
||||||
view.$el,
|
view.$el,
|
||||||
view.model.get('orientation'),
|
view.model.get('orientation'),
|
||||||
view.model.get('blocks').length
|
view.model.get('blocks').length
|
||||||
),
|
);
|
||||||
droppableModel = event.draggable.getDropModel(),
|
var droppableModel = event.draggable.getDropModel();
|
||||||
viewCollection = that.getCollection(),
|
var viewCollection = that.getCollection();
|
||||||
droppedView, droppedModel, index, tempCollection, tempCollection2;
|
var droppedView;
|
||||||
|
var index;
|
||||||
|
var tempCollection;
|
||||||
|
var tempCollection2;
|
||||||
|
var tempModel;
|
||||||
|
|
||||||
if (dropPosition === undefined) return;
|
if (dropPosition === undefined) return;
|
||||||
|
|
||||||
@ -210,7 +220,7 @@ define([
|
|||||||
} else {
|
} else {
|
||||||
// Special insertion by replacing target block with collection
|
// Special insertion by replacing target block with collection
|
||||||
// and inserting dropModel into that
|
// and inserting dropModel into that
|
||||||
var tempModel = viewCollection.at(dropPosition.index);
|
tempModel = viewCollection.at(dropPosition.index);
|
||||||
|
|
||||||
tempCollection = new (window.EditorApplication.getBlockTypeModel('container'))({
|
tempCollection = new (window.EditorApplication.getBlockTypeModel('container'))({
|
||||||
orientation: (view.model.get('orientation') === 'vertical') ? 'horizontal' : 'vertical'
|
orientation: (view.model.get('orientation') === 'vertical') ? 'horizontal' : 'vertical'
|
||||||
@ -271,29 +281,33 @@ define([
|
|||||||
// 2. Remove visual markings of drop position visualization
|
// 2. Remove visual markings of drop position visualization
|
||||||
this.view.$('.mailpoet_drop_marker').remove();
|
this.view.$('.mailpoet_drop_marker').remove();
|
||||||
},
|
},
|
||||||
getDropPosition: function (eventX, eventY, is_unsafe) {
|
getDropPosition: function (eventX, eventY, isUnsafe) {
|
||||||
var SPECIAL_AREA_INSERTION_WIDTH = 0.00, // Disable special insertion. Default: 0.3
|
var SPECIAL_AREA_INSERTION_WIDTH = 0.00; // Disable special insertion. Default: 0.3
|
||||||
|
|
||||||
element = this.view.$el,
|
var element = this.view.$el;
|
||||||
orientation = this.view.model.get('orientation'),
|
var orientation = this.view.model.get('orientation');
|
||||||
|
|
||||||
elementOffset = element.offset(),
|
var elementOffset = element.offset();
|
||||||
elementPageX = elementOffset.left,
|
var elementPageX = elementOffset.left;
|
||||||
elementPageY = elementOffset.top,
|
var elementPageY = elementOffset.top;
|
||||||
elementWidth = element.outerWidth(true),
|
var elementWidth = element.outerWidth(true);
|
||||||
elementHeight = element.outerHeight(true),
|
var elementHeight = element.outerHeight(true);
|
||||||
|
|
||||||
relativeX = eventX - elementPageX,
|
var relativeX = eventX - elementPageX;
|
||||||
relativeY = eventY - elementPageY,
|
var relativeY = eventY - elementPageY;
|
||||||
|
|
||||||
relativeOffset, elementLength,
|
var relativeOffset;
|
||||||
|
var elementLength;
|
||||||
|
|
||||||
canAcceptNormalInsertion = this._canAcceptNormalInsertion(),
|
var canAcceptNormalInsertion = this._canAcceptNormalInsertion();
|
||||||
canAcceptSpecialInsertion = this._canAcceptSpecialInsertion(),
|
var canAcceptSpecialInsertion = this._canAcceptSpecialInsertion();
|
||||||
|
|
||||||
insertionType, index, position, indexAndPosition;
|
var insertionType;
|
||||||
|
var index;
|
||||||
|
var position;
|
||||||
|
var indexAndPosition;
|
||||||
|
|
||||||
var unsafe = !!is_unsafe;
|
var unsafe = !!isUnsafe;
|
||||||
|
|
||||||
if (this.getCollection().length === 0) {
|
if (this.getCollection().length === 0) {
|
||||||
return {
|
return {
|
||||||
@ -344,7 +358,7 @@ define([
|
|||||||
|
|
||||||
if (orientation === 'horizontal' && insertionType === 'special') {
|
if (orientation === 'horizontal' && insertionType === 'special') {
|
||||||
// Disable special insertion for horizontal containers
|
// Disable special insertion for horizontal containers
|
||||||
return;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
@ -359,12 +373,14 @@ define([
|
|||||||
// target element if event happens on the second half of the element.
|
// target element if event happens on the second half of the element.
|
||||||
// Halves depend on orientation.
|
// Halves depend on orientation.
|
||||||
|
|
||||||
var index = this._computeCellIndex(eventX, eventY),
|
var index = this._computeCellIndex(eventX, eventY);
|
||||||
// TODO: Handle case when there are no children, container is empty
|
// TODO: Handle case when there are no children, container is empty
|
||||||
targetView = this.getChildren().findByModel(this.getCollection().at(index)),
|
var targetView = this.getChildren().findByModel(this.getCollection().at(index));
|
||||||
orientation = this.view.model.get('orientation'),
|
var orientation = this.view.model.get('orientation');
|
||||||
element = targetView.$el,
|
var element = targetView.$el;
|
||||||
eventOffset, closeOffset, elementDimension;
|
var eventOffset;
|
||||||
|
var closeOffset;
|
||||||
|
var elementDimension;
|
||||||
|
|
||||||
if (orientation === 'vertical') {
|
if (orientation === 'vertical') {
|
||||||
eventOffset = eventY;
|
eventOffset = eventY;
|
||||||
@ -382,51 +398,51 @@ define([
|
|||||||
index: index,
|
index: index,
|
||||||
position: 'before'
|
position: 'before'
|
||||||
};
|
};
|
||||||
} else {
|
|
||||||
// Second half of the element
|
|
||||||
return {
|
|
||||||
index: index,
|
|
||||||
position: 'after'
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
|
// Second half of the element
|
||||||
|
return {
|
||||||
|
index: index,
|
||||||
|
position: 'after'
|
||||||
|
};
|
||||||
},
|
},
|
||||||
_computeSpecialIndex: function (eventX, eventY) {
|
_computeSpecialIndex: function (eventX, eventY) {
|
||||||
return this._computeCellIndex(eventX, eventY);
|
return this._computeCellIndex(eventX, eventY);
|
||||||
},
|
},
|
||||||
_computeCellIndex: function (eventX, eventY) {
|
_computeCellIndex: function (eventX, eventY) {
|
||||||
var orientation = this.view.model.get('orientation'),
|
var orientation = this.view.model.get('orientation');
|
||||||
eventOffset = (orientation === 'vertical') ? eventY : eventX,
|
var eventOffset = (orientation === 'vertical') ? eventY : eventX;
|
||||||
resultView = this.getChildren().find(function (view) {
|
var resultView = this.getChildren().find(function (view) {
|
||||||
var element = view.$el,
|
var element = view.$el;
|
||||||
closeOffset, farOffset;
|
var closeOffset;
|
||||||
|
var farOffset;
|
||||||
|
|
||||||
if (orientation === 'vertical') {
|
if (orientation === 'vertical') {
|
||||||
closeOffset = element.offset().top;
|
closeOffset = element.offset().top;
|
||||||
farOffset = element.outerHeight(true);
|
farOffset = element.outerHeight(true);
|
||||||
} else {
|
} else {
|
||||||
closeOffset = element.offset().left;
|
closeOffset = element.offset().left;
|
||||||
farOffset = element.outerWidth(true);
|
farOffset = element.outerWidth(true);
|
||||||
}
|
}
|
||||||
farOffset += closeOffset;
|
farOffset += closeOffset;
|
||||||
|
|
||||||
return closeOffset <= eventOffset && eventOffset <= farOffset;
|
return closeOffset <= eventOffset && eventOffset <= farOffset;
|
||||||
});
|
});
|
||||||
|
|
||||||
var index = (typeof resultView === 'object') ? resultView._index : 0;
|
var index = (typeof resultView === 'object') ? resultView._index : 0;
|
||||||
|
|
||||||
return index;
|
return index;
|
||||||
},
|
},
|
||||||
_canAcceptNormalInsertion: function () {
|
_canAcceptNormalInsertion: function () {
|
||||||
var orientation = this.view.model.get('orientation'),
|
var orientation = this.view.model.get('orientation');
|
||||||
depth = this.view.renderOptions.depth,
|
var depth = this.view.renderOptions.depth;
|
||||||
childCount = this.getChildren().length;
|
var childCount = this.getChildren().length;
|
||||||
// Note that depth is zero indexed. Root container has depth=0
|
// Note that depth is zero indexed. Root container has depth=0
|
||||||
return orientation === 'vertical' || (orientation === 'horizontal' && depth === 1 && childCount < this.options.columnLimit);
|
return orientation === 'vertical' || (orientation === 'horizontal' && depth === 1 && childCount < this.options.columnLimit);
|
||||||
},
|
},
|
||||||
_canAcceptSpecialInsertion: function () {
|
_canAcceptSpecialInsertion: function () {
|
||||||
var orientation = this.view.model.get('orientation'),
|
var orientation = this.view.model.get('orientation');
|
||||||
depth = this.view.renderOptions.depth,
|
var depth = this.view.renderOptions.depth;
|
||||||
childCount = this.getChildren().length;
|
var childCount = this.getChildren().length;
|
||||||
return depth === 0 || (depth === 1 && orientation === 'horizontal' && childCount <= this.options.columnLimit);
|
return depth === 0 || (depth === 1 && orientation === 'horizontal' && childCount <= this.options.columnLimit);
|
||||||
},
|
},
|
||||||
getCollectionView: function () {
|
getCollectionView: function () {
|
||||||
|
@ -10,7 +10,7 @@ define([
|
|||||||
'jquery',
|
'jquery',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup',
|
'newsletter_editor/behaviors/BehaviorsLookup',
|
||||||
'interact'
|
'interact'
|
||||||
], function (Marionette, _, jQuery, BehaviorsLookup, interact) {
|
], function (Marionette, _, jQuery, BehaviorsLookup, interact) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.DraggableBehavior = Marionette.Behavior.extend({
|
BL.DraggableBehavior = Marionette.Behavior.extend({
|
||||||
@ -24,16 +24,16 @@ define([
|
|||||||
*
|
*
|
||||||
* @return Backbone.Model A model that will be passed to the receiver
|
* @return Backbone.Model A model that will be passed to the receiver
|
||||||
*/
|
*/
|
||||||
getDropModel: function () {
|
getDropModel: function () { // eslint-disable-line func-names
|
||||||
throw "Missing 'drop' function for DraggableBehavior";
|
throw "Missing 'drop' function for DraggableBehavior";
|
||||||
},
|
},
|
||||||
|
|
||||||
onDrop: function (model, view) {},
|
onDrop: function () {}, // eslint-disable-line func-names
|
||||||
testAttachToInstance: function (model, view) { return true; }
|
testAttachToInstance: function () { return true; } // eslint-disable-line func-names
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
var that = this,
|
var that = this;
|
||||||
interactable;
|
var interactable;
|
||||||
|
|
||||||
// Give instances more control over whether Draggable should be applied
|
// Give instances more control over whether Draggable should be applied
|
||||||
if (!this.options.testAttachToInstance(this.view.model, this.view)) return;
|
if (!this.options.testAttachToInstance(this.view.model, this.view)) return;
|
||||||
@ -47,18 +47,21 @@ define([
|
|||||||
// Scroll when dragging near edges of a window
|
// Scroll when dragging near edges of a window
|
||||||
autoScroll: true,
|
autoScroll: true,
|
||||||
|
|
||||||
onstart: function (startEvent) {
|
onstart: function (startEvent) { // eslint-disable-line func-names
|
||||||
var event = startEvent;
|
var event = startEvent;
|
||||||
|
var centerXOffset;
|
||||||
|
var centerYOffset;
|
||||||
|
var tempClone;
|
||||||
|
var clone;
|
||||||
|
var $clone;
|
||||||
|
|
||||||
if (that.options.cloneOriginal === true) {
|
if (that.options.cloneOriginal === true) {
|
||||||
// Use substitution instead of a clone
|
// Use substitution instead of a clone
|
||||||
var tempClone = (_.isFunction(that.options.onDragSubstituteBy)) ? that.options.onDragSubstituteBy(that) : undefined,
|
tempClone = (_.isFunction(that.options.onDragSubstituteBy)) ? that.options.onDragSubstituteBy(that) : undefined;
|
||||||
// Or use a clone
|
// Or use a clone
|
||||||
clone = tempClone || event.target.cloneNode(true),
|
clone = tempClone || event.target.cloneNode(true);
|
||||||
|
jQuery(event.target);
|
||||||
$original = jQuery(event.target),
|
$clone = jQuery(clone);
|
||||||
$clone = jQuery(clone),
|
|
||||||
centerXOffset, centerYOffset, parentOffset;
|
|
||||||
|
|
||||||
$clone.addClass('mailpoet_droppable_active');
|
$clone.addClass('mailpoet_droppable_active');
|
||||||
$clone.css('position', 'absolute');
|
$clone.css('position', 'absolute');
|
||||||
@ -81,14 +84,13 @@ define([
|
|||||||
that.view.$el.addClass('mailpoet_hidden');
|
that.view.$el.addClass('mailpoet_hidden');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
},
|
},
|
||||||
// call this function on every dragmove event
|
// call this function on every dragmove event
|
||||||
onmove: function (event) {
|
onmove: function (event) { // eslint-disable-line func-names
|
||||||
var target = event.target,
|
var target = event.target;
|
||||||
// keep the dragged position in the data-x/data-y attributes
|
// keep the dragged position in the data-x/data-y attributes
|
||||||
x = (parseFloat(target.getAttribute('data-x')) || 0) + event.dx,
|
var x = (parseFloat(target.getAttribute('data-x')) || 0) + event.dx;
|
||||||
y = (parseFloat(target.getAttribute('data-y')) || 0) + event.dy;
|
var y = (parseFloat(target.getAttribute('data-y')) || 0) + event.dy;
|
||||||
|
|
||||||
// translate the element
|
// translate the element
|
||||||
target.style.transform = 'translate(' + x + 'px, ' + y + 'px)';
|
target.style.transform = 'translate(' + x + 'px, ' + y + 'px)';
|
||||||
@ -98,7 +100,7 @@ define([
|
|||||||
target.setAttribute('data-x', x);
|
target.setAttribute('data-x', x);
|
||||||
target.setAttribute('data-y', y);
|
target.setAttribute('data-y', y);
|
||||||
},
|
},
|
||||||
onend: function (event) {
|
onend: function (event) { // eslint-disable-line func-names
|
||||||
var target = event.target;
|
var target = event.target;
|
||||||
target.style.transform = '';
|
target.style.transform = '';
|
||||||
target.style.webkitTransform = target.style.transform;
|
target.style.webkitTransform = target.style.transform;
|
||||||
@ -117,7 +119,7 @@ define([
|
|||||||
})
|
})
|
||||||
.preventDefault('auto')
|
.preventDefault('auto')
|
||||||
.styleCursor(false)
|
.styleCursor(false)
|
||||||
.actionChecker(function (pointer, event, action) {
|
.actionChecker(function (pointer, event, action) { // eslint-disable-line func-names
|
||||||
// Disable dragging with right click
|
// Disable dragging with right click
|
||||||
if (event.button !== 0) {
|
if (event.button !== 0) {
|
||||||
return null;
|
return null;
|
||||||
@ -131,7 +133,7 @@ define([
|
|||||||
} else {
|
} else {
|
||||||
interactable.getDropModel = this.view.getDropFunc();
|
interactable.getDropModel = this.view.getDropFunc();
|
||||||
}
|
}
|
||||||
interactable.onDrop = function (opts) {
|
interactable.onDrop = function (opts) { // eslint-disable-line func-names
|
||||||
var options = opts;
|
var options = opts;
|
||||||
if (_.isObject(options)) {
|
if (_.isObject(options)) {
|
||||||
// Inject Draggable behavior if possible
|
// Inject Draggable behavior if possible
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
define([
|
define([
|
||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup'
|
'newsletter_editor/behaviors/BehaviorsLookup'
|
||||||
], function (Marionette, BehaviorsLookup) {
|
], function (Marionette, BehaviorsLookup) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.HighlightContainerBehavior = Marionette.Behavior.extend({
|
BL.HighlightContainerBehavior = Marionette.Behavior.extend({
|
||||||
@ -14,10 +14,10 @@ define([
|
|||||||
'mouseenter @ui.tools': 'enableHighlight',
|
'mouseenter @ui.tools': 'enableHighlight',
|
||||||
'mouseleave @ui.tools': 'disableHighlight'
|
'mouseleave @ui.tools': 'disableHighlight'
|
||||||
},
|
},
|
||||||
enableHighlight: function () {
|
enableHighlight: function () { // eslint-disable-line func-names
|
||||||
this.$el.addClass('mailpoet_highlight');
|
this.$el.addClass('mailpoet_highlight');
|
||||||
},
|
},
|
||||||
disableHighlight: function () {
|
disableHighlight: function () { // eslint-disable-line func-names
|
||||||
if (!this.view._isBeingEdited) {
|
if (!this.view._isBeingEdited) {
|
||||||
this.$el.removeClass('mailpoet_highlight');
|
this.$el.removeClass('mailpoet_highlight');
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
define([
|
define([
|
||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup'
|
'newsletter_editor/behaviors/BehaviorsLookup'
|
||||||
], function (Marionette, BehaviorsLookup) {
|
], function (Marionette, BehaviorsLookup) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.HighlightEditingBehavior = Marionette.Behavior.extend({
|
BL.HighlightEditingBehavior = Marionette.Behavior.extend({
|
||||||
@ -14,11 +14,11 @@ define([
|
|||||||
startEditing: 'enableHighlight',
|
startEditing: 'enableHighlight',
|
||||||
stopEditing: 'disableHighlight'
|
stopEditing: 'disableHighlight'
|
||||||
},
|
},
|
||||||
enableHighlight: function () {
|
enableHighlight: function () { // eslint-disable-line func-names
|
||||||
this.view._isBeingEdited = true;
|
this.view._isBeingEdited = true;
|
||||||
this.$el.addClass('mailpoet_highlight');
|
this.$el.addClass('mailpoet_highlight');
|
||||||
},
|
},
|
||||||
disableHighlight: function () {
|
disableHighlight: function () { // eslint-disable-line func-names
|
||||||
this.view._isBeingEdited = false;
|
this.view._isBeingEdited = false;
|
||||||
this.$el.removeClass('mailpoet_highlight');
|
this.$el.removeClass('mailpoet_highlight');
|
||||||
}
|
}
|
||||||
|
@ -7,19 +7,20 @@ define([
|
|||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup',
|
'newsletter_editor/behaviors/BehaviorsLookup',
|
||||||
'interact'
|
'interact'
|
||||||
], function (Marionette, BehaviorsLookup, interact) {
|
], function (Marionette, BehaviorsLookup, interact) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.ResizableBehavior = Marionette.Behavior.extend({
|
BL.ResizableBehavior = Marionette.Behavior.extend({
|
||||||
defaults: {
|
defaults: {
|
||||||
elementSelector: null,
|
elementSelector: null,
|
||||||
resizeHandleSelector: true, // true will use edges of the element itself
|
resizeHandleSelector: true, // true will use edges of the element itself
|
||||||
|
transformationFunction: function transformationFunction(y) { return y; }, // for blocks that use the default onResize function
|
||||||
minLength: 0,
|
minLength: 0,
|
||||||
maxLength: Infinity,
|
maxLength: Infinity,
|
||||||
modelField: 'styles.block.height',
|
modelField: 'styles.block.height',
|
||||||
onResize: function (event) {
|
onResize: function (event) { // eslint-disable-line func-names
|
||||||
var currentLength = parseFloat(this.view.model.get(this.options.modelField)),
|
var currentLength = parseFloat(this.view.model.get(this.options.modelField));
|
||||||
newLength = currentLength + event.y;
|
var newLength = currentLength + this.options.transformationFunction(event.dy);
|
||||||
newLength = Math.min(this.options.maxLength, Math.max(this.options.minLength, newLength));
|
newLength = Math.min(this.options.maxLength, Math.max(this.options.minLength, newLength));
|
||||||
this.view.model.set(this.options.modelField, newLength + 'px');
|
this.view.model.set(this.options.modelField, newLength + 'px');
|
||||||
}
|
}
|
||||||
@ -28,16 +29,16 @@ define([
|
|||||||
mouseenter: 'showResizeHandle',
|
mouseenter: 'showResizeHandle',
|
||||||
mouseleave: 'hideResizeHandle'
|
mouseleave: 'hideResizeHandle'
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.attachResize();
|
this.attachResize();
|
||||||
|
|
||||||
if (this.isBeingResized !== true) {
|
if (this.isBeingResized !== true) {
|
||||||
this.hideResizeHandle();
|
this.hideResizeHandle();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
attachResize: function () {
|
attachResize: function () { // eslint-disable-line func-names
|
||||||
var domElement = (this.options.elementSelector === null) ? this.view.$el.get(0) : this.view.$(this.options.elementSelector).get(0),
|
var domElement = (this.options.elementSelector === null) ? this.view.$el.get(0) : this.view.$(this.options.elementSelector).get(0);
|
||||||
that = this;
|
var that = this;
|
||||||
interact(domElement).resizable({
|
interact(domElement).resizable({
|
||||||
// axis: 'y',
|
// axis: 'y',
|
||||||
edges: {
|
edges: {
|
||||||
@ -47,25 +48,24 @@ define([
|
|||||||
bottom: (typeof this.options.resizeHandleSelector === 'string') ? this.view.$(this.options.resizeHandleSelector).get(0) : this.options.resizeHandleSelector
|
bottom: (typeof this.options.resizeHandleSelector === 'string') ? this.view.$(this.options.resizeHandleSelector).get(0) : this.options.resizeHandleSelector
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.on('resizestart', function (event) {
|
.on('resizestart', function () { // eslint-disable-line func-names
|
||||||
that.isBeingResized = true;
|
that.isBeingResized = true;
|
||||||
that.$el.addClass('mailpoet_resize_active');
|
that.$el.addClass('mailpoet_resize_active');
|
||||||
})
|
}).on('resizemove', function (event) { // eslint-disable-line func-names
|
||||||
.on('resizemove', function (event) {
|
|
||||||
var onResize = that.options.onResize.bind(that);
|
var onResize = that.options.onResize.bind(that);
|
||||||
return onResize(event);
|
return onResize(event);
|
||||||
})
|
})
|
||||||
.on('resizeend', function (event) {
|
.on('resizeend', function () { // eslint-disable-line func-names
|
||||||
that.isBeingResized = null;
|
that.isBeingResized = null;
|
||||||
that.$el.removeClass('mailpoet_resize_active');
|
that.$el.removeClass('mailpoet_resize_active');
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
showResizeHandle: function () {
|
showResizeHandle: function () { // eslint-disable-line func-names
|
||||||
if (typeof this.options.resizeHandleSelector === 'string') {
|
if (typeof this.options.resizeHandleSelector === 'string') {
|
||||||
this.view.$(this.options.resizeHandleSelector).removeClass('mailpoet_hidden');
|
this.view.$(this.options.resizeHandleSelector).removeClass('mailpoet_hidden');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
hideResizeHandle: function () {
|
hideResizeHandle: function () { // eslint-disable-line func-names
|
||||||
if (typeof this.options.resizeHandleSelector === 'string') {
|
if (typeof this.options.resizeHandleSelector === 'string') {
|
||||||
this.view.$(this.options.resizeHandleSelector).addClass('mailpoet_hidden');
|
this.view.$(this.options.resizeHandleSelector).addClass('mailpoet_hidden');
|
||||||
}
|
}
|
||||||
|
@ -7,7 +7,7 @@ define([
|
|||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'jquery',
|
'jquery',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup'
|
'newsletter_editor/behaviors/BehaviorsLookup'
|
||||||
], function (Marionette, jQuery, BehaviorsLookup) {
|
], function (Marionette, jQuery, BehaviorsLookup) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.ShowSettingsBehavior = Marionette.Behavior.extend({
|
BL.ShowSettingsBehavior = Marionette.Behavior.extend({
|
||||||
@ -17,12 +17,12 @@ define([
|
|||||||
events: {
|
events: {
|
||||||
'click .mailpoet_content': 'showSettings'
|
'click .mailpoet_content': 'showSettings'
|
||||||
},
|
},
|
||||||
showSettings: function (event) {
|
showSettings: function (event) { // eslint-disable-line func-names
|
||||||
if (!this.isIgnoredElement(event.target)) {
|
if (!this.isIgnoredElement(event.target)) {
|
||||||
this.view.triggerMethod('showSettings');
|
this.view.triggerMethod('showSettings');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
isIgnoredElement: function (element) {
|
isIgnoredElement: function (element) { // eslint-disable-line func-names
|
||||||
return this.options.ignoreFrom
|
return this.options.ignoreFrom
|
||||||
&& this.options.ignoreFrom.length > 0
|
&& this.options.ignoreFrom.length > 0
|
||||||
&& jQuery(element).is(this.options.ignoreFrom);
|
&& jQuery(element).is(this.options.ignoreFrom);
|
||||||
|
@ -7,26 +7,26 @@ define([
|
|||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'underscore',
|
'underscore',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup'
|
'newsletter_editor/behaviors/BehaviorsLookup'
|
||||||
], function (Marionette, _, BehaviorsLookup) {
|
], function (Marionette, _, BehaviorsLookup) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.SortableBehavior = Marionette.Behavior.extend({
|
BL.SortableBehavior = Marionette.Behavior.extend({
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
var collection = this.view.collection;
|
var collection = this.view.collection;
|
||||||
|
|
||||||
if (_.isFunction(this.$el.sortable)) {
|
if (_.isFunction(this.$el.sortable)) {
|
||||||
this.$el.sortable({
|
this.$el.sortable({
|
||||||
cursor: 'move',
|
cursor: 'move',
|
||||||
start: function (event, ui) {
|
start: function (event, ui) { // eslint-disable-line func-names
|
||||||
ui.item.data('previousIndex', ui.item.index());
|
ui.item.data('previousIndex', ui.item.index());
|
||||||
},
|
},
|
||||||
end: function (event, ui) {
|
end: function (event, ui) { // eslint-disable-line func-names
|
||||||
ui.item.removeData('previousIndex');
|
ui.item.removeData('previousIndex');
|
||||||
},
|
},
|
||||||
update: function (event, ui) {
|
update: function (event, ui) { // eslint-disable-line func-names
|
||||||
var previousIndex = ui.item.data('previousIndex'),
|
var previousIndex = ui.item.data('previousIndex');
|
||||||
newIndex = ui.item.index(),
|
var newIndex = ui.item.index();
|
||||||
model = collection.at(previousIndex);
|
var model = collection.at(previousIndex);
|
||||||
|
|
||||||
// Replicate DOM changes. Move target model to a new position
|
// Replicate DOM changes. Move target model to a new position
|
||||||
// within the collection
|
// within the collection
|
||||||
|
@ -7,7 +7,7 @@ define([
|
|||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'underscore',
|
'underscore',
|
||||||
'newsletter_editor/behaviors/BehaviorsLookup'
|
'newsletter_editor/behaviors/BehaviorsLookup'
|
||||||
], function (Marionette, _, BehaviorsLookup) {
|
], function (Marionette, _, BehaviorsLookup) { // eslint-disable-line func-names
|
||||||
var BL = BehaviorsLookup;
|
var BL = BehaviorsLookup;
|
||||||
|
|
||||||
BL.TextEditorBehavior = Marionette.Behavior.extend({
|
BL.TextEditorBehavior = Marionette.Behavior.extend({
|
||||||
@ -19,9 +19,9 @@ define([
|
|||||||
invalidElements: 'script',
|
invalidElements: 'script',
|
||||||
blockFormats: 'Paragraph=p',
|
blockFormats: 'Paragraph=p',
|
||||||
plugins: 'link textcolor colorpicker mailpoet_shortcodes',
|
plugins: 'link textcolor colorpicker mailpoet_shortcodes',
|
||||||
configurationFilter: function (originalConfig) { return originalConfig; }
|
configurationFilter: function (originalConfig) { return originalConfig; } // eslint-disable-line func-names
|
||||||
},
|
},
|
||||||
onDomRefresh: function () {
|
onDomRefresh: function () { // eslint-disable-line func-names
|
||||||
var that = this;
|
var that = this;
|
||||||
if (this.view.disableTextEditor === true) {
|
if (this.view.disableTextEditor === true) {
|
||||||
return;
|
return;
|
||||||
@ -42,7 +42,7 @@ define([
|
|||||||
relative_urls: false,
|
relative_urls: false,
|
||||||
remove_script_host: false,
|
remove_script_host: false,
|
||||||
convert_urls: true,
|
convert_urls: true,
|
||||||
urlconverter_callback: function (url, node, on_save, name) {
|
urlconverter_callback: function (url) { // eslint-disable-line func-names
|
||||||
if (url.match(/\[.+\]/g)) {
|
if (url.match(/\[.+\]/g)) {
|
||||||
// Do not convert URLs with shortcodes
|
// Do not convert URLs with shortcodes
|
||||||
return url;
|
return url;
|
||||||
@ -56,12 +56,12 @@ define([
|
|||||||
|
|
||||||
plugins: this.options.plugins,
|
plugins: this.options.plugins,
|
||||||
|
|
||||||
setup: function (editor) {
|
setup: function (editor) { // eslint-disable-line func-names
|
||||||
editor.on('change', function (e) {
|
editor.on('change', function () { // eslint-disable-line func-names
|
||||||
that.view.triggerMethod('text:editor:change', editor.getContent());
|
that.view.triggerMethod('text:editor:change', editor.getContent());
|
||||||
});
|
});
|
||||||
|
|
||||||
editor.on('click', function (e) {
|
editor.on('click', function (e) { // eslint-disable-line func-names
|
||||||
editor.focus();
|
editor.focus();
|
||||||
if (that._isActivationClick) {
|
if (that._isActivationClick) {
|
||||||
editor.selection.setRng(
|
editor.selection.setRng(
|
||||||
@ -71,12 +71,12 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
editor.on('focus', function (e) {
|
editor.on('focus', function () { // eslint-disable-line func-names
|
||||||
that.view.triggerMethod('text:editor:focus');
|
that.view.triggerMethod('text:editor:focus');
|
||||||
that._isActivationClick = true;
|
that._isActivationClick = true;
|
||||||
});
|
});
|
||||||
|
|
||||||
editor.on('blur', function (e) {
|
editor.on('blur', function () { // eslint-disable-line func-names
|
||||||
that.view.triggerMethod('text:editor:blur');
|
that.view.triggerMethod('text:editor:blur');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Automated latest content block.
|
* Automated latest content block.
|
||||||
* Only query parameters can be modified by the user. Posts pulled by this
|
* Only query parameters can be modified by the user. Posts pulled by this
|
||||||
@ -27,11 +28,10 @@ define([
|
|||||||
_,
|
_,
|
||||||
jQuery
|
jQuery
|
||||||
) {
|
) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock;
|
var base = BaseBlock;
|
||||||
|
|
||||||
Module.ALCSupervisor = SuperModel.extend({
|
Module.ALCSupervisor = SuperModel.extend({
|
||||||
initialize: function () {
|
initialize: function () {
|
||||||
@ -43,12 +43,13 @@ define([
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
refresh: function () {
|
refresh: function () {
|
||||||
|
var blocks;
|
||||||
var models = App.findModels(function (model) {
|
var models = App.findModels(function (model) {
|
||||||
return model.get('type') === 'automatedLatestContent';
|
return model.get('type') === 'automatedLatestContent';
|
||||||
}) || [];
|
}) || [];
|
||||||
|
|
||||||
if (models.length === 0) return;
|
if (models.length === 0) return;
|
||||||
var blocks = _.map(models, function (model) {
|
blocks = _.map(models, function (model) {
|
||||||
return model.toJSON();
|
return model.toJSON();
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -60,8 +61,8 @@ define([
|
|||||||
_.each(
|
_.each(
|
||||||
_.zip(models, renderedBlocks),
|
_.zip(models, renderedBlocks),
|
||||||
function (args) {
|
function (args) {
|
||||||
var model = args[0],
|
var model = args[0];
|
||||||
contents = args[1];
|
var contents = args[1];
|
||||||
model.trigger('refreshPosts', contents);
|
model.trigger('refreshPosts', contents);
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
@ -150,12 +151,12 @@ define([
|
|||||||
}),
|
}),
|
||||||
onDragSubstituteBy: function () { return Module.AutomatedLatestContentWidgetView; },
|
onDragSubstituteBy: function () { return Module.AutomatedLatestContentWidgetView; },
|
||||||
onRender: function () {
|
onRender: function () {
|
||||||
var ContainerView = App.getBlockTypeView('container'),
|
var ContainerView = App.getBlockTypeView('container');
|
||||||
renderOptions = {
|
var renderOptions = {
|
||||||
disableTextEditor: true,
|
disableTextEditor: true,
|
||||||
disableDragAndDrop: true,
|
disableDragAndDrop: true,
|
||||||
emptyContainerMessage: MailPoet.I18n.t('noPostsToDisplay')
|
emptyContainerMessage: MailPoet.I18n.t('noPostsToDisplay')
|
||||||
};
|
};
|
||||||
this.toolsView = new Module.AutomatedLatestContentBlockToolsView({ model: this.model });
|
this.toolsView = new Module.AutomatedLatestContentBlockToolsView({ model: this.model });
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
this.showChildView('postsRegion', new ContainerView({ model: this.model.get('_container'), renderOptions: renderOptions }));
|
this.showChildView('postsRegion', new ContainerView({ model: this.model.get('_container'), renderOptions: renderOptions }));
|
||||||
@ -213,12 +214,13 @@ define([
|
|||||||
},
|
},
|
||||||
transport: function (options, success, failure) {
|
transport: function (options, success, failure) {
|
||||||
var taxonomies;
|
var taxonomies;
|
||||||
|
var termsPromise;
|
||||||
var promise = CommunicationComponent.getTaxonomies(
|
var promise = CommunicationComponent.getTaxonomies(
|
||||||
that.model.get('contentType')
|
that.model.get('contentType')
|
||||||
).then(function (tax) {
|
).then(function (tax) {
|
||||||
taxonomies = tax;
|
taxonomies = tax;
|
||||||
// Fetch available terms based on the list of taxonomies already fetched
|
// Fetch available terms based on the list of taxonomies already fetched
|
||||||
var promise = CommunicationComponent.getTerms({
|
termsPromise = CommunicationComponent.getTerms({
|
||||||
search: options.data.term,
|
search: options.data.term,
|
||||||
taxonomies: _.keys(taxonomies)
|
taxonomies: _.keys(taxonomies)
|
||||||
}).then(function (terms) {
|
}).then(function (terms) {
|
||||||
@ -227,7 +229,7 @@ define([
|
|||||||
terms: terms
|
terms: terms
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
return promise;
|
return termsPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
promise.then(success);
|
promise.then(success);
|
||||||
@ -264,9 +266,9 @@ define([
|
|||||||
}
|
}
|
||||||
}).trigger('change');
|
}).trigger('change');
|
||||||
},
|
},
|
||||||
toggleDisplayOptions: function (event) {
|
toggleDisplayOptions: function () {
|
||||||
var el = this.$('.mailpoet_automated_latest_content_display_options'),
|
var el = this.$('.mailpoet_automated_latest_content_display_options');
|
||||||
showControl = this.$('.mailpoet_automated_latest_content_show_display_options');
|
var showControl = this.$('.mailpoet_automated_latest_content_show_display_options');
|
||||||
if (el.hasClass('mailpoet_closed')) {
|
if (el.hasClass('mailpoet_closed')) {
|
||||||
el.removeClass('mailpoet_closed');
|
el.removeClass('mailpoet_closed');
|
||||||
showControl.addClass('mailpoet_hidden');
|
showControl.addClass('mailpoet_hidden');
|
||||||
@ -275,7 +277,7 @@ define([
|
|||||||
showControl.removeClass('mailpoet_hidden');
|
showControl.removeClass('mailpoet_hidden');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
showButtonSettings: function (event) {
|
showButtonSettings: function () {
|
||||||
var buttonModule = ButtonBlock;
|
var buttonModule = ButtonBlock;
|
||||||
(new buttonModule.ButtonBlockSettingsView({
|
(new buttonModule.ButtonBlockSettingsView({
|
||||||
model: this.model.get('readMoreButton'),
|
model: this.model.get('readMoreButton'),
|
||||||
@ -286,7 +288,7 @@ define([
|
|||||||
}
|
}
|
||||||
})).render();
|
})).render();
|
||||||
},
|
},
|
||||||
showDividerSettings: function (event) {
|
showDividerSettings: function () {
|
||||||
var dividerModule = DividerBlock;
|
var dividerModule = DividerBlock;
|
||||||
(new dividerModule.DividerBlockSettingsView({
|
(new dividerModule.DividerBlockSettingsView({
|
||||||
model: this.model.get('divider'),
|
model: this.model.get('divider'),
|
||||||
@ -349,8 +351,8 @@ define([
|
|||||||
this.changeField('titleFormat', event);
|
this.changeField('titleFormat', event);
|
||||||
},
|
},
|
||||||
_updateContentTypes: function (postTypes) {
|
_updateContentTypes: function (postTypes) {
|
||||||
var select = this.$('.mailpoet_automated_latest_content_content_type'),
|
var select = this.$('.mailpoet_automated_latest_content_content_type');
|
||||||
selectedValue = this.model.get('contentType');
|
var selectedValue = this.model.get('contentType');
|
||||||
|
|
||||||
select.find('option').remove();
|
select.find('option').remove();
|
||||||
_.each(postTypes, function (type) {
|
_.each(postTypes, function (type) {
|
||||||
@ -378,21 +380,21 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('automatedLatestContent', {
|
BeforeStartApp.registerBlockType('automatedLatestContent', {
|
||||||
blockModel: Module.AutomatedLatestContentBlockModel,
|
blockModel: Module.AutomatedLatestContentBlockModel,
|
||||||
blockView: Module.AutomatedLatestContentBlockView
|
blockView: Module.AutomatedLatestContentBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'automatedLatestContent',
|
name: 'automatedLatestContent',
|
||||||
widgetView: Module.AutomatedLatestContentWidgetView,
|
widgetView: Module.AutomatedLatestContentWidgetView,
|
||||||
priority: 97
|
priority: 97
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function (StartApp) {
|
||||||
var Application = App;
|
var Application = StartApp;
|
||||||
Application._ALCSupervisor = new Module.ALCSupervisor();
|
Application._ALCSupervisor = new Module.ALCSupervisor();
|
||||||
Application._ALCSupervisor.refresh();
|
Application._ALCSupervisor.refresh();
|
||||||
});
|
});
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Defines base classes for actual content blocks to extend.
|
* Defines base classes for actual content blocks to extend.
|
||||||
* Extending content block modules need to at least extend
|
* Extending content block modules need to at least extend
|
||||||
@ -12,17 +13,15 @@ define([
|
|||||||
'jquery',
|
'jquery',
|
||||||
'mailpoet',
|
'mailpoet',
|
||||||
'modal'
|
'modal'
|
||||||
], function (App, Marionette, SuperModel, _, jQuery, MailPoet, Modal) {
|
], function (App, Marionette, SuperModel, _, jQuery, MailPoet) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
AugmentedView = Marionette.View.extend({});
|
var AugmentedView = Marionette.View.extend({});
|
||||||
|
|
||||||
Module.BlockModel = SuperModel.extend({
|
Module.BlockModel = SuperModel.extend({
|
||||||
stale: [], // Attributes to be removed upon saving
|
stale: [], // Attributes to be removed upon saving
|
||||||
initialize: function () {
|
initialize: function () {
|
||||||
var that = this;
|
|
||||||
this.on('change', function () {
|
this.on('change', function () {
|
||||||
App.getChannel().trigger('autoSave');
|
App.getChannel().trigger('autoSave');
|
||||||
});
|
});
|
||||||
@ -68,7 +67,8 @@ define([
|
|||||||
options.dragBehavior.view.model.destroy();
|
options.dragBehavior.view.model.destroy();
|
||||||
},
|
},
|
||||||
onDragSubstituteBy: function (behavior) {
|
onDragSubstituteBy: function (behavior) {
|
||||||
var WidgetView, node;
|
var WidgetView;
|
||||||
|
var node;
|
||||||
// When block is being dragged, display the widget icon instead.
|
// When block is being dragged, display the widget icon instead.
|
||||||
// This will create an instance of block's widget view and
|
// This will create an instance of block's widget view and
|
||||||
// use it's rendered DOM element instead of the content block
|
// use it's rendered DOM element instead of the content block
|
||||||
@ -79,6 +79,7 @@ define([
|
|||||||
WidgetView.destroy();
|
WidgetView.destroy();
|
||||||
return node;
|
return node;
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
HighlightEditingBehavior: {}
|
HighlightEditingBehavior: {}
|
||||||
@ -98,13 +99,13 @@ define([
|
|||||||
this.on('dom:refresh', this.showBlock, this);
|
this.on('dom:refresh', this.showBlock, this);
|
||||||
this._isFirstRender = true;
|
this._isFirstRender = true;
|
||||||
},
|
},
|
||||||
showTools: function (_event) {
|
showTools: function () {
|
||||||
if (!this.showingToolsDisabled) {
|
if (!this.showingToolsDisabled) {
|
||||||
this.$('> .mailpoet_tools').addClass('mailpoet_display_tools');
|
this.$('> .mailpoet_tools').addClass('mailpoet_display_tools');
|
||||||
this.toolsView.triggerMethod('showTools');
|
this.toolsView.triggerMethod('showTools');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
hideTools: function (e) {
|
hideTools: function () {
|
||||||
this.$('> .mailpoet_tools').removeClass('mailpoet_display_tools');
|
this.$('> .mailpoet_tools').removeClass('mailpoet_display_tools');
|
||||||
this.toolsView.triggerMethod('hideTools');
|
this.toolsView.triggerMethod('hideTools');
|
||||||
},
|
},
|
||||||
@ -217,9 +218,19 @@ define([
|
|||||||
(new ViewType(_.extend({ model: this.model }, options || {}))).render();
|
(new ViewType(_.extend({ model: this.model }, options || {}))).render();
|
||||||
},
|
},
|
||||||
showDeletionConfirmation: function () {
|
showDeletionConfirmation: function () {
|
||||||
|
this.$('.mailpoet_delete_block')
|
||||||
|
.closest('.mailpoet_block')
|
||||||
|
.find('> .mailpoet_block_highlight')
|
||||||
|
.css({ background: '#E64047', opacity: 0.5 });
|
||||||
|
|
||||||
this.$('.mailpoet_delete_block').addClass('mailpoet_delete_block_activated');
|
this.$('.mailpoet_delete_block').addClass('mailpoet_delete_block_activated');
|
||||||
},
|
},
|
||||||
hideDeletionConfirmation: function () {
|
hideDeletionConfirmation: function () {
|
||||||
|
this.$('.mailpoet_delete_block')
|
||||||
|
.closest('.mailpoet_block')
|
||||||
|
.find('> .mailpoet_block_highlight')
|
||||||
|
.css({ background: 'transparent', opacity: 1 });
|
||||||
|
|
||||||
this.$('.mailpoet_delete_block').removeClass('mailpoet_delete_block_activated');
|
this.$('.mailpoet_delete_block').removeClass('mailpoet_delete_block_activated');
|
||||||
},
|
},
|
||||||
deleteBlock: function (event) {
|
deleteBlock: function (event) {
|
||||||
@ -240,8 +251,9 @@ define([
|
|||||||
ColorPickerBehavior: {}
|
ColorPickerBehavior: {}
|
||||||
},
|
},
|
||||||
initialize: function (params) {
|
initialize: function (params) {
|
||||||
|
var panelParams;
|
||||||
this.model.trigger('startEditing');
|
this.model.trigger('startEditing');
|
||||||
var panelParams = {
|
panelParams = {
|
||||||
element: this.$el,
|
element: this.$el,
|
||||||
template: '',
|
template: '',
|
||||||
position: 'right',
|
position: 'right',
|
||||||
@ -262,7 +274,7 @@ define([
|
|||||||
model: this.model.toJSON()
|
model: this.model.toJSON()
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
close: function (event) {
|
close: function () {
|
||||||
this.destroy();
|
this.destroy();
|
||||||
},
|
},
|
||||||
changeField: function (field, event) {
|
changeField: function (field, event) {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Button content block
|
* Button content block
|
||||||
*/
|
*/
|
||||||
@ -8,11 +9,10 @@ define([
|
|||||||
'underscore',
|
'underscore',
|
||||||
'jquery'
|
'jquery'
|
||||||
], function (App, BaseBlock, MailPoet, _, jQuery) {
|
], function (App, BaseBlock, MailPoet, _, jQuery) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock;
|
var base = BaseBlock;
|
||||||
|
|
||||||
Module.ButtonBlockModel = base.BlockModel.extend({
|
Module.ButtonBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () {
|
||||||
@ -132,13 +132,13 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('button', {
|
BeforeStartApp.registerBlockType('button', {
|
||||||
blockModel: Module.ButtonBlockModel,
|
blockModel: Module.ButtonBlockModel,
|
||||||
blockView: Module.ButtonBlockView
|
blockView: Module.ButtonBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'button',
|
name: 'button',
|
||||||
widgetView: Module.ButtonWidgetView,
|
widgetView: Module.ButtonWidgetView,
|
||||||
priority: 92
|
priority: 92
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Container content block.
|
* Container content block.
|
||||||
* This is a special kind of block, as it can contain content blocks, as well
|
* This is a special kind of block, as it can contain content blocks, as well
|
||||||
@ -11,12 +12,11 @@ define([
|
|||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'newsletter_editor/blocks/base'
|
'newsletter_editor/blocks/base'
|
||||||
], function (Backbone, Marionette, _, jQuery, App, BaseBlock) {
|
], function (Backbone, Marionette, _, jQuery, App, BaseBlock) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock,
|
var base = BaseBlock;
|
||||||
BlockCollection;
|
var BlockCollection;
|
||||||
|
|
||||||
BlockCollection = Backbone.Collection.extend({
|
BlockCollection = Backbone.Collection.extend({
|
||||||
model: base.BlockModel,
|
model: base.BlockModel,
|
||||||
@ -24,7 +24,6 @@ define([
|
|||||||
this.on('add change remove', function () { App.getChannel().trigger('autoSave'); });
|
this.on('add change remove', function () { App.getChannel().trigger('autoSave'); });
|
||||||
},
|
},
|
||||||
parse: function (response) {
|
parse: function (response) {
|
||||||
var self = this;
|
|
||||||
return _.map(response, function (block) {
|
return _.map(response, function (block) {
|
||||||
var Type = App.getBlockTypeModel(block.type);
|
var Type = App.getBlockTypeModel(block.type);
|
||||||
// TODO: If type has no registered model, use a backup one
|
// TODO: If type has no registered model, use a backup one
|
||||||
@ -55,6 +54,7 @@ define([
|
|||||||
if (invalidBlock) {
|
if (invalidBlock) {
|
||||||
return invalidBlock.validationError;
|
return invalidBlock.validationError;
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
parse: function (response) {
|
parse: function (response) {
|
||||||
// If container has any blocks - add them to a collection
|
// If container has any blocks - add them to a collection
|
||||||
@ -66,7 +66,7 @@ define([
|
|||||||
return response;
|
return response;
|
||||||
},
|
},
|
||||||
getChildren: function () {
|
getChildren: function () {
|
||||||
var models = this.get('blocks').map(function (model, index, list) {
|
var models = this.get('blocks').map(function (model) {
|
||||||
return [model, model.getChildren()];
|
return [model, model.getChildren()];
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -121,7 +121,8 @@ define([
|
|||||||
options.dragBehavior.view.model.destroy();
|
options.dragBehavior.view.model.destroy();
|
||||||
},
|
},
|
||||||
onDragSubstituteBy: function (behavior) {
|
onDragSubstituteBy: function (behavior) {
|
||||||
var WidgetView, node;
|
var WidgetView;
|
||||||
|
var node;
|
||||||
// When block is being dragged, display the widget icon instead.
|
// When block is being dragged, display the widget icon instead.
|
||||||
// This will create an instance of block's widget view and
|
// This will create an instance of block's widget view and
|
||||||
// use it's rendered DOM element instead of the content block
|
// use it's rendered DOM element instead of the content block
|
||||||
@ -132,6 +133,7 @@ define([
|
|||||||
WidgetView.destroy();
|
WidgetView.destroy();
|
||||||
return node;
|
return node;
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
testAttachToInstance: function (model, view) {
|
testAttachToInstance: function (model, view) {
|
||||||
// Attach Draggable only to layout containers and disable it
|
// Attach Draggable only to layout containers and disable it
|
||||||
@ -149,7 +151,6 @@ define([
|
|||||||
if (this.model.get('blocks').length === 2) return Module.TwoColumnContainerWidgetView;
|
if (this.model.get('blocks').length === 2) return Module.TwoColumnContainerWidgetView;
|
||||||
}
|
}
|
||||||
return Module.OneColumnContainerWidgetView;
|
return Module.OneColumnContainerWidgetView;
|
||||||
|
|
||||||
},
|
},
|
||||||
initialize: function (options) {
|
initialize: function (options) {
|
||||||
base.BlockView.prototype.initialize.apply(this, arguments);
|
base.BlockView.prototype.initialize.apply(this, arguments);
|
||||||
@ -190,24 +191,24 @@ define([
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
toggleEditingLayer: function (event) {
|
toggleEditingLayer: function (event) {
|
||||||
var that = this,
|
var that = this;
|
||||||
$toggleButton = this.$('> .mailpoet_tools .mailpoet_newsletter_layer_selector'),
|
var $toggleButton = this.$('> .mailpoet_tools .mailpoet_newsletter_layer_selector');
|
||||||
$overlay = jQuery('.mailpoet_layer_overlay'),
|
var $overlay = jQuery('.mailpoet_layer_overlay');
|
||||||
$container = this.$('> .mailpoet_container'),
|
var $container = this.$('> .mailpoet_container');
|
||||||
enableContainerLayer = function () {
|
var disableContainerLayer = function () {
|
||||||
that.$el.addClass('mailpoet_container_layer_active');
|
that.$el.removeClass('mailpoet_container_layer_active');
|
||||||
$toggleButton.addClass('mailpoet_container_layer_active');
|
$toggleButton.removeClass('mailpoet_container_layer_active');
|
||||||
$container.addClass('mailpoet_layer_highlight');
|
$container.removeClass('mailpoet_layer_highlight');
|
||||||
$overlay.click(disableContainerLayer);
|
$overlay.hide();
|
||||||
$overlay.show();
|
$overlay.off('click');
|
||||||
},
|
};
|
||||||
disableContainerLayer = function () {
|
var enableContainerLayer = function () {
|
||||||
that.$el.removeClass('mailpoet_container_layer_active');
|
that.$el.addClass('mailpoet_container_layer_active');
|
||||||
$toggleButton.removeClass('mailpoet_container_layer_active');
|
$toggleButton.addClass('mailpoet_container_layer_active');
|
||||||
$container.removeClass('mailpoet_layer_highlight');
|
$container.addClass('mailpoet_layer_highlight');
|
||||||
$overlay.hide();
|
$overlay.click(disableContainerLayer);
|
||||||
$overlay.off('click');
|
$overlay.show();
|
||||||
};
|
};
|
||||||
if ($toggleButton.hasClass('mailpoet_container_layer_active')) {
|
if ($toggleButton.hasClass('mailpoet_container_layer_active')) {
|
||||||
disableContainerLayer();
|
disableContainerLayer();
|
||||||
} else {
|
} else {
|
||||||
@ -336,25 +337,25 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('container', {
|
BeforeStartApp.registerBlockType('container', {
|
||||||
blockModel: Module.ContainerBlockModel,
|
blockModel: Module.ContainerBlockModel,
|
||||||
blockView: Module.ContainerBlockView
|
blockView: Module.ContainerBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerLayoutWidget({
|
BeforeStartApp.registerLayoutWidget({
|
||||||
name: 'oneColumnLayout',
|
name: 'oneColumnLayout',
|
||||||
priority: 100,
|
priority: 100,
|
||||||
widgetView: Module.OneColumnContainerWidgetView
|
widgetView: Module.OneColumnContainerWidgetView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerLayoutWidget({
|
BeforeStartApp.registerLayoutWidget({
|
||||||
name: 'twoColumnLayout',
|
name: 'twoColumnLayout',
|
||||||
priority: 100,
|
priority: 100,
|
||||||
widgetView: Module.TwoColumnContainerWidgetView
|
widgetView: Module.TwoColumnContainerWidgetView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerLayoutWidget({
|
BeforeStartApp.registerLayoutWidget({
|
||||||
name: 'threeColumnLayout',
|
name: 'threeColumnLayout',
|
||||||
priority: 100,
|
priority: 100,
|
||||||
widgetView: Module.ThreeColumnContainerWidgetView
|
widgetView: Module.ThreeColumnContainerWidgetView
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Divider content block
|
* Divider content block
|
||||||
*/
|
*/
|
||||||
@ -5,17 +7,13 @@ define([
|
|||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'newsletter_editor/blocks/base',
|
'newsletter_editor/blocks/base',
|
||||||
'underscore',
|
'underscore',
|
||||||
'jquery',
|
'jquery'
|
||||||
'mailpoet'
|
], function (App, BaseBlock, _, jQuery) { // eslint-disable-line func-names
|
||||||
], function (App, BaseBlock, _, jQuery, MailPoet) {
|
var Module = {};
|
||||||
|
var base = BaseBlock;
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Module = {},
|
|
||||||
base = BaseBlock;
|
|
||||||
|
|
||||||
Module.DividerBlockModel = base.BlockModel.extend({
|
Module.DividerBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () { // eslint-disable-line func-names
|
||||||
return this._getDefaults({
|
return this._getDefaults({
|
||||||
type: 'divider',
|
type: 'divider',
|
||||||
styles: {
|
styles: {
|
||||||
@ -33,13 +31,13 @@ define([
|
|||||||
|
|
||||||
Module.DividerBlockView = base.BlockView.extend({
|
Module.DividerBlockView = base.BlockView.extend({
|
||||||
className: 'mailpoet_block mailpoet_divider_block mailpoet_droppable_block',
|
className: 'mailpoet_block mailpoet_divider_block mailpoet_droppable_block',
|
||||||
getTemplate: function () { return window.templates.dividerBlock; },
|
getTemplate: function () { return window.templates.dividerBlock; }, // eslint-disable-line func-names
|
||||||
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'),
|
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'),
|
||||||
behaviors: _.defaults({
|
behaviors: _.defaults({
|
||||||
ResizableBehavior: {
|
ResizableBehavior: {
|
||||||
elementSelector: '.mailpoet_content',
|
elementSelector: '.mailpoet_content',
|
||||||
resizeHandleSelector: '.mailpoet_resize_handle',
|
resizeHandleSelector: '.mailpoet_resize_handle',
|
||||||
transformationFunction: function (y) { return y / 2; },
|
transformationFunction: function (y) { return y / 2; }, // eslint-disable-line func-names
|
||||||
minLength: 0, // TODO: Move this number to editor configuration
|
minLength: 0, // TODO: Move this number to editor configuration
|
||||||
modelField: 'styles.block.padding'
|
modelField: 'styles.block.padding'
|
||||||
},
|
},
|
||||||
@ -47,32 +45,32 @@ define([
|
|||||||
ignoreFrom: '.mailpoet_resize_handle'
|
ignoreFrom: '.mailpoet_resize_handle'
|
||||||
}
|
}
|
||||||
}, base.BlockView.prototype.behaviors),
|
}, base.BlockView.prototype.behaviors),
|
||||||
onDragSubstituteBy: function () { return Module.DividerWidgetView; },
|
onDragSubstituteBy: function () { return Module.DividerWidgetView; }, // eslint-disable-line func-names
|
||||||
initialize: function () {
|
initialize: function () { // eslint-disable-line func-names
|
||||||
base.BlockView.prototype.initialize.apply(this, arguments);
|
|
||||||
var that = this;
|
var that = this;
|
||||||
|
base.BlockView.prototype.initialize.apply(this, arguments);
|
||||||
|
|
||||||
// Listen for attempts to change all dividers in one go
|
// Listen for attempts to change all dividers in one go
|
||||||
this._replaceDividerHandler = function (data) { that.model.set(data); that.model.trigger('applyToAll'); };
|
this._replaceDividerHandler = function (data) { that.model.set(data); that.model.trigger('applyToAll'); }; // eslint-disable-line func-names
|
||||||
App.getChannel().on('replaceAllDividers', this._replaceDividerHandler);
|
App.getChannel().on('replaceAllDividers', this._replaceDividerHandler);
|
||||||
|
|
||||||
this.listenTo(this.model, 'change:src change:styles.block.backgroundColor change:styles.block.borderStyle change:styles.block.borderWidth change:styles.block.borderColor applyToAll', this.render);
|
this.listenTo(this.model, 'change:src change:styles.block.backgroundColor change:styles.block.borderStyle change:styles.block.borderWidth change:styles.block.borderColor applyToAll', this.render);
|
||||||
this.listenTo(this.model, 'change:styles.block.padding', this.changePadding);
|
this.listenTo(this.model, 'change:styles.block.padding', this.changePadding);
|
||||||
},
|
},
|
||||||
templateContext: function () {
|
templateContext: function () { // eslint-disable-line func-names
|
||||||
return _.extend({
|
return _.extend({
|
||||||
totalHeight: parseInt(this.model.get('styles.block.padding'), 10) * 2 + parseInt(this.model.get('styles.block.borderWidth')) + 'px'
|
totalHeight: parseInt(this.model.get('styles.block.padding'), 10) * 2 + parseInt(this.model.get('styles.block.borderWidth')) + 'px'
|
||||||
}, base.BlockView.prototype.templateContext.apply(this));
|
}, base.BlockView.prototype.templateContext.apply(this));
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.toolsView = new Module.DividerBlockToolsView({ model: this.model });
|
this.toolsView = new Module.DividerBlockToolsView({ model: this.model });
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
},
|
},
|
||||||
onBeforeDestroy: function () {
|
onBeforeDestroy: function () { // eslint-disable-line func-names
|
||||||
App.getChannel().off('replaceAllDividers', this._replaceDividerHandler);
|
App.getChannel().off('replaceAllDividers', this._replaceDividerHandler);
|
||||||
this.stopListening(this.model);
|
this.stopListening(this.model);
|
||||||
},
|
},
|
||||||
changePadding: function () {
|
changePadding: function () { // eslint-disable-line func-names
|
||||||
this.$('.mailpoet_content').css('padding-top', this.model.get('styles.block.padding'));
|
this.$('.mailpoet_content').css('padding-top', this.model.get('styles.block.padding'));
|
||||||
this.$('.mailpoet_content').css('padding-bottom', this.model.get('styles.block.padding'));
|
this.$('.mailpoet_content').css('padding-bottom', this.model.get('styles.block.padding'));
|
||||||
this.$('.mailpoet_resize_handle_text').text(parseInt(this.model.get('styles.block.padding'), 10) * 2 + parseInt(this.model.get('styles.block.borderWidth')) + 'px');
|
this.$('.mailpoet_resize_handle_text').text(parseInt(this.model.get('styles.block.padding'), 10) * 2 + parseInt(this.model.get('styles.block.borderWidth')) + 'px');
|
||||||
@ -80,12 +78,12 @@ define([
|
|||||||
});
|
});
|
||||||
|
|
||||||
Module.DividerBlockToolsView = base.BlockToolsView.extend({
|
Module.DividerBlockToolsView = base.BlockToolsView.extend({
|
||||||
getSettingsView: function () { return Module.DividerBlockSettingsView; }
|
getSettingsView: function () { return Module.DividerBlockSettingsView; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.DividerBlockSettingsView = base.BlockSettingsView.extend({
|
Module.DividerBlockSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.dividerBlockSettings; },
|
getTemplate: function () { return window.templates.dividerBlockSettings; }, // eslint-disable-line func-names
|
||||||
events: function () {
|
events: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'click .mailpoet_field_divider_style': 'changeStyle',
|
'click .mailpoet_field_divider_style': 'changeStyle',
|
||||||
|
|
||||||
@ -99,53 +97,53 @@ define([
|
|||||||
'click .mailpoet_done_editing': 'close'
|
'click .mailpoet_done_editing': 'close'
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
modelEvents: function () {
|
modelEvents: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'change:styles.block.borderColor': 'repaintDividerStyleOptions'
|
'change:styles.block.borderColor': 'repaintDividerStyleOptions'
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
templateContext: function () {
|
templateContext: function () { // eslint-disable-line func-names
|
||||||
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
||||||
availableStyles: App.getAvailableStyles().toJSON(),
|
availableStyles: App.getAvailableStyles().toJSON(),
|
||||||
renderOptions: this.renderOptions
|
renderOptions: this.renderOptions
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
changeStyle: function (event) {
|
changeStyle: function (event) { // eslint-disable-line func-names
|
||||||
var style = jQuery(event.currentTarget).data('style');
|
var style = jQuery(event.currentTarget).data('style');
|
||||||
this.model.set('styles.block.borderStyle', style);
|
this.model.set('styles.block.borderStyle', style);
|
||||||
this.$('.mailpoet_field_divider_style').removeClass('mailpoet_active_divider_style');
|
this.$('.mailpoet_field_divider_style').removeClass('mailpoet_active_divider_style');
|
||||||
this.$('.mailpoet_field_divider_style[data-style="' + style + '"]').addClass('mailpoet_active_divider_style');
|
this.$('.mailpoet_field_divider_style[data-style="' + style + '"]').addClass('mailpoet_active_divider_style');
|
||||||
},
|
},
|
||||||
repaintDividerStyleOptions: function () {
|
repaintDividerStyleOptions: function () { // eslint-disable-line func-names
|
||||||
this.$('.mailpoet_field_divider_style > div').css('border-top-color', this.model.get('styles.block.borderColor'));
|
this.$('.mailpoet_field_divider_style > div').css('border-top-color', this.model.get('styles.block.borderColor'));
|
||||||
},
|
},
|
||||||
applyToAll: function (event) {
|
applyToAll: function () { // eslint-disable-line func-names
|
||||||
App.getChannel().trigger('replaceAllDividers', this.model.toJSON());
|
App.getChannel().trigger('replaceAllDividers', this.model.toJSON());
|
||||||
},
|
},
|
||||||
updateValueAndCall: function (fieldToUpdate, callable, event) {
|
updateValueAndCall: function (fieldToUpdate, callable, event) { // eslint-disable-line func-names
|
||||||
this.$(fieldToUpdate).val(jQuery(event.target).val());
|
this.$(fieldToUpdate).val(jQuery(event.target).val());
|
||||||
callable(event);
|
callable(event);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.DividerWidgetView = base.WidgetView.extend({
|
Module.DividerWidgetView = base.WidgetView.extend({
|
||||||
getTemplate: function () { return window.templates.dividerInsertion; },
|
getTemplate: function () { return window.templates.dividerInsertion; }, // eslint-disable-line func-names
|
||||||
behaviors: {
|
behaviors: {
|
||||||
DraggableBehavior: {
|
DraggableBehavior: {
|
||||||
cloneOriginal: true,
|
cloneOriginal: true,
|
||||||
drop: function () {
|
drop: function () { // eslint-disable-line func-names
|
||||||
return new Module.DividerBlockModel();
|
return new Module.DividerBlockModel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) { // eslint-disable-line func-names
|
||||||
App.registerBlockType('divider', {
|
BeforeStartApp.registerBlockType('divider', {
|
||||||
blockModel: Module.DividerBlockModel,
|
blockModel: Module.DividerBlockModel,
|
||||||
blockView: Module.DividerBlockView
|
blockView: Module.DividerBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'divider',
|
name: 'divider',
|
||||||
widgetView: Module.DividerWidgetView,
|
widgetView: Module.DividerWidgetView,
|
||||||
priority: 93
|
priority: 93
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Footer content block
|
* Footer content block
|
||||||
*/
|
*/
|
||||||
@ -6,15 +8,12 @@ define([
|
|||||||
'newsletter_editor/blocks/base',
|
'newsletter_editor/blocks/base',
|
||||||
'underscore',
|
'underscore',
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (App, BaseBlock, _, MailPoet) {
|
], function (App, BaseBlock, _, MailPoet) { // eslint-disable-line func-names
|
||||||
|
var Module = {};
|
||||||
'use strict';
|
var base = BaseBlock;
|
||||||
|
|
||||||
var Module = {},
|
|
||||||
base = BaseBlock;
|
|
||||||
|
|
||||||
Module.FooterBlockModel = base.BlockModel.extend({
|
Module.FooterBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () { // eslint-disable-line func-names
|
||||||
return this._getDefaults({
|
return this._getDefaults({
|
||||||
type: 'footer',
|
type: 'footer',
|
||||||
text: '<a href="[link:subscription_unsubscribe_url]">Unsubscribe</a> | <a href="[link:subscription_manage_url]">Manage subscription</a><br /><b>Add your postal address here!</b>',
|
text: '<a href="[link:subscription_unsubscribe_url]">Unsubscribe</a> | <a href="[link:subscription_manage_url]">Manage subscription</a><br /><b>Add your postal address here!</b>',
|
||||||
@ -39,13 +38,13 @@ define([
|
|||||||
|
|
||||||
Module.FooterBlockView = base.BlockView.extend({
|
Module.FooterBlockView = base.BlockView.extend({
|
||||||
className: 'mailpoet_block mailpoet_footer_block mailpoet_droppable_block',
|
className: 'mailpoet_block mailpoet_footer_block mailpoet_droppable_block',
|
||||||
getTemplate: function () { return window.templates.footerBlock; },
|
getTemplate: function () { return window.templates.footerBlock; }, // eslint-disable-line func-names
|
||||||
modelEvents: _.extend({
|
modelEvents: _.extend({
|
||||||
'change:styles.block.backgroundColor change:styles.text.fontColor change:styles.text.fontFamily change:styles.text.fontSize change:styles.text.textAlign change:styles.link.fontColor change:styles.link.textDecoration': 'render'
|
'change:styles.block.backgroundColor change:styles.text.fontColor change:styles.text.fontFamily change:styles.text.fontSize change:styles.text.textAlign change:styles.link.fontColor change:styles.link.textDecoration': 'render'
|
||||||
}, _.omit(base.BlockView.prototype.modelEvents, 'change')),
|
}, _.omit(base.BlockView.prototype.modelEvents, 'change')),
|
||||||
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
||||||
TextEditorBehavior: {
|
TextEditorBehavior: {
|
||||||
configurationFilter: function (originalSettings) {
|
configurationFilter: function (originalSettings) { // eslint-disable-line func-names
|
||||||
return _.extend({}, originalSettings, {
|
return _.extend({}, originalSettings, {
|
||||||
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
||||||
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
||||||
@ -53,37 +52,37 @@ define([
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
onDragSubstituteBy: function () { return Module.FooterWidgetView; },
|
onDragSubstituteBy: function () { return Module.FooterWidgetView; }, // eslint-disable-line func-names
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.toolsView = new Module.FooterBlockToolsView({ model: this.model });
|
this.toolsView = new Module.FooterBlockToolsView({ model: this.model });
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
},
|
},
|
||||||
onTextEditorChange: function (newContent) {
|
onTextEditorChange: function (newContent) { // eslint-disable-line func-names
|
||||||
this.model.set('text', newContent);
|
this.model.set('text', newContent);
|
||||||
},
|
},
|
||||||
onTextEditorFocus: function () {
|
onTextEditorFocus: function () { // eslint-disable-line func-names
|
||||||
this.disableDragging();
|
this.disableDragging();
|
||||||
this.disableShowingTools();
|
this.disableShowingTools();
|
||||||
},
|
},
|
||||||
onTextEditorBlur: function () {
|
onTextEditorBlur: function () { // eslint-disable-line func-names
|
||||||
this.enableDragging();
|
this.enableDragging();
|
||||||
this.enableShowingTools();
|
this.enableShowingTools();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.FooterBlockToolsView = base.BlockToolsView.extend({
|
Module.FooterBlockToolsView = base.BlockToolsView.extend({
|
||||||
getSettingsView: function () { return Module.FooterBlockSettingsView; }
|
getSettingsView: function () { return Module.FooterBlockSettingsView; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.FooterBlockSettingsView = base.BlockSettingsView.extend({
|
Module.FooterBlockSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.footerBlockSettings; },
|
getTemplate: function () { return window.templates.footerBlockSettings; }, // eslint-disable-line func-names
|
||||||
events: function () {
|
events: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'change .mailpoet_field_footer_text_color': _.partial(this.changeColorField, 'styles.text.fontColor'),
|
'change .mailpoet_field_footer_text_color': _.partial(this.changeColorField, 'styles.text.fontColor'),
|
||||||
'change .mailpoet_field_footer_text_font_family': _.partial(this.changeField, 'styles.text.fontFamily'),
|
'change .mailpoet_field_footer_text_font_family': _.partial(this.changeField, 'styles.text.fontFamily'),
|
||||||
'change .mailpoet_field_footer_text_size': _.partial(this.changeField, 'styles.text.fontSize'),
|
'change .mailpoet_field_footer_text_size': _.partial(this.changeField, 'styles.text.fontSize'),
|
||||||
'change #mailpoet_field_footer_link_color': _.partial(this.changeColorField, 'styles.link.fontColor'),
|
'change #mailpoet_field_footer_link_color': _.partial(this.changeColorField, 'styles.link.fontColor'),
|
||||||
'change #mailpoet_field_footer_link_underline': function (event) {
|
'change #mailpoet_field_footer_link_underline': function (event) { // eslint-disable-line func-names
|
||||||
this.model.set('styles.link.textDecoration', (event.target.checked) ? event.target.value : 'none');
|
this.model.set('styles.link.textDecoration', (event.target.checked) ? event.target.value : 'none');
|
||||||
},
|
},
|
||||||
'change .mailpoet_field_footer_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
'change .mailpoet_field_footer_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
||||||
@ -91,7 +90,7 @@ define([
|
|||||||
'click .mailpoet_done_editing': 'close'
|
'click .mailpoet_done_editing': 'close'
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
templateContext: function () {
|
templateContext: function () { // eslint-disable-line func-names
|
||||||
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
||||||
availableStyles: App.getAvailableStyles().toJSON()
|
availableStyles: App.getAvailableStyles().toJSON()
|
||||||
});
|
});
|
||||||
@ -99,24 +98,24 @@ define([
|
|||||||
});
|
});
|
||||||
|
|
||||||
Module.FooterWidgetView = base.WidgetView.extend({
|
Module.FooterWidgetView = base.WidgetView.extend({
|
||||||
getTemplate: function () { return window.templates.footerInsertion; },
|
getTemplate: function () { return window.templates.footerInsertion; }, // eslint-disable-line func-names
|
||||||
behaviors: {
|
behaviors: {
|
||||||
DraggableBehavior: {
|
DraggableBehavior: {
|
||||||
cloneOriginal: true,
|
cloneOriginal: true,
|
||||||
drop: function () {
|
drop: function () { // eslint-disable-line func-names
|
||||||
return new Module.FooterBlockModel();
|
return new Module.FooterBlockModel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) { // eslint-disable-line func-names
|
||||||
App.registerBlockType('footer', {
|
BeforeStartApp.registerBlockType('footer', {
|
||||||
blockModel: Module.FooterBlockModel,
|
blockModel: Module.FooterBlockModel,
|
||||||
blockView: Module.FooterBlockView
|
blockView: Module.FooterBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'footer',
|
name: 'footer',
|
||||||
widgetView: Module.FooterWidgetView,
|
widgetView: Module.FooterWidgetView,
|
||||||
priority: 99
|
priority: 99
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Header content block
|
* Header content block
|
||||||
*/
|
*/
|
||||||
@ -6,15 +8,12 @@ define([
|
|||||||
'newsletter_editor/blocks/base',
|
'newsletter_editor/blocks/base',
|
||||||
'underscore',
|
'underscore',
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (App, BaseBlock, _, MailPoet) {
|
], function (App, BaseBlock, _, MailPoet) { // eslint-disable-line func-names
|
||||||
|
var Module = {};
|
||||||
'use strict';
|
var base = BaseBlock;
|
||||||
|
|
||||||
var Module = {},
|
|
||||||
base = BaseBlock;
|
|
||||||
|
|
||||||
Module.HeaderBlockModel = base.BlockModel.extend({
|
Module.HeaderBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () { // eslint-disable-line func-names
|
||||||
return this._getDefaults({
|
return this._getDefaults({
|
||||||
type: 'header',
|
type: 'header',
|
||||||
text: 'Display problems? <a href="[link:newsletter_view_in_browser_url]">View it in your browser</a>',
|
text: 'Display problems? <a href="[link:newsletter_view_in_browser_url]">View it in your browser</a>',
|
||||||
@ -39,13 +38,13 @@ define([
|
|||||||
|
|
||||||
Module.HeaderBlockView = base.BlockView.extend({
|
Module.HeaderBlockView = base.BlockView.extend({
|
||||||
className: 'mailpoet_block mailpoet_header_block mailpoet_droppable_block',
|
className: 'mailpoet_block mailpoet_header_block mailpoet_droppable_block',
|
||||||
getTemplate: function () { return window.templates.headerBlock; },
|
getTemplate: function () { return window.templates.headerBlock; }, // eslint-disable-line func-names
|
||||||
modelEvents: _.extend({
|
modelEvents: _.extend({
|
||||||
'change:styles.block.backgroundColor change:styles.text.fontColor change:styles.text.fontFamily change:styles.text.fontSize change:styles.text.textAlign change:styles.link.fontColor change:styles.link.textDecoration': 'render'
|
'change:styles.block.backgroundColor change:styles.text.fontColor change:styles.text.fontFamily change:styles.text.fontSize change:styles.text.textAlign change:styles.link.fontColor change:styles.link.textDecoration': 'render'
|
||||||
}, _.omit(base.BlockView.prototype.modelEvents, 'change')),
|
}, _.omit(base.BlockView.prototype.modelEvents, 'change')),
|
||||||
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
||||||
TextEditorBehavior: {
|
TextEditorBehavior: {
|
||||||
configurationFilter: function (originalSettings) {
|
configurationFilter: function (originalSettings) { // eslint-disable-line func-names
|
||||||
return _.extend({}, originalSettings, {
|
return _.extend({}, originalSettings, {
|
||||||
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
||||||
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
||||||
@ -53,37 +52,37 @@ define([
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
onDragSubstituteBy: function () { return Module.HeaderWidgetView; },
|
onDragSubstituteBy: function () { return Module.HeaderWidgetView; }, // eslint-disable-line func-names
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.toolsView = new Module.HeaderBlockToolsView({ model: this.model });
|
this.toolsView = new Module.HeaderBlockToolsView({ model: this.model });
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
},
|
},
|
||||||
onTextEditorChange: function (newContent) {
|
onTextEditorChange: function (newContent) { // eslint-disable-line func-names
|
||||||
this.model.set('text', newContent);
|
this.model.set('text', newContent);
|
||||||
},
|
},
|
||||||
onTextEditorFocus: function () {
|
onTextEditorFocus: function () { // eslint-disable-line func-names
|
||||||
this.disableDragging();
|
this.disableDragging();
|
||||||
this.disableShowingTools();
|
this.disableShowingTools();
|
||||||
},
|
},
|
||||||
onTextEditorBlur: function () {
|
onTextEditorBlur: function () { // eslint-disable-line func-names
|
||||||
this.enableDragging();
|
this.enableDragging();
|
||||||
this.enableShowingTools();
|
this.enableShowingTools();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.HeaderBlockToolsView = base.BlockToolsView.extend({
|
Module.HeaderBlockToolsView = base.BlockToolsView.extend({
|
||||||
getSettingsView: function () { return Module.HeaderBlockSettingsView; }
|
getSettingsView: function () { return Module.HeaderBlockSettingsView; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.HeaderBlockSettingsView = base.BlockSettingsView.extend({
|
Module.HeaderBlockSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.headerBlockSettings; },
|
getTemplate: function () { return window.templates.headerBlockSettings; }, // eslint-disable-line func-names
|
||||||
events: function () {
|
events: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'change .mailpoet_field_header_text_color': _.partial(this.changeColorField, 'styles.text.fontColor'),
|
'change .mailpoet_field_header_text_color': _.partial(this.changeColorField, 'styles.text.fontColor'),
|
||||||
'change .mailpoet_field_header_text_font_family': _.partial(this.changeField, 'styles.text.fontFamily'),
|
'change .mailpoet_field_header_text_font_family': _.partial(this.changeField, 'styles.text.fontFamily'),
|
||||||
'change .mailpoet_field_header_text_size': _.partial(this.changeField, 'styles.text.fontSize'),
|
'change .mailpoet_field_header_text_size': _.partial(this.changeField, 'styles.text.fontSize'),
|
||||||
'change #mailpoet_field_header_link_color': _.partial(this.changeColorField, 'styles.link.fontColor'),
|
'change #mailpoet_field_header_link_color': _.partial(this.changeColorField, 'styles.link.fontColor'),
|
||||||
'change #mailpoet_field_header_link_underline': function (event) {
|
'change #mailpoet_field_header_link_underline': function (event) { // eslint-disable-line func-names
|
||||||
this.model.set('styles.link.textDecoration', (event.target.checked) ? event.target.value : 'none');
|
this.model.set('styles.link.textDecoration', (event.target.checked) ? event.target.value : 'none');
|
||||||
},
|
},
|
||||||
'change .mailpoet_field_header_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
'change .mailpoet_field_header_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
||||||
@ -91,7 +90,7 @@ define([
|
|||||||
'click .mailpoet_done_editing': 'close'
|
'click .mailpoet_done_editing': 'close'
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
templateContext: function () {
|
templateContext: function () { // eslint-disable-line func-names
|
||||||
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
||||||
availableStyles: App.getAvailableStyles().toJSON()
|
availableStyles: App.getAvailableStyles().toJSON()
|
||||||
});
|
});
|
||||||
@ -99,24 +98,24 @@ define([
|
|||||||
});
|
});
|
||||||
|
|
||||||
Module.HeaderWidgetView = base.WidgetView.extend({
|
Module.HeaderWidgetView = base.WidgetView.extend({
|
||||||
getTemplate: function () { return window.templates.headerInsertion; },
|
getTemplate: function () { return window.templates.headerInsertion; }, // eslint-disable-line func-names
|
||||||
behaviors: {
|
behaviors: {
|
||||||
DraggableBehavior: {
|
DraggableBehavior: {
|
||||||
cloneOriginal: true,
|
cloneOriginal: true,
|
||||||
drop: function () {
|
drop: function () { // eslint-disable-line func-names
|
||||||
return new Module.HeaderBlockModel();
|
return new Module.HeaderBlockModel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) { // eslint-disable-line func-names
|
||||||
App.registerBlockType('header', {
|
BeforeStartApp.registerBlockType('header', {
|
||||||
blockModel: Module.HeaderBlockModel,
|
blockModel: Module.HeaderBlockModel,
|
||||||
blockView: Module.HeaderBlockView
|
blockView: Module.HeaderBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'header',
|
name: 'header',
|
||||||
widgetView: Module.HeaderWidgetView,
|
widgetView: Module.HeaderWidgetView,
|
||||||
priority: 98
|
priority: 98
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Image content block
|
* Image content block
|
||||||
*/
|
*/
|
||||||
@ -8,12 +9,11 @@ define([
|
|||||||
'mailpoet',
|
'mailpoet',
|
||||||
'jquery'
|
'jquery'
|
||||||
], function (App, BaseBlock, _, MailPoet, jQuery) {
|
], function (App, BaseBlock, _, MailPoet, jQuery) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock,
|
var base = BaseBlock;
|
||||||
ImageWidgetView;
|
var ImageWidgetView;
|
||||||
|
|
||||||
Module.ImageBlockModel = base.BlockModel.extend({
|
Module.ImageBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () {
|
||||||
@ -48,8 +48,8 @@ define([
|
|||||||
elementSelector: '.mailpoet_image',
|
elementSelector: '.mailpoet_image',
|
||||||
resizeHandleSelector: '.mailpoet_image_resize_handle',
|
resizeHandleSelector: '.mailpoet_image_resize_handle',
|
||||||
onResize: function (event) {
|
onResize: function (event) {
|
||||||
var corner = this.$('.mailpoet_image').offset(),
|
var corner = this.$('.mailpoet_image').offset();
|
||||||
width = event.pageX - corner.left;
|
var width = event.pageX - corner.left;
|
||||||
this.view.model.set('width', width + 'px');
|
this.view.model.set('width', width + 'px');
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -127,13 +127,16 @@ define([
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
showMediaManager: function () {
|
showMediaManager: function () {
|
||||||
|
var that = this;
|
||||||
|
var MediaManager;
|
||||||
|
var theFrame;
|
||||||
if (this._mediaManager) {
|
if (this._mediaManager) {
|
||||||
this._mediaManager.resetSelections();
|
this._mediaManager.resetSelections();
|
||||||
this._mediaManager.open();
|
this._mediaManager.open();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var MediaManager = window.wp.media.view.MediaFrame.Select.extend({
|
MediaManager = window.wp.media.view.MediaFrame.Select.extend({
|
||||||
|
|
||||||
initialize: function () {
|
initialize: function () {
|
||||||
window.wp.media.view.MediaFrame.prototype.initialize.apply(this, arguments);
|
window.wp.media.view.MediaFrame.prototype.initialize.apply(this, arguments);
|
||||||
@ -196,6 +199,7 @@ define([
|
|||||||
},
|
},
|
||||||
|
|
||||||
bindHandlers: function () {
|
bindHandlers: function () {
|
||||||
|
var handlers;
|
||||||
// from Select
|
// from Select
|
||||||
this.on('router:create:browse', this.createRouter, this);
|
this.on('router:create:browse', this.createRouter, this);
|
||||||
this.on('router:render:browse', this.browseRouter, this);
|
this.on('router:render:browse', this.browseRouter, this);
|
||||||
@ -210,7 +214,7 @@ define([
|
|||||||
|
|
||||||
this.on('updateExcluded', this.browseContent, this);
|
this.on('updateExcluded', this.browseContent, this);
|
||||||
|
|
||||||
var handlers = {
|
handlers = {
|
||||||
content: {
|
content: {
|
||||||
embed: 'embedContent',
|
embed: 'embedContent',
|
||||||
'edit-selection': 'editSelectionContent'
|
'edit-selection': 'editSelectionContent'
|
||||||
@ -244,9 +248,9 @@ define([
|
|||||||
},
|
},
|
||||||
|
|
||||||
editSelectionContent: function () {
|
editSelectionContent: function () {
|
||||||
var state = this.state(),
|
var state = this.state();
|
||||||
selection = state.get('selection'),
|
var selection = state.get('selection');
|
||||||
view;
|
var view;
|
||||||
|
|
||||||
view = new window.wp.media.view.AttachmentsBrowser({
|
view = new window.wp.media.view.AttachmentsBrowser({
|
||||||
controller: this,
|
controller: this,
|
||||||
@ -302,8 +306,8 @@ define([
|
|||||||
requires: { selection: true },
|
requires: { selection: true },
|
||||||
|
|
||||||
click: function () {
|
click: function () {
|
||||||
var state = controller.state(),
|
var state = controller.state();
|
||||||
selection = state.get('selection');
|
var selection = state.get('selection');
|
||||||
|
|
||||||
controller.close();
|
controller.close();
|
||||||
state.trigger('insert', selection).reset();
|
state.trigger('insert', selection).reset();
|
||||||
@ -321,46 +325,42 @@ define([
|
|||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
var theFrame = new MediaManager({
|
theFrame = new MediaManager({
|
||||||
id: 'mailpoet-media-manager',
|
id: 'mailpoet-media-manager',
|
||||||
frame: 'select',
|
frame: 'select',
|
||||||
title: 'Select image',
|
title: 'Select image',
|
||||||
editing: false,
|
editing: false,
|
||||||
multiple: false,
|
multiple: false,
|
||||||
library: {
|
library: {
|
||||||
type: 'image'
|
type: 'image'
|
||||||
},
|
},
|
||||||
displaySettings: false,
|
displaySettings: false,
|
||||||
button: {
|
button: {
|
||||||
text: 'Select'
|
text: 'Select'
|
||||||
}
|
}
|
||||||
}),
|
});
|
||||||
that = this;
|
|
||||||
this._mediaManager = theFrame;
|
this._mediaManager = theFrame;
|
||||||
|
|
||||||
this._mediaManager.on('insert', function () {
|
this._mediaManager.on('insert', function () {
|
||||||
// Append media manager image selections to Images tab
|
// Append media manager image selections to Images tab
|
||||||
var selection = theFrame.state().get('selection');
|
var selection = theFrame.state().get('selection');
|
||||||
selection.each(function (attachment) {
|
selection.each(function (attachment) {
|
||||||
var sizes = attachment.get('sizes'),
|
var sizes = attachment.get('sizes');
|
||||||
// Following advice from Becs, the target width should
|
// Following advice from Becs, the target width should
|
||||||
// be a double of one column width to render well on
|
// be a double of one column width to render well on
|
||||||
// retina screen devices
|
// retina screen devices
|
||||||
targetImageWidth = 1320,
|
var targetImageWidth = 1320;
|
||||||
|
|
||||||
// For main image use the size, that's closest to being 660px in width
|
// Pick the width that is closest to target width
|
||||||
sizeKeys = _.keys(sizes),
|
var increasingByWidthDifference = _.sortBy(
|
||||||
|
_.keys(sizes),
|
||||||
|
function (size) { return Math.abs(targetImageWidth - sizes[size].width); }
|
||||||
|
);
|
||||||
|
var bestWidth = sizes[_.first(increasingByWidthDifference)].width;
|
||||||
|
var imagesOfBestWidth = _.filter(_.values(sizes), function (size) { return size.width === bestWidth; });
|
||||||
|
|
||||||
// Pick the width that is closest to target width
|
// Maximize the height if there are multiple images with same width
|
||||||
increasingByWidthDifference = _.sortBy(
|
var mainSize = _.max(imagesOfBestWidth, function (size) { return size.height; });
|
||||||
_.keys(sizes),
|
|
||||||
function (size) { return Math.abs(targetImageWidth - sizes[size].width); }
|
|
||||||
),
|
|
||||||
bestWidth = sizes[_.first(increasingByWidthDifference)].width,
|
|
||||||
imagesOfBestWidth = _.filter(_.values(sizes), function (size) { return size.width === bestWidth; }),
|
|
||||||
|
|
||||||
// Maximize the height if there are multiple images with same width
|
|
||||||
mainSize = _.max(imagesOfBestWidth, function (size) { return size.height; });
|
|
||||||
|
|
||||||
that.model.set({
|
that.model.set({
|
||||||
height: mainSize.height + 'px',
|
height: mainSize.height + 'px',
|
||||||
@ -413,13 +413,13 @@ define([
|
|||||||
});
|
});
|
||||||
Module.ImageWidgetView = ImageWidgetView;
|
Module.ImageWidgetView = ImageWidgetView;
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('image', {
|
BeforeStartApp.registerBlockType('image', {
|
||||||
blockModel: Module.ImageBlockModel,
|
blockModel: Module.ImageBlockModel,
|
||||||
blockView: Module.ImageBlockView
|
blockView: Module.ImageBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'image',
|
name: 'image',
|
||||||
widgetView: Module.ImageWidgetView,
|
widgetView: Module.ImageWidgetView,
|
||||||
priority: 91
|
priority: 91
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Posts block.
|
* Posts block.
|
||||||
*
|
*
|
||||||
@ -36,11 +37,15 @@ define([
|
|||||||
ButtonBlock,
|
ButtonBlock,
|
||||||
DividerBlock
|
DividerBlock
|
||||||
) {
|
) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock;
|
var base = BaseBlock;
|
||||||
|
var PostsDisplayOptionsSettingsView;
|
||||||
|
var SinglePostSelectionSettingsView;
|
||||||
|
var EmptyPostSelectionSettingsView;
|
||||||
|
var PostSelectionSettingsView;
|
||||||
|
var PostsSelectionCollectionView;
|
||||||
|
|
||||||
Module.PostsBlockModel = base.BlockModel.extend({
|
Module.PostsBlockModel = base.BlockModel.extend({
|
||||||
stale: ['_selectedPosts', '_availablePosts', '_transformedPosts'],
|
stale: ['_selectedPosts', '_availablePosts', '_transformedPosts'],
|
||||||
@ -89,10 +94,9 @@ define([
|
|||||||
};
|
};
|
||||||
},
|
},
|
||||||
initialize: function () {
|
initialize: function () {
|
||||||
var that = this,
|
var POST_REFRESH_DELAY_MS = 500;
|
||||||
POST_REFRESH_DELAY_MS = 500,
|
var refreshAvailablePosts = _.debounce(this.fetchAvailablePosts.bind(this), POST_REFRESH_DELAY_MS);
|
||||||
refreshAvailablePosts = _.debounce(this.fetchAvailablePosts.bind(this), POST_REFRESH_DELAY_MS),
|
var refreshTransformedPosts = _.debounce(this._refreshTransformedPosts.bind(this), POST_REFRESH_DELAY_MS);
|
||||||
refreshTransformedPosts = _.debounce(this._refreshTransformedPosts.bind(this), POST_REFRESH_DELAY_MS);
|
|
||||||
|
|
||||||
// Attach Radio.Requests API primarily for highlighting
|
// Attach Radio.Requests API primarily for highlighting
|
||||||
_.extend(this, Radio.Requests);
|
_.extend(this, Radio.Requests);
|
||||||
@ -120,9 +124,9 @@ define([
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
_loadMorePosts: function () {
|
_loadMorePosts: function () {
|
||||||
var that = this,
|
var that = this;
|
||||||
postCount = this.get('_availablePosts').length,
|
var postCount = this.get('_availablePosts').length;
|
||||||
nextOffset = this.get('offset') + Number(this.get('amount'));
|
var nextOffset = this.get('offset') + Number(this.get('amount'));
|
||||||
|
|
||||||
if (postCount === 0 || postCount < nextOffset) {
|
if (postCount === 0 || postCount < nextOffset) {
|
||||||
// No more posts to load
|
// No more posts to load
|
||||||
@ -139,10 +143,11 @@ define([
|
|||||||
}).always(function () {
|
}).always(function () {
|
||||||
that.trigger('morePostsLoaded');
|
that.trigger('morePostsLoaded');
|
||||||
});
|
});
|
||||||
|
return true;
|
||||||
},
|
},
|
||||||
_refreshTransformedPosts: function () {
|
_refreshTransformedPosts: function () {
|
||||||
var that = this,
|
var that = this;
|
||||||
data = this.toJSON();
|
var data = this.toJSON();
|
||||||
|
|
||||||
data.posts = this.get('_selectedPosts').pluck('ID');
|
data.posts = this.get('_selectedPosts').pluck('ID');
|
||||||
|
|
||||||
@ -158,10 +163,9 @@ define([
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
_insertSelectedPosts: function () {
|
_insertSelectedPosts: function () {
|
||||||
var that = this,
|
var data = this.toJSON();
|
||||||
data = this.toJSON(),
|
var index = this.collection.indexOf(this);
|
||||||
index = this.collection.indexOf(this),
|
var collection = this.collection;
|
||||||
collection = this.collection;
|
|
||||||
|
|
||||||
data.posts = this.get('_selectedPosts').pluck('ID');
|
data.posts = this.get('_selectedPosts').pluck('ID');
|
||||||
|
|
||||||
@ -190,17 +194,19 @@ define([
|
|||||||
this.model.reply('blockView', this.notifyAboutSelf, this);
|
this.model.reply('blockView', this.notifyAboutSelf, this);
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () {
|
||||||
|
var ContainerView;
|
||||||
|
var renderOptions;
|
||||||
if (!this.getRegion('toolsRegion').hasView()) {
|
if (!this.getRegion('toolsRegion').hasView()) {
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
}
|
}
|
||||||
this.trigger('showSettings');
|
this.trigger('showSettings');
|
||||||
|
|
||||||
var ContainerView = App.getBlockTypeView('container'),
|
ContainerView = App.getBlockTypeView('container');
|
||||||
renderOptions = {
|
renderOptions = {
|
||||||
disableTextEditor: true,
|
disableTextEditor: true,
|
||||||
disableDragAndDrop: true,
|
disableDragAndDrop: true,
|
||||||
emptyContainerMessage: MailPoet.I18n.t('noPostsToDisplay')
|
emptyContainerMessage: MailPoet.I18n.t('noPostsToDisplay')
|
||||||
};
|
};
|
||||||
this.showChildView('postsRegion', new ContainerView({ model: this.model.get('_transformedPosts'), renderOptions: renderOptions }));
|
this.showChildView('postsRegion', new ContainerView({ model: this.model.get('_transformedPosts'), renderOptions: renderOptions }));
|
||||||
},
|
},
|
||||||
notifyAboutSelf: function () {
|
notifyAboutSelf: function () {
|
||||||
@ -237,8 +243,8 @@ define([
|
|||||||
this.displayOptionsView = new PostsDisplayOptionsSettingsView({ model: this.model });
|
this.displayOptionsView = new PostsDisplayOptionsSettingsView({ model: this.model });
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () {
|
||||||
var that = this,
|
var that = this;
|
||||||
blockView = this.model.request('blockView');
|
this.model.request('blockView');
|
||||||
|
|
||||||
this.showChildView('selectionRegion', this.selectionView);
|
this.showChildView('selectionRegion', this.selectionView);
|
||||||
this.showChildView('displayOptionsRegion', this.displayOptionsView);
|
this.showChildView('displayOptionsRegion', this.displayOptionsView);
|
||||||
@ -283,7 +289,7 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var PostsSelectionCollectionView = Marionette.CollectionView.extend({
|
PostsSelectionCollectionView = Marionette.CollectionView.extend({
|
||||||
className: 'mailpoet_post_scroll_container',
|
className: 'mailpoet_post_scroll_container',
|
||||||
childView: function () { return SinglePostSelectionSettingsView; },
|
childView: function () { return SinglePostSelectionSettingsView; },
|
||||||
emptyView: function () { return EmptyPostSelectionSettingsView; },
|
emptyView: function () { return EmptyPostSelectionSettingsView; },
|
||||||
@ -307,7 +313,7 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var PostSelectionSettingsView = Marionette.View.extend({
|
PostSelectionSettingsView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.postSelectionPostsBlockSettings; },
|
getTemplate: function () { return window.templates.postSelectionPostsBlockSettings; },
|
||||||
regions: {
|
regions: {
|
||||||
posts: '.mailpoet_post_selection_container'
|
posts: '.mailpoet_post_selection_container'
|
||||||
@ -334,9 +340,10 @@ define([
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () {
|
||||||
|
var postsView;
|
||||||
// Dynamically update available post types
|
// Dynamically update available post types
|
||||||
CommunicationComponent.getPostTypes().done(_.bind(this._updateContentTypes, this));
|
CommunicationComponent.getPostTypes().done(_.bind(this._updateContentTypes, this));
|
||||||
var postsView = new PostsSelectionCollectionView({
|
postsView = new PostsSelectionCollectionView({
|
||||||
collection: this.model.get('_availablePosts'),
|
collection: this.model.get('_availablePosts'),
|
||||||
blockModel: this.model
|
blockModel: this.model
|
||||||
});
|
});
|
||||||
@ -358,12 +365,13 @@ define([
|
|||||||
},
|
},
|
||||||
transport: function (options, success, failure) {
|
transport: function (options, success, failure) {
|
||||||
var taxonomies;
|
var taxonomies;
|
||||||
|
var termsPromise;
|
||||||
var promise = CommunicationComponent.getTaxonomies(
|
var promise = CommunicationComponent.getTaxonomies(
|
||||||
that.model.get('contentType')
|
that.model.get('contentType')
|
||||||
).then(function (tax) {
|
).then(function (tax) {
|
||||||
taxonomies = tax;
|
taxonomies = tax;
|
||||||
// Fetch available terms based on the list of taxonomies already fetched
|
// Fetch available terms based on the list of taxonomies already fetched
|
||||||
var promise = CommunicationComponent.getTerms({
|
termsPromise = CommunicationComponent.getTerms({
|
||||||
search: options.data.term,
|
search: options.data.term,
|
||||||
taxonomies: _.keys(taxonomies)
|
taxonomies: _.keys(taxonomies)
|
||||||
}).then(function (terms) {
|
}).then(function (terms) {
|
||||||
@ -372,7 +380,7 @@ define([
|
|||||||
terms: terms
|
terms: terms
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
return promise;
|
return termsPromise;
|
||||||
});
|
});
|
||||||
|
|
||||||
promise.then(success);
|
promise.then(success);
|
||||||
@ -413,8 +421,8 @@ define([
|
|||||||
this.model.set(field, jQuery(event.target).val());
|
this.model.set(field, jQuery(event.target).val());
|
||||||
},
|
},
|
||||||
_updateContentTypes: function (postTypes) {
|
_updateContentTypes: function (postTypes) {
|
||||||
var select = this.$('.mailpoet_settings_posts_content_type'),
|
var select = this.$('.mailpoet_settings_posts_content_type');
|
||||||
selectedValue = this.model.get('contentType');
|
var selectedValue = this.model.get('contentType');
|
||||||
|
|
||||||
select.find('option').remove();
|
select.find('option').remove();
|
||||||
_.each(postTypes, function (type) {
|
_.each(postTypes, function (type) {
|
||||||
@ -427,11 +435,11 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var EmptyPostSelectionSettingsView = Marionette.View.extend({
|
EmptyPostSelectionSettingsView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.emptyPostPostsBlockSettings; }
|
getTemplate: function () { return window.templates.emptyPostPostsBlockSettings; }
|
||||||
});
|
});
|
||||||
|
|
||||||
var SinglePostSelectionSettingsView = Marionette.View.extend({
|
SinglePostSelectionSettingsView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.singlePostPostsBlockSettings; },
|
getTemplate: function () { return window.templates.singlePostPostsBlockSettings; },
|
||||||
events: function () {
|
events: function () {
|
||||||
return {
|
return {
|
||||||
@ -448,8 +456,8 @@ define([
|
|||||||
this.blockModel = options.blockModel;
|
this.blockModel = options.blockModel;
|
||||||
},
|
},
|
||||||
postSelectionChange: function (event) {
|
postSelectionChange: function (event) {
|
||||||
var checkBox = jQuery(event.target),
|
var checkBox = jQuery(event.target);
|
||||||
selectedPostsCollection = this.blockModel.get('_selectedPosts');
|
var selectedPostsCollection = this.blockModel.get('_selectedPosts');
|
||||||
if (checkBox.prop('checked')) {
|
if (checkBox.prop('checked')) {
|
||||||
selectedPostsCollection.add(this.model);
|
selectedPostsCollection.add(this.model);
|
||||||
} else {
|
} else {
|
||||||
@ -458,7 +466,7 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var PostsDisplayOptionsSettingsView = base.BlockSettingsView.extend({
|
PostsDisplayOptionsSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.displayOptionsPostsBlockSettings; },
|
getTemplate: function () { return window.templates.displayOptionsPostsBlockSettings; },
|
||||||
events: function () {
|
events: function () {
|
||||||
return {
|
return {
|
||||||
@ -488,7 +496,7 @@ define([
|
|||||||
model: this.model.toJSON()
|
model: this.model.toJSON()
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
showButtonSettings: function (event) {
|
showButtonSettings: function () {
|
||||||
var buttonModule = ButtonBlock;
|
var buttonModule = ButtonBlock;
|
||||||
(new buttonModule.ButtonBlockSettingsView({
|
(new buttonModule.ButtonBlockSettingsView({
|
||||||
model: this.model.get('readMoreButton'),
|
model: this.model.get('readMoreButton'),
|
||||||
@ -499,7 +507,7 @@ define([
|
|||||||
}
|
}
|
||||||
})).render();
|
})).render();
|
||||||
},
|
},
|
||||||
showDividerSettings: function (event) {
|
showDividerSettings: function () {
|
||||||
var dividerModule = DividerBlock;
|
var dividerModule = DividerBlock;
|
||||||
(new dividerModule.DividerBlockSettingsView({
|
(new dividerModule.DividerBlockSettingsView({
|
||||||
model: this.model.get('divider'),
|
model: this.model.get('divider'),
|
||||||
@ -575,13 +583,13 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('posts', {
|
BeforeStartApp.registerBlockType('posts', {
|
||||||
blockModel: Module.PostsBlockModel,
|
blockModel: Module.PostsBlockModel,
|
||||||
blockView: Module.PostsBlockView
|
blockView: Module.PostsBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'posts',
|
name: 'posts',
|
||||||
widgetView: Module.PostsWidgetView,
|
widgetView: Module.PostsWidgetView,
|
||||||
priority: 96
|
priority: 96
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
/**
|
/**
|
||||||
* Social icons content block
|
* Social icons content block
|
||||||
*/
|
*/
|
||||||
@ -10,15 +11,15 @@ define([
|
|||||||
'underscore',
|
'underscore',
|
||||||
'jquery'
|
'jquery'
|
||||||
], function (App, BaseBlock, Backbone, Marionette, SuperModel, _, jQuery) {
|
], function (App, BaseBlock, Backbone, Marionette, SuperModel, _, jQuery) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
base = BaseBlock,
|
var base = BaseBlock;
|
||||||
SocialBlockSettingsIconSelectorView,
|
var SocialBlockSettingsIconSelectorView;
|
||||||
SocialBlockSettingsIconView,
|
var SocialBlockSettingsIconView;
|
||||||
SocialBlockSettingsIconCollectionView,
|
var SocialBlockSettingsIconCollectionView;
|
||||||
SocialBlockSettingsStylesView;
|
var SocialBlockSettingsStylesView;
|
||||||
|
var SocialIconView;
|
||||||
|
|
||||||
Module.SocialIconModel = SuperModel.extend({
|
Module.SocialIconModel = SuperModel.extend({
|
||||||
defaults: function () {
|
defaults: function () {
|
||||||
@ -33,12 +34,12 @@ define([
|
|||||||
text: defaultValues.get('title')
|
text: defaultValues.get('title')
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
initialize: function (options) {
|
initialize: function () {
|
||||||
var that = this;
|
var that = this;
|
||||||
// Make model swap to default values for that type when iconType changes
|
// Make model swap to default values for that type when iconType changes
|
||||||
this.on('change:iconType', function () {
|
this.on('change:iconType', function () {
|
||||||
var defaultValues = App.getConfig().get('socialIcons').get(that.get('iconType')),
|
var defaultValues = App.getConfig().get('socialIcons').get(that.get('iconType'));
|
||||||
iconSet = that.collection.iconBlockModel.getIconSet();
|
var iconSet = that.collection.iconBlockModel.getIconSet();
|
||||||
this.set({
|
this.set({
|
||||||
link: defaultValues.get('defaultLink'),
|
link: defaultValues.get('defaultLink'),
|
||||||
image: iconSet.get(that.get('iconType')),
|
image: iconSet.get(that.get('iconType')),
|
||||||
@ -83,7 +84,7 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var SocialIconView = Marionette.View.extend({
|
SocialIconView = Marionette.View.extend({
|
||||||
tagName: 'span',
|
tagName: 'span',
|
||||||
getTemplate: function () { return window.templates.socialIconBlock; },
|
getTemplate: function () { return window.templates.socialIconBlock; },
|
||||||
modelEvents: {
|
modelEvents: {
|
||||||
@ -175,10 +176,10 @@ define([
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
templateContext: function () {
|
templateContext: function () {
|
||||||
var icons = App.getConfig().get('socialIcons'),
|
var icons = App.getConfig().get('socialIcons');
|
||||||
// Construct icon type list of format [{iconType: 'type', title: 'Title'}, ...]
|
// Construct icon type list of format [{iconType: 'type', title: 'Title'}, ...]
|
||||||
availableIconTypes = _.map(_.keys(icons.attributes), function (key) { return { iconType: key, title: icons.get(key).get('title') }; }),
|
var availableIconTypes = _.map(_.keys(icons.attributes), function (key) { return { iconType: key, title: icons.get(key).get('title') }; });
|
||||||
allIconSets = App.getAvailableStyles().get('socialIconSets');
|
var allIconSets = App.getAvailableStyles().get('socialIconSets');
|
||||||
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
return _.extend({}, base.BlockView.prototype.templateContext.apply(this, arguments), {
|
||||||
iconTypes: availableIconTypes,
|
iconTypes: availableIconTypes,
|
||||||
currentType: icons.get(this.model.get('iconType')).toJSON(),
|
currentType: icons.get(this.model.get('iconType')).toJSON(),
|
||||||
@ -194,6 +195,7 @@ define([
|
|||||||
} else {
|
} else {
|
||||||
return this.changeField('link', event);
|
return this.changeField('link', event);
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
},
|
},
|
||||||
changeField: function (field, event) {
|
changeField: function (field, event) {
|
||||||
this.model.set(field, jQuery(event.target).val());
|
this.model.set(field, jQuery(event.target).val());
|
||||||
@ -297,13 +299,13 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
App.registerBlockType('social', {
|
BeforeStartApp.registerBlockType('social', {
|
||||||
blockModel: Module.SocialBlockModel,
|
blockModel: Module.SocialBlockModel,
|
||||||
blockView: Module.SocialBlockView
|
blockView: Module.SocialBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'social',
|
name: 'social',
|
||||||
widgetView: Module.SocialWidgetView,
|
widgetView: Module.SocialWidgetView,
|
||||||
priority: 95
|
priority: 95
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Spacer content block
|
* Spacer content block
|
||||||
*/
|
*/
|
||||||
@ -5,15 +7,12 @@ define([
|
|||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'newsletter_editor/blocks/base',
|
'newsletter_editor/blocks/base',
|
||||||
'underscore'
|
'underscore'
|
||||||
], function (App, BaseBlock, _) {
|
], function (App, BaseBlock, _) { // eslint-disable-line func-names
|
||||||
|
var Module = {};
|
||||||
'use strict';
|
var base = BaseBlock;
|
||||||
|
|
||||||
var Module = {},
|
|
||||||
base = BaseBlock;
|
|
||||||
|
|
||||||
Module.SpacerBlockModel = base.BlockModel.extend({
|
Module.SpacerBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () { // eslint-disable-line func-names
|
||||||
return this._getDefaults({
|
return this._getDefaults({
|
||||||
type: 'spacer',
|
type: 'spacer',
|
||||||
styles: {
|
styles: {
|
||||||
@ -28,7 +27,7 @@ define([
|
|||||||
|
|
||||||
Module.SpacerBlockView = base.BlockView.extend({
|
Module.SpacerBlockView = base.BlockView.extend({
|
||||||
className: 'mailpoet_block mailpoet_spacer_block mailpoet_droppable_block',
|
className: 'mailpoet_block mailpoet_spacer_block mailpoet_droppable_block',
|
||||||
getTemplate: function () { return window.templates.spacerBlock; },
|
getTemplate: function () { return window.templates.spacerBlock; }, // eslint-disable-line func-names
|
||||||
behaviors: _.defaults({
|
behaviors: _.defaults({
|
||||||
ResizableBehavior: {
|
ResizableBehavior: {
|
||||||
elementSelector: '.mailpoet_spacer',
|
elementSelector: '.mailpoet_spacer',
|
||||||
@ -41,33 +40,33 @@ define([
|
|||||||
}
|
}
|
||||||
}, base.BlockView.prototype.behaviors),
|
}, base.BlockView.prototype.behaviors),
|
||||||
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'),
|
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'),
|
||||||
onDragSubstituteBy: function () { return Module.SpacerWidgetView; },
|
onDragSubstituteBy: function () { return Module.SpacerWidgetView; }, // eslint-disable-line func-names
|
||||||
initialize: function () {
|
initialize: function () { // eslint-disable-line func-names
|
||||||
base.BlockView.prototype.initialize.apply(this, arguments);
|
base.BlockView.prototype.initialize.apply(this, arguments);
|
||||||
|
|
||||||
this.listenTo(this.model, 'change:styles.block.backgroundColor', this.render);
|
this.listenTo(this.model, 'change:styles.block.backgroundColor', this.render);
|
||||||
this.listenTo(this.model, 'change:styles.block.height', this.changeHeight);
|
this.listenTo(this.model, 'change:styles.block.height', this.changeHeight);
|
||||||
},
|
},
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.toolsView = new Module.SpacerBlockToolsView({ model: this.model });
|
this.toolsView = new Module.SpacerBlockToolsView({ model: this.model });
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
},
|
},
|
||||||
changeHeight: function () {
|
changeHeight: function () { // eslint-disable-line func-names
|
||||||
this.$('.mailpoet_spacer').css('height', this.model.get('styles.block.height'));
|
this.$('.mailpoet_spacer').css('height', this.model.get('styles.block.height'));
|
||||||
this.$('.mailpoet_resize_handle_text').text(this.model.get('styles.block.height'));
|
this.$('.mailpoet_resize_handle_text').text(this.model.get('styles.block.height'));
|
||||||
},
|
},
|
||||||
onBeforeDestroy: function () {
|
onBeforeDestroy: function () { // eslint-disable-line func-names
|
||||||
this.stopListening(this.model);
|
this.stopListening(this.model);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.SpacerBlockToolsView = base.BlockToolsView.extend({
|
Module.SpacerBlockToolsView = base.BlockToolsView.extend({
|
||||||
getSettingsView: function () { return Module.SpacerBlockSettingsView; }
|
getSettingsView: function () { return Module.SpacerBlockSettingsView; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.SpacerBlockSettingsView = base.BlockSettingsView.extend({
|
Module.SpacerBlockSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.spacerBlockSettings; },
|
getTemplate: function () { return window.templates.spacerBlockSettings; }, // eslint-disable-line func-names
|
||||||
events: function () {
|
events: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'change .mailpoet_field_spacer_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
'change .mailpoet_field_spacer_background_color': _.partial(this.changeColorField, 'styles.block.backgroundColor'),
|
||||||
'click .mailpoet_done_editing': 'close'
|
'click .mailpoet_done_editing': 'close'
|
||||||
@ -76,24 +75,24 @@ define([
|
|||||||
});
|
});
|
||||||
|
|
||||||
Module.SpacerWidgetView = base.WidgetView.extend({
|
Module.SpacerWidgetView = base.WidgetView.extend({
|
||||||
getTemplate: function () { return window.templates.spacerInsertion; },
|
getTemplate: function () { return window.templates.spacerInsertion; }, // eslint-disable-line func-names
|
||||||
behaviors: {
|
behaviors: {
|
||||||
DraggableBehavior: {
|
DraggableBehavior: {
|
||||||
cloneOriginal: true,
|
cloneOriginal: true,
|
||||||
drop: function () {
|
drop: function () { // eslint-disable-line func-names
|
||||||
return new Module.SpacerBlockModel();
|
return new Module.SpacerBlockModel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) { // eslint-disable-line func-names
|
||||||
App.registerBlockType('spacer', {
|
BeforeStartApp.registerBlockType('spacer', {
|
||||||
blockModel: Module.SpacerBlockModel,
|
blockModel: Module.SpacerBlockModel,
|
||||||
blockView: Module.SpacerBlockView
|
blockView: Module.SpacerBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'spacer',
|
name: 'spacer',
|
||||||
widgetView: Module.SpacerWidgetView,
|
widgetView: Module.SpacerWidgetView,
|
||||||
priority: 94
|
priority: 94
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Text content block
|
* Text content block
|
||||||
*/
|
*/
|
||||||
@ -6,15 +8,12 @@ define([
|
|||||||
'newsletter_editor/blocks/base',
|
'newsletter_editor/blocks/base',
|
||||||
'underscore',
|
'underscore',
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (App, BaseBlock, _, MailPoet) {
|
], function (App, BaseBlock, _, MailPoet) { // eslint-disable-line func-names
|
||||||
|
var Module = {};
|
||||||
'use strict';
|
var base = BaseBlock;
|
||||||
|
|
||||||
var Module = {},
|
|
||||||
base = BaseBlock;
|
|
||||||
|
|
||||||
Module.TextBlockModel = base.BlockModel.extend({
|
Module.TextBlockModel = base.BlockModel.extend({
|
||||||
defaults: function () {
|
defaults: function () { // eslint-disable-line func-names
|
||||||
return this._getDefaults({
|
return this._getDefaults({
|
||||||
type: 'text',
|
type: 'text',
|
||||||
text: 'Edit this to insert text'
|
text: 'Edit this to insert text'
|
||||||
@ -24,7 +23,7 @@ define([
|
|||||||
|
|
||||||
Module.TextBlockView = base.BlockView.extend({
|
Module.TextBlockView = base.BlockView.extend({
|
||||||
className: 'mailpoet_block mailpoet_text_block mailpoet_droppable_block',
|
className: 'mailpoet_block mailpoet_text_block mailpoet_droppable_block',
|
||||||
getTemplate: function () { return window.templates.textBlock; },
|
getTemplate: function () { return window.templates.textBlock; }, // eslint-disable-line func-names
|
||||||
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'), // Prevent rerendering on model change due to text editor redrawing
|
modelEvents: _.omit(base.BlockView.prototype.modelEvents, 'change'), // Prevent rerendering on model change due to text editor redrawing
|
||||||
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
behaviors: _.extend({}, base.BlockView.prototype.behaviors, {
|
||||||
TextEditorBehavior: {
|
TextEditorBehavior: {
|
||||||
@ -34,7 +33,7 @@ define([
|
|||||||
invalidElements: 'script',
|
invalidElements: 'script',
|
||||||
blockFormats: 'Heading 1=h1;Heading 2=h2;Heading 3=h3;Paragraph=p',
|
blockFormats: 'Heading 1=h1;Heading 2=h2;Heading 3=h3;Paragraph=p',
|
||||||
plugins: 'link lists code textcolor colorpicker mailpoet_shortcodes paste',
|
plugins: 'link lists code textcolor colorpicker mailpoet_shortcodes paste',
|
||||||
configurationFilter: function (originalSettings) {
|
configurationFilter: function (originalSettings) { // eslint-disable-line func-names
|
||||||
return _.extend({}, originalSettings, {
|
return _.extend({}, originalSettings, {
|
||||||
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
mailpoet_shortcodes: App.getConfig().get('shortcodes').toJSON(),
|
||||||
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
mailpoet_shortcodes_window_title: MailPoet.I18n.t('shortcodesWindowTitle')
|
||||||
@ -42,7 +41,7 @@ define([
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
initialize: function (options) {
|
initialize: function (options) { // eslint-disable-line func-names
|
||||||
base.BlockView.prototype.initialize.apply(this, arguments);
|
base.BlockView.prototype.initialize.apply(this, arguments);
|
||||||
|
|
||||||
this.renderOptions = _.defaults(options.renderOptions || {}, {
|
this.renderOptions = _.defaults(options.renderOptions || {}, {
|
||||||
@ -51,8 +50,8 @@ define([
|
|||||||
|
|
||||||
this.disableTextEditor = this.renderOptions.disableTextEditor;
|
this.disableTextEditor = this.renderOptions.disableTextEditor;
|
||||||
},
|
},
|
||||||
onDragSubstituteBy: function () { return Module.TextWidgetView; },
|
onDragSubstituteBy: function () { return Module.TextWidgetView; }, // eslint-disable-line func-names
|
||||||
onRender: function () {
|
onRender: function () { // eslint-disable-line func-names
|
||||||
this.toolsView = new Module.TextBlockToolsView({
|
this.toolsView = new Module.TextBlockToolsView({
|
||||||
model: this.model,
|
model: this.model,
|
||||||
tools: {
|
tools: {
|
||||||
@ -61,46 +60,46 @@ define([
|
|||||||
});
|
});
|
||||||
this.showChildView('toolsRegion', this.toolsView);
|
this.showChildView('toolsRegion', this.toolsView);
|
||||||
},
|
},
|
||||||
onTextEditorChange: function (newContent) {
|
onTextEditorChange: function (newContent) { // eslint-disable-line func-names
|
||||||
this.model.set('text', newContent);
|
this.model.set('text', newContent);
|
||||||
},
|
},
|
||||||
onTextEditorFocus: function () {
|
onTextEditorFocus: function () { // eslint-disable-line func-names
|
||||||
this.disableDragging();
|
this.disableDragging();
|
||||||
this.disableShowingTools();
|
this.disableShowingTools();
|
||||||
},
|
},
|
||||||
onTextEditorBlur: function () {
|
onTextEditorBlur: function () { // eslint-disable-line func-names
|
||||||
this.enableDragging();
|
this.enableDragging();
|
||||||
this.enableShowingTools();
|
this.enableShowingTools();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.TextBlockToolsView = base.BlockToolsView.extend({
|
Module.TextBlockToolsView = base.BlockToolsView.extend({
|
||||||
getSettingsView: function () { return Module.TextBlockSettingsView; }
|
getSettingsView: function () { return Module.TextBlockSettingsView; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.TextBlockSettingsView = base.BlockSettingsView.extend({
|
Module.TextBlockSettingsView = base.BlockSettingsView.extend({
|
||||||
getTemplate: function () { return window.templates.textBlockSettings; }
|
getTemplate: function () { return window.templates.textBlockSettings; } // eslint-disable-line func-names
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.TextWidgetView = base.WidgetView.extend({
|
Module.TextWidgetView = base.WidgetView.extend({
|
||||||
getTemplate: function () { return window.templates.textInsertion; },
|
getTemplate: function () { return window.templates.textInsertion; }, // eslint-disable-line func-names
|
||||||
behaviors: {
|
behaviors: {
|
||||||
DraggableBehavior: {
|
DraggableBehavior: {
|
||||||
cloneOriginal: true,
|
cloneOriginal: true,
|
||||||
drop: function () {
|
drop: function () { // eslint-disable-line func-names
|
||||||
return new Module.TextBlockModel();
|
return new Module.TextBlockModel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) { // eslint-disable-line func-names
|
||||||
App.registerBlockType('text', {
|
BeforeStartApp.registerBlockType('text', {
|
||||||
blockModel: Module.TextBlockModel,
|
blockModel: Module.TextBlockModel,
|
||||||
blockView: Module.TextBlockView
|
blockView: Module.TextBlockView
|
||||||
});
|
});
|
||||||
|
|
||||||
App.registerWidget({
|
BeforeStartApp.registerWidget({
|
||||||
name: 'text',
|
name: 'text',
|
||||||
widgetView: Module.TextWidgetView,
|
widgetView: Module.TextWidgetView,
|
||||||
priority: 90
|
priority: 90
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This shim replaces the default Backbone.Marionette communication library
|
* This shim replaces the default Backbone.Marionette communication library
|
||||||
* Backbone.Wreqr with Backbone.Radio ahead of time,
|
* Backbone.Wreqr with Backbone.Radio ahead of time,
|
||||||
@ -6,26 +8,24 @@
|
|||||||
* Courtesy of https://gist.github.com/jmeas/7992474cdb1c5672d88b
|
* Courtesy of https://gist.github.com/jmeas/7992474cdb1c5672d88b
|
||||||
*/
|
*/
|
||||||
|
|
||||||
(function (root, factory) {
|
(function (root, factory) { // eslint-disable-line func-names
|
||||||
|
var Marionette = require('backbone.marionette');
|
||||||
|
var Radio = require('backbone.radio');
|
||||||
|
var _ = require('underscore');
|
||||||
if (typeof define === 'function' && define.amd) {
|
if (typeof define === 'function' && define.amd) {
|
||||||
define(['backbone.marionette', 'backbone.radio', 'underscore'], function (Marionette, Radio, _) {
|
define(['backbone.marionette', 'backbone.radio', 'underscore'], function (BackboneMarionette, BackboneRadio, underscore) { // eslint-disable-line func-names
|
||||||
return factory(Marionette, Radio, _);
|
return factory(BackboneMarionette, BackboneRadio, underscore);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
else if (typeof exports !== 'undefined') {
|
else if (typeof exports !== 'undefined') {
|
||||||
var Marionette = require('backbone.marionette');
|
|
||||||
var Radio = require('backbone.radio');
|
|
||||||
var _ = require('underscore');
|
|
||||||
module.exports = factory(Marionette, Radio, _);
|
module.exports = factory(Marionette, Radio, _);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
factory(root.Backbone.Marionette, root.Backbone.Radio, root._);
|
factory(root.Backbone.Marionette, root.Backbone.Radio, root._);
|
||||||
}
|
}
|
||||||
}(this, function (Marionette, Radio, _) {
|
}(this, function (Marionette, Radio, _) { // eslint-disable-line func-names
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var MarionetteApplication = Marionette.Application;
|
var MarionetteApplication = Marionette.Application;
|
||||||
MarionetteApplication.prototype._initChannel = function () {
|
MarionetteApplication.prototype._initChannel = function () { // eslint-disable-line func-names
|
||||||
this.channelName = _.result(this, 'channelName') || 'global';
|
this.channelName = _.result(this, 'channelName') || 'global';
|
||||||
this.channel = _.result(this, 'channel') || Radio.channel(this.channelName);
|
this.channel = _.result(this, 'channel') || Radio.channel(this.channelName);
|
||||||
};
|
};
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'underscore',
|
'underscore',
|
||||||
'mailpoet',
|
'mailpoet',
|
||||||
'ajax'
|
'ajax'
|
||||||
], function (App, _, MailPoet) {
|
], function (App, _, MailPoet) {
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
|
||||||
Module._query = function (args) {
|
Module._query = function (args) {
|
||||||
@ -98,7 +98,7 @@ define([
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function () {
|
||||||
// Prefetch post types
|
// Prefetch post types
|
||||||
Module.getPostTypes();
|
Module.getPostTypes();
|
||||||
});
|
});
|
||||||
|
@ -1,8 +1,7 @@
|
|||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'backbone.supermodel'
|
'backbone.supermodel'
|
||||||
], function (App, SuperModel) {
|
], function (App, SuperModel) { // eslint-disable-line func-names
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
|
||||||
Module.ConfigModel = SuperModel.extend({
|
Module.ConfigModel = SuperModel.extend({
|
||||||
@ -18,14 +17,14 @@ define([
|
|||||||
|
|
||||||
// Global and available styles for access in blocks and their settings
|
// Global and available styles for access in blocks and their settings
|
||||||
Module._config = {};
|
Module._config = {};
|
||||||
Module.getConfig = function () { return Module._config; };
|
Module.getConfig = function () { return Module._config; }; // eslint-disable-line func-names
|
||||||
Module.setConfig = function (options) {
|
Module.setConfig = function (options) { // eslint-disable-line func-names
|
||||||
Module._config = new Module.ConfigModel(options, { parse: true });
|
Module._config = new Module.ConfigModel(options, { parse: true });
|
||||||
return Module._config;
|
return Module._config;
|
||||||
};
|
};
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp, options) { // eslint-disable-line func-names
|
||||||
var Application = App;
|
var Application = BeforeStartApp;
|
||||||
// Expose config methods globally
|
// Expose config methods globally
|
||||||
Application.getConfig = Module.getConfig;
|
Application.getConfig = Module.getConfig;
|
||||||
Application.setConfig = Module.setConfig;
|
Application.setConfig = Module.setConfig;
|
||||||
|
@ -1,24 +1,24 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'backbone.supermodel',
|
'backbone.supermodel',
|
||||||
'underscore',
|
'underscore',
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (App, SuperModel, _, MailPoet) {
|
], function (App, SuperModel, _, MailPoet) { // eslint-disable-line func-names
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
|
||||||
// Holds newsletter entry fields, such as subject or creation datetime.
|
// Holds newsletter entry fields, such as subject or creation datetime.
|
||||||
// Does not hold newsletter content nor newsletter styles, those are
|
// Does not hold newsletter content nor newsletter styles, those are
|
||||||
// handled by other components.
|
// handled by other components.
|
||||||
Module.NewsletterModel = SuperModel.extend({
|
Module.NewsletterModel = SuperModel.extend({
|
||||||
whitelisted: ['id', 'subject', 'preheader'],
|
whitelisted: ['id', 'subject', 'preheader', 'type'],
|
||||||
initialize: function (options) {
|
initialize: function () { // eslint-disable-line func-names
|
||||||
this.on('change', function () {
|
this.on('change', function () { // eslint-disable-line func-names
|
||||||
App.getChannel().trigger('autoSave');
|
App.getChannel().trigger('autoSave');
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
toJSON: function () {
|
toJSON: function () { // eslint-disable-line func-names
|
||||||
// Use only whitelisted properties to ensure properties editor
|
// Use only whitelisted properties to ensure properties editor
|
||||||
// doesn't control don't change.
|
// doesn't control don't change.
|
||||||
return _.pick(SuperModel.prototype.toJSON.call(this), this.whitelisted);
|
return _.pick(SuperModel.prototype.toJSON.call(this), this.whitelisted);
|
||||||
@ -27,62 +27,60 @@ define([
|
|||||||
|
|
||||||
// Content block view and model handlers for different content types
|
// Content block view and model handlers for different content types
|
||||||
Module._blockTypes = {};
|
Module._blockTypes = {};
|
||||||
Module.registerBlockType = function (type, data) {
|
Module.registerBlockType = function (type, data) { // eslint-disable-line func-names
|
||||||
Module._blockTypes[type] = data;
|
Module._blockTypes[type] = data;
|
||||||
};
|
};
|
||||||
Module.getBlockTypeModel = function (type) {
|
Module.getBlockTypeModel = function (type) { // eslint-disable-line func-names
|
||||||
if (type in Module._blockTypes) {
|
if (type in Module._blockTypes) {
|
||||||
return Module._blockTypes[type].blockModel;
|
return Module._blockTypes[type].blockModel;
|
||||||
} else {
|
|
||||||
throw 'Block type not supported: ' + type;
|
|
||||||
}
|
}
|
||||||
|
throw 'Block type not supported: ' + type;
|
||||||
};
|
};
|
||||||
Module.getBlockTypeView = function (type) {
|
Module.getBlockTypeView = function (type) { // eslint-disable-line func-names
|
||||||
if (type in Module._blockTypes) {
|
if (type in Module._blockTypes) {
|
||||||
return Module._blockTypes[type].blockView;
|
return Module._blockTypes[type].blockView;
|
||||||
} else {
|
|
||||||
throw 'Block type not supported: ' + type;
|
|
||||||
}
|
}
|
||||||
|
throw 'Block type not supported: ' + type;
|
||||||
};
|
};
|
||||||
|
|
||||||
Module.getBody = function () {
|
Module.getBody = function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
content: App._contentContainer.toJSON(),
|
content: App._contentContainer.toJSON(),
|
||||||
globalStyles: App.getGlobalStyles().toJSON()
|
globalStyles: App.getGlobalStyles().toJSON()
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
Module.toJSON = function () {
|
Module.toJSON = function () { // eslint-disable-line func-names
|
||||||
return _.extend({
|
return _.extend({
|
||||||
body: Module.getBody()
|
body: Module.getBody()
|
||||||
}, App.getNewsletter().toJSON());
|
}, App.getNewsletter().toJSON());
|
||||||
};
|
};
|
||||||
|
|
||||||
Module.getNewsletter = function () {
|
Module.getNewsletter = function () { // eslint-disable-line func-names
|
||||||
return Module.newsletter;
|
return Module.newsletter;
|
||||||
};
|
};
|
||||||
|
|
||||||
Module.findModels = function (predicate) {
|
Module.findModels = function (predicate) { // eslint-disable-line func-names
|
||||||
var blocks = App._contentContainer.getChildren();
|
var blocks = App._contentContainer.getChildren();
|
||||||
return _.filter(blocks, predicate);
|
return _.filter(blocks, predicate);
|
||||||
};
|
};
|
||||||
|
|
||||||
App.on('before:start', function (Application, options) {
|
App.on('before:start', function (Application, options) { // eslint-disable-line func-names
|
||||||
var App = Application;
|
var BeforeStartApp = Application;
|
||||||
// Expose block methods globally
|
// Expose block methods globally
|
||||||
App.registerBlockType = Module.registerBlockType;
|
BeforeStartApp.registerBlockType = Module.registerBlockType;
|
||||||
App.getBlockTypeModel = Module.getBlockTypeModel;
|
BeforeStartApp.getBlockTypeModel = Module.getBlockTypeModel;
|
||||||
App.getBlockTypeView = Module.getBlockTypeView;
|
BeforeStartApp.getBlockTypeView = Module.getBlockTypeView;
|
||||||
App.toJSON = Module.toJSON;
|
BeforeStartApp.toJSON = Module.toJSON;
|
||||||
App.getBody = Module.getBody;
|
BeforeStartApp.getBody = Module.getBody;
|
||||||
App.getNewsletter = Module.getNewsletter;
|
BeforeStartApp.getNewsletter = Module.getNewsletter;
|
||||||
App.findModels = Module.findModels;
|
BeforeStartApp.findModels = Module.findModels;
|
||||||
|
|
||||||
Module.newsletter = new Module.NewsletterModel(_.omit(_.clone(options.newsletter), ['body']));
|
Module.newsletter = new Module.NewsletterModel(_.omit(_.clone(options.newsletter), ['body']));
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (Application, options) {
|
App.on('start', function (Application, options) { // eslint-disable-line func-names
|
||||||
var App = Application;
|
var StartApp = Application;
|
||||||
var body = options.newsletter.body;
|
var body = options.newsletter.body;
|
||||||
var content = (_.has(body, 'content')) ? body.content : {};
|
var content = (_.has(body, 'content')) ? body.content : {};
|
||||||
|
|
||||||
@ -93,13 +91,13 @@ define([
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
App._contentContainer = new (App.getBlockTypeModel('container'))(content, { parse: true });
|
StartApp._contentContainer = new (StartApp.getBlockTypeModel('container'))(content, { parse: true });
|
||||||
App._contentContainerView = new (App.getBlockTypeView('container'))({
|
StartApp._contentContainerView = new (StartApp.getBlockTypeView('container'))({
|
||||||
model: App._contentContainer,
|
model: StartApp._contentContainer,
|
||||||
renderOptions: { depth: 0 }
|
renderOptions: { depth: 0 }
|
||||||
});
|
});
|
||||||
|
|
||||||
App._appView.showChildView('contentRegion', App._contentContainerView);
|
StartApp._appView.showChildView('contentRegion', StartApp._contentContainerView);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
'use strict';
|
||||||
|
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'backbone',
|
'backbone',
|
||||||
@ -5,32 +7,29 @@ define([
|
|||||||
'underscore',
|
'underscore',
|
||||||
'jquery',
|
'jquery',
|
||||||
'mailpoet'
|
'mailpoet'
|
||||||
], function (App, Backbone, Marionette, _, jQuery, MailPoet) {
|
], function (App, Backbone, Marionette, _, jQuery, MailPoet) { // eslint-disable-line func-names
|
||||||
|
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
|
||||||
Module.HeadingView = Marionette.View.extend({
|
Module.HeadingView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.heading; },
|
getTemplate: function () { return window.templates.heading; }, // eslint-disable-line func-names
|
||||||
templateContext: function () {
|
templateContext: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
model: this.model.toJSON()
|
model: this.model.toJSON()
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
events: function () {
|
events: function () { // eslint-disable-line func-names
|
||||||
return {
|
return {
|
||||||
'keyup .mailpoet_input_title': _.partial(this.changeField, 'subject'),
|
'keyup .mailpoet_input_title': _.partial(this.changeField, 'subject'),
|
||||||
'keyup .mailpoet_input_preheader': _.partial(this.changeField, 'preheader')
|
'keyup .mailpoet_input_preheader': _.partial(this.changeField, 'preheader')
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
changeField: function (field, event) {
|
changeField: function (field, event) { // eslint-disable-line func-names
|
||||||
this.model.set(field, jQuery(event.target).val());
|
this.model.set(field, jQuery(event.target).val());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function (StartApp) { // eslint-disable-line func-names
|
||||||
App._appView.showChildView('headingRegion', new Module.HeadingView({ model: App.getNewsletter() }));
|
StartApp._appView.showChildView('headingRegion', new Module.HeadingView({ model: StartApp.getNewsletter() }));
|
||||||
MailPoet.helpTooltip.show(document.getElementById('tooltip-designer-subject-line'), {
|
MailPoet.helpTooltip.show(document.getElementById('tooltip-designer-subject-line'), {
|
||||||
tooltipId: 'tooltip-designer-subject-line-ti',
|
tooltipId: 'tooltip-designer-subject-line-ti',
|
||||||
tooltip: MailPoet.I18n.t('helpTooltipDesignerSubjectLine'),
|
tooltip: MailPoet.I18n.t('helpTooltipDesignerSubjectLine'),
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'newsletter_editor/components/communication',
|
'newsletter_editor/components/communication',
|
||||||
@ -25,15 +26,13 @@ define([
|
|||||||
_,
|
_,
|
||||||
$
|
$
|
||||||
) {
|
) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {},
|
var Module = {};
|
||||||
saveTimeout;
|
var saveTimeout;
|
||||||
|
|
||||||
// Save editor contents to server
|
// Save editor contents to server
|
||||||
Module.save = function () {
|
Module.save = function () {
|
||||||
|
|
||||||
var json = App.toJSON();
|
var json = App.toJSON();
|
||||||
|
|
||||||
// Stringify to enable transmission of primitive non-string value types
|
// Stringify to enable transmission of primitive non-string value types
|
||||||
@ -76,10 +75,9 @@ define([
|
|||||||
// Temporary workaround for html2canvas-alpha2.
|
// Temporary workaround for html2canvas-alpha2.
|
||||||
// Removes 1px left transparent border from resulting canvas.
|
// Removes 1px left transparent border from resulting canvas.
|
||||||
|
|
||||||
var oldContext = oldCanvas.getContext('2d'),
|
var newCanvas = document.createElement('canvas');
|
||||||
newCanvas = document.createElement('canvas'),
|
var newContext = newCanvas.getContext('2d');
|
||||||
newContext = newCanvas.getContext('2d'),
|
var leftBorderWidth = 1;
|
||||||
leftBorderWidth = 1;
|
|
||||||
|
|
||||||
newCanvas.width = oldCanvas.width;
|
newCanvas.width = oldCanvas.width;
|
||||||
newCanvas.height = oldCanvas.height;
|
newCanvas.height = oldCanvas.height;
|
||||||
@ -95,13 +93,16 @@ define([
|
|||||||
};
|
};
|
||||||
|
|
||||||
Module.saveTemplate = function (options) {
|
Module.saveTemplate = function (options) {
|
||||||
var that = this,
|
var promise = jQuery.Deferred();
|
||||||
promise = jQuery.Deferred();
|
|
||||||
|
|
||||||
promise.then(function (thumbnail) {
|
promise.then(function (thumbnail) {
|
||||||
var data = _.extend(options || {}, {
|
var data = _.extend(options || {}, {
|
||||||
thumbnail: thumbnail.toDataURL('image/jpeg'),
|
thumbnail: thumbnail.toDataURL('image/jpeg'),
|
||||||
body: JSON.stringify(App.getBody())
|
body: JSON.stringify(App.getBody()),
|
||||||
|
categories: JSON.stringify([
|
||||||
|
'saved',
|
||||||
|
App.getNewsletter().get('type')
|
||||||
|
])
|
||||||
});
|
});
|
||||||
|
|
||||||
return MailPoet.Ajax.post({
|
return MailPoet.Ajax.post({
|
||||||
@ -122,13 +123,13 @@ define([
|
|||||||
};
|
};
|
||||||
|
|
||||||
Module.exportTemplate = function (options) {
|
Module.exportTemplate = function (options) {
|
||||||
var that = this;
|
|
||||||
return Module.getThumbnail(
|
return Module.getThumbnail(
|
||||||
jQuery('#mailpoet_editor_content > .mailpoet_block').get(0)
|
jQuery('#mailpoet_editor_content > .mailpoet_block').get(0)
|
||||||
).then(function (thumbnail) {
|
).then(function (thumbnail) {
|
||||||
var data = _.extend(options || {}, {
|
var data = _.extend(options || {}, {
|
||||||
thumbnail: thumbnail.toDataURL('image/jpeg'),
|
thumbnail: thumbnail.toDataURL('image/jpeg'),
|
||||||
body: App.getBody()
|
body: App.getBody(),
|
||||||
|
categories: JSON.stringify([App.getNewsletter().get('type')])
|
||||||
});
|
});
|
||||||
var blob = new Blob(
|
var blob = new Blob(
|
||||||
[JSON.stringify(data)],
|
[JSON.stringify(data)],
|
||||||
@ -155,7 +156,7 @@ define([
|
|||||||
'click .mailpoet_save_export': 'toggleExportTemplate',
|
'click .mailpoet_save_export': 'toggleExportTemplate',
|
||||||
'click .mailpoet_export_template': 'exportTemplate'
|
'click .mailpoet_export_template': 'exportTemplate'
|
||||||
},
|
},
|
||||||
initialize: function (options) {
|
initialize: function () {
|
||||||
App.getChannel().on('beforeEditorSave', this.beforeSave, this);
|
App.getChannel().on('beforeEditorSave', this.beforeSave, this);
|
||||||
App.getChannel().on('afterEditorSave', this.afterSave, this);
|
App.getChannel().on('afterEditorSave', this.afterSave, this);
|
||||||
},
|
},
|
||||||
@ -170,7 +171,7 @@ define([
|
|||||||
// TODO: Add a loading animation instead
|
// TODO: Add a loading animation instead
|
||||||
this.$('.mailpoet_autosaved_at').text(MailPoet.I18n.t('saving'));
|
this.$('.mailpoet_autosaved_at').text(MailPoet.I18n.t('saving'));
|
||||||
},
|
},
|
||||||
afterSave: function (json, response) {
|
afterSave: function (json) {
|
||||||
this.validateNewsletter(json);
|
this.validateNewsletter(json);
|
||||||
// Update 'Last saved timer'
|
// Update 'Last saved timer'
|
||||||
this.$('.mailpoet_editor_last_saved').removeClass('mailpoet_hidden');
|
this.$('.mailpoet_editor_last_saved').removeClass('mailpoet_hidden');
|
||||||
@ -192,9 +193,9 @@ define([
|
|||||||
this.$('.mailpoet_save_as_template_container').addClass('mailpoet_hidden');
|
this.$('.mailpoet_save_as_template_container').addClass('mailpoet_hidden');
|
||||||
},
|
},
|
||||||
saveAsTemplate: function () {
|
saveAsTemplate: function () {
|
||||||
var templateName = this.$('.mailpoet_save_as_template_name').val(),
|
var templateName = this.$('.mailpoet_save_as_template_name').val();
|
||||||
templateDescription = this.$('.mailpoet_save_as_template_description').val(),
|
var templateDescription = this.$('.mailpoet_save_as_template_description').val();
|
||||||
that = this;
|
var that = this;
|
||||||
|
|
||||||
if (templateName === '') {
|
if (templateName === '') {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
@ -238,7 +239,6 @@ define([
|
|||||||
});
|
});
|
||||||
this.hideOptionContents();
|
this.hideOptionContents();
|
||||||
}
|
}
|
||||||
|
|
||||||
},
|
},
|
||||||
toggleExportTemplate: function () {
|
toggleExportTemplate: function () {
|
||||||
this.$('.mailpoet_export_template_container').toggleClass('mailpoet_hidden');
|
this.$('.mailpoet_export_template_container').toggleClass('mailpoet_hidden');
|
||||||
@ -248,9 +248,9 @@ define([
|
|||||||
this.$('.mailpoet_export_template_container').addClass('mailpoet_hidden');
|
this.$('.mailpoet_export_template_container').addClass('mailpoet_hidden');
|
||||||
},
|
},
|
||||||
exportTemplate: function () {
|
exportTemplate: function () {
|
||||||
var templateName = this.$('.mailpoet_export_template_name').val(),
|
var templateName = this.$('.mailpoet_export_template_name').val();
|
||||||
templateDescription = this.$('.mailpoet_export_template_description').val(),
|
var templateDescription = this.$('.mailpoet_export_template_description').val();
|
||||||
that = this;
|
var that = this;
|
||||||
|
|
||||||
if (templateName === '') {
|
if (templateName === '') {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
@ -285,18 +285,19 @@ define([
|
|||||||
this.hideOptionContents();
|
this.hideOptionContents();
|
||||||
if (!this.$('.mailpoet_save_next').hasClass('button-disabled')) {
|
if (!this.$('.mailpoet_save_next').hasClass('button-disabled')) {
|
||||||
Module._cancelAutosave();
|
Module._cancelAutosave();
|
||||||
Module.save().done(function (response) {
|
Module.save().done(function () {
|
||||||
window.location.href = App.getConfig().get('urls.send');
|
window.location.href = App.getConfig().get('urls.send');
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
validateNewsletter: function (jsonObject) {
|
validateNewsletter: function (jsonObject) {
|
||||||
|
var contents;
|
||||||
if (!App._contentContainer.isValid()) {
|
if (!App._contentContainer.isValid()) {
|
||||||
this.showValidationError(App._contentContainer.validationError);
|
this.showValidationError(App._contentContainer.validationError);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var contents = JSON.stringify(jsonObject);
|
contents = JSON.stringify(jsonObject);
|
||||||
if (App.getConfig().get('validation.validateUnsubscribeLinkPresent') &&
|
if (App.getConfig().get('validation.validateUnsubscribeLinkPresent') &&
|
||||||
contents.indexOf('[link:subscription_unsubscribe_url]') < 0 &&
|
contents.indexOf('[link:subscription_unsubscribe_url]') < 0 &&
|
||||||
contents.indexOf('[link:subscription_unsubscribe]') < 0) {
|
contents.indexOf('[link:subscription_unsubscribe]') < 0) {
|
||||||
@ -340,9 +341,11 @@ define([
|
|||||||
};
|
};
|
||||||
|
|
||||||
Module.beforeExitWithUnsavedChanges = function (e) {
|
Module.beforeExitWithUnsavedChanges = function (e) {
|
||||||
|
var message;
|
||||||
|
var event;
|
||||||
if (saveTimeout) {
|
if (saveTimeout) {
|
||||||
var message = MailPoet.I18n.t('unsavedChangesWillBeLost');
|
message = MailPoet.I18n.t('unsavedChangesWillBeLost');
|
||||||
var event = e || window.event;
|
event = e || window.event;
|
||||||
|
|
||||||
if (event) {
|
if (event) {
|
||||||
event.returnValue = message;
|
event.returnValue = message;
|
||||||
@ -350,10 +353,11 @@ define([
|
|||||||
|
|
||||||
return message;
|
return message;
|
||||||
}
|
}
|
||||||
|
return undefined;
|
||||||
};
|
};
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
var Application = App;
|
var Application = BeforeStartApp;
|
||||||
Application.save = Module.save;
|
Application.save = Module.save;
|
||||||
Application.getChannel().on('autoSave', Module.autoSave);
|
Application.getChannel().on('autoSave', Module.autoSave);
|
||||||
|
|
||||||
@ -362,9 +366,9 @@ define([
|
|||||||
Application.getChannel().reply('save', Application.save);
|
Application.getChannel().reply('save', Application.save);
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function (BeforeStartApp) {
|
||||||
var saveView = new Module.SaveView();
|
var saveView = new Module.SaveView();
|
||||||
App._appView.showChildView('bottomRegion', saveView);
|
BeforeStartApp._appView.showChildView('bottomRegion', saveView);
|
||||||
});
|
});
|
||||||
|
|
||||||
return Module;
|
return Module;
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
/* eslint-disable func-names */
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'newsletter_editor/components/communication',
|
'newsletter_editor/components/communication',
|
||||||
@ -6,8 +7,7 @@ define([
|
|||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'backbone.supermodel',
|
'backbone.supermodel',
|
||||||
'underscore',
|
'underscore',
|
||||||
'jquery',
|
'jquery'
|
||||||
'sticky-kit'
|
|
||||||
], function (
|
], function (
|
||||||
App,
|
App,
|
||||||
CommunicationComponent,
|
CommunicationComponent,
|
||||||
@ -16,14 +16,12 @@ define([
|
|||||||
Marionette,
|
Marionette,
|
||||||
SuperModel,
|
SuperModel,
|
||||||
_,
|
_,
|
||||||
jQuery,
|
jQuery
|
||||||
StickyKit
|
|
||||||
) {
|
) {
|
||||||
|
|
||||||
'use strict';
|
'use strict';
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
var SidebarView;
|
||||||
// Widget handlers for use to create new content blocks via drag&drop
|
// Widget handlers for use to create new content blocks via drag&drop
|
||||||
Module._contentWidgets = new (Backbone.Collection.extend({
|
Module._contentWidgets = new (Backbone.Collection.extend({
|
||||||
model: SuperModel.extend({
|
model: SuperModel.extend({
|
||||||
@ -52,7 +50,7 @@ define([
|
|||||||
Module.registerLayoutWidget = function (widget) { return Module._layoutWidgets.add(widget); };
|
Module.registerLayoutWidget = function (widget) { return Module._layoutWidgets.add(widget); };
|
||||||
Module.getLayoutWidgets = function () { return Module._layoutWidgets; };
|
Module.getLayoutWidgets = function () { return Module._layoutWidgets; };
|
||||||
|
|
||||||
var SidebarView = Marionette.View.extend({
|
SidebarView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.sidebar; },
|
getTemplate: function () { return window.templates.sidebar; },
|
||||||
regions: {
|
regions: {
|
||||||
contentRegion: '.mailpoet_content_region',
|
contentRegion: '.mailpoet_content_region',
|
||||||
@ -62,8 +60,8 @@ define([
|
|||||||
},
|
},
|
||||||
events: {
|
events: {
|
||||||
'click .mailpoet_sidebar_region h3, .mailpoet_sidebar_region .handlediv': function (event) {
|
'click .mailpoet_sidebar_region h3, .mailpoet_sidebar_region .handlediv': function (event) {
|
||||||
var $openRegion = this.$el.find('.mailpoet_sidebar_region:not(.closed)'),
|
var $openRegion = this.$el.find('.mailpoet_sidebar_region:not(.closed)');
|
||||||
$targetRegion = this.$el.find(event.target).closest('.mailpoet_sidebar_region');
|
var $targetRegion = this.$el.find(event.target).closest('.mailpoet_sidebar_region');
|
||||||
|
|
||||||
$openRegion.find('.mailpoet_region_content').velocity(
|
$openRegion.find('.mailpoet_region_content').velocity(
|
||||||
'slideUp',
|
'slideUp',
|
||||||
@ -90,7 +88,7 @@ define([
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
initialize: function (options) {
|
initialize: function () {
|
||||||
jQuery(window)
|
jQuery(window)
|
||||||
.on('resize', this.updateHorizontalScroll.bind(this))
|
.on('resize', this.updateHorizontalScroll.bind(this))
|
||||||
.on('scroll', this.updateHorizontalScroll.bind(this));
|
.on('scroll', this.updateHorizontalScroll.bind(this));
|
||||||
@ -113,13 +111,12 @@ define([
|
|||||||
// position of the sidebar would be scrollable and not fixed
|
// position of the sidebar would be scrollable and not fixed
|
||||||
// partially out of visible screen
|
// partially out of visible screen
|
||||||
this.$el.parent().each(function () {
|
this.$el.parent().each(function () {
|
||||||
var calculated_left, self;
|
var calculatedLeft;
|
||||||
|
var self = jQuery(this);
|
||||||
self = jQuery(this);
|
|
||||||
|
|
||||||
if (self.css('position') === 'fixed') {
|
if (self.css('position') === 'fixed') {
|
||||||
calculated_left = self.parent().offset().left - jQuery(window).scrollLeft();
|
calculatedLeft = self.parent().offset().left - jQuery(window).scrollLeft();
|
||||||
self.css('left', calculated_left + 'px');
|
self.css('left', calculatedLeft + 'px');
|
||||||
} else {
|
} else {
|
||||||
self.css('left', '');
|
self.css('left', '');
|
||||||
}
|
}
|
||||||
@ -271,7 +268,7 @@ define([
|
|||||||
previewUrl: response.meta.preview_url
|
previewUrl: response.meta.preview_url
|
||||||
});
|
});
|
||||||
|
|
||||||
var view = this.previewView.render();
|
this.previewView.render();
|
||||||
this.previewView.$el.css('height', '100%');
|
this.previewView.$el.css('height', '100%');
|
||||||
|
|
||||||
MailPoet.Modal.popup({
|
MailPoet.Modal.popup({
|
||||||
@ -324,7 +321,7 @@ define([
|
|||||||
App.getChannel().request('save').always(function () {
|
App.getChannel().request('save').always(function () {
|
||||||
CommunicationComponent.previewNewsletter(data).always(function () {
|
CommunicationComponent.previewNewsletter(data).always(function () {
|
||||||
MailPoet.Modal.loading(false);
|
MailPoet.Modal.loading(false);
|
||||||
}).done(function (response) {
|
}).done(function () {
|
||||||
MailPoet.Notice.success(
|
MailPoet.Notice.success(
|
||||||
MailPoet.I18n.t('newsletterPreviewSent'),
|
MailPoet.I18n.t('newsletterPreviewSent'),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
@ -342,6 +339,7 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -363,19 +361,18 @@ define([
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp) {
|
||||||
var Application = App;
|
var Application = BeforeStartApp;
|
||||||
Application.registerWidget = Module.registerWidget;
|
Application.registerWidget = Module.registerWidget;
|
||||||
Application.getWidgets = Module.getWidgets;
|
Application.getWidgets = Module.getWidgets;
|
||||||
Application.registerLayoutWidget = Module.registerLayoutWidget;
|
Application.registerLayoutWidget = Module.registerLayoutWidget;
|
||||||
Application.getLayoutWidgets = Module.getLayoutWidgets;
|
Application.getLayoutWidgets = Module.getLayoutWidgets;
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function (StartApp) {
|
||||||
var stylesModel = App.getGlobalStyles(),
|
var sidebarView = new SidebarView();
|
||||||
sidebarView = new SidebarView();
|
|
||||||
|
|
||||||
App._appView.showChildView('sidebarRegion', sidebarView);
|
StartApp._appView.showChildView('sidebarRegion', sidebarView);
|
||||||
|
|
||||||
MailPoet.helpTooltip.show(document.getElementById('tooltip-send-preview'), {
|
MailPoet.helpTooltip.show(document.getElementById('tooltip-send-preview'), {
|
||||||
tooltipId: 'tooltip-editor-send-preview',
|
tooltipId: 'tooltip-editor-send-preview',
|
||||||
|
@ -1,12 +1,12 @@
|
|||||||
|
|
||||||
|
'use strict';
|
||||||
|
|
||||||
define([
|
define([
|
||||||
'newsletter_editor/App',
|
'newsletter_editor/App',
|
||||||
'backbone.marionette',
|
'backbone.marionette',
|
||||||
'backbone.supermodel',
|
'backbone.supermodel',
|
||||||
'underscore'
|
'underscore'
|
||||||
], function (App, Marionette, SuperModel, _) {
|
], function (App, Marionette, SuperModel, _) { // eslint-disable-line func-names
|
||||||
|
|
||||||
'use strict';
|
|
||||||
|
|
||||||
var Module = {};
|
var Module = {};
|
||||||
|
|
||||||
Module.StylesModel = SuperModel.extend({
|
Module.StylesModel = SuperModel.extend({
|
||||||
@ -42,48 +42,50 @@ define([
|
|||||||
backgroundColor: '#cccccc'
|
backgroundColor: '#cccccc'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
initialize: function () {
|
initialize: function () { // eslint-disable-line func-names
|
||||||
this.on('change', function () { App.getChannel().trigger('autoSave'); });
|
this.on('change', function () { App.getChannel().trigger('autoSave'); }); // eslint-disable-line func-names
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module.StylesView = Marionette.View.extend({
|
Module.StylesView = Marionette.View.extend({
|
||||||
getTemplate: function () { return window.templates.styles; },
|
getTemplate: function () { return window.templates.styles; }, // eslint-disable-line func-names
|
||||||
modelEvents: {
|
modelEvents: {
|
||||||
change: 'render'
|
change: 'render'
|
||||||
},
|
},
|
||||||
serializeData: function () {
|
serializeData: function () { // eslint-disable-line func-names
|
||||||
return this.model.toJSON();
|
return this.model.toJSON();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
Module._globalStyles = new SuperModel();
|
Module._globalStyles = new SuperModel();
|
||||||
Module.getGlobalStyles = function () {
|
Module.getGlobalStyles = function () { // eslint-disable-line func-names
|
||||||
return Module._globalStyles;
|
return Module._globalStyles;
|
||||||
};
|
};
|
||||||
Module.setGlobalStyles = function (options) {
|
Module.setGlobalStyles = function (options) { // eslint-disable-line func-names
|
||||||
Module._globalStyles = new Module.StylesModel(options);
|
Module._globalStyles = new Module.StylesModel(options);
|
||||||
return Module._globalStyles;
|
return Module._globalStyles;
|
||||||
};
|
};
|
||||||
Module.getAvailableStyles = function () {
|
Module.getAvailableStyles = function () { // eslint-disable-line func-names
|
||||||
return App.getConfig().get('availableStyles');
|
return App.getConfig().get('availableStyles');
|
||||||
};
|
};
|
||||||
|
|
||||||
App.on('before:start', function (App, options) {
|
App.on('before:start', function (BeforeStartApp, options) { // eslint-disable-line func-names
|
||||||
var Application = App;
|
var Application = BeforeStartApp;
|
||||||
|
var body;
|
||||||
|
var globalStyles;
|
||||||
// Expose style methods to global application
|
// Expose style methods to global application
|
||||||
Application.getGlobalStyles = Module.getGlobalStyles;
|
Application.getGlobalStyles = Module.getGlobalStyles;
|
||||||
Application.setGlobalStyles = Module.setGlobalStyles;
|
Application.setGlobalStyles = Module.setGlobalStyles;
|
||||||
Application.getAvailableStyles = Module.getAvailableStyles;
|
Application.getAvailableStyles = Module.getAvailableStyles;
|
||||||
|
|
||||||
var body = options.newsletter.body;
|
body = options.newsletter.body;
|
||||||
var globalStyles = (_.has(body, 'globalStyles')) ? body.globalStyles : {};
|
globalStyles = (_.has(body, 'globalStyles')) ? body.globalStyles : {};
|
||||||
this.setGlobalStyles(globalStyles);
|
this.setGlobalStyles(globalStyles);
|
||||||
});
|
});
|
||||||
|
|
||||||
App.on('start', function (App, options) {
|
App.on('start', function (StartApp) { // eslint-disable-line func-names
|
||||||
var stylesView = new Module.StylesView({ model: App.getGlobalStyles() });
|
var stylesView = new Module.StylesView({ model: StartApp.getGlobalStyles() });
|
||||||
App._appView.showChildView('stylesRegion', stylesView);
|
StartApp._appView.showChildView('stylesRegion', stylesView);
|
||||||
});
|
});
|
||||||
|
|
||||||
return Module;
|
return Module;
|
||||||
|
@ -10,31 +10,33 @@
|
|||||||
|
|
||||||
/* jshint unused:false */
|
/* jshint unused:false */
|
||||||
/* global tinymce:true */
|
/* global tinymce:true */
|
||||||
tinymce.PluginManager.add('mailpoet_shortcodes', function (editor, url) {
|
tinymce.PluginManager.add('mailpoet_shortcodes', function (editor) { // eslint-disable-line func-names
|
||||||
var appendLabelAndClose = function (shortcode) {
|
var appendLabelAndClose = function (shortcode) { // eslint-disable-line func-names
|
||||||
editor.insertContent(shortcode);
|
editor.insertContent(shortcode);
|
||||||
editor.windowManager.close();
|
editor.windowManager.close();
|
||||||
},
|
};
|
||||||
generateOnClickFunc = function (shortcode) {
|
var generateOnClickFunc = function (shortcode) { // eslint-disable-line func-names
|
||||||
return function () {
|
return function () { // eslint-disable-line func-names
|
||||||
appendLabelAndClose(shortcode);
|
appendLabelAndClose(shortcode);
|
||||||
};
|
|
||||||
};
|
};
|
||||||
|
};
|
||||||
|
|
||||||
editor.addButton('mailpoet_shortcodes', {
|
editor.addButton('mailpoet_shortcodes', {
|
||||||
icon: 'mailpoet_shortcodes',
|
icon: 'mailpoet_shortcodes',
|
||||||
onclick: function () {
|
onclick: function () { // eslint-disable-line func-names
|
||||||
var shortcodes = [],
|
var shortcodes = [];
|
||||||
configShortcodes = editor.settings.mailpoet_shortcodes;
|
var configShortcodes = editor.settings.mailpoet_shortcodes;
|
||||||
|
var segment;
|
||||||
|
var i;
|
||||||
|
|
||||||
for (var segment in configShortcodes) {
|
for (segment in configShortcodes) {
|
||||||
if (configShortcodes.hasOwnProperty(segment)) {
|
if (configShortcodes.hasOwnProperty(segment)) {
|
||||||
shortcodes.push({
|
shortcodes.push({
|
||||||
type: 'label',
|
type: 'label',
|
||||||
text: segment
|
text: segment
|
||||||
});
|
});
|
||||||
|
|
||||||
for (var i = 0; i < configShortcodes[segment].length; i += 1) {
|
for (i = 0; i < configShortcodes[segment].length; i += 1) {
|
||||||
shortcodes.push({
|
shortcodes.push({
|
||||||
type: 'button',
|
type: 'button',
|
||||||
text: configShortcodes[segment][i].text,
|
text: configShortcodes[segment][i].text,
|
||||||
|
@ -49,7 +49,7 @@ const stats = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
class StatsBadge extends React.Component {
|
class StatsBadge extends React.Component {
|
||||||
getBadgeType(stat, rate) {
|
static getBadgeType(stat, rate) {
|
||||||
const len = stat.badgeRanges.length;
|
const len = stat.badgeRanges.length;
|
||||||
for (let i = 0; i < len; i += 1) {
|
for (let i = 0; i < len; i += 1) {
|
||||||
if (rate > stat.badgeRanges[i]) {
|
if (rate > stat.badgeRanges[i]) {
|
||||||
@ -70,7 +70,7 @@ class StatsBadge extends React.Component {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const badgeType = this.getBadgeType(stat, rate);
|
const badgeType = StatsBadge.getBadgeType(stat, rate);
|
||||||
const badge = badges[badgeType] || null;
|
const badge = badges[badgeType] || null;
|
||||||
if (!badge) {
|
if (!badge) {
|
||||||
return null;
|
return null;
|
||||||
|
@ -46,14 +46,14 @@ define(
|
|||||||
|
|
||||||
let label = step.label;
|
let label = step.label;
|
||||||
|
|
||||||
if (step['link'] !== undefined && this.props.step !== step.name) {
|
if (step.link !== undefined && this.props.step !== step.name) {
|
||||||
label = (
|
label = (
|
||||||
<Link to={step.link}>{ step.label }</Link>
|
<Link to={step.link}>{ step.label }</Link>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<span key={'step-' + index}>
|
<span key={`step-${index}`}>
|
||||||
<span className={stepClasses}>
|
<span className={stepClasses}>
|
||||||
{ label }
|
{ label }
|
||||||
</span>
|
</span>
|
||||||
|
@ -9,7 +9,7 @@ import jQuery from 'jquery';
|
|||||||
import Hooks from 'wp-js-hooks';
|
import Hooks from 'wp-js-hooks';
|
||||||
import StatsBadge from 'newsletters/badges/stats.jsx';
|
import StatsBadge from 'newsletters/badges/stats.jsx';
|
||||||
|
|
||||||
const _QueueMixin = {
|
const QueueMixin = {
|
||||||
pauseSending: function (newsletter) {
|
pauseSending: function (newsletter) {
|
||||||
MailPoet.Ajax.post({
|
MailPoet.Ajax.post({
|
||||||
api_version: window.mailpoet_api_version,
|
api_version: window.mailpoet_api_version,
|
||||||
@ -19,12 +19,12 @@ const _QueueMixin = {
|
|||||||
newsletter_id: newsletter.id,
|
newsletter_id: newsletter.id,
|
||||||
},
|
},
|
||||||
}).done(() => {
|
}).done(() => {
|
||||||
jQuery('#resume_' + newsletter.id).show();
|
jQuery(`#resume_${newsletter.id}`).show();
|
||||||
jQuery('#pause_' + newsletter.id).hide();
|
jQuery(`#pause_${newsletter.id}`).hide();
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -39,113 +39,119 @@ const _QueueMixin = {
|
|||||||
newsletter_id: newsletter.id,
|
newsletter_id: newsletter.id,
|
||||||
},
|
},
|
||||||
}).done(() => {
|
}).done(() => {
|
||||||
jQuery('#pause_' + newsletter.id).show();
|
jQuery(`#pause_${newsletter.id}`).show();
|
||||||
jQuery('#resume_' + newsletter.id).hide();
|
jQuery(`#resume_${newsletter.id}`).hide();
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
renderQueueStatus: function (newsletter, mailer_log) {
|
renderQueueStatus: function (newsletter, mailerLog) {
|
||||||
if (!newsletter.queue) {
|
if (!newsletter.queue) {
|
||||||
return (
|
return (
|
||||||
<span>{MailPoet.I18n.t('notSentYet')}</span>
|
<span>{MailPoet.I18n.t('notSentYet')}</span>
|
||||||
);
|
);
|
||||||
} else if (mailer_log.status === 'paused' && newsletter.queue.status !== 'completed') {
|
} else if (mailerLog.status === 'paused' && newsletter.queue.status !== 'completed') {
|
||||||
return (
|
return (
|
||||||
<span>{MailPoet.I18n.t('paused')}</span>
|
<span>{MailPoet.I18n.t('paused')}</span>
|
||||||
);
|
);
|
||||||
} else {
|
}
|
||||||
if (newsletter.queue.status === 'scheduled') {
|
if (newsletter.queue.status === 'scheduled') {
|
||||||
return (
|
return (
|
||||||
<span>
|
<span>
|
||||||
{ MailPoet.I18n.t('scheduledFor') } { MailPoet.Date.format(newsletter.queue.scheduled_at) }
|
{ MailPoet.I18n.t('scheduledFor') } { MailPoet.Date.format(newsletter.queue.scheduled_at) }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
const progressClasses = classNames(
|
const progressClasses = classNames(
|
||||||
'mailpoet_progress',
|
'mailpoet_progress',
|
||||||
{ mailpoet_progress_complete: newsletter.queue.status === 'completed' }
|
{ mailpoet_progress_complete: newsletter.queue.status === 'completed' }
|
||||||
);
|
);
|
||||||
|
|
||||||
// calculate percentage done
|
// calculate percentage done
|
||||||
let percentage = Math.round(
|
let percentage = Math.round(
|
||||||
(newsletter.queue.count_processed * 100) / (newsletter.queue.count_total)
|
(newsletter.queue.count_processed * 100) / (newsletter.queue.count_total)
|
||||||
);
|
);
|
||||||
|
|
||||||
let label;
|
let label;
|
||||||
|
|
||||||
if (newsletter.queue.status === 'completed') {
|
if (newsletter.queue.status === 'completed') {
|
||||||
label = (
|
label = (
|
||||||
<span>
|
<span>
|
||||||
{
|
{
|
||||||
MailPoet.I18n.t('newsletterQueueCompleted')
|
MailPoet.I18n.t('newsletterQueueCompleted')
|
||||||
.replace('%$1d', newsletter.queue.count_processed)
|
.replace('%$1d', parseInt(newsletter.queue.count_processed, 10).toLocaleString())
|
||||||
.replace('%$2d', newsletter.queue.count_total)
|
.replace('%$2d', parseInt(newsletter.queue.count_total, 10).toLocaleString())
|
||||||
}
|
}
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
label = (
|
label = (
|
||||||
<span>
|
<span>
|
||||||
{ newsletter.queue.count_processed } / { newsletter.queue.count_total }
|
{ newsletter.queue.count_processed } / { newsletter.queue.count_total }
|
||||||
|
|
||||||
<a
|
<a
|
||||||
id={'resume_' + newsletter.id}
|
id={`resume_${newsletter.id}`}
|
||||||
className="button"
|
className="button"
|
||||||
style={{ display: (newsletter.queue.status === 'paused')
|
style={{ display: (newsletter.queue.status === 'paused')
|
||||||
? 'inline-block' : 'none' }}
|
? 'inline-block' : 'none' }}
|
||||||
href="javascript:;"
|
href="javascript:;"
|
||||||
onClick={this.resumeSending.bind(null, newsletter)}
|
onClick={this.resumeSending.bind(null, newsletter)}
|
||||||
>{MailPoet.I18n.t('resume')}</a>
|
>{MailPoet.I18n.t('resume')}</a>
|
||||||
<a
|
<a
|
||||||
id={'pause_' + newsletter.id}
|
id={`pause_${newsletter.id}`}
|
||||||
className="button mailpoet_pause"
|
className="button mailpoet_pause"
|
||||||
style={{ display: (newsletter.queue.status === null)
|
style={{ display: (newsletter.queue.status === null)
|
||||||
? 'inline-block' : 'none' }}
|
? 'inline-block' : 'none' }}
|
||||||
href="javascript:;"
|
href="javascript:;"
|
||||||
onClick={this.pauseSending.bind(null, newsletter)}
|
onClick={this.pauseSending.bind(null, newsletter)}
|
||||||
>{MailPoet.I18n.t('pause')}</a>
|
>{MailPoet.I18n.t('pause')}</a>
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}
|
|
||||||
|
|
||||||
let progress_bar_width = 0;
|
|
||||||
|
|
||||||
if (isNaN(percentage)) {
|
|
||||||
percentage = MailPoet.I18n.t('noSubscribers');
|
|
||||||
} else {
|
|
||||||
progress_bar_width = percentage;
|
|
||||||
percentage += '%';
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
<div className={progressClasses}>
|
|
||||||
<span
|
|
||||||
className="mailpoet_progress_bar"
|
|
||||||
style={{ width: progress_bar_width + '%' }}
|
|
||||||
></span>
|
|
||||||
<span className="mailpoet_progress_label">
|
|
||||||
{ percentage }
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
<p style={{ textAlign: 'center' }}>
|
|
||||||
{ label }
|
|
||||||
</p>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let progressBarWidth = 0;
|
||||||
|
|
||||||
|
if (isNaN(percentage)) {
|
||||||
|
percentage = MailPoet.I18n.t('noSubscribers');
|
||||||
|
} else {
|
||||||
|
progressBarWidth = percentage;
|
||||||
|
percentage += '%';
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<div className={progressClasses}>
|
||||||
|
<span
|
||||||
|
className="mailpoet_progress_bar"
|
||||||
|
style={{ width: `${progressBarWidth}%` }}
|
||||||
|
></span>
|
||||||
|
<span className="mailpoet_progress_label">
|
||||||
|
{ percentage }
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
<p style={{ textAlign: 'center' }}>
|
||||||
|
{ label }
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
const _StatisticsMixin = {
|
const trackStatsCTAClicked = function () {
|
||||||
renderStatistics: function (newsletter, is_sent, current_time) {
|
MailPoet.trackEvent(
|
||||||
let sent = is_sent;
|
'User has clicked a CTA to view detailed stats',
|
||||||
|
{ 'MailPoet Free version': window.mailpoet_version }
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
const StatisticsMixin = {
|
||||||
|
renderStatistics: function (newsletter, isSent, currentTime) {
|
||||||
|
let sent = isSent;
|
||||||
if (sent === undefined) {
|
if (sent === undefined) {
|
||||||
// condition for standard and post notification listings
|
// condition for standard and post notification listings
|
||||||
sent = newsletter.statistics
|
sent = newsletter.statistics
|
||||||
@ -159,77 +165,78 @@ const _StatisticsMixin = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let params = {};
|
let params = {};
|
||||||
|
Hooks.addFilter('mailpoet_newsletters_listing_stats_before', this.addStatsCTALink);
|
||||||
params = Hooks.applyFilters('mailpoet_newsletters_listing_stats_before', params, newsletter);
|
params = Hooks.applyFilters('mailpoet_newsletters_listing_stats_before', params, newsletter);
|
||||||
|
|
||||||
// welcome emails provide explicit total_sent value
|
// welcome emails provide explicit total_sent value
|
||||||
const total_sent = ~~(newsletter.total_sent || newsletter.queue.count_processed);
|
const totalSent = Number((newsletter.total_sent || newsletter.queue.count_processed));
|
||||||
|
|
||||||
let percentage_clicked = 0;
|
let percentageClicked = 0;
|
||||||
let percentage_opened = 0;
|
let percentageOpened = 0;
|
||||||
let percentage_unsubscribed = 0;
|
let percentageUnsubscribed = 0;
|
||||||
|
|
||||||
if (total_sent > 0) {
|
if (totalSent > 0) {
|
||||||
percentage_clicked = (newsletter.statistics.clicked * 100) / total_sent;
|
percentageClicked = (newsletter.statistics.clicked * 100) / totalSent;
|
||||||
percentage_opened = (newsletter.statistics.opened * 100) / total_sent;
|
percentageOpened = (newsletter.statistics.opened * 100) / totalSent;
|
||||||
percentage_unsubscribed = (newsletter.statistics.unsubscribed * 100) / total_sent;
|
percentageUnsubscribed = (newsletter.statistics.unsubscribed * 100) / totalSent;
|
||||||
}
|
}
|
||||||
|
|
||||||
// format to 1 decimal place
|
// format to 1 decimal place
|
||||||
const percentage_clicked_display = MailPoet.Num.toLocaleFixed(percentage_clicked, 1);
|
const percentageClickedDisplay = MailPoet.Num.toLocaleFixed(percentageClicked, 1);
|
||||||
const percentage_opened_display = MailPoet.Num.toLocaleFixed(percentage_opened, 1);
|
const percentageOpenedDisplay = MailPoet.Num.toLocaleFixed(percentageOpened, 1);
|
||||||
const percentage_unsubscribed_display = MailPoet.Num.toLocaleFixed(percentage_unsubscribed, 1);
|
const percentageUnsubscribedDisplay = MailPoet.Num.toLocaleFixed(percentageUnsubscribed, 1);
|
||||||
|
|
||||||
let show_stats_timeout,
|
let showStatsTimeout;
|
||||||
newsletter_date,
|
let newsletterDate;
|
||||||
sent_hours_ago,
|
let sentHoursAgo;
|
||||||
too_early_for_stats,
|
let tooEarlyForStats;
|
||||||
show_kb_link;
|
let showKbLink;
|
||||||
if (current_time !== undefined) {
|
if (currentTime !== undefined) {
|
||||||
// standard emails and post notifications:
|
// standard emails and post notifications:
|
||||||
// display green box for newsletters that were just sent
|
// display green box for newsletters that were just sent
|
||||||
show_stats_timeout = 6; // in hours
|
showStatsTimeout = 6; // in hours
|
||||||
newsletter_date = newsletter.queue.scheduled_at || newsletter.queue.created_at;
|
newsletterDate = newsletter.queue.scheduled_at || newsletter.queue.created_at;
|
||||||
sent_hours_ago = moment(current_time).diff(moment(newsletter_date), 'hours');
|
sentHoursAgo = moment(currentTime).diff(moment(newsletterDate), 'hours');
|
||||||
too_early_for_stats = sent_hours_ago < show_stats_timeout;
|
tooEarlyForStats = sentHoursAgo < showStatsTimeout;
|
||||||
show_kb_link = true;
|
showKbLink = true;
|
||||||
} else {
|
} else {
|
||||||
// welcome emails: no green box and KB link
|
// welcome emails: no green box and KB link
|
||||||
too_early_for_stats = false;
|
tooEarlyForStats = false;
|
||||||
show_kb_link = false;
|
showKbLink = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
const improveStatsKBLink = 'http://beta.docs.mailpoet.com/article/191-how-to-improve-my-open-and-click-rates';
|
const improveStatsKBLink = 'http://beta.docs.mailpoet.com/article/191-how-to-improve-my-open-and-click-rates';
|
||||||
|
|
||||||
// thresholds to display badges
|
// thresholds to display badges
|
||||||
const min_newsletters_sent = 20;
|
const minNewslettersSent = 20;
|
||||||
const min_newsletter_opens = 5;
|
const minNewsletterOpens = 5;
|
||||||
|
|
||||||
let content;
|
let content;
|
||||||
if (total_sent >= min_newsletters_sent
|
if (totalSent >= minNewslettersSent
|
||||||
&& newsletter.statistics.opened >= min_newsletter_opens
|
&& newsletter.statistics.opened >= minNewsletterOpens
|
||||||
&& !too_early_for_stats
|
&& !tooEarlyForStats
|
||||||
) {
|
) {
|
||||||
// display stats with badges
|
// display stats with badges
|
||||||
content = (
|
content = (
|
||||||
<div className="mailpoet_stats_text">
|
<div className="mailpoet_stats_text">
|
||||||
<div>
|
<div>
|
||||||
<span>{ percentage_opened_display }% </span>
|
<span>{ percentageOpenedDisplay }% </span>
|
||||||
<StatsBadge
|
<StatsBadge
|
||||||
stat="opened"
|
stat="opened"
|
||||||
rate={percentage_opened}
|
rate={percentageOpened}
|
||||||
tooltipId={`opened-${newsletter.id}`}
|
tooltipId={`opened-${newsletter.id}`}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<span>{ percentage_clicked_display }% </span>
|
<span>{ percentageClickedDisplay }% </span>
|
||||||
<StatsBadge
|
<StatsBadge
|
||||||
stat="clicked"
|
stat="clicked"
|
||||||
rate={percentage_clicked}
|
rate={percentageClicked}
|
||||||
tooltipId={`clicked-${newsletter.id}`}
|
tooltipId={`clicked-${newsletter.id}`}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
<span className="mailpoet_stat_hidden">{ percentage_unsubscribed_display }%</span>
|
<span className="mailpoet_stat_hidden">{ percentageUnsubscribedDisplay }%</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
@ -238,17 +245,17 @@ const _StatisticsMixin = {
|
|||||||
content = (
|
content = (
|
||||||
<div>
|
<div>
|
||||||
<span className="mailpoet_stats_text">
|
<span className="mailpoet_stats_text">
|
||||||
{ percentage_opened_display }%,
|
{ percentageOpenedDisplay }%,
|
||||||
{ ' ' }
|
{ ' ' }
|
||||||
{ percentage_clicked_display }%
|
{ percentageClickedDisplay }%
|
||||||
<span className="mailpoet_stat_hidden">
|
<span className="mailpoet_stat_hidden">
|
||||||
, { percentage_unsubscribed_display }%
|
, { percentageUnsubscribedDisplay }%
|
||||||
</span>
|
</span>
|
||||||
</span>
|
</span>
|
||||||
{ too_early_for_stats && (
|
{ tooEarlyForStats && (
|
||||||
<div className="mailpoet_badge mailpoet_badge_green">
|
<div className="mailpoet_badge mailpoet_badge_green">
|
||||||
{MailPoet.I18n.t('checkBackInHours')
|
{MailPoet.I18n.t('checkBackInHours')
|
||||||
.replace('%$1d', show_stats_timeout - sent_hours_ago)}
|
.replace('%$1d', showStatsTimeout - sentHoursAgo)}
|
||||||
</div>
|
</div>
|
||||||
) }
|
) }
|
||||||
</div>
|
</div>
|
||||||
@ -256,18 +263,18 @@ const _StatisticsMixin = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// thresholds to display bad open rate help
|
// thresholds to display bad open rate help
|
||||||
const max_percentage_opened = 5;
|
const maxPercentageOpened = 5;
|
||||||
const min_sent_hours_ago = 24;
|
const minSentHoursAgo = 24;
|
||||||
const min_total_sent = 10;
|
const minTotalSent = 10;
|
||||||
|
|
||||||
let after_content;
|
let afterContent;
|
||||||
if (show_kb_link
|
if (showKbLink
|
||||||
&& percentage_opened < max_percentage_opened
|
&& percentageOpened < maxPercentageOpened
|
||||||
&& sent_hours_ago >= min_sent_hours_ago
|
&& sentHoursAgo >= minSentHoursAgo
|
||||||
&& total_sent >= min_total_sent
|
&& totalSent >= minTotalSent
|
||||||
) {
|
) {
|
||||||
// help link for bad open rate
|
// help link for bad open rate
|
||||||
after_content = (
|
afterContent = (
|
||||||
<div>
|
<div>
|
||||||
<a
|
<a
|
||||||
href={improveStatsKBLink}
|
href={improveStatsKBLink}
|
||||||
@ -280,18 +287,32 @@ const _StatisticsMixin = {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (total_sent > 0 && params.link) {
|
if (totalSent > 0 && params.link) {
|
||||||
// wrap content in a link
|
// wrap content in a link
|
||||||
|
if (params.externalLink) {
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<a
|
||||||
|
key={`stats-${newsletter.id}`}
|
||||||
|
href={params.link}
|
||||||
|
onClick={params.onClick || null}
|
||||||
|
>
|
||||||
|
{content}
|
||||||
|
</a>
|
||||||
|
{afterContent}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<Link
|
<Link
|
||||||
key={`stats-${newsletter.id}`}
|
key={`stats-${newsletter.id}`}
|
||||||
to={params.link}
|
to={params.link}
|
||||||
onClick={params.onClick || null}
|
onClick={params.onClick || null}
|
||||||
>
|
>
|
||||||
{content}
|
{content}
|
||||||
</Link>
|
</Link>
|
||||||
{after_content}
|
{afterContent}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -299,13 +320,44 @@ const _StatisticsMixin = {
|
|||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
{content}
|
{content}
|
||||||
{after_content}
|
{afterContent}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
addStatsCTAAction: function (actions) {
|
||||||
|
if (window.mailpoet_premium_active) {
|
||||||
|
return actions;
|
||||||
|
}
|
||||||
|
actions.unshift({
|
||||||
|
name: 'stats',
|
||||||
|
link: function () {
|
||||||
|
return (
|
||||||
|
<a href={'admin.php?page=mailpoet-premium'} onClick={trackStatsCTAClicked}>
|
||||||
|
{MailPoet.I18n.t('statsListingActionTitle')}
|
||||||
|
</a>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
display: function (newsletter) {
|
||||||
|
// welcome emails provide explicit total_sent value
|
||||||
|
const countProcessed = newsletter.queue && newsletter.queue.count_processed;
|
||||||
|
return Number(newsletter.total_sent || countProcessed) > 0;
|
||||||
|
},
|
||||||
|
});
|
||||||
|
return actions;
|
||||||
|
},
|
||||||
|
addStatsCTALink: function (params) {
|
||||||
|
if (window.mailpoet_premium_active) {
|
||||||
|
return params;
|
||||||
|
}
|
||||||
|
const newParams = params;
|
||||||
|
newParams.link = 'admin.php?page=mailpoet-premium';
|
||||||
|
newParams.externalLink = true;
|
||||||
|
newParams.onClick = trackStatsCTAClicked;
|
||||||
|
return newParams;
|
||||||
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
const _MailerMixin = {
|
const MailerMixin = {
|
||||||
checkMailerStatus: function (state) {
|
checkMailerStatus: function (state) {
|
||||||
if (state.meta.mta_log.error && state.meta.mta_log.status === 'paused') {
|
if (state.meta.mta_log.error && state.meta.mta_log.status === 'paused') {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
@ -322,8 +374,8 @@ const _MailerMixin = {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
getMailerError(state) {
|
getMailerError(state) {
|
||||||
let mailer_error_notice;
|
let mailerErrorNotice;
|
||||||
const mailer_check_settings_notice = ReactStringReplace(
|
const mailerCheckSettingsNotice = ReactStringReplace(
|
||||||
MailPoet.I18n.t('mailerCheckSettingsNotice'),
|
MailPoet.I18n.t('mailerCheckSettingsNotice'),
|
||||||
/\[link\](.*?)\[\/link\]/g,
|
/\[link\](.*?)\[\/link\]/g,
|
||||||
match => (
|
match => (
|
||||||
@ -331,19 +383,23 @@ const _MailerMixin = {
|
|||||||
)
|
)
|
||||||
);
|
);
|
||||||
if (state.meta.mta_log.error.operation === 'send') {
|
if (state.meta.mta_log.error.operation === 'send') {
|
||||||
mailer_error_notice =
|
mailerErrorNotice =
|
||||||
MailPoet.I18n.t('mailerSendErrorNotice')
|
MailPoet.I18n.t('mailerSendErrorNotice')
|
||||||
.replace('%$1s', state.meta.mta_method)
|
.replace('%$1s', state.meta.mta_method)
|
||||||
.replace('%$2s', state.meta.mta_log.error.error_message);
|
.replace('%$2s', state.meta.mta_log.error.error_message);
|
||||||
} else {
|
} else {
|
||||||
mailer_error_notice =
|
mailerErrorNotice =
|
||||||
MailPoet.I18n.t('mailerConnectionErrorNotice')
|
MailPoet.I18n.t('mailerConnectionErrorNotice')
|
||||||
.replace('%$1s', state.meta.mta_log.error.error_message);
|
.replace('%$1s', state.meta.mta_log.error.error_message);
|
||||||
}
|
}
|
||||||
|
if (state.meta.mta_log.error.error_code) {
|
||||||
|
mailerErrorNotice += ` ${MailPoet.I18n.t('mailerErrorCode')
|
||||||
|
.replace('%$1s', state.meta.mta_log.error.error_code)}`;
|
||||||
|
}
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<p>{ mailer_error_notice }</p>
|
<p>{ mailerErrorNotice }</p>
|
||||||
<p>{ mailer_check_settings_notice }</p>
|
<p>{ mailerCheckSettingsNotice }</p>
|
||||||
<p>
|
<p>
|
||||||
<a href="javascript:;"
|
<a href="javascript:;"
|
||||||
className="button"
|
className="button"
|
||||||
@ -365,7 +421,7 @@ const _MailerMixin = {
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -374,6 +430,6 @@ const _MailerMixin = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
export { _QueueMixin as QueueMixin };
|
export { QueueMixin };
|
||||||
export { _StatisticsMixin as StatisticsMixin };
|
export { StatisticsMixin };
|
||||||
export { _MailerMixin as MailerMixin };
|
export { MailerMixin };
|
||||||
|
@ -18,7 +18,7 @@ import {
|
|||||||
|
|
||||||
const messages = {
|
const messages = {
|
||||||
onTrash: (response) => {
|
onTrash: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -33,7 +33,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onDelete: (response) => {
|
onDelete: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -48,7 +48,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onRestore: (response) => {
|
onRestore: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -91,7 +91,7 @@ const columns = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const bulk_actions = [
|
const bulkActions = [
|
||||||
{
|
{
|
||||||
name: 'trash',
|
name: 'trash',
|
||||||
label: MailPoet.I18n.t('moveToTrash'),
|
label: MailPoet.I18n.t('moveToTrash'),
|
||||||
@ -99,7 +99,7 @@ const bulk_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const newsletter_actions = [
|
const newsletterActions = [
|
||||||
{
|
{
|
||||||
name: 'view',
|
name: 'view',
|
||||||
link: function (newsletter) {
|
link: function (newsletter) {
|
||||||
@ -141,7 +141,7 @@ const newsletter_actions = [
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -165,7 +165,7 @@ const NewsletterListNotification = React.createClass({
|
|||||||
endpoint: 'newsletters',
|
endpoint: 'newsletters',
|
||||||
action: 'setStatus',
|
action: 'setStatus',
|
||||||
data: {
|
data: {
|
||||||
id: ~~(e.target.getAttribute('data-id')),
|
id: Number(e.target.getAttribute('data-id')),
|
||||||
status: e.target.value,
|
status: e.target.value,
|
||||||
},
|
},
|
||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
@ -195,12 +195,12 @@ const NewsletterListNotification = React.createClass({
|
|||||||
},
|
},
|
||||||
renderSettings: function (newsletter) {
|
renderSettings: function (newsletter) {
|
||||||
let sendingFrequency;
|
let sendingFrequency;
|
||||||
let sendingToSegments;
|
|
||||||
|
|
||||||
// get list of segments' name
|
// get list of segments' name
|
||||||
const segments = newsletter.segments.map((segment) => {
|
const segments = newsletter.segments.map(segment => segment.name);
|
||||||
return segment.name;
|
const sendingToSegments = MailPoet.I18n.t('ifNewContentToSegments').replace(
|
||||||
});
|
'%$1s', segments.join(', ')
|
||||||
|
);
|
||||||
|
|
||||||
// check if the user has specified segments to send to
|
// check if the user has specified segments to send to
|
||||||
if (segments.length === 0) {
|
if (segments.length === 0) {
|
||||||
@ -209,51 +209,52 @@ const NewsletterListNotification = React.createClass({
|
|||||||
{ MailPoet.I18n.t('sendingToSegmentsNotSpecified') }
|
{ MailPoet.I18n.t('sendingToSegmentsNotSpecified') }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else {
|
}
|
||||||
sendingToSegments = MailPoet.I18n.t('ifNewContentToSegments').replace(
|
|
||||||
'%$1s', segments.join(', ')
|
|
||||||
);
|
|
||||||
|
|
||||||
// set sending frequency
|
// set sending frequency
|
||||||
switch (newsletter.options.intervalType) {
|
switch (newsletter.options.intervalType) {
|
||||||
case 'daily':
|
case 'daily':
|
||||||
sendingFrequency = MailPoet.I18n.t('sendDaily').replace(
|
sendingFrequency = MailPoet.I18n.t('sendDaily').replace(
|
||||||
'%$1s', timeOfDayValues[newsletter.options.timeOfDay]
|
'%$1s', timeOfDayValues[newsletter.options.timeOfDay]
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'weekly':
|
case 'weekly':
|
||||||
sendingFrequency = MailPoet.I18n.t('sendWeekly').replace(
|
sendingFrequency = MailPoet.I18n.t('sendWeekly').replace(
|
||||||
'%$1s', weekDayValues[newsletter.options.weekDay]
|
'%$1s', weekDayValues[newsletter.options.weekDay]
|
||||||
).replace(
|
).replace(
|
||||||
'%$2s', timeOfDayValues[newsletter.options.timeOfDay]
|
'%$2s', timeOfDayValues[newsletter.options.timeOfDay]
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'monthly':
|
case 'monthly':
|
||||||
sendingFrequency = MailPoet.I18n.t('sendMonthly').replace(
|
sendingFrequency = MailPoet.I18n.t('sendMonthly').replace(
|
||||||
'%$1s', monthDayValues[newsletter.options.monthDay]
|
'%$1s', monthDayValues[newsletter.options.monthDay]
|
||||||
).replace(
|
).replace(
|
||||||
'%$2s', timeOfDayValues[newsletter.options.timeOfDay]
|
'%$2s', timeOfDayValues[newsletter.options.timeOfDay]
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'nthWeekDay':
|
case 'nthWeekDay':
|
||||||
sendingFrequency = MailPoet.I18n.t('sendNthWeekDay').replace(
|
sendingFrequency = MailPoet.I18n.t('sendNthWeekDay').replace(
|
||||||
'%$1s', nthWeekDayValues[newsletter.options.nthWeekDay]
|
'%$1s', nthWeekDayValues[newsletter.options.nthWeekDay]
|
||||||
).replace(
|
).replace(
|
||||||
'%$2s', weekDayValues[newsletter.options.weekDay]
|
'%$2s', weekDayValues[newsletter.options.weekDay]
|
||||||
).replace(
|
).replace(
|
||||||
'%$3s', timeOfDayValues[newsletter.options.timeOfDay]
|
'%$3s', timeOfDayValues[newsletter.options.timeOfDay]
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'immediately':
|
case 'immediately':
|
||||||
sendingFrequency = MailPoet.I18n.t('sendImmediately');
|
sendingFrequency = MailPoet.I18n.t('sendImmediately');
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
|
default:
|
||||||
|
sendingFrequency = 'Invalid sending frequency';
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<span>
|
<span>
|
||||||
{ sendingFrequency } { sendingToSegments }
|
{ sendingFrequency } { sendingToSegments }
|
||||||
@ -261,18 +262,17 @@ const NewsletterListNotification = React.createClass({
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
renderHistoryLink: function (newsletter) {
|
renderHistoryLink: function (newsletter) {
|
||||||
const childrenCount = ~~(newsletter.children_count);
|
const childrenCount = Number((newsletter.children_count));
|
||||||
if (childrenCount === 0) {
|
if (childrenCount === 0) {
|
||||||
return (
|
return (
|
||||||
MailPoet.I18n.t('notSentYet')
|
MailPoet.I18n.t('notSentYet')
|
||||||
);
|
);
|
||||||
} else {
|
|
||||||
return (
|
|
||||||
<Link
|
|
||||||
to={`/notification/history/${newsletter.id}`}
|
|
||||||
>{ MailPoet.I18n.t('viewHistory') }</Link>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
return (
|
||||||
|
<Link
|
||||||
|
to={`/notification/history/${newsletter.id}`}
|
||||||
|
>{ MailPoet.I18n.t('viewHistory') }</Link>
|
||||||
|
);
|
||||||
},
|
},
|
||||||
renderItem: function (newsletter, actions) {
|
renderItem: function (newsletter, actions) {
|
||||||
const rowClasses = classNames(
|
const rowClasses = classNames(
|
||||||
@ -311,7 +311,7 @@ const NewsletterListNotification = React.createClass({
|
|||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<h1 className="title">
|
<h1 className="title">
|
||||||
{MailPoet.I18n.t('pageTitle')} <Link className="page-title-action" to="/new">{MailPoet.I18n.t('new')}</Link>
|
{MailPoet.I18n.t('pageTitle')} <Link className="page-title-action" to="/new" data-automation-id="new_email">{MailPoet.I18n.t('new')}</Link>
|
||||||
</h1>
|
</h1>
|
||||||
|
|
||||||
<ListingTabs tab="notification" />
|
<ListingTabs tab="notification" />
|
||||||
@ -325,8 +325,8 @@ const NewsletterListNotification = React.createClass({
|
|||||||
base_url="notification"
|
base_url="notification"
|
||||||
onRenderItem={this.renderItem}
|
onRenderItem={this.renderItem}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
item_actions={newsletter_actions}
|
item_actions={newsletterActions}
|
||||||
messages={messages}
|
messages={messages}
|
||||||
auto_refresh={true}
|
auto_refresh={true}
|
||||||
sort_by="updated_at"
|
sort_by="updated_at"
|
||||||
|
@ -13,7 +13,7 @@ import {
|
|||||||
MailerMixin,
|
MailerMixin,
|
||||||
} from 'newsletters/listings/mixins.jsx';
|
} from 'newsletters/listings/mixins.jsx';
|
||||||
|
|
||||||
const mailpoet_tracking_enabled = (!!(window['mailpoet_tracking_enabled']));
|
const mailpoetTrackingEnabled = (!!(window.mailpoet_tracking_enabled));
|
||||||
|
|
||||||
const columns = [
|
const columns = [
|
||||||
{
|
{
|
||||||
@ -31,7 +31,7 @@ const columns = [
|
|||||||
{
|
{
|
||||||
name: 'statistics',
|
name: 'statistics',
|
||||||
label: MailPoet.I18n.t('statistics'),
|
label: MailPoet.I18n.t('statistics'),
|
||||||
display: mailpoet_tracking_enabled,
|
display: mailpoetTrackingEnabled,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'sent_at',
|
name: 'sent_at',
|
||||||
@ -39,7 +39,7 @@ const columns = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
let newsletter_actions = [
|
let newsletterActions = [
|
||||||
{
|
{
|
||||||
name: 'view',
|
name: 'view',
|
||||||
link: function (newsletter) {
|
link: function (newsletter) {
|
||||||
@ -52,7 +52,8 @@ let newsletter_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
newsletter_actions = Hooks.applyFilters('mailpoet_newsletters_listings_notification_history_actions', newsletter_actions);
|
Hooks.addFilter('mailpoet_newsletters_listings_notification_history_actions', StatisticsMixin.addStatsCTAAction);
|
||||||
|
newsletterActions = Hooks.applyFilters('mailpoet_newsletters_listings_notification_history_actions', newsletterActions);
|
||||||
|
|
||||||
const NewsletterListNotificationHistory = React.createClass({
|
const NewsletterListNotificationHistory = React.createClass({
|
||||||
mixins: [QueueMixin, StatisticsMixin, MailerMixin],
|
mixins: [QueueMixin, StatisticsMixin, MailerMixin],
|
||||||
@ -63,9 +64,7 @@ const NewsletterListNotificationHistory = React.createClass({
|
|||||||
'has-row-actions'
|
'has-row-actions'
|
||||||
);
|
);
|
||||||
|
|
||||||
const segments = newsletter.segments.map((segment) => {
|
const segments = newsletter.segments.map(segment => segment.name).join(', ');
|
||||||
return segment.name;
|
|
||||||
}).join(', ');
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
@ -84,7 +83,7 @@ const NewsletterListNotificationHistory = React.createClass({
|
|||||||
<td className="column" data-colname={MailPoet.I18n.t('lists')}>
|
<td className="column" data-colname={MailPoet.I18n.t('lists')}>
|
||||||
{ segments }
|
{ segments }
|
||||||
</td>
|
</td>
|
||||||
{ (mailpoet_tracking_enabled === true) ? (
|
{ (mailpoetTrackingEnabled === true) ? (
|
||||||
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
||||||
{ this.renderStatistics(newsletter, undefined, meta.current_time) }
|
{ this.renderStatistics(newsletter, undefined, meta.current_time) }
|
||||||
</td>
|
</td>
|
||||||
@ -99,7 +98,7 @@ const NewsletterListNotificationHistory = React.createClass({
|
|||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<h1 className="title">
|
<h1 className="title">
|
||||||
{MailPoet.I18n.t('pageTitle')} <Link className="page-title-action" to="/new">{MailPoet.I18n.t('new')}</Link>
|
{MailPoet.I18n.t('pageTitle')} <Link className="page-title-action" to="/new" data-automation-id="new_email">{MailPoet.I18n.t('new')}</Link>
|
||||||
</h1>
|
</h1>
|
||||||
|
|
||||||
<ListingTabs tab="notification" />
|
<ListingTabs tab="notification" />
|
||||||
@ -118,7 +117,7 @@ const NewsletterListNotificationHistory = React.createClass({
|
|||||||
base_url="notification/history/:parent_id"
|
base_url="notification/history/:parent_id"
|
||||||
onRenderItem={this.renderItem}
|
onRenderItem={this.renderItem}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
item_actions={newsletter_actions}
|
item_actions={newsletterActions}
|
||||||
auto_refresh={true}
|
auto_refresh={true}
|
||||||
sort_by="sent_at"
|
sort_by="sent_at"
|
||||||
sort_order="desc"
|
sort_order="desc"
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { Link } from 'react-router';
|
import { Link } from 'react-router';
|
||||||
|
import { confirmAlert } from 'react-confirm-alert';
|
||||||
import classNames from 'classnames';
|
import classNames from 'classnames';
|
||||||
import MailPoet from 'mailpoet';
|
import MailPoet from 'mailpoet';
|
||||||
import Hooks from 'wp-js-hooks';
|
import Hooks from 'wp-js-hooks';
|
||||||
@ -13,11 +14,11 @@ import {
|
|||||||
MailerMixin,
|
MailerMixin,
|
||||||
} from 'newsletters/listings/mixins.jsx';
|
} from 'newsletters/listings/mixins.jsx';
|
||||||
|
|
||||||
const mailpoet_tracking_enabled = (!!(window['mailpoet_tracking_enabled']));
|
const mailpoetTrackingEnabled = (!!(window.mailpoet_tracking_enabled));
|
||||||
|
|
||||||
const messages = {
|
const messages = {
|
||||||
onTrash: (response) => {
|
onTrash: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -32,7 +33,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onDelete: (response) => {
|
onDelete: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -47,7 +48,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onRestore: (response) => {
|
onRestore: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -80,7 +81,7 @@ const columns = [
|
|||||||
{
|
{
|
||||||
name: 'statistics',
|
name: 'statistics',
|
||||||
label: MailPoet.I18n.t('statistics'),
|
label: MailPoet.I18n.t('statistics'),
|
||||||
display: mailpoet_tracking_enabled,
|
display: mailpoetTrackingEnabled,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'sent_at',
|
name: 'sent_at',
|
||||||
@ -89,7 +90,7 @@ const columns = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const bulk_actions = [
|
const bulkActions = [
|
||||||
{
|
{
|
||||||
name: 'trash',
|
name: 'trash',
|
||||||
label: MailPoet.I18n.t('moveToTrash'),
|
label: MailPoet.I18n.t('moveToTrash'),
|
||||||
@ -98,17 +99,27 @@ const bulk_actions = [
|
|||||||
];
|
];
|
||||||
|
|
||||||
const confirmEdit = (newsletter) => {
|
const confirmEdit = (newsletter) => {
|
||||||
|
const redirectToEditing = () => {
|
||||||
|
window.location.href = `?page=mailpoet-newsletter-editor&id=${newsletter.id}`;
|
||||||
|
};
|
||||||
if (
|
if (
|
||||||
!newsletter.queue
|
!newsletter.queue
|
||||||
|| newsletter.status != 'sending'
|
|| newsletter.status !== 'sending'
|
||||||
|| newsletter.queue.status !== null
|
|| newsletter.queue.status !== null
|
||||||
|| window.confirm(MailPoet.I18n.t('confirmEdit'))
|
|
||||||
) {
|
) {
|
||||||
window.location.href = `?page=mailpoet-newsletter-editor&id=${newsletter.id}`;
|
redirectToEditing();
|
||||||
|
} else {
|
||||||
|
confirmAlert({
|
||||||
|
title: MailPoet.I18n.t('confirmTitle'),
|
||||||
|
message: MailPoet.I18n.t('confirmEdit'),
|
||||||
|
confirmLabel: MailPoet.I18n.t('confirmLabel'),
|
||||||
|
cancelLabel: MailPoet.I18n.t('cancelLabel'),
|
||||||
|
onConfirm: redirectToEditing,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let newsletter_actions = [
|
let newsletterActions = [
|
||||||
{
|
{
|
||||||
name: 'view',
|
name: 'view',
|
||||||
link: function (newsletter) {
|
link: function (newsletter) {
|
||||||
@ -145,7 +156,7 @@ let newsletter_actions = [
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -157,7 +168,8 @@ let newsletter_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
newsletter_actions = Hooks.applyFilters('mailpoet_newsletters_listings_standard_actions', newsletter_actions);
|
Hooks.addFilter('mailpoet_newsletters_listings_standard_actions', StatisticsMixin.addStatsCTAAction);
|
||||||
|
newsletterActions = Hooks.applyFilters('mailpoet_newsletters_listings_standard_actions', newsletterActions);
|
||||||
|
|
||||||
const NewsletterListStandard = React.createClass({
|
const NewsletterListStandard = React.createClass({
|
||||||
mixins: [QueueMixin, StatisticsMixin, MailerMixin],
|
mixins: [QueueMixin, StatisticsMixin, MailerMixin],
|
||||||
@ -168,9 +180,7 @@ const NewsletterListStandard = React.createClass({
|
|||||||
'has-row-actions'
|
'has-row-actions'
|
||||||
);
|
);
|
||||||
|
|
||||||
const segments = newsletter.segments.map((segment) => {
|
const segments = newsletter.segments.map(segment => segment.name).join(', ');
|
||||||
return segment.name;
|
|
||||||
}).join(', ');
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
@ -190,7 +200,7 @@ const NewsletterListStandard = React.createClass({
|
|||||||
<td className="column" data-colname={MailPoet.I18n.t('lists')}>
|
<td className="column" data-colname={MailPoet.I18n.t('lists')}>
|
||||||
{ segments }
|
{ segments }
|
||||||
</td>
|
</td>
|
||||||
{ (mailpoet_tracking_enabled === true) ? (
|
{ (mailpoetTrackingEnabled === true) ? (
|
||||||
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
||||||
{ this.renderStatistics(newsletter, undefined, meta.current_time) }
|
{ this.renderStatistics(newsletter, undefined, meta.current_time) }
|
||||||
</td>
|
</td>
|
||||||
@ -210,6 +220,7 @@ const NewsletterListStandard = React.createClass({
|
|||||||
onClick={() => MailPoet.trackEvent('Emails > Add New',
|
onClick={() => MailPoet.trackEvent('Emails > Add New',
|
||||||
{ 'MailPoet Free version': window.mailpoet_version }
|
{ 'MailPoet Free version': window.mailpoet_version }
|
||||||
)}
|
)}
|
||||||
|
data-automation-id="new_email"
|
||||||
>
|
>
|
||||||
{MailPoet.I18n.t('new')}
|
{MailPoet.I18n.t('new')}
|
||||||
</Link>
|
</Link>
|
||||||
@ -226,8 +237,8 @@ const NewsletterListStandard = React.createClass({
|
|||||||
base_url="standard"
|
base_url="standard"
|
||||||
onRenderItem={this.renderItem}
|
onRenderItem={this.renderItem}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
item_actions={newsletter_actions}
|
item_actions={newsletterActions}
|
||||||
messages={messages}
|
messages={messages}
|
||||||
auto_refresh={true}
|
auto_refresh={true}
|
||||||
sort_by="sent_at"
|
sort_by="sent_at"
|
||||||
|
@ -35,7 +35,7 @@ const ListingTabs = React.createClass({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Link
|
<Link
|
||||||
key={'tab-' + index}
|
key={`tab-${index}`}
|
||||||
className={tabClasses}
|
className={tabClasses}
|
||||||
to={tab.link}
|
to={tab.link}
|
||||||
onClick={() => MailPoet.trackEvent(`Tab Emails > ${tab.name} clicked`,
|
onClick={() => MailPoet.trackEvent(`Tab Emails > ${tab.name} clicked`,
|
||||||
@ -46,7 +46,7 @@ const ListingTabs = React.createClass({
|
|||||||
});
|
});
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<h2 className="nav-tab-wrapper">
|
<h2 className="nav-tab-wrapper" data-automation-id="newsletters_listing_tabs">
|
||||||
{ tabs }
|
{ tabs }
|
||||||
</h2>
|
</h2>
|
||||||
);
|
);
|
||||||
|
@ -11,13 +11,13 @@ import MailPoet from 'mailpoet';
|
|||||||
import _ from 'underscore';
|
import _ from 'underscore';
|
||||||
import Hooks from 'wp-js-hooks';
|
import Hooks from 'wp-js-hooks';
|
||||||
|
|
||||||
const mailpoet_roles = window.mailpoet_roles || {};
|
const mailpoetRoles = window.mailpoet_roles || {};
|
||||||
const mailpoet_segments = window.mailpoet_segments || {};
|
const mailpoetSegments = window.mailpoet_segments || {};
|
||||||
const mailpoet_tracking_enabled = (!!(window['mailpoet_tracking_enabled']));
|
const mailpoetTrackingEnabled = (!!(window.mailpoet_tracking_enabled));
|
||||||
|
|
||||||
const messages = {
|
const messages = {
|
||||||
onTrash: (response) => {
|
onTrash: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -32,7 +32,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onDelete: (response) => {
|
onDelete: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -47,7 +47,7 @@ const messages = {
|
|||||||
MailPoet.Notice.success(message);
|
MailPoet.Notice.success(message);
|
||||||
},
|
},
|
||||||
onRestore: (response) => {
|
onRestore: (response) => {
|
||||||
const count = ~~response.meta.count;
|
const count = Number(response.meta.count);
|
||||||
let message = null;
|
let message = null;
|
||||||
|
|
||||||
if (count === 1) {
|
if (count === 1) {
|
||||||
@ -81,7 +81,7 @@ const columns = [
|
|||||||
{
|
{
|
||||||
name: 'statistics',
|
name: 'statistics',
|
||||||
label: MailPoet.I18n.t('statistics'),
|
label: MailPoet.I18n.t('statistics'),
|
||||||
display: mailpoet_tracking_enabled,
|
display: mailpoetTrackingEnabled,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: 'updated_at',
|
name: 'updated_at',
|
||||||
@ -90,7 +90,7 @@ const columns = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
const bulk_actions = [
|
const bulkActions = [
|
||||||
{
|
{
|
||||||
name: 'trash',
|
name: 'trash',
|
||||||
label: MailPoet.I18n.t('moveToTrash'),
|
label: MailPoet.I18n.t('moveToTrash'),
|
||||||
@ -98,7 +98,7 @@ const bulk_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
let newsletter_actions = [
|
let newsletterActions = [
|
||||||
{
|
{
|
||||||
name: 'view',
|
name: 'view',
|
||||||
link: function (newsletter) {
|
link: function (newsletter) {
|
||||||
@ -124,7 +124,8 @@ let newsletter_actions = [
|
|||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
newsletter_actions = Hooks.applyFilters('mailpoet_newsletters_listings_welcome_notification_actions', newsletter_actions);
|
Hooks.addFilter('mailpoet_newsletters_listings_welcome_notification_actions', StatisticsMixin.addStatsCTAAction);
|
||||||
|
newsletterActions = Hooks.applyFilters('mailpoet_newsletters_listings_welcome_notification_actions', newsletterActions);
|
||||||
|
|
||||||
const NewsletterListWelcome = React.createClass({
|
const NewsletterListWelcome = React.createClass({
|
||||||
mixins: [StatisticsMixin, MailerMixin],
|
mixins: [StatisticsMixin, MailerMixin],
|
||||||
@ -138,7 +139,7 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
endpoint: 'newsletters',
|
endpoint: 'newsletters',
|
||||||
action: 'setStatus',
|
action: 'setStatus',
|
||||||
data: {
|
data: {
|
||||||
id: ~~(e.target.getAttribute('data-id')),
|
id: Number(e.target.getAttribute('data-id')),
|
||||||
status: e.target.value,
|
status: e.target.value,
|
||||||
},
|
},
|
||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
@ -155,7 +156,7 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
renderStatus: function (newsletter) {
|
renderStatus: function (newsletter) {
|
||||||
const total_sent = (
|
const totalSent = (
|
||||||
MailPoet.I18n.t('sentToXSubscribers')
|
MailPoet.I18n.t('sentToXSubscribers')
|
||||||
.replace('%$1d', newsletter.total_sent.toLocaleString())
|
.replace('%$1d', newsletter.total_sent.toLocaleString())
|
||||||
);
|
);
|
||||||
@ -172,13 +173,14 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
<option value="draft">{ MailPoet.I18n.t('inactive') }</option>
|
<option value="draft">{ MailPoet.I18n.t('inactive') }</option>
|
||||||
</select>
|
</select>
|
||||||
</p>
|
</p>
|
||||||
<p>{ total_sent }</p>
|
<p>{ totalSent }</p>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
renderSettings: function (newsletter) {
|
renderSettings: function (newsletter) {
|
||||||
let sendingEvent;
|
let sendingEvent;
|
||||||
let sendingDelay;
|
let sendingDelay;
|
||||||
|
let segment;
|
||||||
|
|
||||||
// set sending event
|
// set sending event
|
||||||
switch (newsletter.options.event) {
|
switch (newsletter.options.event) {
|
||||||
@ -188,16 +190,17 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
sendingEvent = MailPoet.I18n.t('welcomeEventWPUserAnyRole');
|
sendingEvent = MailPoet.I18n.t('welcomeEventWPUserAnyRole');
|
||||||
} else {
|
} else {
|
||||||
sendingEvent = MailPoet.I18n.t('welcomeEventWPUserWithRole').replace(
|
sendingEvent = MailPoet.I18n.t('welcomeEventWPUserWithRole').replace(
|
||||||
'%$1s', mailpoet_roles[newsletter.options.role]
|
'%$1s', mailpoetRoles[newsletter.options.role]
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'segment':
|
default:
|
||||||
// get segment
|
// get segment
|
||||||
const segment = _.find(mailpoet_segments, (segment) => {
|
segment = _.find(
|
||||||
return (~~(segment.id) === ~~(newsletter.options.segment));
|
mailpoetSegments,
|
||||||
});
|
seg => (Number(seg.id) === Number(newsletter.options.segment))
|
||||||
|
);
|
||||||
|
|
||||||
if (segment === undefined) {
|
if (segment === undefined) {
|
||||||
return (
|
return (
|
||||||
@ -205,11 +208,11 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
{ MailPoet.I18n.t('sendingToSegmentsNotSpecified') }
|
{ MailPoet.I18n.t('sendingToSegmentsNotSpecified') }
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
} else {
|
}
|
||||||
sendingEvent = MailPoet.I18n.t('welcomeEventSegment').replace(
|
sendingEvent = MailPoet.I18n.t('welcomeEventSegment').replace(
|
||||||
'%$1s', segment.name
|
'%$1s', segment.name
|
||||||
);
|
);
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -234,8 +237,12 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
'%$1d', newsletter.options.afterTimeNumber
|
'%$1d', newsletter.options.afterTimeNumber
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
sendingDelay = 'Invalid sending delay';
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
sendingEvent += ' [' + sendingDelay + ']';
|
sendingEvent += ` [${sendingDelay}]`;
|
||||||
}
|
}
|
||||||
// add a "period" at the end if we do have a sendingEvent
|
// add a "period" at the end if we do have a sendingEvent
|
||||||
sendingEvent += '.';
|
sendingEvent += '.';
|
||||||
@ -271,7 +278,7 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
<td className="column" data-colname={MailPoet.I18n.t('settings')}>
|
<td className="column" data-colname={MailPoet.I18n.t('settings')}>
|
||||||
{ this.renderSettings(newsletter) }
|
{ this.renderSettings(newsletter) }
|
||||||
</td>
|
</td>
|
||||||
{ (mailpoet_tracking_enabled === true) ? (
|
{ (mailpoetTrackingEnabled === true) ? (
|
||||||
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
<td className="column" data-colname={MailPoet.I18n.t('statistics')}>
|
||||||
{ this.renderStatistics(
|
{ this.renderStatistics(
|
||||||
newsletter,
|
newsletter,
|
||||||
@ -289,7 +296,7 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<h1 className="title">
|
<h1 className="title">
|
||||||
{ MailPoet.I18n.t('pageTitle') } <Link className="page-title-action" to="/new">{ MailPoet.I18n.t('new') }</Link>
|
{ MailPoet.I18n.t('pageTitle') } <Link className="page-title-action" to="/new" data-automation-id="new_email">{ MailPoet.I18n.t('new') }</Link>
|
||||||
</h1>
|
</h1>
|
||||||
|
|
||||||
<ListingTabs tab="welcome" />
|
<ListingTabs tab="welcome" />
|
||||||
@ -303,8 +310,8 @@ const NewsletterListWelcome = React.createClass({
|
|||||||
base_url="welcome"
|
base_url="welcome"
|
||||||
onRenderItem={this.renderItem}
|
onRenderItem={this.renderItem}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
bulk_actions={bulk_actions}
|
bulk_actions={bulkActions}
|
||||||
item_actions={newsletter_actions}
|
item_actions={newsletterActions}
|
||||||
messages={messages}
|
messages={messages}
|
||||||
auto_refresh={true}
|
auto_refresh={true}
|
||||||
sort_by="updated_at"
|
sort_by="updated_at"
|
||||||
|
@ -27,17 +27,18 @@ const App = React.createClass({
|
|||||||
const container = document.getElementById('newsletters_container');
|
const container = document.getElementById('newsletters_container');
|
||||||
|
|
||||||
if (container) {
|
if (container) {
|
||||||
let extra_routes = [];
|
let extraRoutes = [];
|
||||||
extra_routes = Hooks.applyFilters('mailpoet_newsletters_before_router', extra_routes);
|
extraRoutes = Hooks.applyFilters('mailpoet_newsletters_before_router', extraRoutes);
|
||||||
|
|
||||||
const mailpoet_listing = ReactDOM.render((
|
const mailpoetListing = ReactDOM.render((
|
||||||
<Router history={history}>
|
<Router history={history}>
|
||||||
<Route path="/" component={App}>
|
<Route path="/" component={App}>
|
||||||
<IndexRedirect to="standard" />
|
<IndexRedirect to="standard" />
|
||||||
{/* Listings */}
|
{/* Listings */}
|
||||||
<Route path="standard(/)**" params={{ tab: 'standard' }} component={NewsletterListStandard} />
|
<Route path="standard(/)**" params={{ tab: 'standard' }} component={NewsletterListStandard} />
|
||||||
<Route path="welcome(/)**" component={NewsletterListWelcome} />
|
<Route path="welcome(/)**" component={NewsletterListWelcome} />
|
||||||
<Route path="notification/history/:parent_id(/)**" component={NewsletterListNotificationHistory} />
|
<Route path="notification/history/:parent_id(/)**"
|
||||||
|
component={NewsletterListNotificationHistory} />
|
||||||
<Route path="notification(/)**" component={NewsletterListNotification} />
|
<Route path="notification(/)**" component={NewsletterListNotification} />
|
||||||
{/* Newsletter: type selection */}
|
{/* Newsletter: type selection */}
|
||||||
<Route path="new" component={NewsletterTypes} />
|
<Route path="new" component={NewsletterTypes} />
|
||||||
@ -49,10 +50,12 @@ if (container) {
|
|||||||
{/* Sending options */}
|
{/* Sending options */}
|
||||||
<Route path="send/:id" component={NewsletterSend} />
|
<Route path="send/:id" component={NewsletterSend} />
|
||||||
{/* Extra routes */}
|
{/* Extra routes */}
|
||||||
{ extra_routes.map(rt => <Route key={rt.path} path={rt.path} component={rt.component} />) }
|
{extraRoutes.map(rt =>
|
||||||
|
<Route key={rt.path} path={rt.path} component={rt.component} data={rt.data || null} />
|
||||||
|
)}
|
||||||
</Route>
|
</Route>
|
||||||
</Router>
|
</Router>
|
||||||
), container);
|
), container);
|
||||||
|
|
||||||
window.mailpoet_listing = mailpoet_listing;
|
window.mailpoet_listing = mailpoetListing;
|
||||||
}
|
}
|
||||||
|
@ -4,14 +4,14 @@ import MailPoet from 'mailpoet';
|
|||||||
const timeFormat = window.mailpoet_time_format || 'H:i';
|
const timeFormat = window.mailpoet_time_format || 'H:i';
|
||||||
|
|
||||||
// welcome emails
|
// welcome emails
|
||||||
const _timeDelayValues = {
|
const timeDelayValues = {
|
||||||
immediate: MailPoet.I18n.t('delayImmediately'),
|
immediate: MailPoet.I18n.t('delayImmediately'),
|
||||||
hours: MailPoet.I18n.t('delayHoursAfter'),
|
hours: MailPoet.I18n.t('delayHoursAfter'),
|
||||||
days: MailPoet.I18n.t('delayDaysAfter'),
|
days: MailPoet.I18n.t('delayDaysAfter'),
|
||||||
weeks: MailPoet.I18n.t('delayWeeksAfter'),
|
weeks: MailPoet.I18n.t('delayWeeksAfter'),
|
||||||
};
|
};
|
||||||
|
|
||||||
const _intervalValues = {
|
const intervalValues = {
|
||||||
daily: MailPoet.I18n.t('daily'),
|
daily: MailPoet.I18n.t('daily'),
|
||||||
weekly: MailPoet.I18n.t('weekly'),
|
weekly: MailPoet.I18n.t('weekly'),
|
||||||
monthly: MailPoet.I18n.t('monthly'),
|
monthly: MailPoet.I18n.t('monthly'),
|
||||||
@ -24,18 +24,16 @@ const SECONDS_IN_DAY = 86400;
|
|||||||
const TIME_STEP_SECONDS = 3600;
|
const TIME_STEP_SECONDS = 3600;
|
||||||
const numberOfTimeSteps = SECONDS_IN_DAY / TIME_STEP_SECONDS;
|
const numberOfTimeSteps = SECONDS_IN_DAY / TIME_STEP_SECONDS;
|
||||||
|
|
||||||
const _timeOfDayValues = _.object(_.map(
|
const timeOfDayValues = _.object(_.map(
|
||||||
_.times(numberOfTimeSteps, (step) => {
|
_.times(numberOfTimeSteps, step => step * TIME_STEP_SECONDS), (seconds) => {
|
||||||
return step * TIME_STEP_SECONDS;
|
const date = new Date(null);
|
||||||
}), (seconds) => {
|
date.setSeconds(seconds);
|
||||||
const date = new Date(null);
|
const timeLabel = MailPoet.Date.format(date, { format: timeFormat, offset: 0 });
|
||||||
date.setSeconds(seconds);
|
return [seconds, timeLabel];
|
||||||
const timeLabel = MailPoet.Date.format(date, { format: timeFormat, offset: 0 });
|
})
|
||||||
return [seconds, timeLabel];
|
|
||||||
})
|
|
||||||
);
|
);
|
||||||
|
|
||||||
const _weekDayValues = {
|
const weekDayValues = {
|
||||||
0: MailPoet.I18n.t('sunday'),
|
0: MailPoet.I18n.t('sunday'),
|
||||||
1: MailPoet.I18n.t('monday'),
|
1: MailPoet.I18n.t('monday'),
|
||||||
2: MailPoet.I18n.t('tuesday'),
|
2: MailPoet.I18n.t('tuesday'),
|
||||||
@ -46,37 +44,35 @@ const _weekDayValues = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const NUMBER_OF_DAYS_IN_MONTH = 28;
|
const NUMBER_OF_DAYS_IN_MONTH = 28;
|
||||||
const _monthDayValues = _.object(
|
const monthDayValues = _.object(
|
||||||
_.map(
|
_.map(
|
||||||
_.times(NUMBER_OF_DAYS_IN_MONTH, (day) => {
|
_.times(NUMBER_OF_DAYS_IN_MONTH, day => day), (day) => {
|
||||||
return day;
|
const labels = {
|
||||||
}), (day) => {
|
0: MailPoet.I18n.t('first'),
|
||||||
const labels = {
|
1: MailPoet.I18n.t('second'),
|
||||||
0: MailPoet.I18n.t('first'),
|
2: MailPoet.I18n.t('third'),
|
||||||
1: MailPoet.I18n.t('second'),
|
};
|
||||||
2: MailPoet.I18n.t('third'),
|
let label;
|
||||||
};
|
if (labels[day] !== undefined) {
|
||||||
let label;
|
label = labels[day];
|
||||||
if (labels[day] !== undefined) {
|
} else {
|
||||||
label = labels[day];
|
label = MailPoet.I18n.t('nth').replace('%$1d', day + 1);
|
||||||
} else {
|
}
|
||||||
label = MailPoet.I18n.t('nth').replace('%$1d', day + 1);
|
return [day + 1, label];
|
||||||
}
|
}
|
||||||
return [day + 1, label];
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
|
|
||||||
const _nthWeekDayValues = {
|
const nthWeekDayValues = {
|
||||||
1: MailPoet.I18n.t('first'),
|
1: MailPoet.I18n.t('first'),
|
||||||
2: MailPoet.I18n.t('second'),
|
2: MailPoet.I18n.t('second'),
|
||||||
3: MailPoet.I18n.t('third'),
|
3: MailPoet.I18n.t('third'),
|
||||||
L: MailPoet.I18n.t('last'),
|
L: MailPoet.I18n.t('last'),
|
||||||
};
|
};
|
||||||
|
|
||||||
export { _timeDelayValues as timeDelayValues };
|
export { timeDelayValues };
|
||||||
export { _intervalValues as intervalValues };
|
export { intervalValues };
|
||||||
export { _timeOfDayValues as timeOfDayValues };
|
export { timeOfDayValues };
|
||||||
export { _weekDayValues as weekDayValues };
|
export { weekDayValues };
|
||||||
export { _monthDayValues as monthDayValues };
|
export { monthDayValues };
|
||||||
export { _nthWeekDayValues as nthWeekDayValues };
|
export { nthWeekDayValues };
|
||||||
|
@ -11,6 +11,7 @@ define(
|
|||||||
'newsletters/breadcrumb.jsx',
|
'newsletters/breadcrumb.jsx',
|
||||||
'help-tooltip.jsx',
|
'help-tooltip.jsx',
|
||||||
'jquery',
|
'jquery',
|
||||||
|
'html2canvas',
|
||||||
],
|
],
|
||||||
(
|
(
|
||||||
React,
|
React,
|
||||||
@ -23,9 +24,9 @@ define(
|
|||||||
WelcomeNewsletterFields,
|
WelcomeNewsletterFields,
|
||||||
Breadcrumb,
|
Breadcrumb,
|
||||||
HelpTooltip,
|
HelpTooltip,
|
||||||
jQuery
|
jQuery,
|
||||||
|
html2canvas
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const NewsletterSend = React.createClass({
|
const NewsletterSend = React.createClass({
|
||||||
contextTypes: {
|
contextTypes: {
|
||||||
router: React.PropTypes.object.isRequired,
|
router: React.PropTypes.object.isRequired,
|
||||||
@ -89,13 +90,39 @@ define(
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
saveTemplate: function (response, done) {
|
||||||
|
const iframe = document.createElement('iframe');
|
||||||
|
iframe.src = response.meta.preview_url;
|
||||||
|
iframe.onload = () => {
|
||||||
|
html2canvas(iframe.contentDocument.documentElement).then((thumbnail) => {
|
||||||
|
document.body.removeChild(iframe);
|
||||||
|
MailPoet.Ajax.post({
|
||||||
|
api_version: window.mailpoet_api_version,
|
||||||
|
endpoint: 'newsletterTemplates',
|
||||||
|
action: 'save',
|
||||||
|
data: {
|
||||||
|
newsletter_id: response.data.id,
|
||||||
|
name: response.data.subject,
|
||||||
|
description: response.data.preheader,
|
||||||
|
thumbnail: thumbnail.toDataURL('image/jpeg'),
|
||||||
|
body: JSON.stringify(response.data.body),
|
||||||
|
categories: '["recent"]',
|
||||||
|
},
|
||||||
|
}).then(done).fail(this.showError);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
// just to hide the iframe
|
||||||
|
iframe.className ='mailpoet_template_iframe';
|
||||||
|
document.body.appendChild(iframe);
|
||||||
|
},
|
||||||
handleSend: function (e) {
|
handleSend: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
|
|
||||||
if (!this.isValid()) {
|
if (!this.isValid()) {
|
||||||
jQuery('#mailpoet_newsletter').parsley().validate();
|
jQuery('#mailpoet_newsletter').parsley().validate();
|
||||||
} else {
|
} else {
|
||||||
this._save(e).done(() => {
|
MailPoet.Modal.loading(true);
|
||||||
|
this.saveNewsletter(e).done(() => {
|
||||||
this.setState({ loading: true });
|
this.setState({ loading: true });
|
||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
switch (response.data.type) {
|
switch (response.data.type) {
|
||||||
@ -109,30 +136,38 @@ define(
|
|||||||
id: this.props.params.id,
|
id: this.props.params.id,
|
||||||
status: 'active',
|
status: 'active',
|
||||||
},
|
},
|
||||||
}).done((response) => {
|
}).done((response2) => {
|
||||||
// redirect to listing based on newsletter type
|
// save template in recently sent category
|
||||||
this.context.router.push(`/${this.state.item.type || ''}`);
|
this.saveTemplate(response, () => {
|
||||||
const opts = this.state.item.options;
|
// redirect to listing based on newsletter type
|
||||||
// display success message depending on newsletter type
|
this.context.router.push(`/${this.state.item.type || ''}`);
|
||||||
if (response.data.type === 'welcome') {
|
const opts = this.state.item.options;
|
||||||
MailPoet.Notice.success(
|
// display success message depending on newsletter type
|
||||||
MailPoet.I18n.t('welcomeEmailActivated')
|
if (response2.data.type === 'welcome') {
|
||||||
);
|
MailPoet.Notice.success(
|
||||||
MailPoet.trackEvent('Emails > Welcome email activated', {
|
MailPoet.I18n.t('welcomeEmailActivated')
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
);
|
||||||
'List type': opts.event,
|
MailPoet.trackEvent('Emails > Welcome email activated', {
|
||||||
Delay: opts.afterTimeNumber + ' ' + opts.afterTimeType,
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
});
|
'List type': opts.event,
|
||||||
} else if (response.data.type === 'notification') {
|
Delay: `${opts.afterTimeNumber} ${opts.afterTimeType}`,
|
||||||
MailPoet.Notice.success(
|
});
|
||||||
MailPoet.I18n.t('postNotificationActivated')
|
} else if (response2.data.type === 'notification') {
|
||||||
);
|
MailPoet.Notice.success(
|
||||||
MailPoet.trackEvent('Emails > Post notifications activated', {
|
MailPoet.I18n.t('postNotificationActivated')
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
);
|
||||||
Frequency: opts.intervalType,
|
MailPoet.trackEvent('Emails > Post notifications activated', {
|
||||||
});
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
}
|
Frequency: opts.intervalType,
|
||||||
}).fail(this._showError);
|
});
|
||||||
|
}
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
|
});
|
||||||
|
}).fail((err) => {
|
||||||
|
this.showError(err);
|
||||||
|
this.setState({ loading: false });
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
|
});
|
||||||
default:
|
default:
|
||||||
return MailPoet.Ajax.post({
|
return MailPoet.Ajax.post({
|
||||||
api_version: window.mailpoet_api_version,
|
api_version: window.mailpoet_api_version,
|
||||||
@ -141,33 +176,43 @@ define(
|
|||||||
data: {
|
data: {
|
||||||
newsletter_id: this.props.params.id,
|
newsletter_id: this.props.params.id,
|
||||||
},
|
},
|
||||||
}).done((response) => {
|
}).done((response2) => {
|
||||||
// redirect to listing based on newsletter type
|
// save template in recently sent category
|
||||||
this.context.router.push(`/${this.state.item.type || ''}`);
|
this.saveTemplate(response, () => {
|
||||||
|
// redirect to listing based on newsletter type
|
||||||
|
this.context.router.push(`/${this.state.item.type || ''}`);
|
||||||
|
|
||||||
if (response.data.status === 'scheduled') {
|
if (response2.data.status === 'scheduled') {
|
||||||
MailPoet.Notice.success(
|
MailPoet.Notice.success(
|
||||||
MailPoet.I18n.t('newsletterHasBeenScheduled')
|
MailPoet.I18n.t('newsletterHasBeenScheduled')
|
||||||
);
|
);
|
||||||
MailPoet.trackEvent('Emails > Newsletter sent', {
|
MailPoet.trackEvent('Emails > Newsletter sent', {
|
||||||
scheduled: true,
|
scheduled: true,
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
MailPoet.Notice.success(
|
MailPoet.Notice.success(
|
||||||
MailPoet.I18n.t('newsletterBeingSent')
|
MailPoet.I18n.t('newsletterBeingSent')
|
||||||
);
|
);
|
||||||
MailPoet.trackEvent('Emails > Newsletter sent', {
|
MailPoet.trackEvent('Emails > Newsletter sent', {
|
||||||
scheduled: false,
|
scheduled: false,
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}).fail(this._showError);
|
MailPoet.Modal.loading(false);
|
||||||
|
});
|
||||||
|
})
|
||||||
|
.fail((err) => {
|
||||||
|
this.showError(err);
|
||||||
|
this.setState({ loading: false });
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.fail(this._showError)
|
.fail((err) => {
|
||||||
.always(() => {
|
this.showError(err);
|
||||||
this.setState({ loading: false });
|
this.setState({ loading: false });
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@ -177,7 +222,7 @@ define(
|
|||||||
if (!this.isValid()) {
|
if (!this.isValid()) {
|
||||||
jQuery('#mailpoet_newsletter').parsley().validate();
|
jQuery('#mailpoet_newsletter').parsley().validate();
|
||||||
} else {
|
} else {
|
||||||
this._save(e).done(() => {
|
this.saveNewsletter(e).done(() => {
|
||||||
this.setState({ loading: true });
|
this.setState({ loading: true });
|
||||||
}).done(() => {
|
}).done(() => {
|
||||||
MailPoet.Ajax.post({
|
MailPoet.Ajax.post({
|
||||||
@ -195,13 +240,13 @@ define(
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
.fail(this._showError)
|
.fail(this.showError)
|
||||||
.always(() => {
|
.always(() => {
|
||||||
this.setState({ loading: false });
|
this.setState({ loading: false });
|
||||||
});
|
});
|
||||||
@ -211,27 +256,27 @@ define(
|
|||||||
handleSave: function (e) {
|
handleSave: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
|
|
||||||
this._save(e).done(() => {
|
this.saveNewsletter(e).done(() => {
|
||||||
MailPoet.Notice.success(
|
MailPoet.Notice.success(
|
||||||
MailPoet.I18n.t('newsletterUpdated')
|
MailPoet.I18n.t('newsletterUpdated')
|
||||||
);
|
);
|
||||||
}).done(() => {
|
}).done(() => {
|
||||||
this.context.router.push(`/${this.state.item.type || ''}`);
|
this.context.router.push(`/${this.state.item.type || ''}`);
|
||||||
}).fail(this._showError);
|
}).fail(this.showError);
|
||||||
},
|
},
|
||||||
handleRedirectToDesign: function (e) {
|
handleRedirectToDesign: function (e) {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
const redirectTo = e.target.href;
|
const redirectTo = e.target.href;
|
||||||
|
|
||||||
this._save(e).done(() => {
|
this.saveNewsletter(e).done(() => {
|
||||||
MailPoet.Notice.success(
|
MailPoet.Notice.success(
|
||||||
MailPoet.I18n.t('newsletterUpdated')
|
MailPoet.I18n.t('newsletterUpdated')
|
||||||
);
|
);
|
||||||
}).done(() => {
|
}).done(() => {
|
||||||
window.location = redirectTo;
|
window.location = redirectTo;
|
||||||
}).fail(this._showError);
|
}).fail(this.showError);
|
||||||
},
|
},
|
||||||
_save: function () {
|
saveNewsletter: function () {
|
||||||
const data = this.state.item;
|
const data = this.state.item;
|
||||||
data.queue = undefined;
|
data.queue = undefined;
|
||||||
this.setState({ loading: true });
|
this.setState({ loading: true });
|
||||||
@ -255,10 +300,10 @@ define(
|
|||||||
this.setState({ loading: false });
|
this.setState({ loading: false });
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
_showError: (response) => {
|
showError: (response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -275,12 +320,12 @@ define(
|
|||||||
return true;
|
return true;
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const isPaused = this.state.item.status == 'sending'
|
const isPaused = this.state.item.status === 'sending'
|
||||||
&& this.state.item.queue
|
&& this.state.item.queue
|
||||||
&& this.state.item.queue.status == 'paused';
|
&& this.state.item.queue.status === 'paused';
|
||||||
const fields = this.state.fields.map((field) => {
|
const fields = this.state.fields.map((field) => {
|
||||||
const newField = field;
|
const newField = field;
|
||||||
if (field.name == 'segments' || field.name == 'options') {
|
if (field.name === 'segments' || field.name === 'options') {
|
||||||
newField.disabled = isPaused;
|
newField.disabled = isPaused;
|
||||||
}
|
}
|
||||||
return newField;
|
return newField;
|
||||||
@ -325,13 +370,13 @@ define(
|
|||||||
{MailPoet.I18n.t('orSimply')}
|
{MailPoet.I18n.t('orSimply')}
|
||||||
<a
|
<a
|
||||||
href={
|
href={
|
||||||
'?page=mailpoet-newsletter-editor&id=' + this.props.params.id
|
`?page=mailpoet-newsletter-editor&id=${this.props.params.id}`
|
||||||
}
|
}
|
||||||
onClick={this.handleRedirectToDesign}>
|
onClick={this.handleRedirectToDesign}>
|
||||||
{MailPoet.I18n.t('goBackToDesign')}
|
{MailPoet.I18n.t('goBackToDesign')}
|
||||||
</a>.
|
</a>.
|
||||||
</p>
|
</p>
|
||||||
{ !isPaused && sendButtonOptions['disabled'] && sendButtonOptions['disabled'] === 'disabled' && (
|
{ !isPaused && sendButtonOptions.disabled && sendButtonOptions.disabled === 'disabled' && (
|
||||||
<HelpTooltip
|
<HelpTooltip
|
||||||
tooltip={MailPoet.I18n.t('helpTooltipSendEmail')}
|
tooltip={MailPoet.I18n.t('helpTooltipSendEmail')}
|
||||||
tooltipId="helpTooltipSendEmail"
|
tooltipId="helpTooltipSendEmail"
|
||||||
|
@ -11,7 +11,6 @@ define(
|
|||||||
Scheduling,
|
Scheduling,
|
||||||
_
|
_
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
let fields = [
|
let fields = [
|
||||||
{
|
{
|
||||||
name: 'subject',
|
name: 'subject',
|
||||||
@ -40,18 +39,14 @@ define(
|
|||||||
endpoint: 'segments',
|
endpoint: 'segments',
|
||||||
multiple: true,
|
multiple: true,
|
||||||
filter: function (segment) {
|
filter: function (segment) {
|
||||||
return !!(!segment.deleted_at);
|
return !segment.deleted_at;
|
||||||
},
|
},
|
||||||
getLabel: function (segment) {
|
getLabel: function (segment) {
|
||||||
return segment.name + ' (' + parseInt(segment.subscribers, 10).toLocaleString() + ')';
|
return `${segment.name} (${parseInt(segment.subscribers, 10).toLocaleString()})`;
|
||||||
},
|
},
|
||||||
transformChangedValue: function (segment_ids) {
|
transformChangedValue: function (segmentIds) {
|
||||||
const all_segments = this.state.items;
|
const allSegments = this.state.items;
|
||||||
return _.map(segment_ids, (id) => {
|
return _.map(segmentIds, id => _.find(allSegments, segment => segment.id === id));
|
||||||
return _.find(all_segments, (segment) => {
|
|
||||||
return segment.id === id;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
validation: {
|
validation: {
|
||||||
'data-parsley-required': true,
|
'data-parsley-required': true,
|
||||||
|
@ -13,11 +13,10 @@ define(
|
|||||||
MailPoet,
|
MailPoet,
|
||||||
Hooks
|
Hooks
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const jQuery = jq;
|
const jQuery = jq;
|
||||||
|
|
||||||
const currentTime = window.mailpoet_current_time || '00:00';
|
const currentTime = window.mailpoet_current_time || '00:00';
|
||||||
const defaultDateTime = window.mailpoet_current_date + ' ' + '00:00:00';
|
const defaultDateTime = `${window.mailpoet_current_date} 00:00:00`;
|
||||||
const timeOfDayItems = window.mailpoet_schedule_time_of_day;
|
const timeOfDayItems = window.mailpoet_schedule_time_of_day;
|
||||||
const dateDisplayFormat = window.mailpoet_date_display_format;
|
const dateDisplayFormat = window.mailpoet_date_display_format;
|
||||||
const dateStorageFormat = window.mailpoet_date_storage_format;
|
const dateStorageFormat = window.mailpoet_date_storage_format;
|
||||||
@ -169,15 +168,13 @@ define(
|
|||||||
const TimeSelect = React.createClass({
|
const TimeSelect = React.createClass({
|
||||||
render: function () {
|
render: function () {
|
||||||
const options = Object.keys(timeOfDayItems).map(
|
const options = Object.keys(timeOfDayItems).map(
|
||||||
(value, index) => {
|
(value, index) => (
|
||||||
return (
|
<option
|
||||||
<option
|
key={`option-${index}`}
|
||||||
key={'option-' + index}
|
value={value}>
|
||||||
value={value}>
|
{ timeOfDayItems[value] }
|
||||||
{ timeOfDayItems[value] }
|
</option>
|
||||||
</option>
|
)
|
||||||
);
|
|
||||||
}
|
|
||||||
);
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@ -195,16 +192,16 @@ define(
|
|||||||
});
|
});
|
||||||
|
|
||||||
const DateTime = React.createClass({
|
const DateTime = React.createClass({
|
||||||
_DATE_TIME_SEPARATOR: ' ',
|
DATE_TIME_SEPARATOR: ' ',
|
||||||
getInitialState: function () {
|
getInitialState: function () {
|
||||||
return this._buildStateFromProps(this.props);
|
return this.buildStateFromProps(this.props);
|
||||||
},
|
},
|
||||||
componentWillReceiveProps: function (nextProps) {
|
componentWillReceiveProps: function (nextProps) {
|
||||||
this.setState(this._buildStateFromProps(nextProps));
|
this.setState(this.buildStateFromProps(nextProps));
|
||||||
},
|
},
|
||||||
_buildStateFromProps: function (props) {
|
buildStateFromProps: function (props) {
|
||||||
const value = props.value || defaultDateTime;
|
const value = props.value || defaultDateTime;
|
||||||
const [date, time] = value.split(this._DATE_TIME_SEPARATOR);
|
const [date, time] = value.split(this.DATE_TIME_SEPARATOR);
|
||||||
return {
|
return {
|
||||||
date: date,
|
date: date,
|
||||||
time: time,
|
time: time,
|
||||||
@ -220,7 +217,7 @@ define(
|
|||||||
},
|
},
|
||||||
propagateChange: function () {
|
propagateChange: function () {
|
||||||
if (this.props.onChange) {
|
if (this.props.onChange) {
|
||||||
return this.props.onChange({
|
this.props.onChange({
|
||||||
target: {
|
target: {
|
||||||
name: this.props.name || '',
|
name: this.props.name || '',
|
||||||
value: this.getDateTime(),
|
value: this.getDateTime(),
|
||||||
@ -229,7 +226,7 @@ define(
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
getDateTime: function () {
|
getDateTime: function () {
|
||||||
return [this.state.date, this.state.time].join(this._DATE_TIME_SEPARATOR);
|
return [this.state.date, this.state.time].join(this.DATE_TIME_SEPARATOR);
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
return (
|
return (
|
||||||
@ -254,7 +251,7 @@ define(
|
|||||||
});
|
});
|
||||||
|
|
||||||
const StandardScheduling = React.createClass({
|
const StandardScheduling = React.createClass({
|
||||||
_getCurrentValue: function () {
|
getCurrentValue: function () {
|
||||||
return _.defaults(
|
return _.defaults(
|
||||||
this.props.item[this.props.field.name] || {},
|
this.props.item[this.props.field.name] || {},
|
||||||
{
|
{
|
||||||
@ -264,7 +261,7 @@ define(
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
handleValueChange: function (event) {
|
handleValueChange: function (event) {
|
||||||
const oldValue = this._getCurrentValue();
|
const oldValue = this.getCurrentValue();
|
||||||
const newValue = {};
|
const newValue = {};
|
||||||
newValue[event.target.name] = event.target.value;
|
newValue[event.target.name] = event.target.value;
|
||||||
|
|
||||||
@ -281,7 +278,7 @@ define(
|
|||||||
return this.handleValueChange(changeEvent);
|
return this.handleValueChange(changeEvent);
|
||||||
},
|
},
|
||||||
isScheduled: function () {
|
isScheduled: function () {
|
||||||
return this._getCurrentValue().isScheduled === '1';
|
return this.getCurrentValue().isScheduled === '1';
|
||||||
},
|
},
|
||||||
getDateValidation: function () {
|
getDateValidation: function () {
|
||||||
return {
|
return {
|
||||||
@ -298,7 +295,7 @@ define(
|
|||||||
<span id="mailpoet_scheduling">
|
<span id="mailpoet_scheduling">
|
||||||
<DateTime
|
<DateTime
|
||||||
name="scheduledAt"
|
name="scheduledAt"
|
||||||
value={this._getCurrentValue().scheduledAt}
|
value={this.getCurrentValue().scheduledAt}
|
||||||
onChange={this.handleValueChange}
|
onChange={this.handleValueChange}
|
||||||
disabled={this.props.field.disabled}
|
disabled={this.props.field.disabled}
|
||||||
dateValidation={this.getDateValidation()} />
|
dateValidation={this.getDateValidation()} />
|
||||||
@ -348,18 +345,14 @@ define(
|
|||||||
endpoint: 'segments',
|
endpoint: 'segments',
|
||||||
multiple: true,
|
multiple: true,
|
||||||
filter: function (segment) {
|
filter: function (segment) {
|
||||||
return !!(!segment.deleted_at);
|
return !segment.deleted_at;
|
||||||
},
|
},
|
||||||
getLabel: function (segment) {
|
getLabel: function (segment) {
|
||||||
return segment.name + ' (' + parseInt(segment.subscribers, 10).toLocaleString() + ')';
|
return `${segment.name} (${parseInt(segment.subscribers, 10).toLocaleString()})`;
|
||||||
},
|
},
|
||||||
transformChangedValue: function (segment_ids) {
|
transformChangedValue: function (segmentIds) {
|
||||||
const all_segments = this.state.items;
|
const allSegments = this.state.items;
|
||||||
return _.map(segment_ids, (id) => {
|
return _.map(segmentIds, id => _.find(allSegments, segment => segment.id === id));
|
||||||
return _.find(all_segments, (segment) => {
|
|
||||||
return segment.id === id;
|
|
||||||
});
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
validation: {
|
validation: {
|
||||||
'data-parsley-required': true,
|
'data-parsley-required': true,
|
||||||
@ -437,7 +430,7 @@ define(
|
|||||||
|
|
||||||
if (newsletterOptions.status === 'sent'
|
if (newsletterOptions.status === 'sent'
|
||||||
|| newsletterOptions.status === 'sending') {
|
|| newsletterOptions.status === 'sending') {
|
||||||
options['disabled'] = 'disabled';
|
options.disabled = 'disabled';
|
||||||
}
|
}
|
||||||
|
|
||||||
return options;
|
return options;
|
||||||
|
@ -9,8 +9,6 @@ define(
|
|||||||
Hooks,
|
Hooks,
|
||||||
Scheduling
|
Scheduling
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
|
|
||||||
let fields = [
|
let fields = [
|
||||||
{
|
{
|
||||||
name: 'subject',
|
name: 'subject',
|
||||||
|
@ -1,295 +1,385 @@
|
|||||||
define(
|
import React from 'react';
|
||||||
[
|
import _ from 'underscore';
|
||||||
'react',
|
import MailPoet from 'mailpoet';
|
||||||
'underscore',
|
import { confirmAlert } from 'react-confirm-alert';
|
||||||
'mailpoet',
|
import classNames from 'classnames';
|
||||||
'react-router',
|
import Breadcrumb from 'newsletters/breadcrumb.jsx';
|
||||||
'classnames',
|
import HelpTooltip from 'help-tooltip.jsx';
|
||||||
'newsletters/breadcrumb.jsx',
|
|
||||||
'help-tooltip.jsx',
|
|
||||||
],
|
|
||||||
(
|
|
||||||
React,
|
|
||||||
_,
|
|
||||||
MailPoet,
|
|
||||||
Router,
|
|
||||||
classNames,
|
|
||||||
Breadcrumb,
|
|
||||||
HelpTooltip
|
|
||||||
) => {
|
|
||||||
|
|
||||||
const ImportTemplate = React.createClass({
|
const ImportTemplate = React.createClass({
|
||||||
saveTemplate: function (saveTemplate) {
|
saveTemplate: function (saveTemplate) {
|
||||||
const template = saveTemplate;
|
const template = saveTemplate;
|
||||||
|
|
||||||
// Stringify to enable transmission of primitive non-string value types
|
// Stringify to enable transmission of primitive non-string value types
|
||||||
if (!_.isUndefined(template.body)) {
|
if (!_.isUndefined(template.body)) {
|
||||||
template.body = JSON.stringify(template.body);
|
template.body = JSON.stringify(template.body);
|
||||||
}
|
}
|
||||||
|
|
||||||
MailPoet.Modal.loading(true);
|
if (undefined === template.categories) {
|
||||||
|
template.categories = '["saved"]';
|
||||||
|
}
|
||||||
|
MailPoet.Modal.loading(true);
|
||||||
|
|
||||||
MailPoet.Ajax.post({
|
MailPoet.Ajax.post({
|
||||||
api_version: window.mailpoet_api_version,
|
api_version: window.mailpoet_api_version,
|
||||||
endpoint: 'newsletterTemplates',
|
endpoint: 'newsletterTemplates',
|
||||||
action: 'save',
|
action: 'save',
|
||||||
data: template,
|
data: template,
|
||||||
}).always(() => {
|
}).always(() => {
|
||||||
MailPoet.Modal.loading(false);
|
MailPoet.Modal.loading(false);
|
||||||
}).done((response) => {
|
}).done((response) => {
|
||||||
this.props.onImport(response.data);
|
this.props.onImport(response.data);
|
||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
},
|
|
||||||
handleSubmit: function (e) {
|
|
||||||
e.preventDefault();
|
|
||||||
|
|
||||||
if (_.size(this.refs.templateFile.files) <= 0) return false;
|
|
||||||
|
|
||||||
|
|
||||||
const file = _.first(this.refs.templateFile.files);
|
|
||||||
const reader = new FileReader();
|
|
||||||
const saveTemplate = this.saveTemplate;
|
|
||||||
|
|
||||||
reader.onload = (e) => {
|
|
||||||
try {
|
|
||||||
saveTemplate(JSON.parse(e.target.result));
|
|
||||||
MailPoet.trackEvent('Emails > Template imported', {
|
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
|
||||||
});
|
|
||||||
} catch (err) {
|
|
||||||
MailPoet.Notice.error(MailPoet.I18n.t('templateFileMalformedError'));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
reader.readAsText(file);
|
|
||||||
},
|
|
||||||
render: function () {
|
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
<h2>{MailPoet.I18n.t('importTemplateTitle')} <HelpTooltip
|
|
||||||
tooltip={MailPoet.I18n.t('helpTooltipTemplateUpload')}
|
|
||||||
place="right"
|
|
||||||
className="tooltip-help-import-template"
|
|
||||||
/></h2>
|
|
||||||
<form onSubmit={this.handleSubmit}>
|
|
||||||
<input type="file" placeholder={MailPoet.I18n.t('selectJsonFileToUpload')} ref="templateFile" />
|
|
||||||
<p className="submit">
|
|
||||||
<input
|
|
||||||
className="button button-primary"
|
|
||||||
type="submit"
|
|
||||||
value={MailPoet.I18n.t('upload')} />
|
|
||||||
</p>
|
|
||||||
</form>
|
|
||||||
</div>
|
|
||||||
);
|
);
|
||||||
},
|
}
|
||||||
});
|
});
|
||||||
|
},
|
||||||
|
handleSubmit: function (e) {
|
||||||
|
e.preventDefault();
|
||||||
|
|
||||||
const NewsletterTemplates = React.createClass({
|
if (_.size(this.refs.templateFile.files) <= 0) return false;
|
||||||
getInitialState: function () {
|
|
||||||
return {
|
|
||||||
loading: false,
|
|
||||||
templates: [],
|
|
||||||
};
|
|
||||||
},
|
|
||||||
componentDidMount: function () {
|
|
||||||
this.getTemplates();
|
|
||||||
},
|
|
||||||
getTemplates: function () {
|
|
||||||
this.setState({ loading: true });
|
|
||||||
|
|
||||||
MailPoet.Modal.loading(true);
|
|
||||||
|
|
||||||
MailPoet.Ajax.post({
|
const file = _.first(this.refs.templateFile.files);
|
||||||
api_version: window.mailpoet_api_version,
|
const reader = new FileReader();
|
||||||
endpoint: 'newsletterTemplates',
|
const saveTemplate = this.saveTemplate;
|
||||||
action: 'getAll',
|
|
||||||
}).always(() => {
|
|
||||||
MailPoet.Modal.loading(false);
|
|
||||||
}).done((response) => {
|
|
||||||
if (this.isMounted()) {
|
|
||||||
if (response.data.length === 0) {
|
|
||||||
response.data = [
|
|
||||||
{
|
|
||||||
name:
|
|
||||||
MailPoet.I18n.t('mailpoetGuideTemplateTitle'),
|
|
||||||
description:
|
|
||||||
MailPoet.I18n.t('mailpoetGuideTemplateDescription'),
|
|
||||||
readonly: '1',
|
|
||||||
},
|
|
||||||
];
|
|
||||||
}
|
|
||||||
this.setState({
|
|
||||||
templates: response.data,
|
|
||||||
loading: false,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}).fail((response) => {
|
|
||||||
if (response.errors.length > 0) {
|
|
||||||
MailPoet.Notice.error(
|
|
||||||
response.errors.map((error) => { return error.message; }),
|
|
||||||
{ scroll: true }
|
|
||||||
);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
},
|
|
||||||
handleSelectTemplate: function (template) {
|
|
||||||
let body = template.body;
|
|
||||||
|
|
||||||
// Stringify to enable transmission of primitive non-string value types
|
reader.onload = (evt) => {
|
||||||
if (!_.isUndefined(body)) {
|
try {
|
||||||
body = JSON.stringify(body);
|
saveTemplate(JSON.parse(evt.target.result));
|
||||||
}
|
MailPoet.trackEvent('Emails > Template imported', {
|
||||||
|
|
||||||
MailPoet.trackEvent('Emails > Template selected', {
|
|
||||||
'MailPoet Free version': window.mailpoet_version,
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
'Email name': template.name,
|
|
||||||
});
|
});
|
||||||
|
} catch (err) {
|
||||||
|
MailPoet.Notice.error(MailPoet.I18n.t('templateFileMalformedError'));
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
MailPoet.Ajax.post({
|
reader.readAsText(file);
|
||||||
api_version: window.mailpoet_api_version,
|
return true;
|
||||||
endpoint: 'newsletters',
|
},
|
||||||
action: 'save',
|
render: function () {
|
||||||
data: {
|
return (
|
||||||
id: this.props.params.id,
|
<div>
|
||||||
body: body,
|
<h2>{MailPoet.I18n.t('importTemplateTitle')} <HelpTooltip
|
||||||
},
|
tooltip={MailPoet.I18n.t('helpTooltipTemplateUpload')}
|
||||||
}).done((response) => {
|
place="right"
|
||||||
// TODO: Move this URL elsewhere
|
className="tooltip-help-import-template"
|
||||||
window.location = 'admin.php?page=mailpoet-newsletter-editor&id=' + response.data.id;
|
/></h2>
|
||||||
}).fail((response) => {
|
<form onSubmit={this.handleSubmit}>
|
||||||
if (response.errors.length > 0) {
|
<input type="file" placeholder={MailPoet.I18n.t('selectJsonFileToUpload')} ref="templateFile" />
|
||||||
MailPoet.Notice.error(
|
<p className="submit">
|
||||||
response.errors.map((error) => { return error.message; }),
|
<input
|
||||||
{ scroll: true }
|
className="button button-primary"
|
||||||
);
|
type="submit"
|
||||||
}
|
value={MailPoet.I18n.t('upload')} />
|
||||||
});
|
</p>
|
||||||
},
|
</form>
|
||||||
handleDeleteTemplate: function (template) {
|
</div>
|
||||||
this.setState({ loading: true });
|
);
|
||||||
if (
|
},
|
||||||
window.confirm(
|
});
|
||||||
(
|
|
||||||
MailPoet.I18n.t('confirmTemplateDeletion')
|
const templatesCategories = [
|
||||||
).replace('%$1s', template.name)
|
{
|
||||||
)
|
name: 'standard',
|
||||||
) {
|
label: MailPoet.I18n.t('tabStandardTitle'),
|
||||||
MailPoet.Ajax.post({
|
},
|
||||||
api_version: window.mailpoet_api_version,
|
{
|
||||||
endpoint: 'newsletterTemplates',
|
name: 'welcome',
|
||||||
action: 'delete',
|
label: MailPoet.I18n.t('tabWelcomeTitle'),
|
||||||
data: {
|
},
|
||||||
id: template.id,
|
{
|
||||||
|
name: 'notification',
|
||||||
|
label: MailPoet.I18n.t('tabNotificationTitle'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'sample',
|
||||||
|
label: MailPoet.I18n.t('sample'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'blank',
|
||||||
|
label: MailPoet.I18n.t('blank'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'recent',
|
||||||
|
label: MailPoet.I18n.t('recentlySent'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'saved',
|
||||||
|
label: MailPoet.I18n.t('savedTemplates'),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
const CategoryTab = ({ name, label, selected, select }) => (
|
||||||
|
<li><a
|
||||||
|
href="javascript:"
|
||||||
|
className={selected === name ? 'current' : ''}
|
||||||
|
onClick={() => select(name)}
|
||||||
|
> {label}
|
||||||
|
</a></li>
|
||||||
|
);
|
||||||
|
|
||||||
|
const NewsletterTemplates = React.createClass({
|
||||||
|
getInitialState: function () {
|
||||||
|
return {
|
||||||
|
loading: false,
|
||||||
|
templates: {},
|
||||||
|
selectedCategory: '',
|
||||||
|
};
|
||||||
|
},
|
||||||
|
componentDidMount: function () {
|
||||||
|
this.getTemplates();
|
||||||
|
},
|
||||||
|
getTemplates: function () {
|
||||||
|
this.setState({ loading: true });
|
||||||
|
|
||||||
|
MailPoet.Modal.loading(true);
|
||||||
|
|
||||||
|
MailPoet.Ajax.post({
|
||||||
|
api_version: window.mailpoet_api_version,
|
||||||
|
endpoint: 'newsletterTemplates',
|
||||||
|
action: 'getAll',
|
||||||
|
}).done((response) => {
|
||||||
|
if (this.isMounted()) {
|
||||||
|
if (response.data.length === 0) {
|
||||||
|
response.data = [
|
||||||
|
{
|
||||||
|
name:
|
||||||
|
MailPoet.I18n.t('mailpoetGuideTemplateTitle'),
|
||||||
|
description:
|
||||||
|
MailPoet.I18n.t('mailpoetGuideTemplateDescription'),
|
||||||
|
categories: '["welcome", "notification", "standard"]',
|
||||||
|
readonly: '1',
|
||||||
},
|
},
|
||||||
}).done(() => {
|
];
|
||||||
this.getTemplates();
|
|
||||||
}).fail((response) => {
|
|
||||||
if (response.errors.length > 0) {
|
|
||||||
MailPoet.Notice.error(
|
|
||||||
response.errors.map((error) => { return error.message; }),
|
|
||||||
{ scroll: true }
|
|
||||||
);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
this.setState({ loading: false });
|
|
||||||
}
|
}
|
||||||
},
|
|
||||||
handleShowTemplate: function (template) {
|
|
||||||
MailPoet.Modal.popup({
|
|
||||||
title: template.name,
|
|
||||||
template: '<div class="mailpoet_boxes_preview" style="background-color: {{ body.globalStyles.body.backgroundColor }}"><img src="{{ thumbnail }}" /></div>',
|
|
||||||
data: template,
|
|
||||||
});
|
|
||||||
},
|
|
||||||
handleTemplateImport: function () {
|
|
||||||
this.getTemplates();
|
|
||||||
},
|
|
||||||
render: function () {
|
|
||||||
const templates = this.state.templates.map((template, index) => {
|
|
||||||
const deleteLink = (
|
|
||||||
<div className="mailpoet_delete">
|
|
||||||
<a
|
|
||||||
href="javascript:;"
|
|
||||||
onClick={this.handleDeleteTemplate.bind(null, template)}
|
|
||||||
>
|
|
||||||
{MailPoet.I18n.t('delete')}
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
let thumbnail = '';
|
|
||||||
|
|
||||||
if (typeof template.thumbnail === 'string'
|
let templates = templatesCategories.reduce((result, { name }) => {
|
||||||
&& template.thumbnail.length > 0) {
|
const obj = result;
|
||||||
thumbnail = (
|
obj[name] = [];
|
||||||
<a href="javascript:;" onClick={this.handleShowTemplate.bind(null, template)}>
|
return obj;
|
||||||
<img src={template.thumbnail} />
|
}, {});
|
||||||
<div className="mailpoet_overlay"></div>
|
|
||||||
</a>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
templates = response.data.reduce((result, item) => {
|
||||||
<li key={'template-' + index}>
|
JSON.parse(item.categories).forEach((category) => {
|
||||||
<div className="mailpoet_thumbnail">
|
result[category].push(item);
|
||||||
{ thumbnail }
|
});
|
||||||
</div>
|
return result;
|
||||||
|
}, templates);
|
||||||
|
|
||||||
<div className="mailpoet_description">
|
this.selectInitialCategory(templates);
|
||||||
<h3>{ template.name }</h3>
|
}
|
||||||
<p>{ template.description }</p>
|
}).fail((response) => {
|
||||||
</div>
|
if (response.errors.length > 0) {
|
||||||
|
MailPoet.Notice.error(
|
||||||
<div className="mailpoet_actions">
|
response.errors.map(error => error.message),
|
||||||
<a
|
{ scroll: true }
|
||||||
className="button button-secondary"
|
|
||||||
onClick={this.handleShowTemplate.bind(null, template)}
|
|
||||||
>
|
|
||||||
{MailPoet.I18n.t('preview')}
|
|
||||||
</a>
|
|
||||||
|
|
||||||
<a
|
|
||||||
className="button button-primary"
|
|
||||||
onClick={this.handleSelectTemplate.bind(null, template)}
|
|
||||||
>
|
|
||||||
{MailPoet.I18n.t('select')}
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
{ (template.readonly === '1') ? false : deleteLink }
|
|
||||||
</li>
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
const boxClasses = classNames(
|
|
||||||
'mailpoet_boxes',
|
|
||||||
'clearfix',
|
|
||||||
{ mailpoet_boxes_loading: this.state.loading }
|
|
||||||
);
|
|
||||||
|
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
<h1>{MailPoet.I18n.t('selectTemplateTitle')}</h1>
|
|
||||||
|
|
||||||
<Breadcrumb step="template" />
|
|
||||||
|
|
||||||
<ul className={boxClasses}>
|
|
||||||
{ templates }
|
|
||||||
</ul>
|
|
||||||
|
|
||||||
<ImportTemplate onImport={this.handleTemplateImport} />
|
|
||||||
</div>
|
|
||||||
);
|
);
|
||||||
|
}
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
|
});
|
||||||
|
},
|
||||||
|
selectInitialCategory: function (templates) {
|
||||||
|
MailPoet.Ajax.post({
|
||||||
|
api_version: window.mailpoet_api_version,
|
||||||
|
endpoint: 'newsletters',
|
||||||
|
action: 'get',
|
||||||
|
data: {
|
||||||
|
id: this.props.params.id,
|
||||||
},
|
},
|
||||||
|
}).always(() => {
|
||||||
|
MailPoet.Modal.loading(false);
|
||||||
|
}).done((response) => {
|
||||||
|
this.setState({
|
||||||
|
templates: templates,
|
||||||
|
selectedCategory: response.data.type,
|
||||||
|
loading: false,
|
||||||
|
});
|
||||||
|
}).fail((response) => {
|
||||||
|
if (response.errors.length > 0) {
|
||||||
|
MailPoet.Notice.error(
|
||||||
|
response.errors.map(error => error.message),
|
||||||
|
{ scroll: true }
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
handleSelectTemplate: function (template) {
|
||||||
|
let body = template.body;
|
||||||
|
|
||||||
|
// Stringify to enable transmission of primitive non-string value types
|
||||||
|
if (!_.isUndefined(body)) {
|
||||||
|
body = JSON.stringify(body);
|
||||||
|
}
|
||||||
|
|
||||||
|
MailPoet.trackEvent('Emails > Template selected', {
|
||||||
|
'MailPoet Free version': window.mailpoet_version,
|
||||||
|
'Email name': template.name,
|
||||||
});
|
});
|
||||||
|
|
||||||
return NewsletterTemplates;
|
MailPoet.Ajax.post({
|
||||||
}
|
api_version: window.mailpoet_api_version,
|
||||||
);
|
endpoint: 'newsletters',
|
||||||
|
action: 'save',
|
||||||
|
data: {
|
||||||
|
id: this.props.params.id,
|
||||||
|
body: body,
|
||||||
|
},
|
||||||
|
}).done((response) => {
|
||||||
|
// TODO: Move this URL elsewhere
|
||||||
|
window.location = `admin.php?page=mailpoet-newsletter-editor&id=${response.data.id}`;
|
||||||
|
}).fail((response) => {
|
||||||
|
if (response.errors.length > 0) {
|
||||||
|
MailPoet.Notice.error(
|
||||||
|
response.errors.map(error => error.message),
|
||||||
|
{ scroll: true }
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
},
|
||||||
|
handleDeleteTemplate: function (template) {
|
||||||
|
this.setState({ loading: true });
|
||||||
|
const onConfirm = () => {
|
||||||
|
MailPoet.Ajax.post({
|
||||||
|
api_version: window.mailpoet_api_version,
|
||||||
|
endpoint: 'newsletterTemplates',
|
||||||
|
action: 'delete',
|
||||||
|
data: {
|
||||||
|
id: template.id,
|
||||||
|
},
|
||||||
|
}).done(() => {
|
||||||
|
this.getTemplates();
|
||||||
|
}).fail((response) => {
|
||||||
|
if (response.errors.length > 0) {
|
||||||
|
MailPoet.Notice.error(
|
||||||
|
response.errors.map(error => error.message),
|
||||||
|
{ scroll: true }
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
const onCancel = () => {
|
||||||
|
this.setState({ loading: false });
|
||||||
|
};
|
||||||
|
confirmAlert({
|
||||||
|
title: MailPoet.I18n.t('confirmTitle'),
|
||||||
|
message: MailPoet.I18n.t('confirmTemplateDeletion').replace('%$1s', template.name),
|
||||||
|
confirmLabel: MailPoet.I18n.t('confirmLabel'),
|
||||||
|
cancelLabel: MailPoet.I18n.t('cancelLabel'),
|
||||||
|
onConfirm: onConfirm,
|
||||||
|
onCancel: onCancel,
|
||||||
|
});
|
||||||
|
},
|
||||||
|
handleShowTemplate: function (template) {
|
||||||
|
MailPoet.Modal.popup({
|
||||||
|
title: template.name,
|
||||||
|
template: '<div class="mailpoet_boxes_preview" style="background-color: {{ body.globalStyles.body.backgroundColor }}"><img src="{{ thumbnail }}" /></div>',
|
||||||
|
data: template,
|
||||||
|
});
|
||||||
|
},
|
||||||
|
handleTemplateImport: function () {
|
||||||
|
this.getTemplates();
|
||||||
|
},
|
||||||
|
render: function () {
|
||||||
|
let templates = this.state.templates[this.state.selectedCategory] || [];
|
||||||
|
|
||||||
|
templates = templates.map((template, index) => {
|
||||||
|
const deleteLink = (
|
||||||
|
<div className="mailpoet_delete">
|
||||||
|
<a
|
||||||
|
href="javascript:;"
|
||||||
|
onClick={this.handleDeleteTemplate.bind(null, template)}
|
||||||
|
>
|
||||||
|
{MailPoet.I18n.t('delete')}
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
let thumbnail = '';
|
||||||
|
|
||||||
|
if (typeof template.thumbnail === 'string'
|
||||||
|
&& template.thumbnail.length > 0) {
|
||||||
|
thumbnail = (
|
||||||
|
<a href="javascript:;" onClick={this.handleShowTemplate.bind(null, template)}>
|
||||||
|
<img src={template.thumbnail} />
|
||||||
|
<div className="mailpoet_overlay"></div>
|
||||||
|
</a>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
return (
|
||||||
|
<li key={`template-${index}`}>
|
||||||
|
<div className="mailpoet_thumbnail">
|
||||||
|
{ thumbnail }
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="mailpoet_description">
|
||||||
|
<h3>{ template.name }</h3>
|
||||||
|
<p>{ template.description }</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="mailpoet_actions">
|
||||||
|
<a
|
||||||
|
className="button button-secondary"
|
||||||
|
onClick={this.handleShowTemplate.bind(null, template)}
|
||||||
|
>
|
||||||
|
{MailPoet.I18n.t('preview')}
|
||||||
|
</a>
|
||||||
|
|
||||||
|
<a
|
||||||
|
className="button button-primary"
|
||||||
|
data-automation-id={`select_template_${index}`}
|
||||||
|
onClick={this.handleSelectTemplate.bind(null, template)}
|
||||||
|
>
|
||||||
|
{MailPoet.I18n.t('select')}
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
{ (template.readonly === '1') ? false : deleteLink }
|
||||||
|
</li>
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (templates.length === 0) {
|
||||||
|
templates = <p>{MailPoet.I18n.t('noTemplates')}</p>;
|
||||||
|
}
|
||||||
|
|
||||||
|
const boxClasses = classNames(
|
||||||
|
'mailpoet_boxes',
|
||||||
|
'clearfix',
|
||||||
|
{ mailpoet_boxes_loading: this.state.loading }
|
||||||
|
);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div>
|
||||||
|
<h1>{MailPoet.I18n.t('selectTemplateTitle')}</h1>
|
||||||
|
|
||||||
|
<Breadcrumb step="template" />
|
||||||
|
|
||||||
|
<div className="wp-filter hide-if-no-js">
|
||||||
|
<ul className="filter-links">
|
||||||
|
{templatesCategories.map(({ name, label }) => (
|
||||||
|
<CategoryTab
|
||||||
|
key={name}
|
||||||
|
name={name}
|
||||||
|
label={label}
|
||||||
|
selected={this.state.selectedCategory}
|
||||||
|
select={category => this.setState({ selectedCategory: category })} />
|
||||||
|
))}
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<ul className={boxClasses}>
|
||||||
|
{ templates }
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<ImportTemplate onImport={this.handleTemplateImport} />
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
export default NewsletterTemplates;
|
||||||
|
@ -44,7 +44,7 @@ define(
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -58,7 +58,7 @@ define(
|
|||||||
description: MailPoet.I18n.t('regularNewsletterTypeDescription'),
|
description: MailPoet.I18n.t('regularNewsletterTypeDescription'),
|
||||||
action: function () {
|
action: function () {
|
||||||
return (
|
return (
|
||||||
<a className="button button-primary" onClick={this.createNewsletter.bind(null, 'standard')}>
|
<a className="button button-primary" data-automation-id="create_standard" onClick={this.createNewsletter.bind(null, 'standard')}>
|
||||||
{MailPoet.I18n.t('create')}
|
{MailPoet.I18n.t('create')}
|
||||||
</a>
|
</a>
|
||||||
);
|
);
|
||||||
@ -68,7 +68,7 @@ define(
|
|||||||
id: 'welcome',
|
id: 'welcome',
|
||||||
title: MailPoet.I18n.t('welcomeNewsletterTypeTitle'),
|
title: MailPoet.I18n.t('welcomeNewsletterTypeTitle'),
|
||||||
description: MailPoet.I18n.t('welcomeNewsletterTypeDescription'),
|
description: MailPoet.I18n.t('welcomeNewsletterTypeDescription'),
|
||||||
action: function () {
|
action: (function () {
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<a href="?page=mailpoet-premium" target="_blank">
|
<a href="?page=mailpoet-premium" target="_blank">
|
||||||
@ -76,7 +76,7 @@ define(
|
|||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}(),
|
}()),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: 'notification',
|
id: 'notification',
|
||||||
@ -84,7 +84,7 @@ define(
|
|||||||
description: MailPoet.I18n.t('postNotificationNewsletterTypeDescription'),
|
description: MailPoet.I18n.t('postNotificationNewsletterTypeDescription'),
|
||||||
action: function () {
|
action: function () {
|
||||||
return (
|
return (
|
||||||
<a className="button button-primary" onClick={this.setupNewsletter.bind(null, 'notification')}>
|
<a className="button button-primary" data-automation-id="create_notification" onClick={this.setupNewsletter.bind(null, 'notification')}>
|
||||||
{MailPoet.I18n.t('setUp')}
|
{MailPoet.I18n.t('setUp')}
|
||||||
</a>
|
</a>
|
||||||
);
|
);
|
||||||
@ -101,24 +101,23 @@ define(
|
|||||||
<Breadcrumb step="type" />
|
<Breadcrumb step="type" />
|
||||||
|
|
||||||
<ul className="mailpoet_boxes clearfix">
|
<ul className="mailpoet_boxes clearfix">
|
||||||
{types.map((type, index) => {
|
{types.map((type, index) => (
|
||||||
return (
|
<li key={index} data-type={type.id}>
|
||||||
<li key={index} data-type={type.id}>
|
<div>
|
||||||
<div>
|
<div className="mailpoet_thumbnail">
|
||||||
<div className="mailpoet_thumbnail"></div>
|
{type.thumbnailImage ? <img src={type.thumbnailImage} /> : null}
|
||||||
|
|
||||||
<div className="mailpoet_description">
|
|
||||||
<h3>{type.title}</h3>
|
|
||||||
<p>{type.description}</p>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div className="mailpoet_actions">
|
|
||||||
{type.action}
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</li>
|
<div className="mailpoet_description">
|
||||||
);
|
<h3>{type.title}</h3>
|
||||||
}, this)}
|
<p>{type.description}</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className="mailpoet_actions">
|
||||||
|
{type.action}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</li>
|
||||||
|
), this)}
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -15,7 +15,6 @@ define(
|
|||||||
Scheduling,
|
Scheduling,
|
||||||
Breadcrumb
|
Breadcrumb
|
||||||
) => {
|
) => {
|
||||||
|
|
||||||
const field = {
|
const field = {
|
||||||
name: 'options',
|
name: 'options',
|
||||||
type: 'reactComponent',
|
type: 'reactComponent',
|
||||||
@ -56,7 +55,7 @@ define(
|
|||||||
}).fail((response) => {
|
}).fail((response) => {
|
||||||
if (response.errors.length > 0) {
|
if (response.errors.length > 0) {
|
||||||
MailPoet.Notice.error(
|
MailPoet.Notice.error(
|
||||||
response.errors.map((error) => { return error.message; }),
|
response.errors.map(error => error.message),
|
||||||
{ scroll: true }
|
{ scroll: true }
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -35,11 +35,11 @@ const nthWeekDayField = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const NotificationScheduling = React.createClass({
|
const NotificationScheduling = React.createClass({
|
||||||
_getCurrentValue: function () {
|
getCurrentValue: function () {
|
||||||
return (this.props.item[this.props.field.name] || {});
|
return (this.props.item[this.props.field.name] || {});
|
||||||
},
|
},
|
||||||
handleValueChange: function (name, value) {
|
handleValueChange: function (name, value) {
|
||||||
const oldValue = this._getCurrentValue();
|
const oldValue = this.getCurrentValue();
|
||||||
const newValue = {};
|
const newValue = {};
|
||||||
|
|
||||||
newValue[name] = value;
|
newValue[name] = value;
|
||||||
@ -82,7 +82,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
);
|
);
|
||||||
},
|
},
|
||||||
render: function () {
|
render: function () {
|
||||||
const value = this._getCurrentValue();
|
const value = this.getCurrentValue();
|
||||||
let timeOfDaySelection;
|
let timeOfDaySelection;
|
||||||
let weekDaySelection;
|
let weekDaySelection;
|
||||||
let monthDaySelection;
|
let monthDaySelection;
|
||||||
@ -92,7 +92,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
timeOfDaySelection = (
|
timeOfDaySelection = (
|
||||||
<Select
|
<Select
|
||||||
field={timeOfDayField}
|
field={timeOfDayField}
|
||||||
item={this._getCurrentValue()}
|
item={this.getCurrentValue()}
|
||||||
onValueChange={this.handleTimeOfDayChange} />
|
onValueChange={this.handleTimeOfDayChange} />
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -101,7 +101,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
weekDaySelection = (
|
weekDaySelection = (
|
||||||
<Select
|
<Select
|
||||||
field={weekDayField}
|
field={weekDayField}
|
||||||
item={this._getCurrentValue()}
|
item={this.getCurrentValue()}
|
||||||
onValueChange={this.handleWeekDayChange} />
|
onValueChange={this.handleWeekDayChange} />
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -110,7 +110,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
monthDaySelection = (
|
monthDaySelection = (
|
||||||
<Select
|
<Select
|
||||||
field={monthDayField}
|
field={monthDayField}
|
||||||
item={this._getCurrentValue()}
|
item={this.getCurrentValue()}
|
||||||
onValueChange={this.handleMonthDayChange} />
|
onValueChange={this.handleMonthDayChange} />
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -119,7 +119,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
nthWeekDaySelection = (
|
nthWeekDaySelection = (
|
||||||
<Select
|
<Select
|
||||||
field={nthWeekDayField}
|
field={nthWeekDayField}
|
||||||
item={this._getCurrentValue()}
|
item={this.getCurrentValue()}
|
||||||
onValueChange={this.handleNthWeekDayChange} />
|
onValueChange={this.handleNthWeekDayChange} />
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -128,7 +128,7 @@ const NotificationScheduling = React.createClass({
|
|||||||
<div>
|
<div>
|
||||||
<Select
|
<Select
|
||||||
field={intervalField}
|
field={intervalField}
|
||||||
item={this._getCurrentValue()}
|
item={this.getCurrentValue()}
|
||||||
onValueChange={this.handleIntervalChange} />
|
onValueChange={this.handleIntervalChange} />
|
||||||
|
|
||||||
{nthWeekDaySelection}
|
{nthWeekDaySelection}
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user