Tridion 2011图像库的图像大小调整

Tridion 2011图像库的图像大小调整,tridion,tridion-2011,Tridion,Tridion 2011,我目前正在一个网站上工作,该网站将在一些细节页面上显示一个图片库。它必须在底部显示带有小缩略图的导航,并且必须为每个元素显示一些基本信息和大图 大图像也必须调整大小,因为它们有一个允许的最大大小 关键是每个多媒体组件只使用一个源图像,并且能够在发布时调整图像大小,以便从源图像向客户端浏览器发送缩略图和大图像。可以只使用样式或HTML显示大小图像,但这是非常不有效的,因为源图像(其中一些非常重)总是发送给客户 我的第一个想法是定制代码片段,这是用C#编写的,但我发现只将一些图像调整到某个大小,然后

我目前正在一个网站上工作,该网站将在一些细节页面上显示一个图片库。它必须在底部显示带有小缩略图的导航,并且必须为每个元素显示一些基本信息和大图

大图像也必须调整大小,因为它们有一个允许的最大大小

关键是每个多媒体组件只使用一个源图像,并且能够在发布时调整图像大小,以便从源图像向客户端浏览器发送缩略图和大图像。可以只使用样式或HTML显示大小图像,但这是非常不有效的,因为源图像(其中一些非常重)总是发送给客户

我的第一个想法是定制代码片段,这是用C#编写的,但我发现只将一些图像调整到某个大小,然后再将它们调整到另一个大小很复杂。我也找不到用合适的路径替换最终HTML上的SRC的方法

另一个想法是创建一个老式的PublishBinary方法,但我发现这真的很复杂,因为看起来当前的Tridion架构根本不打算这么做

最重要的一点是,即使我们能够成功地(以某种方式)调整大小,目前Tridion 2011年的一期杂志也会发布两次相同的图像。大版本和小版本实际上都来自同一个多媒体组件,因此不可能同时发布它们或播放名称,第一个版本将一直消失,因为路径将用第二个更新:-S


有什么想法吗?

Tridion完全可以在一个MMC上发布多个变体。调用
AddBinary
时,您可以指定该二进制文件是MMC的一个变体,每个变体都由您指定的一个简单字符串标识

public Binary AddBinary(
    Stream content,
    string filename,
    StructureGroup location,
    string variantId,
    Component relatedComponent,
    string mimeType
)


如您所见,您还可以指定二进制文件的文件名。如果您这样做,您的责任是变体具有唯一的文件名,并且不同MMC之间的文件名保持唯一。因此,通常最简单的方法是在文件名的前面或后面加上一些variantId的指示:
\u thumbnail.jpg

我过去构建了一个图像大小调整TBB,它读取Dreamweaver或XSLT模板的输出。其思想是使用第一个模板生成如下所示的标记

<img src="tcm:1-123" maxWidth="250" maxHeight="400" 
     cropPosition="middle" variantId="250x400" 
     action="PostProcess" enlargeIfTooSmall="true"
/>

“重新调整大小”TBB然后对包中的输出项进行post处理,查找具有后处理操作的节点

然后,它使用
System.Drawing
库根据
maxhight
maxWidth
维度属性创建多媒体组件的变体,并使用前面提到的
AddBinary()
方法@frank将其发布,并使用
variantId
属性作为文件名前缀,和变量id(并用新二进制文件的URL替换SRC属性)

为了使这100%灵活,如果
maxHeight
maxWidth
属性中的任何一个设置为0,则TBB仅基于“非零”维度重新调整大小,或者如果两者都设置,则它将基于裁剪位置属性裁剪图像。这使我们能够为横向和纵向图像制作sqare缩略图,而不会扭曲它们。
enlargeIfTooSmall
属性用于防止小图像被拉伸过多

您可以在此处看到最终图库的示例:

以及其他图像大小调整示例:


所有图像只需上传到CMS一次,然后在发布时重新调整大小并进行动态裁剪。

对于最近的一个演示项目,我采用了完全不同的方法。二进制文件都发布到代理数据库。它们通过HttpModule从代理中提取,HttpModule将二进制数据写入文件系统。 我可以在图像的URL中编码所需的宽度或高度(当然,对于非图像的二进制文件,这部分逻辑将不起作用)。然后,该模块动态调整图像大小(真正的动态调整,不是在发布期间!),并将调整大小的版本写入磁盘

