make tag autocomplete less scary looking in the editor. If this works out we can simplify and get rid of a huge amount of spaghetti tag logic.

This commit is contained in:
zotlabs 2018-04-24 15:32:24 -07:00
parent a6c42e8756
commit 8face5a66c
3 changed files with 82 additions and 51 deletions

View File

@ -354,7 +354,7 @@ class Acl extends \Zotlabs\Web\Controller {
"name" => $g['name'] . (($type === 'f') ? '' : '+'), "name" => $g['name'] . (($type === 'f') ? '' : '+'),
"id" => urlencode($g['id']) . (($type === 'f') ? '' : '+'), "id" => urlencode($g['id']) . (($type === 'f') ? '' : '+'),
"xid" => $g['hash'], "xid" => $g['hash'],
"link" => $g['nick'], "link" => (($g['nick']) ? $g['nick'] : $g['url']),
"nick" => substr($g['nick'],0,strpos($g['nick'],'@')), "nick" => substr($g['nick'],0,strpos($g['nick'],'@')),
"self" => (intval($g['abook_self']) ? 'abook-self' : ''), "self" => (intval($g['abook_self']) ? 'abook-self' : ''),
"taggable" => 'taggable', "taggable" => 'taggable',
@ -368,7 +368,7 @@ class Acl extends \Zotlabs\Web\Controller {
"name" => $g['name'], "name" => $g['name'],
"id" => urlencode($g['id']), "id" => urlencode($g['id']),
"xid" => $g['hash'], "xid" => $g['hash'],
"link" => $g['nick'], "link" => (($g['nick']) ? $g['nick'] : $g['url']),
"nick" => (($g['nick']) ? substr($g['nick'],0,strpos($g['nick'],'@')) : $g['nick']), "nick" => (($g['nick']) ? substr($g['nick'],0,strpos($g['nick'],'@')) : $g['nick']),
"self" => (intval($g['abook_self']) ? 'abook-self' : ''), "self" => (intval($g['abook_self']) ? 'abook-self' : ''),
"taggable" => '', "taggable" => '',

View File

@ -822,6 +822,14 @@ function get_tags($s) {
} }
} }
// match bracket mentions
if(preg_match_all('/([@!]\{.*?\})/',$s,$match)) {
foreach($match[1] as $mtch) {
$ret[] = $mtch;
}
}
// Match full names against @tags including the space between first and last // Match full names against @tags including the space between first and last
// We will look these up afterward to see if they are full names or not recognisable. // We will look these up afterward to see if they are full names or not recognisable.
@ -2029,18 +2037,33 @@ function undo_post_tagging($s) {
$cnt = preg_match_all('/([@#])(\!*)\[zrl=(.*?)\](.*?)\[\/zrl\]/ism',$s,$matches,PREG_SET_ORDER); $cnt = preg_match_all('/([@#])(\!*)\[zrl=(.*?)\](.*?)\[\/zrl\]/ism',$s,$matches,PREG_SET_ORDER);
if($cnt) { if($cnt) {
foreach($matches as $mtch) { foreach($matches as $mtch) {
$s = str_replace($mtch[0], $mtch[1] . $mtch[2] . quote_tag($mtch[4]),$s); $x = q("select xchan_addr, xchan_url from xchan where xchan_url = '%s' limit 1",
dbesc($mtch[3])
);
if($x) {
$s = str_replace($mtch[0], $mtch[1] . $mtch[2] . '{' . (($x[0]['xchan_addr']) ? $x[0]['xchan_addr'] : $x[0]['xchan_url']) . '}', $s);
}
else {
$s = str_replace($mtch[0], $mtch[1] . $mtch[2] . quote_tag($mtch[4]),$s);
}
} }
} }
// undo forum tags // undo forum tags
$cnt = preg_match_all('/\!\[zrl=(.*?)\](.*?)\[\/zrl\]/ism',$s,$matches,PREG_SET_ORDER); $cnt = preg_match_all('/\!\[zrl=(.*?)\](.*?)\[\/zrl\]/ism',$s,$matches,PREG_SET_ORDER);
if($cnt) { if($cnt) {
foreach($matches as $mtch) { foreach($matches as $mtch) {
$s = str_replace($mtch[0], '!' . quote_tag($mtch[2]),$s); $x = q("select xchan_addr, xchan_url from xchan where xchan_url = '%s' limit 1",
dbesc($mtch[1])
);
if($x) {
$s = str_replace($mtch[0], '!' . '{' . (($x[0]['xchan_addr']) ? $x[0]['xchan_addr'] : $x[0]['xchan_url']) . '}', $s);
}
else {
$s = str_replace($mtch[0], '!' . quote_tag($mtch[2]),$s);
}
} }
} }
return $s; return $s;
} }
@ -2615,53 +2638,66 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $d
$forum = false; $forum = false;
$trailing_plus_name = false; $trailing_plus_name = false;
// @channel+ is a forum or network delivery tag if(substr($name,0,1) === '{' && substr($name,-1,1) === '}') {
$newname = substr($name,1);
if(substr($newname,-1,1) === '+') {
$forum = true;
$newname = substr($newname,0,-1); $newname = substr($newname,0,-1);
$r = q("select * from xchan where xchan_addr = '%s' or xchan_url = '%s' limit 1",
dbesc($newname),
dbesc($newname)
);
} }
// Here we're looking for an address book entry as provided by the auto-completer if(! $r) {
// of the form something+nnn where nnn is an abook_id or the first chars of xchan_hash
// @channel+ is a forum or network delivery tag
// If there's a +nnn in the string make sure there isn't a space preceding it if(substr($newname,-1,1) === '+') {
$forum = true;
$t1 = strpos($newname,' '); $newname = substr($newname,0,-1);
$t2 = strrpos($newname,'+');
if($t1 && $t2 && $t1 < $t2)
$t2 = 0;
if(($t2) && (! $diaspora)) {
//get the id
$tagcid = urldecode(substr($newname,$t2 + 1));
if(strrpos($tagcid,' '))
$tagcid = substr($tagcid,0,strrpos($tagcid,' '));
if(strlen($tagcid) < 16)
$abook_id = intval($tagcid);
//remove the next word from tag's name
if(strpos($name,' ')) {
$name = substr($name,0,strpos($name,' '));
} }
if($abook_id) { // if there was an id // Here we're looking for an address book entry as provided by the auto-completer
// select channel with that id from the logged in user's address book // of the form something+nnn where nnn is an abook_id or the first chars of xchan_hash
$r = q("SELECT * FROM abook left join xchan on abook_xchan = xchan_hash
WHERE abook_id = %d AND abook_channel = %d LIMIT 1",
intval($abook_id), // If there's a +nnn in the string make sure there isn't a space preceding it
intval($profile_uid)
); $t1 = strpos($newname,' ');
} $t2 = strrpos($newname,'+');
else {
$r = q("SELECT * FROM xchan if($t1 && $t2 && $t1 < $t2)
WHERE xchan_hash like '%s%%' LIMIT 1", $t2 = 0;
dbesc($tagcid)
); if(($t2) && (! $diaspora)) {
//get the id
$tagcid = urldecode(substr($newname,$t2 + 1));
if(strrpos($tagcid,' '))
$tagcid = substr($tagcid,0,strrpos($tagcid,' '));
if(strlen($tagcid) < 16)
$abook_id = intval($tagcid);
//remove the next word from tag's name
if(strpos($name,' ')) {
$name = substr($name,0,strpos($name,' '));
}
if($abook_id) { // if there was an id
// select channel with that id from the logged in user's address book
$r = q("SELECT * FROM abook left join xchan on abook_xchan = xchan_hash
WHERE abook_id = %d AND abook_channel = %d LIMIT 1",
intval($abook_id),
intval($profile_uid)
);
}
else {
$r = q("SELECT * FROM xchan
WHERE xchan_hash like '%s%%' LIMIT 1",
dbesc($tagcid)
);
}
} }
} }

View File

@ -84,13 +84,8 @@ function editor_replace(item) {
} }
// $2 ensures that prefix (@,@!) is preserved // $2 ensures that prefix (@,@!) is preserved
var id = item.id;
// 16 chars of hash should be enough. Full hash could be used if it can be done in a visually appealing way.
// 16 chars is also the minimum length in the backend (otherwise it's interpreted as a local id).
if(id.length > 16)
id = item.id.substring(0,16);
return '$1$2' + item.nick.replace(' ', '') + '+' + id + ' '; return '$1$2{' + item.link + '} ';
} }
function basic_replace(item) { function basic_replace(item) {