function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
BryanTSCBryanTSC 

getting and setting and updating and getting!

Oh this seems so simple, yet I'm stuck!

 

Here's what I have now in my controller:

    public date d {
        get{
            d = date.today();
            return d;
            }
            set;
       }
    
    
    public List<event> all {
    get {
    all = [select subject, activitydate, location from Event where activitydate = :d Order By location ASC];
    return all;
    }
    set;
    }

 

All is peachy and the page loads up Today()'s info just fine.

 

Now, what I really want to do is load up the page initially with today's date and resulting info, but also have a button called "Next" that will add 1 day to the current date and update an outputPanel on my page with the new query results when clicked.

 

I know I need to add a function for the button action, but I'm not sure how to change the code above to manipulate the date variable accordingly.

 

Thanks in advance for any help you might provide!

aballardaballard

You should be able to increment the date by calling d.addDays(1)

 

 

Edwin VijayEdwin Vijay

Not sure if  this might help... But, here is an article which helps you understand getter and setter

 

http://www.forcetree.com/2009/07/getter-and-setter-methods-what-are-they.html

aballardaballard

Ah yes, should have read that code more carefully.  As it is written the getter is going to always return today's date, regardless of what you do in a setter. 

 

You need d to be initialzed today's date in a constructor, then you can increment using d.addDays()

Marty Y. ChangMarty Y. Chang

Hello, BryanTSC,

 

To clarify aballard's point, here's what your code may end up looking like:

 

public class ListEventsCtrl {
    
    /**
     * The date for which events should be listed.
     */
    public Date eventDate { get; set; }
    
    /**
     * Default constructor.
     */
    public ListEventsCtrl() {
        eventDate = Date.today();
    }   // public ListEventsCtrl()
    
    /**
     * Return a list of all events occuring on the specified
     * <code>eventDate</code>.
     *
     * @return <code>List</code> of all <code>Event</code> objects for the
     *         specified <code>eventDate</code>
     */
    public List<Event> getEventsThisDay() {
        return [SELECT Subject, ActivityDate, Location
                FROM Event
                WHERE ActivityDate = :eventDate
                ORDER BY Location ASC];
    }   // public List<Event> getEventsThisDay()
}   // public class ListEventsCtrl

 

P.S.  What's interesting to me is that there is a significant difference between using the { get; set; } notation vs. defining actual get and set methods for a property.  Thanks for bringing this to light, everyone!

BryanTSCBryanTSC

Thanks, Marty.

 

I worked on this a bit this afternoon, though I admittedly don't fully understand what I have going on here.  The page partially works, but it's not quite doing what I expect.

 

All joking aside - can anybody tell me what in my code is A) correct, B) wrong, and C) how to make this better/functional?  I'm a motivated "learn by doing" kind of guy!

 

THANKS!

 

public class devRepeat {

    public date d {get;set;}
    public integer schedSize {get;set;}
    public integer outSize {get;set;}

    public list<Event> all = new list<event>();
    public list<Event> schedule = new list<event>();
    public list<Event> out = new list<event>();
     

    public devRepeat() {
       d = date.today();
       buildLists(d);
       
    }
   
    public list<event> getSchedule() {return schedule;}
    public list<event> getOut() {return out;}
    
    public void buildLists(date x){
    
    schedule = new list<event>();
    out = new list<event>();
    
    d = x;
    
    all = [SELECT subject, activitydate, location, Owner.Name, startdatetime, enddatetime, isalldayevent, who.Name, whoid
           FROM Event
           WHERE activitydate = :d
           ORDER BY StartDateTime ASC, Owner.Name ASC];
    
    
    for(Event e : all)
    {
       if(e.subject != 'location' && e.subject != 'out' && e.subject != 'interview'){
           schedule.add(e);
       }
       
       if(e.subject == 'out'){
           out.add(e);
       }
       
    }
    
    schedSize = schedule.size();
    outSize = out.size();
    
    }

    
    public void addDay() {
    d = d.addDays(1);
    buildLists(d);
    }
    
    public void subDay() {
    d = d.addDays(-1);
    buildLists(d);
    }
    

}

 

<apex:page controller="devRepeat" showHeader="false" sidebar="false" standardstylesheets="true">

<apex:outputPanel id="page">

<div class="header">
<apex:outputText value=" Events for {0,date,EEEE, MMMM dd', 'yyyy}">
    <apex:param value="{!d}" />
</apex:outputText>


<apex:form >
    <apex:commandButton value="Prev" action="{!subday}" reRender="page"/>
    <apex:commandButton value="Next" action="{!addday}" reRender="page"/>
</apex:form>

<br/><apex:outputText value="Schedule Size: {!schedSize}" />
<br/><apex:outputText value="Out Size: {!outSize}" />
</div>

<div class="schedule">
<table>
<th class="tHeader" colspan="3">Schedule</th>
<apex:repeat value="{!schedule}" var="a">
<tr>
<td>
   <apex:outputText value="{!a.Owner.Name}"/>
</td>
<td>
   <a href="https://cs8.salesforce.com/{!a.id}">{!a.Subject}</a>
