在磁盘上加载图像,但不包含在XAML上的项目中 [英] Loading images on disk but not included in the project on XAML

查看:57
本文介绍了在磁盘上加载图像,但不包含在XAML上的项目中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述



我需要根据我使用的数据库为我提供的路径从磁盘加载映像.问题是:我只能在项目中包含图像的情况下加载图像,而情况并非如此.

是否可以仅使用XAML加载磁盘中但项目中未包含的映像?我该怎么做?如果仅使用XAML是不可能的,我该如何使用C#?

这是我的代码的一部分,用于在XAML上加载图像,我使用的是Telerik RadGridView for Silverlight,图像与文本块(文本的某些部分)一起加载到此网格的单元格中是巴西葡萄牙语).

Hi,

I need to load an image from disk based on a path provided for me by the database I''m using. The problem is: I can only load the image if it''s included in the project, wich will not be the case.

Is it possible to, using XAML only, load an image that is in disk but not included in the project? How can I do it? If it''s not possible using XAML only, how can I do it with C#?

Here''s the part of my code used to load the images on XAML, I''m using Telerik RadGridView for Silverlight, and the image is being loaded in a cell of this grid, together with a textblock (some parts of the text is in brazilian portuguese).

<StackPanel.Resources>
                        <AiPede:CellTemplateSelector x:Key="CellTemplateSelectorImageAndText">
                            <AiPede:CellTemplateSelector.ImageAndTextCell>
                                <DataTemplate>
                                    <StackPanel Orientation="Vertical">
                                        <Image Width="57" Height="57" HorizontalAlignment="Center" VerticalAlignment="Center" Source="{Binding Imagem}"/>
                                        <TextBlock HorizontalAlignment="Center" VerticalAlignment="Center" TextWrapping="Wrap" Text="{Binding Produto}"/>
                                    </StackPanel>
                                </DataTemplate>
                            </AiPede:CellTemplateSelector.ImageAndTextCell>
                        </AiPede:CellTemplateSelector>
                    </StackPanel.Resources>
                    <sdk:Label Content="Disponíveis" FontFamily="Portable User Interface" FontSize="14" FontWeight="Bold" Foreground="#FF686765" Name="label2" Margin="5" />
                    <telerik:RadGridView Name="rgvBebidasComAlcoolDisponiveis" ShowGroupPanel="False" Width="220" Height="383" IsReadOnly="True" AutoGenerateColumns="False">
                        <telerik:RadGridView.Columns>
                            <telerik:GridViewDataColumn Header="Produto" CellTemplateSelector="{StaticResource CellTemplateSelectorImageAndText}" Width="*"/>
                        </telerik:RadGridView.Columns>
                    </telerik:RadGridView>





Thanks in advance!

推荐答案

请参阅我对问题的评论:当然这是可能且容易的,但是您需要弄清楚自己的形象. >
如果这是位图,则通常使用以下类:System.Windows.Media.Imaging.BitmapImage:
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapimage.aspx [ ^ ].

