blob: eae008d6d967fafe941d8e6c93205d75987c82d5 [file] [log] [blame]
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<!-- NewPage -->
<html lang="en">
<head>
<!-- Generated by javadoc (1.8.0_281) on Sun Jan 15 15:58:33 CET 2023 -->
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>DirectiveCallPlace (FreeMarker 2.3.32 API)</title>
<meta name="date" content="2023-01-15">
<link rel="stylesheet" type="text/css" href="../../stylesheet.css" title="Style">
<script type="text/javascript" src="../../script.js"></script>
</head>
<body>
<script type="text/javascript"><!--
try {
if (location.href.indexOf('is-external=true') == -1) {
parent.document.title="DirectiveCallPlace (FreeMarker 2.3.32 API)";
}
}
catch(err) {
}
//-->
var methods = {"i0":6,"i1":6,"i2":6,"i3":6,"i4":6,"i5":6,"i6":6};
var tabs = {65535:["t0","All Methods"],2:["t2","Instance Methods"],4:["t3","Abstract Methods"]};
var altColor = "altColor";
var rowColor = "rowColor";
var tableTab = "tableTab";
var activeTableTab = "activeTableTab";
</script>
<noscript>
<div>JavaScript is disabled on your browser.</div>
</noscript>
<!-- ========= START OF TOP NAVBAR ======= -->
<div class="topNav"><a name="navbar.top">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.top" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.top.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li><a href="../../overview-summary.html">Overview</a></li>
<li><a href="package-summary.html">Package</a></li>
<li class="navBarCell1Rev">Class</li>
<li><a href="class-use/DirectiveCallPlace.html">Use</a></li>
<li><a href="package-tree.html">Tree</a></li>
<li><a href="../../deprecated-list.html">Deprecated</a></li>
<li><a href="../../index-all.html">Index</a></li>
<li><a href="../../help-doc.html">Help</a></li>
</ul>
</div>
<div class="subNav">
<ul class="navList">
<li><a href="../../freemarker/core/DefaultTruncateBuiltinAlgorithm.html" title="class in freemarker.core"><span class="typeNameLink">Prev&nbsp;Class</span></a></li>
<li><a href="../../freemarker/core/Environment.html" title="class in freemarker.core"><span class="typeNameLink">Next&nbsp;Class</span></a></li>
</ul>
<ul class="navList">
<li><a href="../../index.html?freemarker/core/DirectiveCallPlace.html" target="_top">Frames</a></li>
<li><a href="DirectiveCallPlace.html" target="_top">No&nbsp;Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_top">
<li><a href="../../allclasses-noframe.html">All&nbsp;Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_top");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<div>
<ul class="subNavList">
<li>Summary:&nbsp;</li>
<li>Nested&nbsp;|&nbsp;</li>
<li>Field&nbsp;|&nbsp;</li>
<li>Constr&nbsp;|&nbsp;</li>
<li><a href="#method.summary">Method</a></li>
</ul>
<ul class="subNavList">
<li>Detail:&nbsp;</li>
<li>Field&nbsp;|&nbsp;</li>
<li>Constr&nbsp;|&nbsp;</li>
<li><a href="#method.detail">Method</a></li>
</ul>
</div>
<a name="skip.navbar.top">
<!-- -->
</a></div>
<!-- ========= END OF TOP NAVBAR ========= -->
<!-- ======== START OF CLASS DATA ======== -->
<div class="header">
<div class="subTitle">freemarker.core</div>
<h2 title="Interface DirectiveCallPlace" class="title">Interface DirectiveCallPlace</h2>
</div>
<div class="contentContainer">
<div class="description">
<ul class="blockList">
<li class="blockList">
<hr>
<br>
<pre>public interface <span class="typeNameLabel">DirectiveCallPlace</span></pre>
<div class="block">Gives information about the place where a directive is called from, also lets you attach a custom data object to that
place. Each directive call in a template has its own <a href="../../freemarker/core/DirectiveCallPlace.html" title="interface in freemarker.core"><code>DirectiveCallPlace</code></a> object (even when they call the same
directive with the same parameters). The life cycle of the <a href="../../freemarker/core/DirectiveCallPlace.html" title="interface in freemarker.core"><code>DirectiveCallPlace</code></a> object is bound to the
<a href="../../freemarker/template/Template.html" title="class in freemarker.template"><code>Template</code></a> object that contains the directive call. Hence, the <a href="../../freemarker/core/DirectiveCallPlace.html" title="interface in freemarker.core"><code>DirectiveCallPlace</code></a> object and the custom
data you put into it is cached together with the <a href="../../freemarker/template/Template.html" title="class in freemarker.template"><code>Template</code></a> (and templates are normally cached - see
<a href="../../freemarker/template/Configuration.html#getTemplate-java.lang.String-"><code>Configuration.getTemplate(String)</code></a>). The custom data is normally initialized on demand, that is, when the
directive call is first executed, via <a href="../../freemarker/core/DirectiveCallPlace.html#getOrCreateCustomData-java.lang.Object-freemarker.template.utility.ObjectFactory-"><code>getOrCreateCustomData(Object, ObjectFactory)</code></a>.
<p>
<b>Don't implement this interface yourself</b>, as new methods can be added to it any time! It's only meant to be
implemented by the FreeMarker core.
<p>
This interface is currently only used for custom directive calls (that is, a <code>&lt;@...&gt;</code> that calls a
<a href="../../freemarker/template/TemplateDirectiveModel.html" title="interface in freemarker.template"><code>TemplateDirectiveModel</code></a>, <a href="../../freemarker/template/TemplateTransformModel.html" title="interface in freemarker.template"><code>TemplateTransformModel</code></a>, or a macro).</div>
<dl>
<dt><span class="simpleTagLabel">Since:</span></dt>
<dd>2.3.22</dd>
<dt><span class="seeLabel">See Also:</span></dt>
<dd><a href="../../freemarker/core/Environment.html#getCurrentDirectiveCallPlace--"><code>Environment.getCurrentDirectiveCallPlace()</code></a></dd>
</dl>
</li>
</ul>
</div>
<div class="summary">
<ul class="blockList">
<li class="blockList">
<!-- ========== METHOD SUMMARY =========== -->
<ul class="blockList">
<li class="blockList"><a name="method.summary">
<!-- -->
</a>
<h3>Method Summary</h3>
<table class="memberSummary" border="0" cellpadding="3" cellspacing="0" summary="Method Summary table, listing methods, and an explanation">
<caption><span id="t0" class="activeTableTab"><span>All Methods</span><span class="tabEnd">&nbsp;</span></span><span id="t2" class="tableTab"><span><a href="javascript:show(2);">Instance Methods</a></span><span class="tabEnd">&nbsp;</span></span><span id="t3" class="tableTab"><span><a href="javascript:show(4);">Abstract Methods</a></span><span class="tabEnd">&nbsp;</span></span></caption>
<tr>
<th class="colFirst" scope="col">Modifier and Type</th>
<th class="colLast" scope="col">Method and Description</th>
</tr>
<tr id="i0" class="altColor">
<td class="colFirst"><code>int</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getBeginColumn--">getBeginColumn</a></span>()</code>
<div class="block">The 1-based column number of the first character of the directive call in the template source code, or -1 if it's
not known.</div>
</td>
</tr>
<tr id="i1" class="rowColor">
<td class="colFirst"><code>int</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getBeginLine--">getBeginLine</a></span>()</code>
<div class="block">The 1-based line number of the first character of the directive call in the template source code, or -1 if it's
not known.</div>
</td>
</tr>
<tr id="i2" class="altColor">
<td class="colFirst"><code>int</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getEndColumn--">getEndColumn</a></span>()</code>
<div class="block">The 1-based column number of the last character of the directive call in the template source code, or -1 if it's
not known.</div>
</td>
</tr>
<tr id="i3" class="rowColor">
<td class="colFirst"><code>int</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getEndLine--">getEndLine</a></span>()</code>
<div class="block">The 1-based line number of the last character of the directive call in the template source code, or -1 if it's
not known.</div>
</td>
</tr>
<tr id="i4" class="altColor">
<td class="colFirst"><code>java.lang.Object</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getOrCreateCustomData-java.lang.Object-freemarker.template.utility.ObjectFactory-">getOrCreateCustomData</a></span>(java.lang.Object&nbsp;providerIdentity,
<a href="../../freemarker/template/utility/ObjectFactory.html" title="interface in freemarker.template.utility">ObjectFactory</a>&nbsp;objectFactory)</code>
<div class="block">Returns the custom data, or if that's <code>null</code>, then it creates and stores it in an atomic operation then
returns it.</div>
</td>
</tr>
<tr id="i5" class="rowColor">
<td class="colFirst"><code><a href="../../freemarker/template/Template.html" title="class in freemarker.template">Template</a></code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#getTemplate--">getTemplate</a></span>()</code>
<div class="block">The template that contains this call; <code>null</code> if the call is not from a template (but directly from
user Java code, for example).</div>
</td>
</tr>
<tr id="i6" class="altColor">
<td class="colFirst"><code>boolean</code></td>
<td class="colLast"><code><span class="memberNameLink"><a href="../../freemarker/core/DirectiveCallPlace.html#isNestedOutputCacheable--">isNestedOutputCacheable</a></span>()</code>
<div class="block">Tells if the nested content (the body) can be safely cached, as it only depends on the template content (not on
variable values and such) and has no side-effects (other than writing to the output).</div>
</td>
</tr>
</table>
</li>
</ul>
</li>
</ul>
</div>
<div class="details">
<ul class="blockList">
<li class="blockList">
<!-- ============ METHOD DETAIL ========== -->
<ul class="blockList">
<li class="blockList"><a name="method.detail">
<!-- -->
</a>
<h3>Method Detail</h3>
<a name="getTemplate--">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getTemplate</h4>
<pre><a href="../../freemarker/template/Template.html" title="class in freemarker.template">Template</a>&nbsp;getTemplate()</pre>
<div class="block">The template that contains this call; <code>null</code> if the call is not from a template (but directly from
user Java code, for example).</div>
<dl>
<dt><span class="simpleTagLabel">Since:</span></dt>
<dd>2.3.28</dd>
</dl>
</li>
</ul>
<a name="getBeginColumn--">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getBeginColumn</h4>
<pre>int&nbsp;getBeginColumn()</pre>
<div class="block">The 1-based column number of the first character of the directive call in the template source code, or -1 if it's
not known.</div>
</li>
</ul>
<a name="getBeginLine--">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getBeginLine</h4>
<pre>int&nbsp;getBeginLine()</pre>
<div class="block">The 1-based line number of the first character of the directive call in the template source code, or -1 if it's
not known.</div>
</li>
</ul>
<a name="getEndColumn--">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getEndColumn</h4>
<pre>int&nbsp;getEndColumn()</pre>
<div class="block">The 1-based column number of the last character of the directive call in the template source code, or -1 if it's
not known. If the directive has an end-tag (<code>&lt;/@...&gt;</code>), then it points to the last character of that.</div>
</li>
</ul>
<a name="getEndLine--">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getEndLine</h4>
<pre>int&nbsp;getEndLine()</pre>
<div class="block">The 1-based line number of the last character of the directive call in the template source code, or -1 if it's
not known. If the directive has an end-tag (<code>&lt;/@...&gt;</code>), then it points to the last character of that.</div>
</li>
</ul>
<a name="getOrCreateCustomData-java.lang.Object-freemarker.template.utility.ObjectFactory-">
<!-- -->
</a>
<ul class="blockList">
<li class="blockList">
<h4>getOrCreateCustomData</h4>
<pre>java.lang.Object&nbsp;getOrCreateCustomData(java.lang.Object&nbsp;providerIdentity,
<a href="../../freemarker/template/utility/ObjectFactory.html" title="interface in freemarker.template.utility">ObjectFactory</a>&nbsp;objectFactory)
throws <a href="../../freemarker/core/CallPlaceCustomDataInitializationException.html" title="class in freemarker.core">CallPlaceCustomDataInitializationException</a></pre>
<div class="block">Returns the custom data, or if that's <code>null</code>, then it creates and stores it in an atomic operation then
returns it. This method is thread-safe, however, it doesn't ensure thread safe (like synchronized) access to the
custom data itself. See the top-level documentation of <a href="../../freemarker/core/DirectiveCallPlace.html" title="interface in freemarker.core"><code>DirectiveCallPlace</code></a> to understand the scope and
life-cycle of the custom data. Be sure that the custom data only depends on things that get their final value
during template parsing, not on runtime settings.
<p>
This method will block other calls while the <code>objectFactory</code> is executing, thus, the object will be
<em>usually</em> created only once, even if multiple threads request the value when it's still <code>null</code>. It
doesn't stand though when <code>providerIdentity</code> mismatches occur (see later). Furthermore, then it's also
possible that multiple objects created by the same <a href="../../freemarker/template/utility/ObjectFactory.html" title="interface in freemarker.template.utility"><code>ObjectFactory</code></a> will be in use on the same time, because
of directive executions already running in parallel, and because of memory synchronization delays (hardware
dependent) between the threads.</div>
<dl>
<dt><span class="paramLabel">Parameters:</span></dt>
<dd><code>providerIdentity</code> - This is usually the class of the <a href="../../freemarker/template/TemplateDirectiveModel.html" title="interface in freemarker.template"><code>TemplateDirectiveModel</code></a> that creates (and uses) the custom
data, or if you are using your own class for the custom data object (as opposed to a class from some
more generic API), then that class. This is needed as the same call place might calls different
directives depending on runtime conditions, and so it must be ensured that these directives won't
accidentally read each other's custom data, ending up with class cast exceptions or worse. In the
current implementation, if there's a <code>providerIdentity</code> mismatch (means, the
<code>providerIdentity</code> object used when the custom data was last set isn't the exactly same object
as the one provided with the parameter now), the previous custom data will be just ignored as if it
was <code>null</code>. So if multiple directives that use the custom data feature use the same call place,
the caching of the custom data can be inefficient, as they will keep overwriting each other's custom
data. (In a more generic implementation the <code>providerIdentity</code> would be a key in a
<a href="../../freemarker/ext/util/IdentityHashMap.html" title="class in freemarker.ext.util"><code>IdentityHashMap</code></a>, but then this feature would be slower, while <code>providerIdentity</code>
mismatches aren't occurring in most applications.)</dd>
<dd><code>objectFactory</code> - Called when the custom data wasn't yet set, to create its initial value. If this parameter is
<code>null</code> and the custom data wasn't set yet, then <code>null</code> will be returned. The returned
value of <a href="../../freemarker/template/utility/ObjectFactory.html#createObject--"><code>ObjectFactory.createObject()</code></a> can be any kind of object, but can't be <code>null</code>.</dd>
<dt><span class="returnLabel">Returns:</span></dt>
<dd>The current custom data object, or possibly <code>null</code> if there was no <a href="../../freemarker/template/utility/ObjectFactory.html" title="interface in freemarker.template.utility"><code>ObjectFactory</code></a> provided.</dd>
<dt><span class="throwsLabel">Throws:</span></dt>
<dd><code><a href="../../freemarker/core/CallPlaceCustomDataInitializationException.html" title="class in freemarker.core">CallPlaceCustomDataInitializationException</a></code> - If the <a href="../../freemarker/template/utility/ObjectFactory.html" title="interface in freemarker.template.utility"><code>ObjectFactory</code></a> had to be invoked but failed.</dd>
</dl>
</li>
</ul>
<a name="isNestedOutputCacheable--">
<!-- -->
</a>
<ul class="blockListLast">
<li class="blockList">
<h4>isNestedOutputCacheable</h4>
<pre>boolean&nbsp;isNestedOutputCacheable()</pre>
<div class="block">Tells if the nested content (the body) can be safely cached, as it only depends on the template content (not on
variable values and such) and has no side-effects (other than writing to the output). Examples of cases that give
<code>false</code>: <code>&lt;@foo&gt;Name: </code> <tt>${name}</tt>,
<code>&lt;@foo&gt;Name: &lt;#if showIt&gt;Joe&lt;/#if&gt;&lt;/@foo&gt;</code>. Examples of cases that give <code>true</code>:
<code>&lt;@foo&gt;Name: Joe&lt;/@foo&gt;</code>, <code>&lt;@foo /&gt;</code>. Note that we get <code>true</code> for no nested content, because
that's equivalent with 0-length nested content in FTL.
<p>
This method returns a pessimistic result. For example, if it sees a custom directive call, it can't know what it
does, so it will assume that it's not cacheable.</div>
</li>
</ul>
</li>
</ul>
</li>
</ul>
</div>
</div>
<!-- ========= END OF CLASS DATA ========= -->
<!-- ======= START OF BOTTOM NAVBAR ====== -->
<div class="bottomNav"><a name="navbar.bottom">
<!-- -->
</a>
<div class="skipNav"><a href="#skip.navbar.bottom" title="Skip navigation links">Skip navigation links</a></div>
<a name="navbar.bottom.firstrow">
<!-- -->
</a>
<ul class="navList" title="Navigation">
<li><a href="../../overview-summary.html">Overview</a></li>
<li><a href="package-summary.html">Package</a></li>
<li class="navBarCell1Rev">Class</li>
<li><a href="class-use/DirectiveCallPlace.html">Use</a></li>
<li><a href="package-tree.html">Tree</a></li>
<li><a href="../../deprecated-list.html">Deprecated</a></li>
<li><a href="../../index-all.html">Index</a></li>
<li><a href="../../help-doc.html">Help</a></li>
</ul>
</div>
<div class="subNav">
<ul class="navList">
<li><a href="../../freemarker/core/DefaultTruncateBuiltinAlgorithm.html" title="class in freemarker.core"><span class="typeNameLink">Prev&nbsp;Class</span></a></li>
<li><a href="../../freemarker/core/Environment.html" title="class in freemarker.core"><span class="typeNameLink">Next&nbsp;Class</span></a></li>
</ul>
<ul class="navList">
<li><a href="../../index.html?freemarker/core/DirectiveCallPlace.html" target="_top">Frames</a></li>
<li><a href="DirectiveCallPlace.html" target="_top">No&nbsp;Frames</a></li>
</ul>
<ul class="navList" id="allclasses_navbar_bottom">
<li><a href="../../allclasses-noframe.html">All&nbsp;Classes</a></li>
</ul>
<div>
<script type="text/javascript"><!--
allClassesLink = document.getElementById("allclasses_navbar_bottom");
if(window==top) {
allClassesLink.style.display = "block";
}
else {
allClassesLink.style.display = "none";
}
//-->
</script>
</div>
<div>
<ul class="subNavList">
<li>Summary:&nbsp;</li>
<li>Nested&nbsp;|&nbsp;</li>
<li>Field&nbsp;|&nbsp;</li>
<li>Constr&nbsp;|&nbsp;</li>
<li><a href="#method.summary">Method</a></li>
</ul>
<ul class="subNavList">
<li>Detail:&nbsp;</li>
<li>Field&nbsp;|&nbsp;</li>
<li>Constr&nbsp;|&nbsp;</li>
<li><a href="#method.detail">Method</a></li>
</ul>
</div>
<a name="skip.navbar.bottom">
<!-- -->
</a></div>
<!-- ======== END OF BOTTOM NAVBAR ======= -->
</body>
</html>