</td>
<td>
<apex:outputText value="{0,date,h:mm a}">
    <apex:param value="{!a.startdatetime}" />
</apex:outputText>
</td>
</tr>
</apex:repeat>
</table>
</div>

<div id="locatorWrapper">
<div class="locator">
<table>
<th class="tHeader" colspan="2">OUT</th>
<apex:repeat value="{!out}" var="o">
<tr>
<td>
    <apex:outputText value="{!o.Owner.Name}"/>
</td>
<td class="locatorCol2">
    <apex:outputPanel rendered="{!o.isalldayevent == true}">All Day</apex:outputPanel>
    <apex:outputPanel rendered="{!o.isalldayevent == false}">
    <apex:outputText value="{0,date,h:mm}-">
    <apex:param value="{!o.startdatetime}" />
    </apex:outputText>
    <apex:outputText value="{0,date,h:mm}">
    <apex:param value="{!o.enddatetime}" />
    </apex:outputText>
    </apex:outputPanel>
</td>
</tr>
</apex:repeat></table>
</div>
</div>
</apex:outputPanel>
</apex:page>

 

Marty Y. ChangMarty Y. Chang

Hello, Bryan,

 

Would you give a few more details on what exactly is not working the way you want?

 

My initial feedback would be:

  • Comment your code. :-)
  • Use descriptive variable names like calendarDate instead of d and x.  Aside from improving readability, this practice may help you better identify situations where your code may be getting convoluted.
  • You can reference object properties in Visualforce.  For example, instead of creating schedSize and all the code around it, all you have to do is use {!schedule.size} in your Visualforce page.
  • The Date x parameter in your buildLists method is extraneous.  You don't really need it.
BryanTSCBryanTSC

When I click the "prev" / "next" buttons I have set up, the schedule repeat div updates correctly, but the repeat for my "out" div disappears from the page.

 

If I click back to a date where data is available for "out", the "out" div reappears, but shows duplicate information, since the list is not getting cleared, but rather appended to.

 

I tried to add out = new list<event>(); in buildList() below the schedule=new list<event>(); line, but then my buttons don't appear to do anything when clicked.

 

Thanks for the other advice, commenting is definitely a practice I need to endorse!

Marty Y. ChangMarty Y. Chang

The disappearing div is pretty interesting, and it has something to do with your partial page refresh (which isn't necessary for this page).  I tested your code, and to fix the disappearing div issue all I did was remove the all-encompasing apex:outputPanel along with the reRender attributes from your apex:commandButton elements.

 

<apex:page controller="devRepeat" showHeader="false" sidebar="false" standardstylesheets="true">

<!-- <apex:outputPanel id="page"> -->

<div class="header">
<apex:outputText value=" Events for {0,date,EEEE, MMMM dd', 'yyyy}">
    <apex:param value="{!d}" />
</apex:outputText>


<apex:form >
    <apex:commandButton value="Prev" action="{!subday}"/><!-- reRender="page"/> -->
    <apex:commandButton value="Next" action="{!addday}"/><!-- reRender="page"/> -->
</apex:form>

<br/><apex:outputText value="Schedule Size: {!schedSize}" />
<br/><apex:outputText value="Out Size: {!outSize}" />
</div>

<div class="schedule">
<table>
<th class="tHeader" colspan="3">Schedule</th>
<apex:repeat value="{!schedule}" var="a">
<tr>
<td>
   <apex:outputText value="{!a.Owner.Name}"/>
</td>
<td>
   <a href="https://cs8.salesforce.com/{!a.id}">{!a.Subject}</a>
</td>
<td>
<apex:outputText value="{0,date,h:mm a}">
    <apex:param value="{!a.startdatetime}" />
</apex:outputText>
</td>
</tr>
</apex:repeat>
</table>
</div>

<div id="locatorWrapper">
<div class="locator">
<table>
<th class="tHeader" colspan="2">OUT</th>
<apex:repeat value="{!out}" var="o">
<tr>
<td>
    <apex:outputText value="{!o.Owner.Name}"/>
</td>
<td class="locatorCol2">
    <apex:outputPanel rendered="{!o.isalldayevent == true}">All Day</apex:outputPanel>
    <apex:outputPanel rendered="{!o.isalldayevent == false}">
    <apex:outputText value="{0,date,h:mm}-">
    <apex:param value="{!o.startdatetime}" />
    </apex:outputText>
    <apex:outputText value="{0,date,h:mm}">
    <apex:param value="{!o.enddatetime}" />
    </apex:outputText>
    </apex:outputPanel>
</td>
</tr>
</apex:repeat></table>
</div>
</div>
<!-- </apex:outputPanel> -->
</apex:page>

 

I'm also not seeing the "duplicate info" behavior you described.  To me it appears that the rest of your code functions as you're expecting.

 

P.S. Your table header is missing a tr tag.  th elements should always be nested within a tr element.

BryanTSCBryanTSC

That definitely fixes the issue.  I was attempting to use the partial page refresh as a way to make the data switch look more seamless than a full page refresh.  Perhaps this isn't necessary or there is a better way to do it.