Merge remote branch 'upstream/master'
BIN
adult_smile.tgz
|
@ -1,34 +0,0 @@
|
||||||
<?php
|
|
||||||
/*
|
|
||||||
* Name: Adult Smilies
|
|
||||||
* Description: Smily icons that could or should not be included in core
|
|
||||||
* Version: 1.0
|
|
||||||
* Author: Mike Macgirvin <http://macgirvin.com/profile/mike>
|
|
||||||
*
|
|
||||||
* This is a template for how to extend the "smily" code.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
function adult_smile_install() {
|
|
||||||
register_hook('smilie', 'addon/adult_smile/adult_smile.php', 'adult_smile_smilies');
|
|
||||||
}
|
|
||||||
|
|
||||||
function adult_smile_uninstall() {
|
|
||||||
unregister_hook('smilie', 'addon/adult_smile/adult_smile.php', 'adult_smile_smilies');
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
function adult_smile_smilies(&$a,&$b) {
|
|
||||||
|
|
||||||
$b['texts'][] = '(o)(o)';
|
|
||||||
$b['icons'][] = '<img src="' . $a->get_baseurl() . '/addon/adult_smile/icons/tits.gif' . '" alt="' . '(o)(o)' . '" />';
|
|
||||||
|
|
||||||
$b['texts'][] = '(.)(.)';
|
|
||||||
$b['icons'][] = '<img src="' . $a->get_baseurl() . '/addon/adult_smile/icons/tits.gif' . '" alt="' . '(.)(.)' . '" />';
|
|
||||||
|
|
||||||
$b['texts'][] = ':bong';
|
|
||||||
$b['icons'][] = '<img src="' . $a->get_baseurl() . '/addon/adult_smile/icons/bong.gif' . '" alt="' . ':bong' . '" />';
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
BIN
blockem.tgz
|
@ -109,7 +109,7 @@ function blockem_prepare_body(&$a,&$b) {
|
||||||
|
|
||||||
function blockem_display_item(&$a,&$b) {
|
function blockem_display_item(&$a,&$b) {
|
||||||
if(strstr($b['output']['body'],'id="blockem-wrap-'))
|
if(strstr($b['output']['body'],'id="blockem-wrap-'))
|
||||||
$b['output']['thumb'] = $a->get_baseurl() . "/images/default-profile-sm.jpg";
|
$b['output']['thumb'] = $a->get_baseurl() . "/images/person-80.jpg";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -35,7 +35,7 @@ function communityhome_home(&$a, &$o){
|
||||||
$aside['$login_form'] = login(($a->config['register_policy'] == REGISTER_CLOSED) ? false : true);
|
$aside['$login_form'] = login(($a->config['register_policy'] == REGISTER_CLOSED) ? false : true);
|
||||||
|
|
||||||
// last 12 users
|
// last 12 users
|
||||||
$aside['$lastusers_title'] = t('Last users');
|
$aside['$lastusers_title'] = t('Latest users');
|
||||||
$aside['$lastusers_items'] = array();
|
$aside['$lastusers_items'] = array();
|
||||||
$sql_extra = "";
|
$sql_extra = "";
|
||||||
$publish = (get_config('system','publish_all') ? '' : " AND `publish` = 1 " );
|
$publish = (get_config('system','publish_all') ? '' : " AND `publish` = 1 " );
|
||||||
|
@ -95,7 +95,7 @@ function communityhome_home(&$a, &$o){
|
||||||
}
|
}
|
||||||
|
|
||||||
// last 12 photos
|
// last 12 photos
|
||||||
$aside['$photos_title'] = t('Last photos');
|
$aside['$photos_title'] = t('Latest photos');
|
||||||
$aside['$photos_items'] = array();
|
$aside['$photos_items'] = array();
|
||||||
$r = q("SELECT `photo`.`id`, `photo`.`resource-id`, `photo`.`scale`, `photo`.`desc`, `user`.`nickname`, `user`.`username` FROM
|
$r = q("SELECT `photo`.`id`, `photo`.`resource-id`, `photo`.`scale`, `photo`.`desc`, `user`.`nickname`, `user`.`username` FROM
|
||||||
(SELECT `resource-id`, MAX(`scale`) as maxscale FROM `photo`
|
(SELECT `resource-id`, MAX(`scale`) as maxscale FROM `photo`
|
||||||
|
@ -130,7 +130,7 @@ function communityhome_home(&$a, &$o){
|
||||||
}
|
}
|
||||||
|
|
||||||
// last 10 liked items
|
// last 10 liked items
|
||||||
$aside['$like_title'] = t('Last likes');
|
$aside['$like_title'] = t('Latest likes');
|
||||||
$aside['$like_items'] = array();
|
$aside['$like_items'] = array();
|
||||||
$r = q("SELECT `T1`.`created`, `T1`.`liker`, `T1`.`liker-link`, `item`.* FROM
|
$r = q("SELECT `T1`.`created`, `T1`.`liker`, `T1`.`liker-link`, `item`.* FROM
|
||||||
(SELECT `parent-uri`, `created`, `author-name` AS `liker`,`author-link` AS `liker-link`
|
(SELECT `parent-uri`, `created`, `author-name` AS `liker`,`author-link` AS `liker-link`
|
||||||
|
|
|
@ -1,7 +1,3 @@
|
||||||
Thomas Willingham
|
This is a variant of the community home. Instead of displaying the community tab in the front page, we still use home.html, but we also add the latest users to the sidebar.
|
||||||
|
|
||||||
This isn't even close to being worth a pull request, but some people might find it useful.
|
Simply replace addon/communityhome/communityhome.php with this version then enable community home in your admin panel as usual.
|
||||||
|
|
||||||
Enable community home in your admin panel, then replace communityhome.php with this one to get a front page like mine (a normal front page, but with latest users shown in the sidebar, which looks bleak when there's nothing in it).
|
|
||||||
|
|
||||||
There are more graceful ways of doing this, I used communityhome as I plan to make use of a limited stream and likes in future.
|
|
BIN
dwpost.tgz
BIN
facebook.tgz
|
@ -1,35 +1,43 @@
|
||||||
Installing the Friendica/Facebook connector
|
Installing the Friendica/Facebook connector
|
||||||
|
|
||||||
1. register an API key for your site from developer.facebook.com
|
1. Visit https://developers.facebook.com/apps to register an app.
|
||||||
a. We'd be very happy if you include "Friendica" in the application name
|
a) Click "Create a new app"
|
||||||
to increase name recognition. The Friendica icons are also present
|
b) We'd be very happy if you include "Friendica" in the application name
|
||||||
in the images directory and may be uploaded as a Facebook app icon.
|
to increase name recognition.
|
||||||
Use images/friendica-16.jpg for the Icon and images/friendica-128.jpg for the Logo.
|
c) Edit your app settings on the setup page. The Friendica icons are present
|
||||||
b. The url should be your site URL with a trailing slash.
|
in the images directory and may be uploaded as a Facebook app icon. Use
|
||||||
You may use http://portal.friendika.com/privacy as the privacy policy
|
images/friendica-16.jpg for the Icon and images/Friendica-128.jpg for the logo.
|
||||||
URL unless your site has different requirements, and
|
d) In the App Display name enter the name of your app (this should default to the
|
||||||
http://portal.friendika.com as the Terms of Service URL unless
|
name you chose in part a).
|
||||||
you have different requirements. (Friendica is a software application
|
e) Enter YourDomain.com in the App Domain field and hit return.
|
||||||
and does not require Terms of Service, though your installation of it might).
|
f) In "Select how your app connects with Facebook select "Website" and enter the
|
||||||
c. Set the following values in your .htconfig.php file
|
full URL to your Friendica install including HTTPS and a trailing slash.
|
||||||
$a->config['facebook']['appid'] = 'xxxxxxxxxxx';
|
|
||||||
$a->config['facebook']['appsecret'] = 'xxxxxxxxxxxxxxx';
|
2. Enable the Facebook plugin by clicking on the icon next to it's name on the plugin
|
||||||
Replace with the settings Facebook gives you.
|
page of your admin panel.
|
||||||
d. Navigate to Set Web->Site URL & Domain -> Website Settings. Set Site URL
|
b) return to the Facebook plugin page in your admin panel, and fill in the App-ID
|
||||||
to yoursubdomain.yourdomain.com. Set Site Domain to your yourdomain.com.
|
and Application Secret settings you got from Facebook.
|
||||||
e. Chose "Website" (the url should be your site URL with a trailing slash) in the
|
c) Click save.
|
||||||
"Select how your app integrates with Facebook" section.
|
d) Finally, return to the Facebook settings page, and activate real-time updates.
|
||||||
2. Enable the facebook plugin by including it in .htconfig.php - e.g.
|
|
||||||
$a->config['system']['addon'] = 'plugin1,plugin2,facebook';
|
i. If you for any reason prefer to use a configuration file instead of the admin panels,
|
||||||
3. Visit the Facebook Settings section of the "Settings->Plugin Settings" page.
|
Activate the plugin by including it in .htconfig.php, e.g.
|
||||||
and click 'Install Facebook Connector'.
|
|
||||||
4. This will ask you to login to Facebook and grant permission to the
|
$a->config['system']['addon'] = 'plugin1,plugin2,facebook';
|
||||||
plugin to do its stuff. Allow it to do so.
|
|
||||||
5. Optional step: If you want to use Facebook Real Time Updates (so new messages
|
and set the following values:
|
||||||
and new contacts are added ~1min after they are postet / added on FB), go to
|
$a->config['facebook']['appid'] = 'xxxxxxxxxxx';
|
||||||
Settings -> plugins -> facebook and press the "Activate Real-Time Updates"-button.
|
$a->config['facebook']['appsecret'] = 'xxxxxxxxxxxxxxx';
|
||||||
6. You're done. To turn it off visit the Plugin Settings page again and
|
|
||||||
'Remove Facebook posting'.
|
Replace with the settings Facebook gives you.
|
||||||
|
|
||||||
|
|
||||||
|
3. To use the Facebook plugin, visit the "connector settings" area of your settings
|
||||||
|
page. Click "Install Facebook Connector".
|
||||||
|
4. This will ask you to login to Facebook and allow the plugin to do it's stuff.
|
||||||
|
Allow it to do so.
|
||||||
|
5. You're done. To turn it off visit the Plugin Settings page again and
|
||||||
|
'Remove Facebook posting'.
|
||||||
|
|
||||||
Vidoes and embeds will not be posted if there is no other content. Links
|
Vidoes and embeds will not be posted if there is no other content. Links
|
||||||
and images will be converted to a format suitable for the Facebook API and
|
and images will be converted to a format suitable for the Facebook API and
|
||||||
|
|
|
@ -25,9 +25,8 @@
|
||||||
* d. Navigate to Set Web->Site URL & Domain -> Website Settings. Set
|
* d. Navigate to Set Web->Site URL & Domain -> Website Settings. Set
|
||||||
* Site URL to yoursubdomain.yourdomain.com. Set Site Domain to your
|
* Site URL to yoursubdomain.yourdomain.com. Set Site Domain to your
|
||||||
* yourdomain.com.
|
* yourdomain.com.
|
||||||
* 2. (This step is now obsolete. Enable the plugin via the Admin panel.)
|
* 2. Visit the Facebook Settings section of the "Settings->Plugin Settings" page.
|
||||||
* Enable the facebook plugin by including it in .htconfig.php - e.g.
|
* and click 'Install Facebook Connector'.
|
||||||
* $a->config['system']['addon'] = 'plugin1,plugin2,facebook';
|
|
||||||
* 3. Visit the Facebook Settings section of the "Settings->Plugin Settings" page.
|
* 3. Visit the Facebook Settings section of the "Settings->Plugin Settings" page.
|
||||||
* and click 'Install Facebook Connector'.
|
* and click 'Install Facebook Connector'.
|
||||||
* 4. This will ask you to login to Facebook and grant permission to the
|
* 4. This will ask you to login to Facebook and grant permission to the
|
||||||
|
@ -47,7 +46,18 @@
|
||||||
* in a future release.
|
* in a future release.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
define('FACEBOOK_MAXPOSTLEN', 420);
|
/** TODO
|
||||||
|
* - Implement a method for the administrator to delete all configuration data the plugin has created,
|
||||||
|
* e.g. the app_access_token
|
||||||
|
*/
|
||||||
|
|
||||||
|
// Size of maximum post length increased
|
||||||
|
// see http://www.facebook.com/schrep/posts/203969696349811
|
||||||
|
// define('FACEBOOK_MAXPOSTLEN', 420);
|
||||||
|
define('FACEBOOK_MAXPOSTLEN', 63206);
|
||||||
|
define('FACEBOOK_SESSION_ERR_NOTIFICATION_INTERVAL', 259200); // 3 days
|
||||||
|
define('FACEBOOK_DEFAULT_POLL_INTERVAL', 60); // given in minutes
|
||||||
|
define('FACEBOOK_MIN_POLL_INTERVAL', 5);
|
||||||
|
|
||||||
|
|
||||||
function facebook_install() {
|
function facebook_install() {
|
||||||
|
@ -56,9 +66,8 @@ function facebook_install() {
|
||||||
register_hook('jot_networks', 'addon/facebook/facebook.php', 'facebook_jot_nets');
|
register_hook('jot_networks', 'addon/facebook/facebook.php', 'facebook_jot_nets');
|
||||||
register_hook('connector_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
register_hook('connector_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
||||||
register_hook('cron', 'addon/facebook/facebook.php', 'facebook_cron');
|
register_hook('cron', 'addon/facebook/facebook.php', 'facebook_cron');
|
||||||
|
register_hook('enotify', 'addon/facebook/facebook.php', 'facebook_enotify');
|
||||||
register_hook('queue_predeliver', 'addon/facebook/facebook.php', 'fb_queue_hook');
|
register_hook('queue_predeliver', 'addon/facebook/facebook.php', 'fb_queue_hook');
|
||||||
|
|
||||||
if (get_config('facebook', 'realtime_active') == 1) facebook_subscription_add_users(); // Restore settings, if the plugin was installed before
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -68,13 +77,12 @@ function facebook_uninstall() {
|
||||||
unregister_hook('jot_networks', 'addon/facebook/facebook.php', 'facebook_jot_nets');
|
unregister_hook('jot_networks', 'addon/facebook/facebook.php', 'facebook_jot_nets');
|
||||||
unregister_hook('connector_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
unregister_hook('connector_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
||||||
unregister_hook('cron', 'addon/facebook/facebook.php', 'facebook_cron');
|
unregister_hook('cron', 'addon/facebook/facebook.php', 'facebook_cron');
|
||||||
|
unregister_hook('enotify', 'addon/facebook/facebook.php', 'facebook_enotify');
|
||||||
unregister_hook('queue_predeliver', 'addon/facebook/facebook.php', 'fb_queue_hook');
|
unregister_hook('queue_predeliver', 'addon/facebook/facebook.php', 'fb_queue_hook');
|
||||||
|
|
||||||
// hook moved
|
// hook moved
|
||||||
unregister_hook('post_local_end', 'addon/facebook/facebook.php', 'facebook_post_hook');
|
unregister_hook('post_local_end', 'addon/facebook/facebook.php', 'facebook_post_hook');
|
||||||
unregister_hook('plugin_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
unregister_hook('plugin_settings', 'addon/facebook/facebook.php', 'facebook_plugin_settings');
|
||||||
|
|
||||||
if (get_config('facebook', 'realtime_active') == 1) facebook_subscription_del_users();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -150,8 +158,12 @@ function facebook_init(&$a) {
|
||||||
$s = fetch_url('https://graph.facebook.com/me/feed?access_token=' . $access_token);
|
$s = fetch_url('https://graph.facebook.com/me/feed?access_token=' . $access_token);
|
||||||
if($s) {
|
if($s) {
|
||||||
$j = json_decode($s);
|
$j = json_decode($s);
|
||||||
logger('facebook_init: wall: ' . print_r($j,true), LOGGER_DATA);
|
if (isset($j->data)) {
|
||||||
fb_consume_stream($uid,$j,($private_wall) ? false : true);
|
logger('facebook_init: wall: ' . print_r($j,true), LOGGER_DATA);
|
||||||
|
fb_consume_stream($uid,$j,($private_wall) ? false : true);
|
||||||
|
} else {
|
||||||
|
logger('facebook_init: wall: got no data from Facebook: ' . print_r($j,true), LOGGER_NORMAL);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -256,6 +268,10 @@ function fb_get_friends_sync_full($uid, $access_token, $person) {
|
||||||
|
|
||||||
$jp->link = 'http://facebook.com/profile.php?id=' . $person->id;
|
$jp->link = 'http://facebook.com/profile.php?id=' . $person->id;
|
||||||
|
|
||||||
|
// If its a page then set the first name from the username
|
||||||
|
if (!$jp->first_name and $jp->username)
|
||||||
|
$jp->first_name = $jp->username;
|
||||||
|
|
||||||
// check if we already have a contact
|
// check if we already have a contact
|
||||||
|
|
||||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `url` = '%s' LIMIT 1",
|
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `url` = '%s' LIMIT 1",
|
||||||
|
@ -455,8 +471,20 @@ function facebook_content(&$a) {
|
||||||
info( t('Updating contacts') . EOL);
|
info( t('Updating contacts') . EOL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$o = '';
|
||||||
|
|
||||||
$fb_installed = get_pconfig(local_user(),'facebook','post');
|
$fb_installed = false;
|
||||||
|
if (get_pconfig(local_user(),'facebook','post')) {
|
||||||
|
$access_token = get_pconfig(local_user(),'facebook','access_token');
|
||||||
|
if ($access_token) {
|
||||||
|
$private_wall = intval(get_pconfig($uid,'facebook','private_wall'));
|
||||||
|
$s = fetch_url('https://graph.facebook.com/me/feed?access_token=' . $access_token);
|
||||||
|
if($s) {
|
||||||
|
$j = json_decode($s);
|
||||||
|
if (isset($j->data)) $fb_installed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
$appid = get_config('facebook','appid');
|
$appid = get_config('facebook','appid');
|
||||||
|
|
||||||
|
@ -534,7 +562,7 @@ function facebook_cron($a,$b) {
|
||||||
|
|
||||||
$poll_interval = intval(get_config('facebook','poll_interval'));
|
$poll_interval = intval(get_config('facebook','poll_interval'));
|
||||||
if(! $poll_interval)
|
if(! $poll_interval)
|
||||||
$poll_interval = 3600;
|
$poll_interval = FACEBOOK_DEFAULT_POLL_INTERVAL;
|
||||||
|
|
||||||
if($last) {
|
if($last) {
|
||||||
$next = $last + $poll_interval;
|
$next = $last + $poll_interval;
|
||||||
|
@ -589,7 +617,7 @@ function facebook_cron($a,$b) {
|
||||||
|
|
||||||
if(strlen($a->config['admin_email']) && !get_config('facebook', 'realtime_err_mailsent')) {
|
if(strlen($a->config['admin_email']) && !get_config('facebook', 'realtime_err_mailsent')) {
|
||||||
$res = mail($a->config['admin_email'], t('Problems with Facebook Real-Time Updates'),
|
$res = mail($a->config['admin_email'], t('Problems with Facebook Real-Time Updates'),
|
||||||
"Hi!\n\nThere's a problem with the Facebook Real-Time Updates that cannob be solved automatically. Maybe an permission issue?\n\nThis e-mail will only be sent once.",
|
"Hi!\n\nThere's a problem with the Facebook Real-Time Updates that cannot be solved automatically. Maybe a permission issue?\n\nPlease try to re-activate it on " . $a->config["system"]["url"] . "/admin/plugins/facebook\n\nThis e-mail will only be sent once.",
|
||||||
'From: ' . t('Administrator') . '@' . $_SERVER['SERVER_NAME'] . "\n"
|
'From: ' . t('Administrator') . '@' . $_SERVER['SERVER_NAME'] . "\n"
|
||||||
. 'Content-type: text/plain; charset=UTF-8' . "\n"
|
. 'Content-type: text/plain; charset=UTF-8' . "\n"
|
||||||
. 'Content-transfer-encoding: 8bit'
|
. 'Content-transfer-encoding: 8bit'
|
||||||
|
@ -620,17 +648,58 @@ function facebook_plugin_settings(&$a,&$b) {
|
||||||
|
|
||||||
|
|
||||||
function facebook_plugin_admin(&$a, &$o){
|
function facebook_plugin_admin(&$a, &$o){
|
||||||
|
$o = '<input type="hidden" name="form_security_token" value="' . get_form_security_token("fbsave") . '">';
|
||||||
|
|
||||||
$activated = facebook_check_realtime_active();
|
$o .= '<h4>' . t('Facebook API Key') . '</h4>';
|
||||||
if ($activated) {
|
|
||||||
$o = t('Real-Time Updates are activated.') . '<br><br>';
|
$appid = get_config('facebook', 'appid' );
|
||||||
$o .= '<input type="submit" name="real_time_deactivate" value="' . t('Deactivate Real-Time Updates') . '">';
|
$appsecret = get_config('facebook', 'appsecret' );
|
||||||
} else {
|
$poll_interval = get_config('facebook', 'poll_interval' );
|
||||||
$o = t('Real-Time Updates not activated.') . '<br><input type="submit" name="real_time_activate" value="' . t('Activate Real-Time Updates') . '">';
|
if (!$poll_interval) $poll_interval = FACEBOOK_DEFAULT_POLL_INTERVAL;
|
||||||
|
|
||||||
|
$ret1 = q("SELECT `v` FROM `config` WHERE `cat` = 'facebook' AND `k` = 'appid' LIMIT 1");
|
||||||
|
$ret2 = q("SELECT `v` FROM `config` WHERE `cat` = 'facebook' AND `k` = 'appsecret' LIMIT 1");
|
||||||
|
if ((count($ret1) > 0 && $ret1[0]['v'] != $appid) || (count($ret2) > 0 && $ret2[0]['v'] != $appsecret)) $o .= t('Error: it appears that you have specified the App-ID and -Secret in your .htconfig.php file. As long as they are specified there, they cannot be set using this form.<br><br>');
|
||||||
|
|
||||||
|
$working_connection = false;
|
||||||
|
if ($appid && $appsecret) {
|
||||||
|
$subs = facebook_subscriptions_get();
|
||||||
|
if ($subs === null) $o .= t('Error: the given API Key seems to be incorrect (the application access token could not be retrieved).') . '<br>';
|
||||||
|
elseif (is_array($subs)) {
|
||||||
|
$o .= t('The given API Key seems to work correctly.') . '<br>';
|
||||||
|
$working_connection = true;
|
||||||
|
} else $o .= t('The correctness of the API Key could not be detected. Somthing strange\'s going on.') . '<br>';
|
||||||
|
}
|
||||||
|
|
||||||
|
$o .= '<label for="fb_appid">' . t('App-ID / API-Key') . '</label><input name="appid" type="text" value="' . escape_tags($appid ? $appid : "") . '"><br style="clear: both;">';
|
||||||
|
$o .= '<label for="fb_appsecret">' . t('Application secret') . '</label><input name="appsecret" type="text" value="' . escape_tags($appsecret ? $appsecret : "") . '"><br style="clear: both;">';
|
||||||
|
$o .= '<label for="fb_poll_interval">' . sprintf(t('Polling Interval (min. %1$s minutes)'), FACEBOOK_MIN_POLL_INTERVAL) . '</label><input name="poll_interval" type="number" min="' . FACEBOOK_MIN_POLL_INTERVAL . '" value="' . $poll_interval . '"><br style="clear: both;">';
|
||||||
|
$o .= '<input type="submit" name="fb_save_keys" value="' . t('Save') . '">';
|
||||||
|
|
||||||
|
if ($working_connection) {
|
||||||
|
$o .= '<h4>' . t('Real-Time Updates') . '</h4>';
|
||||||
|
|
||||||
|
$activated = facebook_check_realtime_active();
|
||||||
|
if ($activated) {
|
||||||
|
$o .= t('Real-Time Updates are activated.') . '<br><br>';
|
||||||
|
$o .= '<input type="submit" name="real_time_deactivate" value="' . t('Deactivate Real-Time Updates') . '">';
|
||||||
|
} else {
|
||||||
|
$o .= t('Real-Time Updates not activated.') . '<br><input type="submit" name="real_time_activate" value="' . t('Activate Real-Time Updates') . '">';
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function facebook_plugin_admin_post(&$a, &$o){
|
function facebook_plugin_admin_post(&$a, &$o){
|
||||||
|
check_form_security_token_redirectOnErr('/admin/plugins/facebook', 'fbsave');
|
||||||
|
|
||||||
|
if (x($_REQUEST,'fb_save_keys')) {
|
||||||
|
set_config('facebook', 'appid', $_REQUEST['appid']);
|
||||||
|
set_config('facebook', 'appsecret', $_REQUEST['appsecret']);
|
||||||
|
$poll_interval = IntVal($_REQUEST['poll_interval']);
|
||||||
|
if ($poll_interval >= FACEBOOK_MIN_POLL_INTERVAL) set_config('facebook', 'poll_interval', $poll_interval);
|
||||||
|
del_config('facebook', 'app_access_token');
|
||||||
|
info(t('The new values have been saved.'));
|
||||||
|
}
|
||||||
if (x($_REQUEST,'real_time_activate')) {
|
if (x($_REQUEST,'real_time_activate')) {
|
||||||
facebook_subscription_add_users();
|
facebook_subscription_add_users();
|
||||||
}
|
}
|
||||||
|
@ -664,6 +733,7 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
*/
|
*/
|
||||||
|
|
||||||
require_once('include/group.php');
|
require_once('include/group.php');
|
||||||
|
require_once('include/html2plain.php');
|
||||||
|
|
||||||
logger('Facebook post');
|
logger('Facebook post');
|
||||||
|
|
||||||
|
@ -784,7 +854,8 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
if($b['verb'] == ACTIVITY_DISLIKE)
|
if($b['verb'] == ACTIVITY_DISLIKE)
|
||||||
$msg = trim(strip_tags(bbcode($msg)));
|
$msg = trim(strip_tags(bbcode($msg)));
|
||||||
|
|
||||||
$search_str = $a->get_baseurl() . '/search';
|
// Old code
|
||||||
|
/*$search_str = $a->get_baseurl() . '/search';
|
||||||
|
|
||||||
if(preg_match("/\[url=(.*?)\](.*?)\[\/url\]/is",$msg,$matches)) {
|
if(preg_match("/\[url=(.*?)\](.*?)\[\/url\]/is",$msg,$matches)) {
|
||||||
|
|
||||||
|
@ -813,24 +884,83 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
if((strpos($link,z_root()) !== false) && (! $image))
|
if((strpos($link,z_root()) !== false) && (! $image))
|
||||||
$image = $a->get_baseurl() . '/images/friendica-64.jpg';
|
$image = $a->get_baseurl() . '/images/friendica-64.jpg';
|
||||||
|
|
||||||
$msg = trim(strip_tags(bbcode($msg)));
|
$msg = trim(strip_tags(bbcode($msg)));*/
|
||||||
|
|
||||||
|
// New code
|
||||||
|
|
||||||
|
// Looking for the first image
|
||||||
|
$image = '';
|
||||||
|
if(preg_match("/\[img\=([0-9]*)x([0-9]*)\](.*?)\[\/img\]/is",$b['body'],$matches))
|
||||||
|
$image = $matches[3];
|
||||||
|
|
||||||
|
if ($image != '')
|
||||||
|
if(preg_match("/\[img\](.*?)\[\/img\]/is",$b['body'],$matches))
|
||||||
|
$image = $matches[1];
|
||||||
|
|
||||||
|
// Checking for a bookmark element
|
||||||
|
$body = $b['body'];
|
||||||
|
if (strpos($body, "[bookmark") !== false) {
|
||||||
|
// splitting the text in two parts:
|
||||||
|
// before and after the bookmark
|
||||||
|
$pos = strpos($body, "[bookmark");
|
||||||
|
$body1 = substr($body, 0, $pos);
|
||||||
|
$body2 = substr($body, $pos);
|
||||||
|
|
||||||
|
// Removing the bookmark and all quotes after the bookmark
|
||||||
|
// they are mostly only the content after the bookmark.
|
||||||
|
$body2 = preg_replace("/\[bookmark\=([^\]]*)\](.*?)\[\/bookmark\]/ism",'',$body2);
|
||||||
|
$body2 = preg_replace("/\[quote\=([^\]]*)\](.*?)\[\/quote\]/ism",'',$body2);
|
||||||
|
$body2 = preg_replace("/\[quote\](.*?)\[\/quote\]/ism",'',$body2);
|
||||||
|
|
||||||
|
$body = $body1.$body2;
|
||||||
|
}
|
||||||
|
|
||||||
|
// At first convert the text to html
|
||||||
|
$html = bbcode($body);
|
||||||
|
|
||||||
|
// Then convert it to plain text
|
||||||
|
$msg = trim($b['title']." \n\n".html2plain($html, 0, true));
|
||||||
$msg = html_entity_decode($msg,ENT_QUOTES,'UTF-8');
|
$msg = html_entity_decode($msg,ENT_QUOTES,'UTF-8');
|
||||||
|
|
||||||
|
// Removing multiple newlines
|
||||||
|
while (strpos($msg, "\n\n\n") !== false)
|
||||||
|
$msg = str_replace("\n\n\n", "\n\n", $msg);
|
||||||
|
|
||||||
// add any attachments as text urls
|
// add any attachments as text urls
|
||||||
|
$arr = explode(',',$b['attach']);
|
||||||
|
|
||||||
$arr = explode(',',$b['attach']);
|
if(count($arr)) {
|
||||||
|
|
||||||
if(count($arr)) {
|
|
||||||
$msg .= "\n";
|
$msg .= "\n";
|
||||||
foreach($arr as $r) {
|
foreach($arr as $r) {
|
||||||
$matches = false;
|
$matches = false;
|
||||||
$cnt = preg_match('|\[attach\]href=\"(.*?)\" size=\"(.*?)\" type=\"(.*?)\" title=\"(.*?)\"\[\/attach\]|',$r,$matches);
|
$cnt = preg_match('|\[attach\]href=\"(.*?)\" size=\"(.*?)\" type=\"(.*?)\" title=\"(.*?)\"\[\/attach\]|',$r,$matches);
|
||||||
if($cnt) {
|
if($cnt) {
|
||||||
$msg .= $matches[1];
|
$msg .= "\n".$matches[1];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$link = '';
|
||||||
|
$linkname = '';
|
||||||
|
// look for bookmark-bbcode and handle it with priority
|
||||||
|
if(preg_match("/\[bookmark\=([^\]]*)\](.*?)\[\/bookmark\]/is",$b['body'],$matches)) {
|
||||||
|
$link = $matches[1];
|
||||||
|
$linkname = $matches[2];
|
||||||
|
}
|
||||||
|
|
||||||
|
// If there is no bookmark element then take the first link
|
||||||
|
if ($link == '') {
|
||||||
|
$links = collecturls($html);
|
||||||
|
if (sizeof($links) > 0) {
|
||||||
|
reset($links);
|
||||||
|
$link = current($links);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove trailing and leading spaces
|
||||||
|
$msg = trim($msg);
|
||||||
|
|
||||||
|
// Since facebook increased the maxpostlen massively this never should happen again :)
|
||||||
if (strlen($msg) > FACEBOOK_MAXPOSTLEN) {
|
if (strlen($msg) > FACEBOOK_MAXPOSTLEN) {
|
||||||
$shortlink = "";
|
$shortlink = "";
|
||||||
require_once('library/slinky.php');
|
require_once('library/slinky.php');
|
||||||
|
@ -848,7 +978,19 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
$msg = substr($msg, 0, FACEBOOK_MAXPOSTLEN - strlen($shortlink) - 4);
|
$msg = substr($msg, 0, FACEBOOK_MAXPOSTLEN - strlen($shortlink) - 4);
|
||||||
$msg .= '... ' . $shortlink;
|
$msg .= '... ' . $shortlink;
|
||||||
}
|
}
|
||||||
if(! strlen($msg))
|
|
||||||
|
// Fallback - if message is empty
|
||||||
|
if(!strlen($msg))
|
||||||
|
$msg = $link;
|
||||||
|
|
||||||
|
if(!strlen($msg))
|
||||||
|
$msg = $image;
|
||||||
|
|
||||||
|
if(!strlen($msg))
|
||||||
|
$msg = $linkname;
|
||||||
|
|
||||||
|
// If there is nothing to post then exit
|
||||||
|
if(!strlen($msg))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
logger('Facebook post: msg=' . $msg, LOGGER_DATA);
|
logger('Facebook post: msg=' . $msg, LOGGER_DATA);
|
||||||
|
@ -896,6 +1038,7 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
|
|
||||||
if(! get_config('facebook','test_mode')) {
|
if(! get_config('facebook','test_mode')) {
|
||||||
$x = post_url($url, $postvars);
|
$x = post_url($url, $postvars);
|
||||||
|
logger('Facebook post returns: ' . $x, LOGGER_DEBUG);
|
||||||
|
|
||||||
$retj = json_decode($x);
|
$retj = json_decode($x);
|
||||||
if($retj->id) {
|
if($retj->id) {
|
||||||
|
@ -911,15 +1054,45 @@ function facebook_post_hook(&$a,&$b) {
|
||||||
add_to_queue($a->contact,NETWORK_FACEBOOK,$s);
|
add_to_queue($a->contact,NETWORK_FACEBOOK,$s);
|
||||||
notice( t('Facebook post failed. Queued for retry.') . EOL);
|
notice( t('Facebook post failed. Queued for retry.') . EOL);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
logger('Facebook post returns: ' . $x, LOGGER_DEBUG);
|
if (isset($retj->error) && $retj->error->type == "OAuthException" && $retj->error->code == 190) {
|
||||||
|
logger('Facebook session has expired due to changed password.', LOGGER_DEBUG);
|
||||||
|
|
||||||
|
$last_notification = get_pconfig($b['uid'], 'facebook', 'session_expired_mailsent');
|
||||||
|
if (!$last_notification || $last_notification < (time() - FACEBOOK_SESSION_ERR_NOTIFICATION_INTERVAL)) {
|
||||||
|
require_once('include/enotify.php');
|
||||||
|
|
||||||
|
$r = q("SELECT * FROM `user` WHERE `uid` = %d LIMIT 1", intval($b['uid']) );
|
||||||
|
notification(array(
|
||||||
|
'uid' => $b['uid'],
|
||||||
|
'type' => NOTIFY_SYSTEM,
|
||||||
|
'system_type' => 'facebook_connection_invalid',
|
||||||
|
'language' => $r[0]['language'],
|
||||||
|
'to_name' => $r[0]['username'],
|
||||||
|
'to_email' => $r[0]['email'],
|
||||||
|
'source_name' => t('Administrator'),
|
||||||
|
'source_link' => $a->config["system"]["url"],
|
||||||
|
'source_photo' => $a->config["system"]["url"] . '/images/person-80.jpg',
|
||||||
|
));
|
||||||
|
|
||||||
|
set_pconfig($b['uid'], 'facebook', 'session_expired_mailsent', time());
|
||||||
|
} else logger('Facebook: No notification, as the last one was sent on ' . $last_notification, LOGGER_DEBUG);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function facebook_enotify(&$app, &$data) {
|
||||||
|
if (x($data, 'params') && $data['params']['type'] == NOTIFY_SYSTEM && x($data['params'], 'system_type') && $data['params']['system_type'] == 'facebook_connection_invalid') {
|
||||||
|
$data['itemlink'] = '/facebook';
|
||||||
|
$data['epreamble'] = $data['preamble'] = t('Your Facebook connection became invalid. Please Re-authenticate.');
|
||||||
|
$data['subject'] = t('Facebook connection became invalid');
|
||||||
|
$data['body'] = sprintf( t("Hi %1\$s,\n\nThe connection between your accounts on %2\$s and Facebook became invalid. This usually happens after you change your Facebook-password. To enable the connection again, you have to %3\$sre-authenticate the Facebook-connector%4\$s."), $data['params']['to_name'], "[url=" . $app->config["system"]["url"] . "]" . $app->config["sitename"] . "[/url]", "[url=" . $app->config["system"]["url"] . "/facebook]", "[/url]");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
function facebook_post_local(&$a,&$b) {
|
function facebook_post_local(&$a,&$b) {
|
||||||
|
|
||||||
|
@ -1005,6 +1178,46 @@ function fb_queue_hook(&$a,&$b) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function fb_get_timeline($access_token, &$since) {
|
||||||
|
|
||||||
|
$entries->data = array();
|
||||||
|
$newest = 0;
|
||||||
|
|
||||||
|
$url = 'https://graph.facebook.com/me/home?access_token='.$access_token;
|
||||||
|
|
||||||
|
if ($since != 0)
|
||||||
|
$url .= "&since=".$since;
|
||||||
|
|
||||||
|
do {
|
||||||
|
$s = fetch_url($url);
|
||||||
|
$j = json_decode($s);
|
||||||
|
$oldestdate = time();
|
||||||
|
if (isset($j->data))
|
||||||
|
foreach ($j->data as $entry) {
|
||||||
|
$created = strtotime($entry->created_time);
|
||||||
|
|
||||||
|
if ($newest < $created)
|
||||||
|
$newest = $created;
|
||||||
|
|
||||||
|
if ($created >= $since)
|
||||||
|
$entries->data[] = $entry;
|
||||||
|
|
||||||
|
if ($created <= $oldestdate)
|
||||||
|
$oldestdate = $created;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
break;
|
||||||
|
|
||||||
|
$url = $j->paging->next;
|
||||||
|
|
||||||
|
} while (($oldestdate > $since) and ($since != 0) and ($url != ''));
|
||||||
|
|
||||||
|
if ($newest > $since)
|
||||||
|
$since = $newest;
|
||||||
|
|
||||||
|
return($entries);
|
||||||
|
}
|
||||||
|
|
||||||
function fb_consume_all($uid) {
|
function fb_consume_all($uid) {
|
||||||
|
|
||||||
require_once('include/items.php');
|
require_once('include/items.php');
|
||||||
|
@ -1018,23 +1231,33 @@ function fb_consume_all($uid) {
|
||||||
$s = fetch_url('https://graph.facebook.com/me/feed?access_token=' . $access_token);
|
$s = fetch_url('https://graph.facebook.com/me/feed?access_token=' . $access_token);
|
||||||
if($s) {
|
if($s) {
|
||||||
$j = json_decode($s);
|
$j = json_decode($s);
|
||||||
logger('fb_consume_stream: wall: ' . print_r($j,true), LOGGER_DATA);
|
if (isset($j->data)) {
|
||||||
fb_consume_stream($uid,$j,($private_wall) ? false : true);
|
logger('fb_consume_stream: wall: ' . print_r($j,true), LOGGER_DATA);
|
||||||
|
fb_consume_stream($uid,$j,($private_wall) ? false : true);
|
||||||
|
} else {
|
||||||
|
logger('fb_consume_stream: wall: got no data from Facebook: ' . print_r($j,true), LOGGER_NORMAL);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
$s = fetch_url('https://graph.facebook.com/me/home?access_token=' . $access_token);
|
// Get the last date
|
||||||
if($s) {
|
$lastdate = get_pconfig($uid,'facebook','lastdate');
|
||||||
$j = json_decode($s);
|
// fetch all items since the last date
|
||||||
|
$j = fb_get_timeline($access_token, &$lastdate);
|
||||||
|
if (isset($j->data)) {
|
||||||
logger('fb_consume_stream: feed: ' . print_r($j,true), LOGGER_DATA);
|
logger('fb_consume_stream: feed: ' . print_r($j,true), LOGGER_DATA);
|
||||||
fb_consume_stream($uid,$j,false);
|
fb_consume_stream($uid,$j,false);
|
||||||
}
|
|
||||||
|
|
||||||
|
// Write back the last date
|
||||||
|
set_pconfig($uid,'facebook','lastdate', $lastdate);
|
||||||
|
} else
|
||||||
|
logger('fb_consume_stream: feed: got no data from Facebook: ' . print_r($j,true), LOGGER_NORMAL);
|
||||||
}
|
}
|
||||||
|
|
||||||
function fb_get_photo($uid,$link) {
|
function fb_get_photo($uid,$link) {
|
||||||
$access_token = get_pconfig($uid,'facebook','access_token');
|
$access_token = get_pconfig($uid,'facebook','access_token');
|
||||||
if(! $access_token || (! stristr($link,'facebook.com/photo.php')))
|
if(! $access_token || (! stristr($link,'facebook.com/photo.php')))
|
||||||
return "\n" . '[url=' . $link . ']' . t('link') . '[/url]';
|
return "";
|
||||||
|
//return "\n" . '[url=' . $link . ']' . t('link') . '[/url]';
|
||||||
$ret = preg_match('/fbid=([0-9]*)/',$link,$match);
|
$ret = preg_match('/fbid=([0-9]*)/',$link,$match);
|
||||||
if($ret)
|
if($ret)
|
||||||
$photo_id = $match[1];
|
$photo_id = $match[1];
|
||||||
|
@ -1042,8 +1265,8 @@ function fb_get_photo($uid,$link) {
|
||||||
$j = json_decode($x);
|
$j = json_decode($x);
|
||||||
if($j->picture)
|
if($j->picture)
|
||||||
return "\n\n" . '[url=' . $link . '][img]' . $j->picture . '[/img][/url]';
|
return "\n\n" . '[url=' . $link . '][img]' . $j->picture . '[/img][/url]';
|
||||||
else
|
//else
|
||||||
return "\n" . '[url=' . $link . ']' . t('link') . '[/url]';
|
// return "\n" . '[url=' . $link . ']' . t('link') . '[/url]';
|
||||||
}
|
}
|
||||||
|
|
||||||
function fb_consume_stream($uid,$j,$wall = false) {
|
function fb_consume_stream($uid,$j,$wall = false) {
|
||||||
|
@ -1102,6 +1325,10 @@ function fb_consume_stream($uid,$j,$wall = false) {
|
||||||
if($from->id == $self_id)
|
if($from->id == $self_id)
|
||||||
$datarray['contact-id'] = $self[0]['id'];
|
$datarray['contact-id'] = $self[0]['id'];
|
||||||
else {
|
else {
|
||||||
|
// Looking if user is known - if not he is added
|
||||||
|
$access_token = get_pconfig($uid, 'facebook', 'access_token');
|
||||||
|
fb_get_friends_sync_new($uid, $access_token, $from);
|
||||||
|
|
||||||
$r = q("SELECT * FROM `contact` WHERE `notify` = '%s' AND `uid` = %d AND `blocked` = 0 AND `readonly` = 0 LIMIT 1",
|
$r = q("SELECT * FROM `contact` WHERE `notify` = '%s' AND `uid` = %d AND `blocked` = 0 AND `readonly` = 0 LIMIT 1",
|
||||||
dbesc($from->id),
|
dbesc($from->id),
|
||||||
intval($uid)
|
intval($uid)
|
||||||
|
@ -1111,9 +1338,8 @@ function fb_consume_stream($uid,$j,$wall = false) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// don't store post if we don't have a contact
|
// don't store post if we don't have a contact
|
||||||
|
|
||||||
if(! x($datarray,'contact-id')) {
|
if(! x($datarray,'contact-id')) {
|
||||||
logger('no contact: post ignored');
|
logger('facebook: no contact '.$from->name.' '.$from->id.'. post ignored');
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1148,24 +1374,92 @@ function fb_consume_stream($uid,$j,$wall = false) {
|
||||||
$datarray['author-avatar'] = 'https://graph.facebook.com/' . $from->id . '/picture';
|
$datarray['author-avatar'] = 'https://graph.facebook.com/' . $from->id . '/picture';
|
||||||
$datarray['plink'] = $datarray['author-link'] . '&v=wall&story_fbid=' . substr($entry->id,strpos($entry->id,'_') + 1);
|
$datarray['plink'] = $datarray['author-link'] . '&v=wall&story_fbid=' . substr($entry->id,strpos($entry->id,'_') + 1);
|
||||||
|
|
||||||
|
logger('facebook: post '.$entry->id.' from '.$from->name);
|
||||||
|
|
||||||
$datarray['body'] = escape_tags($entry->message);
|
$datarray['body'] = escape_tags($entry->message);
|
||||||
|
|
||||||
if($entry->picture && $entry->link) {
|
if($entry->name and $entry->link)
|
||||||
$datarray['body'] .= "\n\n" . '[url=' . $entry->link . '][img]' . $entry->picture . '[/img][/url]';
|
$datarray['body'] .= "\n\n[bookmark=".$entry->link."]".$entry->name."[/bookmark]";
|
||||||
|
elseif ($entry->name)
|
||||||
|
$datarray['body'] .= "\n\n[b]" . $entry->name."[/b]";
|
||||||
|
|
||||||
|
if($entry->caption) {
|
||||||
|
if(!$entry->name and $entry->link)
|
||||||
|
$datarray['body'] .= "\n\n[bookmark=".$entry->link."]".$entry->caption."[/bookmark]";
|
||||||
|
else
|
||||||
|
$datarray['body'] .= "[i]" . $entry->caption."[/i]\n";
|
||||||
}
|
}
|
||||||
else {
|
|
||||||
if($entry->picture)
|
if(!$entry->caption and !$entry->name) {
|
||||||
$datarray['body'] .= "\n\n" . '[img]' . $entry->picture . '[/img]';
|
if ($entry->link)
|
||||||
// if just a link, it may be a wall photo - check
|
$datarray['body'] .= "\n[url]".$entry->link."[/url]\n";
|
||||||
if($entry->link)
|
else
|
||||||
$datarray['body'] .= fb_get_photo($uid,$entry->link);
|
$datarray['body'] .= "\n";
|
||||||
}
|
}
|
||||||
if($entry->name)
|
|
||||||
$datarray['body'] .= "\n" . $entry->name;
|
$quote = "";
|
||||||
if($entry->caption)
|
|
||||||
$datarray['body'] .= "\n" . $entry->caption;
|
|
||||||
if($entry->description)
|
if($entry->description)
|
||||||
$datarray['body'] .= "\n" . $entry->description;
|
$quote = $entry->description;
|
||||||
|
|
||||||
|
if ($entry->properties)
|
||||||
|
foreach ($entry->properties as $property)
|
||||||
|
$quote .= "\n".$property->name.": [url=".$property->href."]".$property->text."[/url]";
|
||||||
|
|
||||||
|
if ($quote)
|
||||||
|
$datarray['body'] .= "\n[quote]".$quote."[/quote]";
|
||||||
|
|
||||||
|
// Only import the picture when the message is no video
|
||||||
|
// oembed display a picture of the video as well
|
||||||
|
if ($entry->type != "video") {
|
||||||
|
if($entry->picture && $entry->link) {
|
||||||
|
$datarray['body'] .= "\n" . '[url=' . $entry->link . '][img]'.$entry->picture.'[/img][/url]';
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if($entry->picture)
|
||||||
|
$datarray['body'] .= "\n" . '[img]' . $entry->picture . '[/img]';
|
||||||
|
// if just a link, it may be a wall photo - check
|
||||||
|
if($entry->link)
|
||||||
|
$datarray['body'] .= fb_get_photo($uid,$entry->link);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Just as a test - to see if these are the missing entries
|
||||||
|
//if(trim($datarray['body']) == '')
|
||||||
|
// $datarray['body'] = $entry->story;
|
||||||
|
|
||||||
|
if(trim($datarray['body']) == '') {
|
||||||
|
logger('facebook: empty body '.$entry->id.' '.print_r($entry, true));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
$datarray['body'] .= "\n";
|
||||||
|
|
||||||
|
if ($entry->icon)
|
||||||
|
$datarray['body'] .= "[img]".$entry->icon."[/img] ";
|
||||||
|
|
||||||
|
if ($entry->actions)
|
||||||
|
foreach ($entry->actions as $action)
|
||||||
|
if (($action->name != "Comment") and ($action->name != "Like"))
|
||||||
|
$datarray['body'] .= "[url=".$action->link."]".$action->name."[/url] ";
|
||||||
|
|
||||||
|
$datarray['body'] = trim($datarray['body']);
|
||||||
|
|
||||||
|
//if(($datarray['body'] != '') and ($uid == 1))
|
||||||
|
// $datarray['body'] .= "[noparse]".print_r($entry, true)."[/noparse]";
|
||||||
|
|
||||||
|
if ($entry->place->name)
|
||||||
|
$datarray['coord'] = $entry->place->name;
|
||||||
|
else if ($entry->place->location->street or $entry->place->location->city or $entry->place->location->Denmark) {
|
||||||
|
if ($entry->place->location->street)
|
||||||
|
$datarray['coord'] = $entry->place->location->street;
|
||||||
|
if ($entry->place->location->city)
|
||||||
|
$datarray['coord'] .= " ".$entry->place->location->city;
|
||||||
|
if ($entry->place->location->country)
|
||||||
|
$datarray['coord'] .= " ".$entry->place->location->country;
|
||||||
|
} else if ($entry->place->location->latitude and $entry->place->location->longitude)
|
||||||
|
$datarray['coord'] = substr($entry->place->location->latitude, 0, 8)
|
||||||
|
.' '.substr($entry->place->location->longitude, 0, 8);
|
||||||
|
|
||||||
$datarray['created'] = datetime_convert('UTC','UTC',$entry->created_time);
|
$datarray['created'] = datetime_convert('UTC','UTC',$entry->created_time);
|
||||||
$datarray['edited'] = datetime_convert('UTC','UTC',$entry->updated_time);
|
$datarray['edited'] = datetime_convert('UTC','UTC',$entry->updated_time);
|
||||||
|
|
||||||
|
@ -1174,12 +1468,7 @@ function fb_consume_stream($uid,$j,$wall = false) {
|
||||||
|
|
||||||
if($entry->privacy && $entry->privacy->value !== 'EVERYONE') {
|
if($entry->privacy && $entry->privacy->value !== 'EVERYONE') {
|
||||||
$datarray['private'] = 1;
|
$datarray['private'] = 1;
|
||||||
$datarray['allow_cid'] = '<' . $uid . '>';
|
$datarray['allow_cid'] = '<' . $self[0]['id'] . '>';
|
||||||
}
|
|
||||||
|
|
||||||
if(trim($datarray['body']) == '') {
|
|
||||||
logger('facebook: empty body');
|
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$top_item = item_store($datarray);
|
$top_item = item_store($datarray);
|
||||||
|
@ -1373,8 +1662,8 @@ function fb_get_app_access_token() {
|
||||||
logger('fb_get_app_access_token: appid and/or appsecret not set', LOGGER_DEBUG);
|
logger('fb_get_app_access_token: appid and/or appsecret not set', LOGGER_DEBUG);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
logger('https://graph.facebook.com/oauth/access_token?client_id=' . $appid . '&client_secret=' . $appsecret . '&grant_type=client_credentials', LOGGER_DATA);
|
||||||
$x = fetch_url('https://graph.facebook.com/oauth/access_token?client_id=' . $appid . '&client_secret=' . $appsecret . "&grant_type=client_credentials");
|
$x = fetch_url('https://graph.facebook.com/oauth/access_token?client_id=' . $appid . '&client_secret=' . $appsecret . '&grant_type=client_credentials');
|
||||||
|
|
||||||
if(strpos($x,'access_token=') !== false) {
|
if(strpos($x,'access_token=') !== false) {
|
||||||
logger('fb_get_app_access_token: returned access token: ' . $x, LOGGER_DATA);
|
logger('fb_get_app_access_token: returned access token: ' . $x, LOGGER_DATA);
|
||||||
|
@ -1402,11 +1691,10 @@ function facebook_subscription_del_users() {
|
||||||
$url = "https://graph.facebook.com/" . get_config('facebook', 'appid' ) . "/subscriptions?access_token=" . $access_token;
|
$url = "https://graph.facebook.com/" . get_config('facebook', 'appid' ) . "/subscriptions?access_token=" . $access_token;
|
||||||
facebook_delete_url($url);
|
facebook_delete_url($url);
|
||||||
|
|
||||||
del_config('facebook', 'realtime_active');
|
if (!facebook_check_realtime_active()) del_config('facebook', 'realtime_active');
|
||||||
}
|
}
|
||||||
|
|
||||||
function facebook_subscription_add_users() {
|
function facebook_subscription_add_users($second_try = false) {
|
||||||
|
|
||||||
$a = get_app();
|
$a = get_app();
|
||||||
$access_token = fb_get_app_access_token();
|
$access_token = fb_get_app_access_token();
|
||||||
|
|
||||||
|
@ -1427,9 +1715,18 @@ function facebook_subscription_add_users() {
|
||||||
del_config('facebook', 'cb_verify_token');
|
del_config('facebook', 'cb_verify_token');
|
||||||
|
|
||||||
if ($j) {
|
if ($j) {
|
||||||
|
$x = json_decode($j);
|
||||||
logger("Facebook reponse: " . $j, LOGGER_DATA);
|
logger("Facebook reponse: " . $j, LOGGER_DATA);
|
||||||
|
if (isset($x->error)) {
|
||||||
if (facebook_check_realtime_active()) set_config('facebook', 'realtime_active', 1);
|
logger('facebook_subscription_add_users: got an error: ' . $j);
|
||||||
|
if ($x->error->type == "OAuthException" && $x->error->code == 190) {
|
||||||
|
del_config('facebook', 'app_access_token');
|
||||||
|
if ($second_try === false) facebook_subscription_add_users(true);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
logger('facebook_subscription_add_users: sucessful');
|
||||||
|
if (facebook_check_realtime_active()) set_config('facebook', 'realtime_active', 1);
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
BIN
ijpost.tar.gz
BIN
ijpost.tgz
Normal file
BIN
impressum.tgz
|
@ -1,9 +1,10 @@
|
||||||
Impressum Plugin for Friendica
|
Impressum Plugin for Friendica
|
||||||
|
|
||||||
Author: Tobias Diekershoff
|
Author: Tobias Diekershoff
|
||||||
|
http://diekershoff.homeunix.net/friendika/profile/tobias
|
||||||
tobias.diekershoff@gmx.net
|
tobias.diekershoff@gmx.net
|
||||||
|
|
||||||
License: 3-clause BSD license (same as Friendica)
|
License: 3-clause BSD license
|
||||||
|
|
||||||
About
|
About
|
||||||
This plugin adds an Impressum block to the /friendica page with informations
|
This plugin adds an Impressum block to the /friendica page with informations
|
||||||
|
@ -12,16 +13,22 @@ About
|
||||||
In the notes and postal fields you can use HTML tags for formatting.
|
In the notes and postal fields you can use HTML tags for formatting.
|
||||||
|
|
||||||
Configuration:
|
Configuration:
|
||||||
For configuration you can set the following variables in the .htconfig file
|
Simply fill in the fields in the impressium settings page in the plugins area
|
||||||
* $a->config['impressum']['owner'] this is the Name of the Operator
|
of your admin panel.
|
||||||
* $a->config['impressum']['ownerprofile'] this is an optional Friendica account
|
|
||||||
where the above owner name will link to
|
|
||||||
* $a->config['impressum']['email'] a contact email address (optional)
|
|
||||||
will be displayed slightly obfuscated
|
|
||||||
as name(at)example(dot)com
|
|
||||||
* $a->config['impressum']['postal'] should contain a postal address where
|
|
||||||
you can be reached at (optional)
|
|
||||||
* $a->config['impressum']['notes'] additional informations that should
|
|
||||||
be displayed in the Impressum block
|
|
||||||
|
|
||||||
|
If you for any reason prefer to use a configuration file instead, you can set the
|
||||||
|
following variables in the .htconfig file
|
||||||
|
|
||||||
|
* $a->config['impressum']['owner'] this is the Name of the Operator
|
||||||
|
* $a->config['impressum']['ownerprofile'] this is an optional Friendica account
|
||||||
|
where the above owner name will link to
|
||||||
|
* $a->config['impressum']['email'] a contact email address (optional)
|
||||||
|
will be displayed slightly obfuscated
|
||||||
|
as name(at)example(dot)com
|
||||||
|
|
||||||
|
* $a->config['impressum']['postal'] should contain a postal address where
|
||||||
|
you can be reached at (optional)
|
||||||
|
* $a->config['impressum']['notes'] additional informations that should
|
||||||
|
be displayed in the Impressum block
|
||||||
|
* $a->config['impressum']['footer_text'] Text that will be displayed at
|
||||||
|
the bottom of the pages.
|
||||||
|
|
|
@ -3,4 +3,5 @@
|
||||||
{{ inc field_input.tpl with $field=$postal }}{{ endinc }}
|
{{ inc field_input.tpl with $field=$postal }}{{ endinc }}
|
||||||
{{ inc field_input.tpl with $field=$notes }}{{ endinc }}
|
{{ inc field_input.tpl with $field=$notes }}{{ endinc }}
|
||||||
{{ inc field_input.tpl with $field=$email }}{{ endinc }}
|
{{ inc field_input.tpl with $field=$email }}{{ endinc }}
|
||||||
|
{{ inc field_input.tpl with $field=$footer_text }}{{ endinc }}
|
||||||
<div class="submit"><input type="submit" name="page_site" value="$submit" /></div>
|
<div class="submit"><input type="submit" name="page_site" value="$submit" /></div>
|
||||||
|
|
4
impressum/impressum.css
Normal file
|
@ -0,0 +1,4 @@
|
||||||
|
#impressum_footer {
|
||||||
|
padding-top: 15px;
|
||||||
|
font-size: 0.8em;
|
||||||
|
}
|
|
@ -2,18 +2,20 @@
|
||||||
/**
|
/**
|
||||||
* Name: Impressum
|
* Name: Impressum
|
||||||
* Description: Plugin to add contact information to the about page (/friendica)
|
* Description: Plugin to add contact information to the about page (/friendica)
|
||||||
* Version: 1.0
|
* Version: 1.1
|
||||||
* Author: Tobias Diekershoff <https://diekershoff.homeunix.net/friendika/profile/tobias>
|
* Author: Tobias Diekershoff <http://diekershoff.homeunix.net/friendika/profile/tobias>
|
||||||
* License: 3-clause BSD license
|
* License: 3-clause BSD license
|
||||||
*/
|
*/
|
||||||
|
|
||||||
function impressum_install() {
|
function impressum_install() {
|
||||||
register_hook('about_hook', 'addon/impressum/impressum.php', 'impressum_show');
|
register_hook('about_hook', 'addon/impressum/impressum.php', 'impressum_show');
|
||||||
|
register_hook('page_end', 'addon/impressum/impressum.php', 'impressum_footer');
|
||||||
logger("installed impressum plugin");
|
logger("installed impressum plugin");
|
||||||
}
|
}
|
||||||
|
|
||||||
function impressum_uninstall() {
|
function impressum_uninstall() {
|
||||||
unregister_hook('about_hook', 'addon/impressum/impressum.php', 'impressum_show');
|
unregister_hook('about_hook', 'addon/impressum/impressum.php', 'impressum_show');
|
||||||
|
unregister_hook('page_end', 'addon/impressum/impressum.php', 'impressum_footer');
|
||||||
logger("uninstalled impressum plugin");
|
logger("uninstalled impressum plugin");
|
||||||
}
|
}
|
||||||
function obfuscate_email ($s) {
|
function obfuscate_email ($s) {
|
||||||
|
@ -21,6 +23,13 @@ function obfuscate_email ($s) {
|
||||||
$s = str_replace('.','(dot)',$s);
|
$s = str_replace('.','(dot)',$s);
|
||||||
return $s;
|
return $s;
|
||||||
}
|
}
|
||||||
|
function impressum_footer($a, &$b) {
|
||||||
|
$text = get_config('impressum','footer_text');
|
||||||
|
if (! $text == '') {
|
||||||
|
$a->page['htmlhead'] .= '<link rel="stylesheet" type="text/css" href="'.$a->get_baseurl().'/addon/impressum/impressum.css" media="all" />';
|
||||||
|
$b .= '<div id="impressum_footer">'.$text.'</div>';
|
||||||
|
}
|
||||||
|
}
|
||||||
function impressum_show($a,&$b) {
|
function impressum_show($a,&$b) {
|
||||||
$b .= '<h3>'.t('Impressum').'</h3>';
|
$b .= '<h3>'.t('Impressum').'</h3>';
|
||||||
$owner = get_config('impressum', 'owner');
|
$owner = get_config('impressum', 'owner');
|
||||||
|
@ -56,21 +65,24 @@ function impressum_plugin_admin_post (&$a) {
|
||||||
$postal = ((x($_POST, 'postal')) ? (trim($_POST['postal'])) : '');
|
$postal = ((x($_POST, 'postal')) ? (trim($_POST['postal'])) : '');
|
||||||
$notes = ((x($_POST, 'notes')) ? (trim($_POST['notes'])) : '');
|
$notes = ((x($_POST, 'notes')) ? (trim($_POST['notes'])) : '');
|
||||||
$email = ((x($_POST, 'email')) ? notags(trim($_POST['email'])) : '');
|
$email = ((x($_POST, 'email')) ? notags(trim($_POST['email'])) : '');
|
||||||
|
$footer_text = ((x($_POST, 'footer_text')) ? (trim($_POST['footer_text'])) : '');
|
||||||
set_config('impressum','owner',$owner);
|
set_config('impressum','owner',$owner);
|
||||||
set_config('impressum','ownerprofile',$ownerprofile);
|
set_config('impressum','ownerprofile',$ownerprofile);
|
||||||
set_config('impressum','postal',$postal);
|
set_config('impressum','postal',$postal);
|
||||||
set_config('impressum','email',$email);
|
set_config('impressum','email',$email);
|
||||||
set_config('impressum','notes',$notes);
|
set_config('impressum','notes',$notes);
|
||||||
|
set_config('impressum','footer_text',$footer_text);
|
||||||
info( t('Settings updated.'). EOL );
|
info( t('Settings updated.'). EOL );
|
||||||
}
|
}
|
||||||
function impressum_plugin_admin (&$a, &$o) {
|
function impressum_plugin_admin (&$a, &$o) {
|
||||||
$t = file_get_contents( dirname(__file__). "/admin.tpl" );
|
$t = file_get_contents( dirname(__file__). "/admin.tpl" );
|
||||||
$o = replace_macros($t, array(
|
$o = replace_macros($t, array(
|
||||||
'$submit' => t('Submit'),
|
'$submit' => t('Submit'),
|
||||||
'$owner' => array('owner', t('Site Owner'), get_config('impressum','owner'), ''),
|
'$owner' => array('owner', t('Site Owner'), get_config('impressum','owner'), t('The page operators name.')),
|
||||||
'$ownerprofile' => array('ownerprofile', t('Site Owners Profile'), get_config('impressum','ownerprofile'), ''),
|
'$ownerprofile' => array('ownerprofile', t('Site Owners Profile'), get_config('impressum','ownerprofile'), t('Profile address of the operator.')),
|
||||||
'$postal' => array('postal', t('Postal Address'), get_config('impressum','postal'), ''),
|
'$postal' => array('postal', t('Postal Address'), get_config('impressum','postal'), t('How to contact the operator via snail mail.')),
|
||||||
'$notes' => array('notes', t('Notes'), get_config('impressum','notes'), ''),
|
'$notes' => array('notes', t('Notes'), get_config('impressum','notes'), t('Additional notes that are displayed beneath the contact information.')),
|
||||||
'$email' => array('email', t('Email Address'), get_config('impressum','email'), ''),
|
'$email' => array('email', t('Email Address'), get_config('impressum','email'), t('How to contact the operator via email. (will be displayed obfuscated)')),
|
||||||
|
'$footer_text' => array('footer_text', t('Footer note'), get_config('impressum','footer_text'), t('Text for the footer.')),
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
28
irc/irc.php
|
@ -22,7 +22,7 @@ unregister_hook('app_menu', 'addon/irc/irc.php', 'irc_app_menu');
|
||||||
}
|
}
|
||||||
|
|
||||||
function irc_app_menu($a,&$b) {
|
function irc_app_menu($a,&$b) {
|
||||||
$b['app_menu'][] = '<div class="app-title"><a href="irc">' . t('irc Chatroom') . '</a></div>';
|
$b['app_menu'][] = '<div class="app-title"><a href="irc">' . t('IRC Chatroom') . '</a></div>';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -33,9 +33,27 @@ return;
|
||||||
|
|
||||||
function irc_content(&$a) {
|
function irc_content(&$a) {
|
||||||
|
|
||||||
$baseurl = $a->get_baseurl() . '/addon/irc';
|
$baseurl = $a->get_baseurl() . '/addon/irc';
|
||||||
$o = '';
|
$o = '';
|
||||||
|
|
||||||
|
$sitechats = get_config('irc','channels');
|
||||||
|
if($sitechats)
|
||||||
|
$chats = explode(',',$sitechats);
|
||||||
|
else
|
||||||
|
$chats = array('friendica','chat','chatback','hottub','ircbar','dateroom','teentalk');
|
||||||
|
|
||||||
|
|
||||||
|
$a->page['aside'] .= '<div class="widget"><h3>' . t('Popular Channels') . '</h3><ul>';
|
||||||
|
foreach($chats as $chat) {
|
||||||
|
$a->page['aside'] .= '<li><a href="' . $a->get_baseurl() . '/irc?channels=' . $chat . '" >' . '#' . $chat . '</a></li>';
|
||||||
|
}
|
||||||
|
$a->page['aside'] .= '</ul></div>';
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
$channels = ((x($_GET,'channels')) ? $_GET['channels'] : 'friendica');
|
||||||
|
|
||||||
/* add the chatroom frame and some html
|
/* add the chatroom frame and some html
|
||||||
* by altering the "channels=friendica" part of the URL, you can add/remove channels.
|
* by altering the "channels=friendica" part of the URL, you can add/remove channels.
|
||||||
|
@ -43,8 +61,8 @@ $o = '';
|
||||||
*/
|
*/
|
||||||
$o .= <<< EOT
|
$o .= <<< EOT
|
||||||
<h2>IRC chat</h2>
|
<h2>IRC chat</h2>
|
||||||
<p><a href="http://tldp.org/HOWTO/IRC/beginners.html" target="_blank">a beginner's guide to using IRC.</a></p>
|
<p><a href="http://tldp.org/HOWTO/IRC/beginners.html" target="_blank">A beginner's guide to using IRC. [en]</a></p>
|
||||||
<iframe src="http://webchat.freenode.net?channels=friendica" width="600" height="600"></iframe>
|
<iframe src="http://webchat.freenode.net?channels=$channels" width="600" height="600"></iframe>
|
||||||
EOT;
|
EOT;
|
||||||
|
|
||||||
return $o;
|
return $o;
|
||||||
|
|
BIN
ljpost.tgz
BIN
namethingy.tgz
Normal file
37
namethingy/namethingy.php
Executable file
|
@ -0,0 +1,37 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* Name: NameThingy
|
||||||
|
* Description: The Ultimate Random Name Generator
|
||||||
|
* Version: 1.0
|
||||||
|
* Author: Mike Macgirvin <http://macgirvin.com/profile/mike>
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
function namethingy_install() {
|
||||||
|
register_hook('app_menu', 'addon/namethingy/namethingy.php', 'namethingy_app_menu');
|
||||||
|
}
|
||||||
|
|
||||||
|
function namethingy_uninstall() {
|
||||||
|
unregister_hook('app_menu', 'addon/namethingy/namethingy.php', 'namethingy_app_menu');
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
function namethingy_app_menu($a,&$b) {
|
||||||
|
$b['app_menu'][] = '<div class="app-title"><a href="namethingy">NameThingy</a></div>';
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function namethingy_module() {}
|
||||||
|
|
||||||
|
function namethingy_content(&$a) {
|
||||||
|
|
||||||
|
$baseurl = $a->get_baseurl() . '/addon/namethingy';
|
||||||
|
|
||||||
|
$o .= <<< EOT
|
||||||
|
<iframe src="http://namethingy.com" width="900" height="700" />
|
||||||
|
EOT;
|
||||||
|
|
||||||
|
return $o;
|
||||||
|
}
|
|
@ -44,13 +44,13 @@ function nsfw_addon_settings(&$a,&$s) {
|
||||||
$words = 'nsfw,';
|
$words = 'nsfw,';
|
||||||
|
|
||||||
$s .= '<div class="settings-block">';
|
$s .= '<div class="settings-block">';
|
||||||
$s .= '<h3>' . t('"Not Safe For Work" Settings') . '</h3>';
|
$s .= '<h3>' . t('Not Safe For Work (General Purpose Content Filter) settings') . '</h3>';
|
||||||
$s .= '<div id="nsfw-wrapper">';
|
$s .= '<div id="nsfw-wrapper">';
|
||||||
|
$s .= '<p>' . t ('This plugin looks in posts for the words/text you specify below, and collapses any content containing those keywords so it is not displayed at inappropriate times, such as sexual innuendo that may be improper in a work setting. It is polite and recommended to tag any content containing nudity with #NSFW. This filter can also match any other word/text you specify, and can thereby be used as a general purpose content filter.') . '</p>';
|
||||||
$s .= '<label id="nsfw-enable-label" for="nsfw-enable">' . t('Enable NSFW filter') . ' </label>';
|
$s .= '<label id="nsfw-enable-label" for="nsfw-enable">' . t('Enable Content filter') . ' </label>';
|
||||||
$s .= '<input id="nsfw-enable" type="checkbox" name="nsfw-enable" value="1"' . $enable_checked . ' />';
|
$s .= '<input id="nsfw-enable" type="checkbox" name="nsfw-enable" value="1"' . $enable_checked . ' />';
|
||||||
$s .= '<div class="clear"></div>';
|
$s .= '<div class="clear"></div>';
|
||||||
$s .= '<label id="nsfw-label" for="nsfw-words">' . t('Comma separated words to treat as NSFW') . ' </label>';
|
$s .= '<label id="nsfw-label" for="nsfw-words">' . t('Comma separated list of keywords to hide') . ' </label>';
|
||||||
$s .= '<input id="nsfw-words" type="text" name="nsfw-words" value="' . $words .'" />';
|
$s .= '<input id="nsfw-words" type="text" name="nsfw-words" value="' . $words .'" />';
|
||||||
$s .= '</div><div class="clear"></div>';
|
$s .= '</div><div class="clear"></div>';
|
||||||
|
|
||||||
|
|
|
@ -16,11 +16,29 @@ Support the OpenStreetMap community and share the load.
|
||||||
|
|
||||||
___ Configuration ___
|
___ Configuration ___
|
||||||
|
|
||||||
|
If you for any reason prefer to use a configuration file instead
|
||||||
|
of the admin panels, please refer to the Alternative Configuration below.
|
||||||
|
|
||||||
|
Activate the plugin from your admin panel.
|
||||||
|
|
||||||
|
You can now add a Tile Server and default zoom level in the plugin settings
|
||||||
|
page of your admin panel.
|
||||||
|
|
||||||
|
The Time Server URL points to the tile server you want to use. Use the full URL,
|
||||||
|
with protocol (http/s) and trailing slash. You can configure the default zoom
|
||||||
|
level on the map in the Default Zoom box. 1 will show the whole world and 18 is the highest
|
||||||
|
zoom level available.
|
||||||
|
|
||||||
|
|
||||||
|
___ Alternative Configuration ___
|
||||||
|
|
||||||
Open the .htconfig.php file and add "openstreetmap" to the list of activated
|
Open the .htconfig.php file and add "openstreetmap" to the list of activated
|
||||||
addons.
|
addons.
|
||||||
|
|
||||||
$a->config['system']['addon'] = "openstreetmap, ..."
|
$a->config['system']['addon'] = "openstreetmap, ..."
|
||||||
|
|
||||||
You have to add two configuration variables for the addon:
|
You have to add two configuration variables for the addon:
|
||||||
|
|
||||||
$a->config['openstreetmap']['tmsserver'] = 'http://www.openstreetmap.org/';
|
$a->config['openstreetmap']['tmsserver'] = 'http://www.openstreetmap.org/';
|
||||||
$a->config['openstreetmap']['zoom'] = '18';
|
$a->config['openstreetmap']['zoom'] = '18';
|
||||||
|
|
||||||
|
|
60
page/page.php
Executable file
|
@ -0,0 +1,60 @@
|
||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* Name: Page
|
||||||
|
* Description: Shows lists of community pages (improved performance over 'pages')
|
||||||
|
* Version: 1.0
|
||||||
|
* Author: Mike Macgirvin <mike@macgirvin.com>
|
||||||
|
* based on pages plugin by
|
||||||
|
* Author: Michael Vogel <ike@piratenpartei.de>
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
function page_install() {
|
||||||
|
register_hook('page_end', 'addon/page/page.php', 'page_page_end');
|
||||||
|
}
|
||||||
|
|
||||||
|
function page_uninstall() {
|
||||||
|
unregister_hook('page_end', 'addon/page/page.php', 'page_page_end');
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
function page_getpage($uid) {
|
||||||
|
|
||||||
|
|
||||||
|
$pagelist = array();
|
||||||
|
|
||||||
|
$contacts = q("SELECT `id`, `url`, `name`, `micro`FROM `contact`
|
||||||
|
WHERE `network`= 'dfrn' AND `forum` = 1 AND `uid` = %d",
|
||||||
|
intval($uid)
|
||||||
|
);
|
||||||
|
|
||||||
|
$page = array();
|
||||||
|
|
||||||
|
// Look if the profile is a community page
|
||||||
|
foreach($contacts as $contact) {
|
||||||
|
$page[] = array("url"=>$contact["url"], "name"=>$contact["name"], "id"=>$contact["id"], "micro"=>$contact['micro']);
|
||||||
|
}
|
||||||
|
return($page);
|
||||||
|
}
|
||||||
|
|
||||||
|
function page_page_end($a,&$b) {
|
||||||
|
// Only move on if if it's the "network" module and there is a logged on user
|
||||||
|
if (($a->module != "network") OR ($a->user['uid'] == 0))
|
||||||
|
return;
|
||||||
|
|
||||||
|
$page = '<div id="page-sidebar" class="widget">
|
||||||
|
<div class="title tool">
|
||||||
|
<h3>'.t("Forums").'</h3></div>
|
||||||
|
<div id="sidebar-page-list"><ul>';
|
||||||
|
|
||||||
|
$contacts = page_getpage($a->user['uid']);
|
||||||
|
|
||||||
|
foreach($contacts as $contact) {
|
||||||
|
$page .= '<li style="list-style-type: none;" class="tool"><img height="20" width="20" src="' . $contact['micro'] .'" alt="' . $contact['url'] . '" /> <a href="'.$a->get_baseurl().'/redir/'.$contact["id"].'" title="' . $contact['url'] . '" class="label" target="external-link">'.
|
||||||
|
$contact["name"]."</a></li>";
|
||||||
|
}
|
||||||
|
$page .= "</ul></div></div>";
|
||||||
|
if (sizeof($contacts) > 0)
|
||||||
|
$a->page['aside'] = $page . $a->page['aside'];
|
||||||
|
}
|
||||||
|
?>
|
BIN
pageheader.tgz
|
@ -10,7 +10,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
function pageheader_install() {
|
function pageheader_install() {
|
||||||
register_hook('page_header', 'addon/pageheader/pageheader.php', 'pageheader_fetch');
|
register_hook('page_content_top', 'addon/pageheader/pageheader.php', 'pageheader_fetch');
|
||||||
register_hook('plugin_settings', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings');
|
register_hook('plugin_settings', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings');
|
||||||
register_hook('plugin_settings_post', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings_post');
|
register_hook('plugin_settings_post', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings_post');
|
||||||
|
|
||||||
|
@ -18,10 +18,13 @@ function pageheader_install() {
|
||||||
|
|
||||||
|
|
||||||
function pageheader_uninstall() {
|
function pageheader_uninstall() {
|
||||||
unregister_hook('page_header', 'addon/pageheader/pageheader.php', 'pageheader_fetch');
|
unregister_hook('page_content_top', 'addon/pageheader/pageheader.php', 'pageheader_fetch');
|
||||||
unregister_hook('plugin_settings', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings');
|
unregister_hook('plugin_settings', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings');
|
||||||
unregister_hook('plugin_settings_post', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings_post');
|
unregister_hook('plugin_settings_post', 'addon/pageheader/pageheader.php', 'pageheader_addon_settings_post');
|
||||||
|
|
||||||
|
// hook moved, uninstall the old one if still there.
|
||||||
|
unregister_hook('page_header', 'addon/pageheader/pageheader.php', 'pageheader_fetch');
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -41,7 +44,7 @@ function pageheader_addon_settings(&$a,&$s) {
|
||||||
|
|
||||||
$words = get_config('pageheader','text');
|
$words = get_config('pageheader','text');
|
||||||
if(! $words)
|
if(! $words)
|
||||||
$words = 'pageheader,';
|
$words = '';
|
||||||
|
|
||||||
$s .= '<div class="settings-block">';
|
$s .= '<div class="settings-block">';
|
||||||
$s .= '<h3>' . t('"pageheader" Settings') . '</h3>';
|
$s .= '<h3>' . t('"pageheader" Settings') . '</h3>';
|
||||||
|
|
|
@ -1,3 +0,0 @@
|
||||||
Pages
|
|
||||||
|
|
||||||
Shows lists of community pages
|
|
|
@ -1,88 +0,0 @@
|
||||||
<?php
|
|
||||||
/**
|
|
||||||
* Name: Pages
|
|
||||||
* Description: Shows lists of community pages
|
|
||||||
* Version: 1.0
|
|
||||||
* Author: Michael Vogel <ike@piratenpartei.de>
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
function pages_install() {
|
|
||||||
register_hook('page_end', 'addon/pages/pages.php', 'pages_page_end');
|
|
||||||
}
|
|
||||||
|
|
||||||
function pages_uninstall() {
|
|
||||||
unregister_hook('page_end', 'addon/pages/pages.php', 'pages_page_end');
|
|
||||||
}
|
|
||||||
|
|
||||||
function pages_iscommunity($url, &$pagelist) {
|
|
||||||
// check every week for the status - should be enough
|
|
||||||
if ($pagelist[$url]["checked"]<time()-86400*7) {
|
|
||||||
// When too old or not found fetch the status from the profile
|
|
||||||
$ch = curl_init();
|
|
||||||
|
|
||||||
$url = str_replace("/profile/","/hcard/", $url);
|
|
||||||
|
|
||||||
curl_setopt($ch, CURLOPT_URL, $url);
|
|
||||||
curl_setopt($ch, CURLOPT_HEADER, 0);
|
|
||||||
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
|
|
||||||
curl_setopt($ch, CURLOPT_TIMEOUT, 2);
|
|
||||||
|
|
||||||
$page = curl_exec($ch);
|
|
||||||
|
|
||||||
curl_close($ch);
|
|
||||||
|
|
||||||
$iscommunity = (strpos($page, '<meta name="friendika.community" content="true" />') != 0);
|
|
||||||
|
|
||||||
$pagelist[$url] = array("community" => $iscommunity, "checked" => time());
|
|
||||||
} else // Fetch from cache
|
|
||||||
$iscommunity = $pagelist[$url]["community"];
|
|
||||||
return($iscommunity);
|
|
||||||
}
|
|
||||||
|
|
||||||
function pages_getpages($uid) {
|
|
||||||
|
|
||||||
// Fetch cached pagelist from configuration
|
|
||||||
$pagelist = get_pconfig($uid,'pages','pagelist');
|
|
||||||
|
|
||||||
if (sizeof($pagelist) == 0)
|
|
||||||
$pagelist = array();
|
|
||||||
|
|
||||||
$contacts = q("SELECT `id`, `url`, `Name` FROM `contact`
|
|
||||||
WHERE `network`= 'dfrn' AND `uid` = %d",
|
|
||||||
intval($uid));
|
|
||||||
|
|
||||||
$pages = array();
|
|
||||||
|
|
||||||
// Look if the profile is a community page
|
|
||||||
foreach($contacts as $contact) {
|
|
||||||
if (pages_iscommunity($contact["url"], $pagelist))
|
|
||||||
$pages[] = array("url"=>$contact["url"], "Name"=>$contact["Name"], "id"=>$contact["id"]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Write back cached pagelist
|
|
||||||
set_pconfig($uid,'pages','pagelist', $pagelist);
|
|
||||||
return($pages);
|
|
||||||
}
|
|
||||||
|
|
||||||
function pages_page_end($a,&$b) {
|
|
||||||
// Only move on if if it's the "network" module and there is a logged on user
|
|
||||||
if (($a->module != "network") OR ($a->user['uid'] == 0))
|
|
||||||
return;
|
|
||||||
|
|
||||||
$pages = '<div id="pages-sidebar" class="widget">
|
|
||||||
<div class="title tool">
|
|
||||||
<h3>'.t("Community").'</h3></div>
|
|
||||||
<div id="sidebar-pages-list"><ul>';
|
|
||||||
|
|
||||||
$contacts = pages_getpages($a->user['uid']);
|
|
||||||
|
|
||||||
foreach($contacts as $contact) {
|
|
||||||
$pages .= '<li class="tool"><a href="'.$a->get_baseurl().'/redir/'.$contact["id"].'" class="label" target="external-link">'.
|
|
||||||
$contact["Name"]."</a></li>";
|
|
||||||
}
|
|
||||||
$pages .= "</ul></div></div>";
|
|
||||||
if (sizeof($contacts) > 0)
|
|
||||||
$a->page['aside'] = $pages.$a->page['aside'];
|
|
||||||
}
|
|
||||||
?>
|
|
|
@ -1,6 +1,7 @@
|
||||||
## Piwik Plugin ##
|
## Piwik Plugin ##
|
||||||
|
|
||||||
by Tobias Diekershoff
|
by Tobias Diekershoff
|
||||||
|
http://diekershoff.homeunix.net/friendika/profile/tobias
|
||||||
tobias.diekershoff(at)gmx.net
|
tobias.diekershoff(at)gmx.net
|
||||||
|
|
||||||
This addon allows you to embed the code necessary for the FLOSS webanalytics
|
This addon allows you to embed the code necessary for the FLOSS webanalytics
|
||||||
|
@ -19,6 +20,13 @@ styling the opt-out notice.
|
||||||
|
|
||||||
### Configuration ###
|
### Configuration ###
|
||||||
|
|
||||||
|
The easiest way to configure this addon is by activating the admin panels of
|
||||||
|
your ~friendica server and then enter the needed details on the config page
|
||||||
|
for the addon.
|
||||||
|
|
||||||
|
If you don't want to use the admin panel, you can configure the addon through
|
||||||
|
the .htconfig file.
|
||||||
|
|
||||||
Open the .htconfig.php file and add "piwik" to the list of activated addons.
|
Open the .htconfig.php file and add "piwik" to the list of activated addons.
|
||||||
|
|
||||||
$a->config['system']['addon'] = "piwik, ..."
|
$a->config['system']['addon'] = "piwik, ..."
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
* Name: Piwik Analytics
|
* Name: Piwik Analytics
|
||||||
* Description: Piwik Analytics Plugin for Friendica
|
* Description: Piwik Analytics Plugin for Friendica
|
||||||
* Version: 1.1
|
* Version: 1.1
|
||||||
* Author: Tobias Diekershoff <https://diekershoff.homeunix.net/friendika/profile/tobias>
|
* Author: Tobias Diekershoff <http://diekershoff.homeunix.net/friendika/profile/tobias>
|
||||||
* Author: Klaus Weidenbach
|
* Author: Klaus Weidenbach
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
@ -49,7 +49,7 @@ function piwik_analytics($a,&$b) {
|
||||||
* associated CSS file. We just have to tell Friendica to get it
|
* associated CSS file. We just have to tell Friendica to get it
|
||||||
* into the page header.
|
* into the page header.
|
||||||
*/
|
*/
|
||||||
$a->page['htmlhead'] .= '<link rel="stylesheet" type="text/css" href="' . $a->get_baseurl() . '/addon/piwik/piwik.css' . '" media="all" />' . "\r\n";
|
$a->page['htmlhead'] .= '<link rel="stylesheet" type="text/css" href="' . $a->get_baseurl() . '/addon/piwik/piwik.css' . '" media="all" />';
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Get the configuration variables from the .htconfig file.
|
* Get the configuration variables from the .htconfig file.
|
||||||
|
|
BIN
showmore.tgz
|
@ -46,7 +46,8 @@ function showmore_addon_settings(&$a,&$s) {
|
||||||
$s .= '</div><div class="clear"></div>';
|
$s .= '</div><div class="clear"></div>';
|
||||||
|
|
||||||
$s .= '<div class="settings-submit-wrapper" ><input type="submit" id="showmore-submit" name="showmore-submit" class="settings-submit" value="' . t('Submit') . '" /></div>';
|
$s .= '<div class="settings-submit-wrapper" ><input type="submit" id="showmore-submit" name="showmore-submit" class="settings-submit" value="' . t('Submit') . '" /></div>';
|
||||||
// $s .= '<div class="showmore-desc">' . t('Use /expression/ to provide regular expressions') . '</div></div>';
|
// $s .= '<div class="showmore-desc">' . t('Use /expression/ to provide regular expressions') . '</div>';
|
||||||
|
$s .= '</div>';
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -83,7 +84,7 @@ function showmore_prepare_body(&$a,&$b) {
|
||||||
if($found) {
|
if($found) {
|
||||||
$rnd = random_string(8);
|
$rnd = random_string(8);
|
||||||
$b['html'] = '<span id="showmore-teaser-'.$rnd.'" style="display: block;">'.$shortened." ".
|
$b['html'] = '<span id="showmore-teaser-'.$rnd.'" style="display: block;">'.$shortened." ".
|
||||||
'<span id="showmore-wrap-'.$rnd.'" style="white-space:nowrap;" class="fakelink" onclick="openClose(\'showmore-'.$rnd.'\'); openClose(\'showmore-teaser-'.$rnd.'\');" >'.sprintf(t('Show More')).'</span></span>'.
|
'<span id="showmore-wrap-'.$rnd.'" style="white-space:nowrap;" class="fakelink" onclick="openClose(\'showmore-'.$rnd.'\'); openClose(\'showmore-teaser-'.$rnd.'\');" >'.sprintf(t('show more')).'</span></span>'.
|
||||||
'<div id="showmore-'.$rnd.'" style="display: none;">'.$b['html'].'</div>';
|
'<div id="showmore-'.$rnd.'" style="display: none;">'.$b['html'].'</div>';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
BIN
smiley_pack.tgz
Normal file
BIN
smiley_pack/icons/animals/bee.gif
Normal file
After Width: | Height: | Size: 4.4 KiB |
BIN
smiley_pack/icons/animals/bigspider.gif
Normal file
After Width: | Height: | Size: 25 KiB |
BIN
smiley_pack/icons/animals/bunny.gif
Normal file
After Width: | Height: | Size: 1.4 KiB |
BIN
smiley_pack/icons/animals/bunnyflowers.gif
Normal file
After Width: | Height: | Size: 6.5 KiB |
BIN
smiley_pack/icons/animals/cat.gif
Normal file
After Width: | Height: | Size: 2.3 KiB |
BIN
smiley_pack/icons/animals/chick.gif
Normal file
After Width: | Height: | Size: 3.6 KiB |
BIN
smiley_pack/icons/animals/cow.gif
Normal file
After Width: | Height: | Size: 780 B |
BIN
smiley_pack/icons/animals/crab.gif
Normal file
After Width: | Height: | Size: 2.7 KiB |
BIN
smiley_pack/icons/animals/dog.gif
Normal file
After Width: | Height: | Size: 5.2 KiB |
BIN
smiley_pack/icons/animals/dolphin.gif
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
smiley_pack/icons/animals/dragonfly.gif
Normal file
After Width: | Height: | Size: 2.5 KiB |
BIN
smiley_pack/icons/animals/elephant.gif
Normal file
After Width: | Height: | Size: 951 B |
BIN
smiley_pack/icons/animals/fish.gif
Normal file
After Width: | Height: | Size: 4.4 KiB |
BIN
smiley_pack/icons/animals/frog.gif
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
smiley_pack/icons/animals/giraffe.gif
Normal file
After Width: | Height: | Size: 4.8 KiB |
BIN
smiley_pack/icons/animals/hamster.gif
Normal file
After Width: | Height: | Size: 1.2 KiB |
BIN
smiley_pack/icons/animals/horse.gif
Normal file
After Width: | Height: | Size: 2.4 KiB |
BIN
smiley_pack/icons/animals/ladybird.gif
Normal file
After Width: | Height: | Size: 990 B |
BIN
smiley_pack/icons/animals/monkey.gif
Normal file
After Width: | Height: | Size: 4.8 KiB |
BIN
smiley_pack/icons/animals/parrot.gif
Normal file
After Width: | Height: | Size: 1.7 KiB |
BIN
smiley_pack/icons/animals/pig.gif
Normal file
After Width: | Height: | Size: 925 B |
BIN
smiley_pack/icons/animals/sheep.gif
Normal file
After Width: | Height: | Size: 7.5 KiB |
BIN
smiley_pack/icons/animals/snail.gif
Normal file
After Width: | Height: | Size: 645 B |
BIN
smiley_pack/icons/animals/tux.gif
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
smiley_pack/icons/babies/baby.gif
Normal file
After Width: | Height: | Size: 334 B |
BIN
smiley_pack/icons/babies/babycot.gif
Normal file
After Width: | Height: | Size: 3.4 KiB |
BIN
smiley_pack/icons/babies/pregnant.gif
Normal file
After Width: | Height: | Size: 1.5 KiB |
BIN
smiley_pack/icons/babies/stork.gif
Normal file
After Width: | Height: | Size: 18 KiB |
BIN
smiley_pack/icons/confused/confused.gif
Normal file
After Width: | Height: | Size: 594 B |
BIN
smiley_pack/icons/confused/dazed.gif
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
smiley_pack/icons/confused/shrug.gif
Normal file
After Width: | Height: | Size: 184 B |
BIN
smiley_pack/icons/confused/stupid.gif
Normal file
After Width: | Height: | Size: 10 KiB |
BIN
smiley_pack/icons/cool/affro.gif
Normal file
After Width: | Height: | Size: 158 B |
BIN
smiley_pack/icons/cool/cool.gif
Normal file
After Width: | Height: | Size: 5 KiB |
BIN
smiley_pack/icons/devilangel/angel.gif
Normal file
After Width: | Height: | Size: 312 B |
BIN
smiley_pack/icons/devilangel/blondedevil.gif
Normal file
After Width: | Height: | Size: 2.9 KiB |
BIN
smiley_pack/icons/devilangel/catdevil.gif
Normal file
After Width: | Height: | Size: 1.9 KiB |
BIN
smiley_pack/icons/devilangel/cherub.gif
Normal file
After Width: | Height: | Size: 1.6 KiB |
BIN
smiley_pack/icons/devilangel/daseesaw.gif
Normal file
After Width: | Height: | Size: 6.6 KiB |
BIN
smiley_pack/icons/devilangel/devil.gif
Normal file
After Width: | Height: | Size: 1.9 KiB |
BIN
smiley_pack/icons/devilangel/graveside.gif
Normal file
After Width: | Height: | Size: 8 KiB |
BIN
smiley_pack/icons/devilangel/saint.gif
Normal file
After Width: | Height: | Size: 1.2 KiB |
BIN
smiley_pack/icons/devilangel/turnevil.gif
Normal file
After Width: | Height: | Size: 636 B |
BIN
smiley_pack/icons/disgust/fartblush.gif
Normal file
After Width: | Height: | Size: 29 KiB |
BIN
smiley_pack/icons/disgust/fartinbed.gif
Normal file
After Width: | Height: | Size: 23 KiB |
BIN
smiley_pack/icons/disgust/toilet.gif
Normal file
After Width: | Height: | Size: 8.7 KiB |
BIN
smiley_pack/icons/disgust/vomit.gif
Normal file
After Width: | Height: | Size: 2.7 KiB |
BIN
smiley_pack/icons/drink/tea.gif
Normal file
After Width: | Height: | Size: 9.7 KiB |
BIN
smiley_pack/icons/drool/drool.gif
Normal file
After Width: | Height: | Size: 1.3 KiB |
BIN
smiley_pack/icons/fantasy/alienmonster.gif
Normal file
After Width: | Height: | Size: 7.5 KiB |
BIN
smiley_pack/icons/fantasy/barbarian.gif
Normal file
After Width: | Height: | Size: 454 B |
BIN
smiley_pack/icons/fantasy/dinosaur.gif
Normal file
After Width: | Height: | Size: 2.8 KiB |
BIN
smiley_pack/icons/fantasy/dragon.gif
Normal file
After Width: | Height: | Size: 3.4 KiB |
BIN
smiley_pack/icons/fantasy/dragonwhelp.gif
Normal file
After Width: | Height: | Size: 2.3 KiB |
BIN
smiley_pack/icons/fantasy/ghost.gif
Normal file
After Width: | Height: | Size: 1 KiB |
BIN
smiley_pack/icons/fantasy/mummy.gif
Normal file
After Width: | Height: | Size: 6.4 KiB |
BIN
smiley_pack/icons/fight/2guns.gif
Normal file
After Width: | Height: | Size: 810 B |
BIN
smiley_pack/icons/fight/acid.gif
Normal file
After Width: | Height: | Size: 69 KiB |
BIN
smiley_pack/icons/fight/alienfight.gif
Normal file
After Width: | Height: | Size: 26 KiB |
BIN
smiley_pack/icons/fight/army.gif
Normal file
After Width: | Height: | Size: 3 KiB |