查看上面引用的MSDN文章的末尾,并找到显示从文件加载图像的示例.您还可以从嵌入在程序集的可执行模块中的资源或任何其他类型的流中加载它.另请参见父类System.Windows.Media.Imaging.BitmapSource和其他派生类:您可能需要对图像或其他东西进行进一步处理.此外,这是WPF图像处理的核心,非常了解:
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapsource.aspx [ ^ ],
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapsource.aspx(继承层次结构) [ http://msdn.microsoft.com/en-us/library/system. windows.controls.canvas.aspx [ ^ ].

要加载它,您将需要使用类System.Windows.Markup.XamlReader:
http://msdn.microsoft.com/en-us/library/system. windows.markup.xamlreader.aspx [ ^ ].

使用它看起来像这样:
Please see my comment to the question: of course this is possible and easy, but you need to clarify what is your image.

If this is a bitmap, you usually use the class: System.Windows.Media.Imaging.BitmapImage:
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapimage.aspx[^].

Look at the end of the MSDN article referenced above and find the sample showing loading an image from file. You can also load it from a resource embedded in your assembly''s executable module or from any other kind of stream. See also the parent class System.Windows.Media.Imaging.BitmapSource and other derived classes: you might need further processing of a image or something else; besides, this is the core or WPF image processing, very good to know:
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapsource.aspx[^],
http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.bitmapsource.aspx (inheritance hierarchy)[^].

You can also use vector graphics. One of the way is using XAML files which content is the instance of some WPF Canvas (System.Windows.Controls.Canvas):
http://msdn.microsoft.com/en-us/library/system.windows.controls.canvas.aspx[^].

To load it, you would need to use the class System.Windows.Markup.XamlReader:
http://msdn.microsoft.com/en-us/library/system.windows.markup.xamlreader.aspx[^].

Using it would look like this:
Canvas image = (Canvas)XamlReader.Load(/* some instance of an input stream is passed here: file, resource or any other one */);



这种方法非常方便,因为用户可以使用许多矢量图形编辑器(尤其是Inkscape)轻松提供这样的XAML图像:
http://en.wikipedia.org/wiki/Inkscape [ http://inkscape.org/ [ ^ ].

它已导出到XAML(但请确保它能正确呈现,因为XSV与SVG相比,表达能力稍差一些,因此无法使用复杂性之类的高级功能.)

我认为矢量图形相对于位图有很多好处(在不损失质量的情况下进行缩放,不依赖于比例和较大尺寸时的质量而降低内存占用),因此可以构建WPF应用程序而根本不包含任何位图,但不包括应用程序图标和窗口标题栏图标.

—SA



This approach is very convenient, because the user can easily supply such a XAML image using a number of vector graphics editors, notably Inkscape:
http://en.wikipedia.org/wiki/Inkscape[^],
http://inkscape.org/[^].

It has export to XAML (but make sure it renders properly, because XAML has a bit less expressing capabilities compared to SVG, advanced features like fussiness cannot be used).

I think vector graphics has a lot of benefits over bitmaps (scaling without loss of quality, low memory footprint independent of scale and quality at bigger sizes), so a WPF application can be built without any bitmaps at all, excluding the application icon and window title bar icons.

—SA


[有关图像文件相对和绝对路径名的后续问题的答案:]

请查看我对您对我的解决方案1的评论的评论.

由于我在此处解释的原因,首先,在任何情况下都不能在功能齐全的应用程序中使用硬编码路径,无论这是绝对路径还是相对路径.所有路径名都应在运行时根据用户,配置文件等提供的某些数据进行计算,但重要的是,还应根据某些特殊"目录(包括当前工作目录)进行计算(在大多数情况下,我不建议正如我在对解决方案1的评论中所解释的那样,使用它,可执行文件目录(更精确地说,是入口程序集的主要可执行模块的位置)以及与用户的个人资料相关联的一些特殊文件夹".

请查看我过去的两个答案,其中提供了有关查找所有相关路径的全面说明:
如何找到我的程序目录(解决方案1) [ ^ ] ,
如何找到我的程序目录(解决方案2) [ ^ ] .

祝你好运,
—SA
[An answer to the follow-up question about relative and absolute path names for image files:]

Please see my comments to your comment to my Solution 1.

By the reasons I explained there, first of all, there are no cases when a hard-coded path can be used in a fully functional application, no matter it this is an absolute or a relative path. all path names should be calculated during run time based on some data supplied by the user, configuration files, etc., but importantly, also based on some "special" directories which include a current working directory (in most cases, I would not recommend using it, as I explained in my comment to Solution 1), executable file directory (a location of the main executable module of the entry assembly, to be more precise) and some "special folders" associated with the user''s profile.

Please see my two past answers where I provided comprehensive explanation on finding all relevant paths:
How to find my programs directory (Solution 1)[^],
How to find my programs directory (Solution 2)[^].

Good luck,
—SA


[有关图像文件相对和绝对路径名的后续问题的答案:]

如果文件是只读的,则可以使用嵌入在某些程序集的可执行模块中的资源.

不要将图像添加到目录中.创建一个.resx资源.使用添加资源" =>对其进行编辑. 添加现有文件".添加一个文件.如果文件与资源文件不在同一目录中,它将被复制到该目录中,因此请注意不要保留同一文件的多个副本.另外,此文件将被添加到项目结构中,并且其引用也将被添加到您的资源中.打开代表图像文件的项目节点的属性.您将看到它不会在构建的输出中被复制.它将放置在嵌入可执行文件中的资源中.您将在代表资源文件的节点的子节点中看到Visual Studio自动生成的代码文件.打开此文件,找到一个静态类及其静态属性,其名称类似于您在输入中使用的图像文件的名称.使用此属性访问资源;不要使用资源管理器和资源的字符串名称-这不是真正可支持的方法.

使用该属性.例如,如果您的图像文件是PNG,则该属性的类型为System.Drawing.Bitmap.您不需要匹配资源名称,从资源流中读取图像数据等.只需使用位图实例即可.

另一个好处是:它将保护您的图像不被用户修改.如果还对装配体进行签名,将几乎无法修改图像.

如您所见,这种方法仅在构建之前有一组固定文件的情况下才有用,这不是您的答案中所阐述的情况,但是我添加此解决方案只是因为您提到您将对此感兴趣问题.

—SA
[An answer to the follow-up question about relative and absolute path names for image files:]

If the files are read-only, you can instead use resources embedded in an executable module of some of your assemblies.

Don''t add an image to your directory. Create a .resx resource. Edit it by using "Add resource" => "Add existing file". Add a file. If a file was not in the same directory with the resource file, it will be copied there, so be careful not to keep multiple copies of the same file. Also, this file will be added to the project structure, and its reference will be added to your resource. Open the property of the project node representing your image file. You will see that it is not to be copied in output of the build. It will be places in resource embedded in your executable file. You will see that Visual Studio auto-generated code file, in a child node of the node representing the resource file. Open this file and locate a static class and its static property with the name resembling the name of your image file you used on input. Use this property to access the resource; don''t use resource manager and string name of the resource — this is not really supportable way.

Use the property. If, for example, your image file is PNG, the property will be of the type System.Drawing.Bitmap. You won''t need to match resource name, read image data from resource stream, etc. Just use the bitmap instance.

One more benefit: it will protect your images from modification by the user. If you also sign your assembly it would make the modification of your images nearly impossible.

As you can see, this way is only good if you have a fixed set of files prior to the build, which is not the case as formulated in your answer, but I added this solution just because you mentioned you would be interested to know this matter.

—SA


这篇关于在磁盘上加载图像,但不包含在XAML上的项目中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