Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/matomo-org/matomo.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormatt <matt@59fd770c-687e-43c8-a1e3-f5a4ff64c105>2010-06-14 21:31:41 +0400
committermatt <matt@59fd770c-687e-43c8-a1e3-f5a4ff64c105>2010-06-14 21:31:41 +0400
commitaf67d984eea3f1beb0dcc3aa7a9fe4bf9fd31985 (patch)
treefbd3f9fc61288c491226962c6d4cf317dc0fb903 /plugins/Goals
parentdacce19245f89c46d15d75a481240fc10d64e6f2 (diff)
Refs #774
* Adding table by segments in the Goal Overview and in each specific Goal report. Data table is ajax loaded when the segment is clicked. In the 'Goal overview', the datatable displays all goals (this can be a lot of columns). In a specific goal tab, the datatable will only show columns for the sum of all goals and for this specific goal. * The 'Goals' datatable is now showing, for each goal: conversions, conversion rate and revenue per visit * Adding widgets for the Goals plugins: Goals overview, and one widget for each goal report
Diffstat (limited to 'plugins/Goals')
-rw-r--r--plugins/Goals/Controller.php236
-rw-r--r--plugins/Goals/Goals.php9
-rw-r--r--plugins/Goals/templates/add_edit_goal.tpl25
-rw-r--r--plugins/Goals/templates/form_add_goal.tpl12
-rw-r--r--plugins/Goals/templates/goals.css32
-rw-r--r--plugins/Goals/templates/list_goal_edit.tpl3
-rw-r--r--plugins/Goals/templates/list_top_segment.tpl16
-rw-r--r--plugins/Goals/templates/overview.tpl40
-rw-r--r--plugins/Goals/templates/release_notes.tpl29
-rw-r--r--plugins/Goals/templates/single_goal.tpl34
-rw-r--r--plugins/Goals/templates/table_by_segment.tpl74
-rw-r--r--plugins/Goals/templates/title_and_evolution_graph.tpl5
12 files changed, 339 insertions, 176 deletions
diff --git a/plugins/Goals/Controller.php b/plugins/Goals/Controller.php
index 15afeb8b5a..662c21698c 100644
--- a/plugins/Goals/Controller.php
+++ b/plugins/Goals/Controller.php
@@ -18,14 +18,35 @@ class Piwik_Goals_Controller extends Piwik_Controller
{
const CONVERSION_RATE_PRECISION = 1;
- function __construct()
+ protected $goalColumnNameToLabel = array(
+ 'nb_conversions' => 'Goals_ColumnConversions',
+ 'conversion_rate'=> 'Goals_ColumnConversionRate',
+ 'revenue' => 'Goals_ColumnRevenue',
+ );
+
+ public function __construct()
{
parent::__construct();
$this->idSite = Piwik_Common::getRequestVar('idSite');
$this->goals = Piwik_Goals_API::getInstance()->getGoals($this->idSite);
}
- function goalReport()
+ public function widgetGoalReport()
+ {
+ $view = $this->getGoalReportView();
+ $view->displayFullReport = false;
+ echo $view->render();
+ }
+
+ public function goalReport()
+ {
+ $view = $this->getGoalReportView();
+ $view->displayFullReport = true;
+ $view->goalSegments = $this->getAvailableGoalSegments();
+ echo $view->render();
+ }
+
+ protected function getGoalReportView()
{
$idGoal = Piwik_Common::getRequestVar('idGoal', null, 'int');
if(!isset($this->goals[$idGoal]))
@@ -41,10 +62,10 @@ class Piwik_Goals_Controller extends Piwik_Controller
{
$view->$name = $value;
}
- $view->name = $goalDefinition['name'];
- $view->title = $goalDefinition['name'] . ' - Conversions';
+ $view->idGoal = $idGoal;
+ $view->goalName = $goalDefinition['name'];
$view->graphEvolution = $this->getEvolutionGraph(true, array(Piwik_Goals::getRecordName('nb_conversions', $idGoal)), $idGoal);
- $view->nameGraphEvolution = 'GoalsgetEvolutionGraph';
+ $view->nameGraphEvolution = 'GoalsgetEvolutionGraph'.$idGoal;
$view->topSegments = $this->getTopSegments($idGoal);
// conversion rate for new and returning visitors
@@ -52,79 +73,31 @@ class Piwik_Goals_Controller extends Piwik_Controller
$view->conversion_rate_returning = round( $request->process(), self::CONVERSION_RATE_PRECISION );
$request = new Piwik_API_Request("method=Goals.getConversionRateNewVisitors&format=original");
$view->conversion_rate_new = round( $request->process(), self::CONVERSION_RATE_PRECISION );
-
- $verticalSlider = array();
- // string label
- // array parameters to ajax call on click (module, action)
- // specific order
- // (intermediate labels)
- // automatically load the first from the list, highlights it
- $view->tableByConversion = Piwik_FrontController::getInstance()->fetchDispatch('Referers', 'getKeywords', array(false, 'tableGoals'));
- echo $view->render();
+ return $view;
}
- protected function getTopSegments($idGoal)
+ public function index()
{
- $columnNbConversions = 'goal_'.$idGoal.'_nb_conversions';
- $columnConversionRate = 'goal_'.$idGoal.'_conversion_rate';
-
- $topSegmentsToLoad = array(
- 'country' => 'UserCountry.getCountry',
- 'keyword' => 'Referers.getKeywords',
- 'website' => 'Referers.getWebsites',
- );
-
- $topSegments = array();
- foreach($topSegmentsToLoad as $segmentName => $apiMethod)
- {
- $request = new Piwik_API_Request("method=$apiMethod
- &format=original
- &filter_update_columns_when_show_all_goals=1
- &filter_sort_order=desc
- &filter_sort_column=$columnNbConversions
- &filter_limit=3");
- $datatable = $request->process();
- $topSegment = array();
- foreach($datatable->getRows() as $row)
- {
- $conversions = $row->getColumn($columnNbConversions);
- if($conversions > 0)
- {
- $topSegment[] = array (
- 'name' => $row->getColumn('label'),
- 'nb_conversions' => $conversions,
- 'conversion_rate' => $row->getColumn($columnConversionRate),
- 'metadata' => $row->getMetadata(),
- );
- }
- }
- $topSegments[$segmentName] = $topSegment;
- }
- return $topSegments;
+ $view = $this->getOverviewView();
+ $view->goalsJSON = json_encode($this->goals);
+ $view->goalSegments = $this->getAvailableGoalSegments();
+ $view->userCanEditGoals = Piwik::isUserHasAdminAccess($this->idSite);
+ $view->displayFullReport = true;
+ echo $view->render();
}
- protected function getMetricsForGoal($idGoal)
+ public function widgetGoalsOverview( )
{
- $request = new Piwik_API_Request("method=Goals.get&format=original&idGoal=$idGoal");
- $datatable = $request->process();
- $dataRow = $datatable->getFirstRow();
- return array (
- 'id' => $idGoal,
- 'nb_conversions' => $dataRow->getColumn(Piwik_Goals::getRecordName('nb_conversions', $idGoal)),
- 'conversion_rate' => round($dataRow->getColumn(Piwik_Goals::getRecordName('conversion_rate', $idGoal)), 1),
- 'revenue' => $dataRow->getColumn(Piwik_Goals::getRecordName('revenue', $idGoal)),
- 'urlSparklineConversions' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('nb_conversions', $idGoal)), 'idGoal' => $idGoal)),
- 'urlSparklineConversionRate' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('conversion_rate', $idGoal)), 'idGoal' => $idGoal)),
- 'urlSparklineRevenue' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('revenue', $idGoal)), 'idGoal' => $idGoal)),
- );
+ $view = $this->getOverviewView();
+ $view->displayFullReport = false;
+ echo $view->render();
}
- function index()
+ protected function getOverviewView()
{
$view = Piwik_View::factory('overview');
$this->setGeneralVariablesView($view);
- $view->title = 'All goals - evolution';
$view->graphEvolution = $this->getEvolutionGraph(true, array(Piwik_Goals::getRecordName('nb_conversions')));
$view->nameGraphEvolution = 'GoalsgetEvolutionGraph';
@@ -149,12 +122,28 @@ class Piwik_Goals_Controller extends Piwik_Controller
$view->goalMetrics = $goalMetrics;
$view->goals = $this->goals;
- $view->goalsJSON = json_encode($this->goals);
- $view->userCanEditGoals = Piwik::isUserHasAdminAccess($this->idSite);
- echo $view->render();
+ return $view;
+ }
+
+ public function getLastNbConversionsGraph( $fetch = false )
+ {
+ $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getConversions');
+ return $this->renderView($view, $fetch);
}
- function addNewGoal()
+ public function getLastConversionRateGraph( $fetch = false )
+ {
+ $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getConversionRate');
+ return $this->renderView($view, $fetch);
+ }
+
+ public function getLastRevenueGraph( $fetch = false )
+ {
+ $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getRevenue');
+ return $this->renderView($view, $fetch);
+ }
+
+ public function addNewGoal()
{
$view = Piwik_View::factory('add_new_goal');
$this->setGeneralVariablesView($view);
@@ -163,12 +152,6 @@ class Piwik_Goals_Controller extends Piwik_Controller
echo $view->render();
}
- protected $goalColumnNameToLabel = array(
- 'nb_conversions' => 'Goals_ColumnConversions',
- 'conversion_rate'=> 'Goals_ColumnConversionRate',
- 'revenue' => 'Goals_ColumnRevenue',
- );
-
public function getEvolutionGraph( $fetch = false, $columns = false, $idGoal = false)
{
if(empty($columns))
@@ -197,7 +180,7 @@ class Piwik_Goals_Controller extends Piwik_Controller
if(!empty($idGoal) && isset($this->goals[$idGoal]))
{
$goalName = $this->goals[$idGoal]['name'];
- $columnTranslation = "$columnTranslation (goal \"$goalName\")";
+ $columnTranslation = "$columnTranslation (".Piwik_Translate('Goals_GoalX', "$goalName").")";
}
$view->setColumnTranslation($columnName, $columnTranslation);
}
@@ -205,21 +188,100 @@ class Piwik_Goals_Controller extends Piwik_Controller
return $this->renderView($view, $fetch);
}
- function getLastNbConversionsGraph( $fetch = false )
+ protected function getAvailableGoalSegments()
{
- $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getConversions');
- return $this->renderView($view, $fetch);
+ return array(
+ Piwik_Translate('Referers_Referers') => array(
+ array(
+ 'name' => Piwik_Translate('Referers_Keywords'),
+ 'module' => 'Referers',
+ 'action' => 'getKeywords',
+ ),
+ array(
+ 'name' => Piwik_Translate('Referers_SearchEngines'),
+ 'module' => 'Referers',
+ 'action' => 'getSearchEngines',
+ ),
+ array(
+ 'name' => Piwik_Translate('Referers_Websites'),
+ 'module' => 'Referers',
+ 'action' => 'getWebsites',
+ ),
+ array(
+ 'name' => Piwik_Translate('Referers_Campaigns'),
+ 'module' => 'Referers',
+ 'action' => 'getCampaigns',
+ ),
+ ),
+
+ Piwik_Translate('UserCountry_Location') => array(
+ array(
+ 'name' => Piwik_Translate('UserCountry_Country'),
+ 'module' => 'UserCountry',
+ 'action' => 'getCountry',
+ ),
+ array(
+ 'name' => Piwik_Translate('UserCountry_Continent'),
+ 'module' => 'UserCountry',
+ 'action' => 'getContinent',
+ ),
+ ),
+ );
}
- function getLastConversionRateGraph( $fetch = false )
+ protected function getTopSegments($idGoal)
{
- $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getConversionRate');
- return $this->renderView($view, $fetch);
+ $columnNbConversions = 'goal_'.$idGoal.'_nb_conversions';
+ $columnConversionRate = 'goal_'.$idGoal.'_conversion_rate';
+
+ $topSegmentsToLoad = array(
+ 'country' => 'UserCountry.getCountry',
+ 'keyword' => 'Referers.getKeywords',
+ 'website' => 'Referers.getWebsites',
+ );
+
+ $topSegments = array();
+ foreach($topSegmentsToLoad as $segmentName => $apiMethod)
+ {
+ $request = new Piwik_API_Request("method=$apiMethod
+ &format=original
+ &filter_update_columns_when_show_all_goals=1
+ &filter_sort_order=desc
+ &filter_sort_column=$columnNbConversions
+ &filter_limit=3");
+ $datatable = $request->process();
+ $topSegment = array();
+ foreach($datatable->getRows() as $row)
+ {
+ $conversions = $row->getColumn($columnNbConversions);
+ if($conversions > 0)
+ {
+ $topSegment[] = array (
+ 'name' => $row->getColumn('label'),
+ 'nb_conversions' => $conversions,
+ 'conversion_rate' => $row->getColumn($columnConversionRate),
+ 'metadata' => $row->getMetadata(),
+ );
+ }
+ }
+ $topSegments[$segmentName] = $topSegment;
+ }
+ return $topSegments;
}
-
- function getLastRevenueGraph( $fetch = false )
+
+ protected function getMetricsForGoal($idGoal)
{
- $view = $this->getLastUnitGraph($this->pluginName, __FUNCTION__, 'Goals.getRevenue');
- return $this->renderView($view, $fetch);
+ $request = new Piwik_API_Request("method=Goals.get&format=original&idGoal=$idGoal");
+ $datatable = $request->process();
+ $dataRow = $datatable->getFirstRow();
+ return array (
+ 'id' => $idGoal,
+ 'nb_conversions' => $dataRow->getColumn(Piwik_Goals::getRecordName('nb_conversions', $idGoal)),
+ 'conversion_rate' => round($dataRow->getColumn(Piwik_Goals::getRecordName('conversion_rate', $idGoal)), 1),
+ 'revenue' => $dataRow->getColumn(Piwik_Goals::getRecordName('revenue', $idGoal)),
+ 'urlSparklineConversions' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('nb_conversions', $idGoal)), 'idGoal' => $idGoal)),
+ 'urlSparklineConversionRate' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('conversion_rate', $idGoal)), 'idGoal' => $idGoal)),
+ 'urlSparklineRevenue' => $this->getUrlSparkline('getEvolutionGraph', array('columns' => array(Piwik_Goals::getRecordName('revenue', $idGoal)), 'idGoal' => $idGoal)),
+ );
}
}
diff --git a/plugins/Goals/Goals.php b/plugins/Goals/Goals.php
index 00e2591d46..6ab468f09e 100644
--- a/plugins/Goals/Goals.php
+++ b/plugins/Goals/Goals.php
@@ -59,6 +59,15 @@ class Piwik_Goals extends Piwik_Plugin
function addWidgets()
{
+ Piwik_AddWidget('Goals_Goals', 'Goals_GoalsOverview', 'Goals', 'widgetGoalsOverview');
+ $goals = Piwik_Tracker_GoalManager::getGoalDefinitions(Piwik_Common::getRequestVar('idSite'));
+ if(count($goals) > 0)
+ {
+ foreach($goals as $goal)
+ {
+ Piwik_AddWidget('Goals_Goals', $goal['name'], 'Goals', 'widgetGoalReport', array('idGoal' => $goal['idgoal']));
+ }
+ }
}
function addMenus()
diff --git a/plugins/Goals/templates/add_edit_goal.tpl b/plugins/Goals/templates/add_edit_goal.tpl
index a2d30eb702..9153559f8c 100644
--- a/plugins/Goals/templates/add_edit_goal.tpl
+++ b/plugins/Goals/templates/add_edit_goal.tpl
@@ -1,3 +1,4 @@
+<br/><br/><br/>
<div id="AddEditGoals">
{if isset($onlyShowAddNewGoal)}
@@ -24,20 +25,20 @@
<script type="text/javascript">
var mappingMatchTypeName = {ldelim}
- "url": "URL",
- "file": "filename",
- "external_website": "external website URL"
+ "url": "{'Goals_URL'|translate|escape}",
+ "file": "{'Goals_Filename'|translate|escape}",
+ "external_website": "{'Goals_ExternalWebsiteUrl'|translate|escape}"
{rdelim};
var mappingMatchTypeExamples = {ldelim}
- "url": "{'General_ForExampleShort'|translate} {'Goals_Contains'|translate:"'checkout/confirmation'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_IsExactly'|translate:"'http://example.com/thank-you.html'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_MatchesExpression'|translate:"matches the expression '(.*)\\\/demo\\\/(.*)'"}",
- "file": "{'General_ForExampleShort'|translate} {'Goals_Contains'|translate:"'files/brochure.pdf'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_IsExactly'|translate:"'http://example.com/files/brochure.pdf'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_MatchesExpression'|translate:"'(.*)\\\.zip'"}",
- "external_website": "{'General_ForExampleShort'|translate} {'Goals_Contains'|translate:"'amazon.com'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_IsExactly'|translate:"'http://mypartner.com/landing.html'"} \
- <br />{'General_ForExampleShort'|translate} {'Goals_MatchesExpression'|translate:"'http://www.amazon.com\\\/(.*)\\\/yourAffiliateId'"}"
+ "url": "{'General_ForExampleShort'|translate} {'Goals_Contains'|translate:"'checkout/confirmation'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_IsExactly'|translate:"'http://example.com/thank-you.html'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_MatchesExpression'|translate:"matches the expression '(.*)\\\/demo\\\/(.*)'"|escape}",
+ "file": "{'General_ForExampleShort'|translate|escape} {'Goals_Contains'|translate:"'files/brochure.pdf'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_IsExactly'|translate:"'http://example.com/files/brochure.pdf'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_MatchesExpression'|translate:"'(.*)\\\.zip'"|escape}",
+ "external_website": "{'General_ForExampleShort'|translate|escape} {'Goals_Contains'|translate:"'amazon.com'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_IsExactly'|translate:"'http://mypartner.com/landing.html'"|escape} \
+ <br />{'General_ForExampleShort'|translate|escape} {'Goals_MatchesExpression'|translate:"'http://www.amazon.com\\\/(.*)\\\/yourAffiliateId'"|escape}"
{rdelim};
bindGoalForm();
diff --git a/plugins/Goals/templates/form_add_goal.tpl b/plugins/Goals/templates/form_add_goal.tpl
index c8265b0244..76350d9f40 100644
--- a/plugins/Goals/templates/form_add_goal.tpl
+++ b/plugins/Goals/templates/form_add_goal.tpl
@@ -1,16 +1,6 @@
-{literal}
-<style>
-.goalInlineHelp{
- color:#9B9B9B;
-}
-.tableForm {
- width:700px;
-}
-</style>
-{/literal}
<span id='GoalForm' style="display:none;">
<form>
-<table class="tableForm">
+<table class="tableForm tableFormGoals">
<tbody>
<tr>
<td>{'Goals_GoalName'|translate} </td>
diff --git a/plugins/Goals/templates/goals.css b/plugins/Goals/templates/goals.css
new file mode 100644
index 0000000000..1414b52450
--- /dev/null
+++ b/plugins/Goals/templates/goals.css
@@ -0,0 +1,32 @@
+ul.ulGoalTopElements {
+ list-style-type:circle;
+ margin-left:30px;
+}
+.ulGoalTopElements a {
+ text-decoration:none;
+ color:#0033CC;
+ border-bottom:1px dotted #0033CC;
+ line-height:2em;
+}
+.goalTopElement {
+ border-bottom:1px dotted;
+}
+.segmentSelector ul {
+ list-style:circle outside none;
+ margin-left:30px;
+}
+.segmentSelector ul li .segment{
+ cursor:pointer;
+ border-bottom:1px dotted black;
+}
+.segmentSelector ul li.activeSegment .segment {
+ font-weight: bold;
+ border:0;
+}
+
+.goalInlineHelp {
+ color:#9B9B9B;
+}
+.tableFormGoals {
+ width:700px;
+} \ No newline at end of file
diff --git a/plugins/Goals/templates/list_goal_edit.tpl b/plugins/Goals/templates/list_goal_edit.tpl
index b5f15f7e84..805f3c2277 100644
--- a/plugins/Goals/templates/list_goal_edit.tpl
+++ b/plugins/Goals/templates/list_goal_edit.tpl
@@ -1,6 +1,5 @@
-
<span id='EditGoals' style="display:none;">
- <table class="tableForm">
+ <table class="tableForm tableFormGoals">
<thead style="font-weight:bold">
<td>Id</td>
<td>{'Goals_GoalName'|translate}</td>
diff --git a/plugins/Goals/templates/list_top_segment.tpl b/plugins/Goals/templates/list_top_segment.tpl
index acb9bdebd9..4e1ca412d3 100644
--- a/plugins/Goals/templates/list_top_segment.tpl
+++ b/plugins/Goals/templates/list_top_segment.tpl
@@ -1,10 +1,10 @@
{foreach from=$topSegment item=element name=topGoalElements}
-{assign var=goal_nb_conversion value=$element.nb_conversions}
-{assign var=goal_conversion_rate value=$element.conversion_rate}
-<span class='goalTopElement' title='{'Goals_Conversions'|translate:"<b>$goal_nb_conversion</b>"},
- {'Goals_ConversionRate'|translate:"<b>$goal_conversion_rate%</b>"}'>
-{$element.name}</span>
-{logoHtml metadata=$element.metadata alt=$element.name}
-{if $smarty.foreach.topGoalElements.iteration == $smarty.foreach.topGoalElements.total-1} and {elseif $smarty.foreach.topGoalElements.iteration < $smarty.foreach.topGoalElements.total-1}, {else}{/if}
-{/foreach} {* (<a href=''>more</a>) *}
+ {assign var=goal_nb_conversion value=$element.nb_conversions}
+ {assign var=goal_conversion_rate value=$element.conversion_rate}
+ <span class='goalTopElement' title='{'Goals_Conversions'|translate:"<b>$goal_nb_conversion</b>"},
+ {'Goals_ConversionRate'|translate:"<b>$goal_conversion_rate%</b>"}'>
+ {$element.name}</span>
+ {logoHtml metadata=$element.metadata alt=$element.name}
+ {if $smarty.foreach.topGoalElements.iteration == $smarty.foreach.topGoalElements.total-1} and {elseif $smarty.foreach.topGoalElements.iteration < $smarty.foreach.topGoalElements.total-1}, {else}{/if}
+{/foreach} \ No newline at end of file
diff --git a/plugins/Goals/templates/overview.tpl b/plugins/Goals/templates/overview.tpl
index 04afb70adb..28fa30cd71 100644
--- a/plugins/Goals/templates/overview.tpl
+++ b/plugins/Goals/templates/overview.tpl
@@ -1,23 +1,31 @@
+<link rel="stylesheet" type="text/css" href="plugins/Goals/templates/goals.css" />
{include file="Goals/templates/title_and_evolution_graph.tpl"}
{foreach from=$goalMetrics item=goal}
-{assign var=nb_conversions value=$goal.nb_conversions}
-{assign var=conversion_rate value=$goal.conversion_rate}
-<h2 style="padding-top: 30px;">{$goal.name} (goal)</h2>
-<div id='leftcolumn'>
- <div class="sparkline">{sparkline src=$goal.urlSparklineConversions}
- {'Goals_Conversions'|translate:"<strong>$nb_conversions</strong>"}</div>
-</div>
-<div id='rightcolumn'>
- <div class="sparkline">{sparkline src=$goal.urlSparklineConversionRate}
- {'Goals_ConversionRate'|translate:"<strong>$conversion_rate%</strong>"}</div>
- {* (<a href=''>{'General_More'|translate}</a>) *}
-</div>
+ {assign var=nb_conversions value=$goal.nb_conversions}
+ {assign var=conversion_rate value=$goal.conversion_rate}
+ {assign var=name value=$goal.name}
+ {if $displayFullReport}<a href="javascript:broadcast.propagateAjax('module=Goals&action=goalReport&idGoal={$goal.id}')">{/if}
+ <h2 style="padding-top: 30px;">{'Goals_GoalX'|translate:"'$name'"}</h2>
+ {if $displayFullReport}</a>{/if}
+ <div id='leftcolumn'>
+ <div class="sparkline">{sparkline src=$goal.urlSparklineConversions}
+ {'Goals_Conversions'|translate:"<strong>$nb_conversions</strong>"}</div>
+ </div>
+ <div id='rightcolumn'>
+ <div class="sparkline">{sparkline src=$goal.urlSparklineConversionRate}
+ {'Goals_ConversionRate'|translate:"<strong>$conversion_rate%</strong>"}</div>
+ </div>
{/foreach}
-{if $userCanEditGoals}
- {include file=Goals/templates/add_edit_goal.tpl}
-{/if}
+{if $displayFullReport}
-{include file="Goals/templates/release_notes.tpl}
+ {include file="Goals/templates/table_by_segment.tpl"}
+
+ {if $userCanEditGoals}
+ {include file=Goals/templates/add_edit_goal.tpl}
+ {/if}
+
+ {include file="Goals/templates/release_notes.tpl}
+{/if} \ No newline at end of file
diff --git a/plugins/Goals/templates/release_notes.tpl b/plugins/Goals/templates/release_notes.tpl
index d8db019f9b..fc64259c0b 100644
--- a/plugins/Goals/templates/release_notes.tpl
+++ b/plugins/Goals/templates/release_notes.tpl
@@ -7,31 +7,28 @@ The Goal Tracking Plugin is in alpha release. There is more coming soon!
Give us Feedback!
If you find any other bug, or if you have suggestions, please send us a message using the "Give us feedback" link at the top of the Piwik pages.
-
Work left to do on the Goal Tracking plugin:
-- The Goal Report page will display conversion table by search engines, country, keyword, campaign, etc.
-- Contemplate adding goal conversions per landing page? If we add Goals per landing page, what page is used for goals that are triggered using piwikTracker.trackGoal in javascript?
-- The Goal Overview page will link to a Goal Report page with a "(more)" link that will ajax reload the page
-- Provide widgets for the dashboard, general goal overview, and one widget for each goal. With: graph evolution, sparklines. Widget with top segments for each goal.
-- Add visits with conversion sparkline in VisitsSummary overview
-- Add link under goal conversion to full goal reports (optional display)
-- Internationalization of all strings i18n
+- Contemplate adding goal conversions per landing page? If we add Goals per landing page,
+what page is used for goals that are triggered using piwikTracker.trackGoal in javascript?
- Provide documentation, screenshots, blog post + add screenshot and inline help in "Add a New Goal"
-- N/A% should be n/a
- Way to test a URL against the regex
- Test summary row works ok with subtables campaigns
-- Numeric records by the goal plugin can contain a lot of value=0 rows. Instead, we should only record the numeric value if it is not zero, and assume zero when not found.
-- The goal table, by segment, for example goal conversions by country, should really display number of conversions as well as the current "conversion rate" by goal. Having the absolute number for each country / search engine / etc. is critical.
+- Numeric records by the goal plugin can contain a lot of value=0 rows. Instead,
+we should only record the numeric value if it is not zero, and assume zero when not found.
+- Add visits with conversion sparkline in VisitsSummary overview
Known bugs
-- Outlink trailing slash is automatically deleted from the URL, there would be a problem when trying to exact match a URL with trailing slash
-- see bug described in http://forum.piwik.org/index.php?showtopic=150
+- Goal conversions by hour are not accurate (no timezone conversion)
+- Outlink trailing slash is automatically deleted from the URL, there would be a problem
+when trying to exact match a URL with trailing slash
Feature requests
-- need to clarify that goals are triggered once per visit max, but can be triggered multiple times by one unique visitor > need option to force only once per uniq visitor? (ie. e-commerce transaction)
+- need to clarify that goals are triggered once per visit max, but can be triggered multiple
+times by one unique visitor > need option to force only once per uniq visitor? (ie. e-commerce transaction)
- GeoIp compatibility, archive goals by city, country? see archiveDayAggregateGoals
- Goal conversions, revenue, etc. by hour
-- I would like to be able to plot conversions, for a given keyword/website, over the last N days/weeks/etc. See #534
-- when entering the regex to detect as a goal, we could query the piwik API for this regex and list all URLs that match the regex; allows for an easy debug/check that the regex is correct and will be triggererd when expected
+- when entering the regex to detect as a goal, we could query the piwik API for this regex
+and list all URLs that match the regex; allows for an easy debug/check that the regex is correct
+and will be triggered when expected
Refs #774 \ No newline at end of file
diff --git a/plugins/Goals/templates/single_goal.tpl b/plugins/Goals/templates/single_goal.tpl
index 47ca1c4654..41968df30e 100644
--- a/plugins/Goals/templates/single_goal.tpl
+++ b/plugins/Goals/templates/single_goal.tpl
@@ -1,3 +1,4 @@
+<link rel="stylesheet" type="text/css" href="plugins/Goals/templates/goals.css" />
{include file="Goals/templates/title_and_evolution_graph.tpl"}
<div style="clear:both;"></div>
@@ -10,31 +11,18 @@
<li>{'Goals_ReturningVisitorsConversionRateIs'|translate:"<b>$conversion_rate_returning%</b>"}, {'Goals_NewVisitorsConversionRateIs'|translate:"<b>$conversion_rate_new%</b>"}</li>
</ul>
{/if}
-<hr />
-{$tableByConversion}
-<hr />
+
{literal}
-<style>
-ul.ulGoalTopElements {
- list-style-type:circle;
- margin-left:30px;
-}
-.ulGoalTopElements a {
- text-decoration:none;
- color:#0033CC;
- border-bottom:1px dotted #0033CC;
- line-height:2em;
-}
-.goalTopElement {
- border-bottom:1px dotted;
-}
-</style>
-<script>
+<script type="text/javascript">
$(document).ready( function() {
- $('.goalTopElement')
- .tooltip()
- ;
- });
+ $('.goalTopElement').tooltip();
+});
</script>
{/literal}
+
+{if $displayFullReport}
+ {if $nb_conversions > 0}
+ {include file="Goals/templates/table_by_segment.tpl"}
+ {/if}
+{/if} \ No newline at end of file
diff --git a/plugins/Goals/templates/table_by_segment.tpl b/plugins/Goals/templates/table_by_segment.tpl
new file mode 100644
index 0000000000..14abc4031c
--- /dev/null
+++ b/plugins/Goals/templates/table_by_segment.tpl
@@ -0,0 +1,74 @@
+<br/>
+<h2 id='titleGoalsBySegment'>{if isset($idGoal)}
+ {'Goals_GoalConversionsBySegment'|translate:$goalName}
+ {else}{'Goals_ConversionsOverviewBySegment'|translate}{/if}</h2>
+
+<div class='segmentSelector' style='float: left;width: 220px;padding-left: 10px;height:450px'>
+ {foreach from=$goalSegments key=segmentFamilyName item=segments}
+ {'Goals_ViewGoalsBySegment'|translate:$segmentFamilyName}
+ <ul>
+ {foreach from=$segments item=segment}
+ <li title='{'Goals_ViewGoalsBySegment'|translate:$segment.name}' class='goalSegment' module='{$segment.module}' action='{$segment.action}'>
+ <span class='segment'>{$segment.name}</span>
+ </li>
+ {/foreach}
+ </ul>
+ <br/>
+ {/foreach}
+</div>
+
+<div style='float: left;'>
+ {ajaxLoadingDiv id=tableGoalsLoading}
+
+ <div id='tableGoalsBySegment'></div>
+</div>
+<div style='clear:both'></div>
+{literal}
+<script type="text/javascript">
+$(document).ready( function() {
+
+ var countLoaded = 0;
+ /*
+ * For each 'segment' in the list, a click will trigger an ajax request to load the datatable
+ * showing Goals metrics (conversion, conv. rates, revenue) for this segment
+ */
+ $('.goalSegment').click( function() {
+ var self = this;
+ $('.goalSegment').removeClass('activeSegment');
+ $(this).addClass('activeSegment');
+ var module = $(this).attr('module');
+ var action = $(this).attr('action');
+ widgetUniqueId = module+action;
+ self.expectedWidgetUniqueId = widgetUniqueId;
+
+ var widgetParameters = {
+ 'module': module,
+ 'action': action,
+ 'viewDataTable': 'tableGoals',
+ 'idGoal': broadcast.getValueFromHash('idGoal')
+ };
+ var onWidgetLoadedCallback = function (response) {
+ if(widgetUniqueId != self.expectedWidgetUniqueId) {
+ return;
+ }
+ $('#tableGoalsBySegment').html($(response));
+ $('#tableGoalsLoading').hide();
+ $('#tableGoalsBySegment').show();
+
+ countLoaded++;
+ // only scroll down to the loaded datatable if this is not the first one
+ // otherwise, screen would jump down to the table when loading the report
+ if(countLoaded > 1)
+ {
+ $.scrollTo("#titleGoalsBySegment", 400);
+ }
+ };
+ $('#tableGoalsBySegment').hide();
+ $('#tableGoalsLoading').show();
+ ajaxRequest = widgetsHelper.getLoadWidgetAjaxRequest(widgetUniqueId, widgetParameters, onWidgetLoadedCallback);
+ $.ajax(ajaxRequest);
+ });
+ $('.goalSegment').first().click();
+});
+</script>
+{/literal}
diff --git a/plugins/Goals/templates/title_and_evolution_graph.tpl b/plugins/Goals/templates/title_and_evolution_graph.tpl
index 373e1d3a78..0ac5707d00 100644
--- a/plugins/Goals/templates/title_and_evolution_graph.tpl
+++ b/plugins/Goals/templates/title_and_evolution_graph.tpl
@@ -1,7 +1,10 @@
<script type="text/javascript" src="plugins/CoreHome/templates/sparkline.js"></script>
<a name="evolutionGraph" graphId="{$nameGraphEvolution}"></a>
-<h2>{$title}</h2>
+
+{if $displayFullReport}
+ <h2>{if isset($goalName)}{'Goals_GoalX'|translate:$goalName}{else}{'Goals_GoalsOverview'|translate}{/if}</h2>
+{/if}
{$graphEvolution}
<div id='leftcolumn'>