Skip to content

Commit b50acbf

Browse files
committed
Initial commit
0 parents  commit b50acbf

File tree

9 files changed

+600
-0
lines changed

9 files changed

+600
-0
lines changed

.gitattributes

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
# Auto detect text files and perform LF normalization
2+
* text=auto

README.md

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
2+
# HQ CB List for Community Builder
3+
4+
## Description
5+
The purpose of this module is to present a Community Builder list of Users with a custom presentation-template with the possibility of using/presenting all user fields from CB and Joomla.
6+
7+
## Screenshots
8+
9+
Example of presentation in front-end:
10+
![cblistfront](https://user-images.githubusercontent.com/23451105/120665837-6a21d600-c48c-11eb-9815-c243f2310b37.png)
11+
12+
Back-end configuration:
13+
![cblistbackend](https://user-images.githubusercontent.com/23451105/120667634-f84a8c00-c48d-11eb-9cd5-a8e6279bb936.png)
14+
15+
## Configuration
16+
The only mandatory configuration for the module is selecting a CB list to show the users from.
17+
18+
### template examples:
19+
``` html
20+
<div class="yourclasstostyle"><p>[firstname] [lastname]<br/>[cb_yourfiled]</p></div>
21+
<div class="yourclasstostyle">[avatar]<br /> <a href="cb-profile/[user_id]">[Name]</a>
22+
<div class="role"><a href="departmens/[cb_department]">[cb_department]</a>,[cb_role]</div>
23+
```
24+
### rule examples;
25+
A basic set of rules will be created when creating the module.
26+
When creating custom tags make sure the tags that you are using within always have a value. For example see the avatar rule and show_avatar rule.
27+
28+
## Download
29+
[Click here to see available downloads](https://github.com/magnushasselquist/hqcblistmodule/releases)

helper.php

Lines changed: 356 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,356 @@
1+
<?php
2+
/**
3+
* @copyright Copyright (C) 2014. All rights reserved.
4+
* @license GNU General Public License version 2 or later.
5+
* @author Magnus Hasselquist <[email protected]> - http://mintekniskasida.blogspot.se/ till version 2.1.2
6+
* @author Tazzios 2021
7+
*/
8+
9+
// No direct access
10+
defined('_JEXEC') or die;
11+
12+
13+
function checkString(array $arr, $str) {
14+
15+
$str = preg_replace( array('/[^ \w]+/', '/\s+/'), ' ', strtolower($str) ); // Remove Special Characters and extra spaces -or- convert to LowerCase
16+
17+
$matchedString = array_intersect( explode(' ', $str), $arr);
18+
19+
if ( count($matchedString) > 0 ) {
20+
return true;
21+
}
22+
return false;
23+
}
24+
25+
26+
function db_field_replace($before_str, $user_id,$rules,$fields,$search_paramtofind) {
27+
28+
//Get data from current user
29+
$db = JFactory::getDbo();
30+
$query = "select * from #__users inner join #__comprofiler on #__users.id = #__comprofiler.user_id WHERE #__users.id =".$user_id;
31+
// echo $query;
32+
$db->setQuery($query);
33+
$person = $db->loadAssoc();
34+
35+
$after_str = $before_str;
36+
37+
38+
// The while will only run multiple times if you have complex rules like using [canvas] in your avatar htmlcode.
39+
// With this while loop we are certain that all paramtofind will be replaced.
40+
$i=0;
41+
while ((str_replace($search_paramtofind, '', $after_str) !== $after_str) and $i<>5){
42+
$i++; // safety count to stop the loop if the user created one. While will run expected once or twice to replace everything.
43+
44+
foreach ($fields as $field) { //for every field that may be in the before_str
45+
$paramtofind = "[".$field['name']."]";
46+
$fieldtouse = $field['name'];
47+
48+
$datatoinsert = '';
49+
//check if the fieldtouse exist (or is null)
50+
if (isset($person[$fieldtouse]) ) {
51+
$datatoinsert = $person[$fieldtouse];
52+
}
53+
54+
55+
56+
// if it is an image check the approved and create full url
57+
$show = 'yes';
58+
if ($field['type']=='image') {
59+
60+
if ( $person[$fieldtouse.'approved']==0 or (empty($datatoinsert)) ) {
61+
$show = 'no';
62+
} else {
63+
//url to the default canvas images are incorrect in stored in the database
64+
if ($fieldtouse=='canvas') {
65+
$datatoinsert = str_ireplace('Gallery/', 'gallery/canvas/', $datatoinsert);
66+
}
67+
//create the full image path
68+
$datatoinsert = JURI::base(). "images/comprofiler/" .$datatoinsert;
69+
}
70+
}
71+
72+
73+
//check if there is a rule for this field
74+
if (null !==(array_search($fieldtouse,array_column($rules,'tag_name'))) ) {
75+
76+
//loop through the rules to find the rule
77+
foreach ($rules as $rule) {
78+
79+
// If the rule is found:
80+
if (strtolower($rule['tag_name']) == $fieldtouse) {
81+
82+
// check if show still true and data is not empty or that it is a custom tag created in the module.
83+
if ($show == 'yes' and ((!empty($datatoinsert)) or $field['type']=='custom') ) {
84+
$datatoinsert = str_ireplace($paramtofind, $datatoinsert, $rule['htmlcode']);
85+
86+
} else {
87+
$datatoinsert = str_ireplace($paramtofind, $datatoinsert, $rule['htmlcode_no']);
88+
89+
}
90+
}
91+
}
92+
}
93+
94+
$after_str = str_ireplace($paramtofind, $datatoinsert, $after_str); // replace the param name with '' if not found.
95+
96+
} // end for each fields
97+
}// end while
98+
99+
return $after_str;
100+
101+
}
102+
103+
class modcbListHelper
104+
{
105+
/**
106+
* Retrieves the Result
107+
*
108+
* @param array $params An object containing the module parameters
109+
* @access public
110+
*/
111+
112+
113+
114+
public static function getData( $params )
115+
{
116+
117+
//retrieve $rules
118+
$subform = $params->get('rules');
119+
$arr = (array) $subform;
120+
121+
$rules = array();
122+
$i=0;
123+
$additional_names = '';
124+
foreach ($arr as $value)
125+
{
126+
$rules[$i]['tag_name']= strtolower($value->tag_name);
127+
$rules[$i]['htmlcode'] = $value->htmlcode;
128+
$rules[$i]['htmlcode_no'] = $value->htmlcode_no;
129+
130+
$additional_names .= " UNION SELECT '". strtolower($value->tag_name). "' AS name, 'custom' as type ";
131+
132+
$i++;
133+
}
134+
135+
136+
// get all the fields that could possibly be part of template to be replaced to get us something to loop through. Also add id and user_id as fields.
137+
$db = JFactory::getDbo();
138+
$query = "SELECT name, type FROM #__comprofiler_fields WHERE (#__comprofiler_fields.table = '#__users' OR #__comprofiler_fields.table = '#__comprofiler') and name not in ('password','params')
139+
UNION SELECT 'id' AS name, '' as type
140+
UNION SELECT 'user_id' AS name, '' as type ";
141+
// add additional names created in the parameters
142+
$query .= $additional_names ;
143+
// retrieve fields from type images as first. this way other tags in the htmlcode then from the image will also be replaced without additional while loop
144+
$query .= " order by FIELD(type,'datetime','image') desc";
145+
$db->setQuery($query);
146+
$fields = $db->loadAssocList();
147+
148+
// create an one row array with paramtofind to use for the while check
149+
$search_paramtofind = array ();
150+
foreach ($fields as $field) {
151+
$search_paramtofind[] = "[".$field['name']."]";
152+
}
153+
154+
155+
156+
157+
$result=''; //reset result
158+
// Get the parameters
159+
$list_id = $params->get('listid');
160+
$list_orderby = $params->get('orderby');
161+
$list_sortorder = $params->get('sortorder');
162+
$list_template = $params->get('template');
163+
$list_textabove = $params->get('text-above');
164+
$list_textbelow = $params->get('text-below');
165+
$list_debug = $params->get('debug');
166+
167+
// Obtain a database connection
168+
$db = JFactory::getDbo();
169+
// Lets make sure to support åäö
170+
// $query = "SET CHARACTER SET utf8";
171+
// $db->setQuery($query);
172+
173+
// Retrieve the selected list
174+
$query = $db->getQuery(true)
175+
->select('params')
176+
->select('usergroupids')
177+
->from('#__comprofiler_lists')
178+
->where('listid = '. $list_id . ' AND published=1')
179+
->order('ordering ASC');
180+
// echo $query;
181+
$db->setQuery($query);
182+
183+
// Load the List row.
184+
$row = $db->loadAssoc();
185+
$select_sql_raw = $row['params'];
186+
$select_sql =""; //declare variable
187+
188+
// avoid Notice Undefined variable:
189+
$debug_text ="";
190+
191+
if ($list_debug == 1) { $debug_text .= "<p>DEBUG: <pre>".$select_sql_raw."</pre></p>"; }
192+
193+
// Process the filterfields to make ut useful for next query
194+
// CB19 $select_sql = utf8_encode(substr(urldecode($select_sql_raw), 2, -1));
195+
$json_a=json_decode($select_sql_raw,true);
196+
$filters_basic = $json_a['filter_basic'];
197+
$filter_advanced = $json_a['filter_advanced'];
198+
if ($json_a['filter_mode'] == 0) {
199+
$i = 0;
200+
foreach ($filters_basic as $filter) {
201+
if ($filter['column']<>'') {
202+
// If it is not the first filter add AND
203+
if ($i>0) {
204+
$select_sql .= " AND " ;
205+
}
206+
207+
// add qoutes if value is text.
208+
if (!is_numeric($filter['value'])) {
209+
$value = "'".$filter['value']."'";
210+
} else {
211+
$value = $filter['value'];
212+
}
213+
214+
// Replace operators from json if needed else default
215+
switch ($filter['operator']) {
216+
case "<>||ISNULL": // CB Not equal to
217+
218+
$select_sql .= "(".$filter['column'] . "<> ".$value ." OR ". $filter['column'] . " IS NULL)";
219+
break;
220+
221+
case "NOT REGEXP||ISNULL": // CB is not regexp
222+
223+
$select_sql .= "(".$filter['column'] . " NOT REGEXP ".$value ." OR ". $filter['column'] . " IS NULL)";
224+
break;
225+
226+
case "NOT LIKE||ISNULL"; //CB Does not contain
227+
228+
$value = "'%" . trim($value,'\'"') . "%'"; // any combination of ' and "
229+
$select_sql .= "(".$filter['column'] . " NOT LIKE ".$value ." OR ". $filter['column'] . " IS NULL)";
230+
break;
231+
232+
case "LIKE"; //CB Does contain
233+
234+
$value = "'%" . trim($value,'\'"') . "%'"; // any combination of ' and "
235+
$select_sql = "(".$filter['column'] . " LIKE " . $value . ")" ;
236+
break;
237+
238+
case "IN"; //CB IN
239+
240+
$i = 0;
241+
$include = "";
242+
//loop al the values from the in filter value. Fetch original value so no aurrounding qoutes are present
243+
foreach ((explode(",",$filter['value'])) as $value) {
244+
// Start with separator is not first one.
245+
if ($i>0) {
246+
$include .= ", " ;
247+
}
248+
249+
// place qoutes if text
250+
if (!is_numeric($value)) {
251+
$value = "'".$filter['value']."'";
252+
}
253+
254+
$include .= "".$value."";
255+
$i++;
256+
}
257+
$select_sql .= "".$filter['column'] . " IN (". $include .") ";
258+
break;
259+
260+
default:
261+
// Default wat to proces json values to query
262+
$select_sql .= "(".$filter['column']." ".$filter['operator']." ".$value.")";
263+
break;
264+
}
265+
$i++;
266+
}
267+
}
268+
}
269+
270+
else if ($json_a['filter_mode'] == 1) {
271+
$select_sql = $filter_advanced;
272+
}
273+
274+
if ($list_orderby=='list_default' or $list_orderby=='') {
275+
$list_orderby = $json_a['sort_basic'][0]['column'];
276+
}
277+
278+
279+
// Sort order
280+
switch ($list_sortorder) {
281+
case "asc":
282+
$userlistorder = $list_orderby . " " . $list_sortorder;
283+
break;
284+
case "desc":
285+
$userlistorder = $list_orderby . " " . $list_sortorder;
286+
break;
287+
case "random":
288+
$userlistorder = 'rand()';
289+
break;
290+
default:
291+
// Default way to order
292+
$userlistorder = $list_orderby . " " . $json_a['sort_basic'][0]['direction'];
293+
break;
294+
}
295+
296+
// Set a base-sql for connecting users, fields and lists
297+
$usergroupids = str_replace("|*|", ",", $row['usergroupids']); //CMJ ADDED
298+
$usergroupids = trim($usergroupids,','); // prevent that the range starts (or ends) with a comma if you also have selected '--- Select User group (CTR/CMD-Click: multiple)---' at the usergroups
299+
300+
$list_show_unapproved = $json_a['list_show_unapproved'];
301+
$list_show_blocked = $json_a['list_show_blocked'];
302+
$list_show_unconfirmed = $json_a['list_show_unconfirmed'];
303+
$fetch_sql = "SELECT ue.id FROM #__users u JOIN #__user_usergroup_map g ON g.`user_id` = u.`id` JOIN #__comprofiler ue ON ue.`id` = u.`id` WHERE g.group_id IN (".$usergroupids.")";
304+
if ($list_show_blocked == 0) {$fetch_sql.=" AND u.block = 0 ";}
305+
if ($list_show_unapproved == 0) {$fetch_sql.=" AND ue.approved = 1 ";}
306+
if ($list_show_unconfirmed == 0) {$fetch_sql.=" AND ue.confirmed = 1 ";}
307+
308+
309+
// add CB list filters only if there are any
310+
if ($select_sql <>'') $fetch_sql = $fetch_sql . " AND (" . $select_sql . ")";
311+
312+
// echo $fetch_sql . "<br>";
313+
//$fetch_sql .= ' GROUP BY u.id';
314+
//Add ordering if list is configured for that
315+
if ($userlistorder <>'') { $fetch_sql .= " ORDER BY ".$userlistorder; }
316+
317+
//Apply limit
318+
$fetch_sql .= " LIMIT ".$params->get('user-limit');
319+
320+
// autofit or fixed amount of columns
321+
if ($params->get('columns') == 0 ) {
322+
$columns= "auto-fit";
323+
}
324+
else {
325+
$columns= $params->get('columns');
326+
}
327+
328+
$minwidth = "5" ;/* prevent errors and give default value when not is numeric*/
329+
if (is_numeric($params->get('Minwidth'))) {
330+
$minwidth = $params->get('Minwidth') ;
331+
}
332+
333+
$result .= " <div style=\" margin: 0 auto; display: grid; grid-gap: 0.2rem;grid-template-columns: repeat(". $columns .", minmax(".$minwidth."rem, 1fr));\" class=\"cblist\"> " ;
334+
335+
// Now, lets use the final SQL to get all Users from Joomla/CB
336+
$query = $fetch_sql;
337+
338+
if ($list_debug == 1) { $debug_text .= "<p>DEBUG: <pre>".$query."</pre></p>"; }
339+
$db->setQuery($query);
340+
$persons = $db->loadAssocList();
341+
if (!empty($persons)){
342+
foreach ($persons as $person) { //for every person that is a reciever, lets do an email.
343+
// $result .= $person['username']."<br/>";
344+
// Lets loop over the Users and create the output using the Template, replacing [fileds] in Template
345+
$result .= "<div style=\"padding: 5px;overflow-wrap: break-word;\" class=\"cblist-user\" >". db_field_replace($list_template, $person['id'],$rules,$fields,$search_paramtofind) ."</div >" ;
346+
}
347+
} else if ($list_debug == 1) { $debug_text .= "<p>DEBUG: Empty list?!</p>"; }
348+
349+
$result .= " </div >";
350+
351+
$resultcomplete = $list_textabove . $debug_text . $result . $list_textbelow;
352+
return $resultcomplete;
353+
354+
}
355+
}
356+
?>

index.html

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
<html><body bgcolor="#FFFFFF"></body></html>

0 commit comments

Comments
 (0)