例如:如果我请求/Images/photo.jpg,我将获得原始图像。如果我请求/Images/photo_h100.jpg,我会得到一个100像素高的版本。url/Images/photo_w150.jpg的宽度为150像素

不需要变体,也不需要因为不同的尺寸要求而重新发布:大小调整完全按需完成!服务器上的性能损失可以忽略不计:在重新发布映像之前,每个大小只生成一次


我使用了.NET,但当然它也可以在Java中工作

根据Frank和Quirijn的回答,您可能会对使用环境数据框架在盒式磁带索赔处理器中调整图像大小感兴趣。此解决方案与技术无关,可以在Java和.Net中重复使用。您只需要将调整大小的图像字节放入声明中,然后在Java或.Net中使用它

Java声明处理器:

public void onRequestStart(ClaimStore claims) throws AmbientDataException {
    int publicationId = getPublicationId();
    int binaryId = getBinaryId();

    BinaryContentDAO bcDAO = (BinaryContentDAO)StorageManagerFactory.getDAO(publicationId, StorageTypeMapping.BINARY_CONTENT);
    BinaryContent binaryContent = bcDAO.findByPrimaryKey(publicationId, binaryId, null);

    byte[] binaryBuff =  binaryContent.getContent();
    pixelRatio = getPixelRatio();

    int resizeWidth = getResizeWidth();

    BufferedImage original = ImageIO.read(new ByteArrayInputStream(binaryBuff));
    if (original.getWidth() < MAX_IMAGE_WIDTH) {
        float ratio = (resizeWidth * 1.0f) / (float)MAX_IMAGE_WIDTH; 

        float width =  original.getWidth() * ratio; 
        float height = original.getHeight() * ratio;

        BufferedImage resized = new BufferedImage(Math.round(width), Math.round(height), original.getType());
        Graphics2D g = resized.createGraphics();
        g.setComposite(AlphaComposite.Src);

        g.drawImage(original, 0, 0, resized.getWidth(), resized.getHeight(), null);
        g.dispose();

        ByteArrayOutputStream output = new ByteArrayOutputStream();

        BinaryMeta meta = new BinaryMetaFactory().getMeta(String.format("tcm:%s-%s", publicationId, binaryId));
        String suffix = meta.getPath().substring(meta.getPath().lastIndexOf('.') + 1);

        ImageIO.write(resized, suffix, output);
        binaryBuff = output.toByteArray();
    }
    claims.put(new URI("taf:extensions:claim:resizedimage"), binaryBuff);
}
public void ProcessRequest(HttpContext context) {
    if (context != null) {
        HttpResponse httpResponse = HttpContext.Current.Response;

        ClaimStore claims = AmbientDataContext.CurrentClaimStore;
        if (claims != null) {
            Codemesh.JuggerNET.byteArray javaArray = claims.Get<Codemesh.JuggerNET.byteArray>("taf:extensions:claim:resizedimage");
            byte[] resizedImage = javaArray.ToNative(javaArray);
            if (resizedImage != null && resizedImage.Length > 0) {
                httpResponse.Expires = -1;
                httpResponse.Flush();
                httpResponse.BinaryWrite(resizedImage);
            }
        }
    }
}
@Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {    
        ClaimStore claims = AmbientDataContext.getCurrentClaimStore();
        if (claims != null) {
            Object resizedImage = claims.get(new URI("taf:extensions:claim:resizedimage"));
            if (resizedImage != null) {
                byte[] binaryBuff = (byte[])resizedImage;
                response.getOutputStream().write(binaryBuff);
            }
        }
    }

你看过开箱即用的“调整图像大小”模板构建块了吗?它创建具有指定尺寸的MM组件变体,看起来这正是您需要的。。。自从2008以来,Trdion就有了一个很好的问题:GLZALEX——如果您有兴趣更多地参与SDL Trdion社区,请考虑在使用堆栈溢出登录时提交SDL Trdion建议,以便将您的帐户链接起来。