How to locate resources in Orchard
Asked Answered
I

5

6

I am writing an Orchard theme, and I'd like to be able to locate some of the resources packaged with the theme (images/swfs etc).

What is the best way of doing this?

I've had a look at ResourceManifest files, using builder.Add.DefineResource but I can't seem to find it's counterpart in the view. Or do I just put the full path in?

Any hints?

Cheers Carl

Indicia answered 27/6, 2011 at 15:49 Comment(2)
As I understand you would only use builder.Add.DefineResource if you wanted to make resources available to other modules. Are you just referencing content in your theme, or trying to make content available to other themes/modules?Terebinthine
I am only looking to reference it in the current theme/module.Indicia
H
2

In stylesheets, relative paths (from the stylesheet path) should be used.

In views, you should use Url.Content.

Harberd answered 27/6, 2011 at 21:47 Comment(0)
T
6

If you need to define the new resource (script or stylesheet):

  1. Create a class inheriting IResourceManifestProvider
  2. Provide the void BuildManifests(ResourceManifestBuilder builder) method and
  3. Add all necessary resources via builder.Add().DefineStyle("") or builder.Add().DefineScript(...), just as you noted in your question.

For example:

public class ResourceManifest : IResourceManifestProvider {
    public void BuildManifests(ResourceManifestBuilder builder) {
        var manifest = builder.Add();
        manifest.DefineStyle("MyStyle").SetUrl("mystyle.css");
        manifest.DefineScript("MyScript").SetUrl("myscript.js").SetDependencies("jQuery");
    }
}

This defines one style and script you can reuse in your views. Urls are relative to /Styles (or /Scripts) folders in your theme/module where the class is located.

If you want to reuse some of resources already defined (in all enabled modules and themes), it's as easy as writing eg.:

...
@{
    Style.Require("MyStyle").AtHead();
    Script.Require("MyScript").AtFoot();
}
...

inside your .cshtml view file. Example above would inject mystyle.css and myscript.js at appropriate locations (header/footer of the final page).

Tactful answered 27/6, 2011 at 23:32 Comment(1)
Hi - thanks for this. Unfortunately I was after resources that weren't styles or scripts :) and being able to arbitrarily place them in the view.Indicia
C
5

I slapped together an extension method for a similar problem:

public static string ResourceUrl(this HtmlHelper helper, string resourceType, string resourceName)
{
    var manager = helper.Resolve<IResourceManager>();
    var settings = new RequireSettings { Type = resourceType, Name = resourceName, BasePath = resourceType };
    var resource = manager.FindResource(settings);
    var context = new ResourceRequiredContext { Resource = resource, Settings = settings };

    var url = context.GetResourceUrl(settings, "/");

    return url;
}

Resource Manifest Definition:

manifest.DefineResource("Content", "MyImage").SetUrl("Content/myimage.png");

View Usage:

@Html.ResourceUrl("Content", "MyImage")

It's not well tested, and could probably use some error handling, but its working for me.

Corri answered 13/2, 2012 at 6:42 Comment(0)
B
3

Just to be clear, there are a few methods depending on your situation. I'll outline the most common I know.

First of all, there is the inclusion of an external script or stylesheet on your particular part or theme. The standard syntax within a Razor template is this:

@Style.Include("YourPartEdit")
@Script.Require("jQuery")
@Script.Include("YourPartEdit")

The include files will look for that particular resource in the corresponding Style or Scripts folder: for @Script.Include("YourPartEdit"), it will look in the scripts folder for YourPartEdit.js.

You might have noticed that with Script.Require you can register a library with Orchard (in this case the registered one is jQuery), and cause a module to require that particular script.

To do this you create your own implementation of the IResourceManifestProvider interface, and implement the BuildManifests(ResourceManifestBuilder builder) method and create a named resource. You can use .AtFoot() or .AtHead() to even target where it will go.

Now say you want to reference a particular image, and you want to use Razor to always point to the correct image Url. First of all I recommend placing the image in your Content folder for your theme (assuming this is a theme related image), and you'll do something along these lines:

<img [email protected](Html.ThemePath(WorkContext.CurrentTheme, "/Content/your-logo.png")) />

Now, say this is on your Layout.cshtml page - you'll now successfully serve the image anywhere on the site.

These particular techniques should account for a multitude of situations.

Bounder answered 8/5, 2013 at 19:0 Comment(0)
H
2

In stylesheets, relative paths (from the stylesheet path) should be used.

In views, you should use Url.Content.

Harberd answered 27/6, 2011 at 21:47 Comment(0)
W
1

Just a side note:

the solution posted by Adam Anderson works only when the controller class serving the view has the attribute [Orchard.Themes.Themed(true)]

Wrinkly answered 16/2, 2015 at 15:47 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.