filter function

Topics: General, XSLT
Jul 5, 2011 at 3:59 PM

Hi,

First i will present my functionality: i have a list of categories and when i select one category the products from this category will be displaied. What i want is to display from the start all the products and when i click a category do apply the filter. How can i do this?

I was thinking to create 2 functions one with the filter and one which is showing all the items and put them in 2 separated pages but my idea haven't been approved so i need to keep everything in a single page. So again this is my problem, to keep everything in a single page even if i'm creating 2 functions.

Thanks

Jul 5, 2011 at 6:16 PM

Hello,

You should consider to create your own C# Filter and use it in XSLT which will render your product list.

How to implement:

1. Create XSLT for product rendering

2. Add Function Call  "Get[product data type name]Xml()"

3. Locate Filter and you will see that it expects the Expression<Func<[product data type name],Boolean>>. Next you should write this expression function, for example in App_Code folder create c# file which will contain method something like this:

 

	public static Expression<Func<Product, bool>> GetProductCategoryFilterFromUrl()
	{
		Expression<Func<Product, bool>> filter = p => true; // returns All Products
		//Check if  Category Query parameter exist in URL then do:
		{
			string categoryFromQuery;
			//code to get caterory filter parameter from URL
			filter = p => p.Category == categoryFromQuery; // returns Products filtred by Category
		}
		return filter;
	}

4. C1 console -> Functions -> C# functions -> add External C# function -> add created method GetProductCategoryFilterFromUrl()

5. Return to step 3 -> Locate Filter and select C# function created on step 4

 

 
Jul 6, 2011 at 9:54 AM

Hello Inna,

Thank you very much for your help.

Unfortunately i don't have very much experience with C1 and i'm not a C# programmer so i have few questions:

  • I already have my xslt function which is creating the products rendering depending on the url category id sent. Do i need to create other function? You can see my function here: http://bestsoftconsulting.com/bogdan/printscreen_c1.png
  • I uploaded a aspx file in app_code folder containing just the function you sent me and i tried to do what you sent me at point 4 but it returns "Could not find type". What am i doing wrong?

I really appreciate your help. Thanks!

Jul 6, 2011 at 10:55 AM

I thought at a backup solution: create a javascript to detect if the url has parameters or not and depending on the result i'll run one of the functions: the one which displays all the results or just the ones from the selected category. What i can't find exactly is how to call the xslt function from JS?

Jul 6, 2011 at 11:01 AM
Edited Jul 6, 2011 at 12:12 PM

i figured it out: i'm calling my xslt function from JS using document.write("my function");\

Update1: Working for simple text not when function is rendering html content

Jul 6, 2011 at 1:38 PM

remember to be careful about using js for content generation... it should more be for effects and functionality; crawlers are not good at executing js and will therefor be having a hard time indexing your content.

Jul 6, 2011 at 2:20 PM
Edited Jul 6, 2011 at 2:25 PM
bogdanfireteanu wrote:

I uploaded a aspx file in app_code folder containing just the function you sent me and i tried to do what you sent me at point 4 but it returns "Could not find type". What am i doing wrong?

Hi bogdanfireteanu,

If you are still going to use Inna's function, you may want to read our guide to C# functions in C1.

Any way, I can suggest 3 causes of you failing at step 4. Please check:

1. The function must be placed within a public class, and the class within a namespace. All this must be in a cs file (not aspx), say, /App_Code/MyFunctions.cs:

namespace My.Name.Space
{
  public class Functions
  {
    public static Expression<Func<Product, bool>> GetProductCategoryFilterFromUrl()
    {
      //...
    }
  }
}

(Alternatively, you can create an internal C# function rather than creating an external one. All is described in the guide I referred to.


2. When you add the GetProductCategoryFilterFromUrl() as described in Step 4 , you first should specify the type, here, namespace+class.
In my example above, you should enter in the field: My.Name.Space.Functions. Then in the next step of the wizard, you'll get a dropdown list where you can choose GetProductCategoryFilterFromUrl

3. Sometimes, C1 does not "see" classes in CS files uploaded to /App_Code right away. Not sure yet why.
You may need to try to re-upload it, do it via Visual Studio, or Restart the Server (Tools > Restart the Server).

/Vitaly


Jul 6, 2011 at 2:53 PM
Edited Jul 6, 2011 at 2:58 PM

>> Unfortunately i don't have very much experience with C1 and i'm not a C# programmer

Then you can write one more XSLT which will choose what function to call, something like this:

 

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
xmlns:in="http://www.composite.net/ns/transformation/input/1.0" 
xmlns:lang="http://www.composite.net/ns/localization/1.0" 
xmlns:f="http://www.composite.net/ns/function/1.0" 
xmlns="http://www.w3.org/1999/xhtml" 
xmlns:c1="http://c1.composite.net/StandardFunctions"
exclude-result-prefixes="xsl in lang f c1"> <xsl:template match="/"> <html> <head></head> <body> <xsl:choose> <xsl:when test="c1:GetQueryStringValue('category') !=''"> <!-- Show filtered --> <f:function name="RequirementOne.UserDisplayPartial" /> </xsl:when> <xsl:otherwise> <!-- Show all --> <f:function name="RequirementOne.UserDisplay" /> </xsl:otherwise> </xsl:choose> </body> </html> </xsl:template> </xsl:stylesheet>

 

Jul 6, 2011 at 3:15 PM

Inna, works just great!

Thank you so much!

Jul 6, 2011 at 3:16 PM

thank you everybody for your help!