Dies ist eine C # .NET 4.0-Anwendung:
Ich binde eine Textdatei als Ressource ein und versuche dann, sie in einem Dialogfeld anzuzeigen:
var assembly = Assembly.GetExecutingAssembly();
var resourceName = "MyProj.Help.txt";
using (Stream stream = assembly.GetManifestResourceStream(resourceName))
{
using (StreamReader reader = new StreamReader(stream))
{
string result = reader.ReadToEnd();
System.Windows.Forms.MessageBox.Show(result, "MyProj", MessageBoxButtons.OK);
}
}
Die Lösung ist MyProjSolution und die ausführbare Datei ist MyProj.exe. Help.txt ist eine eingebettete Ressource. Der Stream ist jedoch null. Ich habe MyProjSolution.Help.txt und MyProjSolution.MyProj.Help.txt ausprobiert, aber nichts scheint zu funktionieren.
Antworten:
Sie können mithilfe von überprüfen, ob die Ressourcen korrekt eingebettet sind
beim Debuggen. Dadurch werden alle (vollständig qualifizierten Namen) aller Ressourcen aufgelistet, die in die Assembly eingebettet sind, in die Ihr Code geschrieben ist.
Siehe Assembly.GetManifestResourceNames () auf MSDN.
Kopieren Sie einfach den entsprechenden Namen und verwenden Sie diesen anstelle dessen, was Sie in der Variablen 'resourceName' definiert haben.
Hinweise - Der Ressourcenname unterscheidet zwischen Groß- und Kleinschreibung. Wenn Sie die Ressourcendatei falsch eingebettet haben, wird sie nicht in der Liste angezeigt, die vom Aufruf von GetManifestResourceNames () zurückgegeben wird. Stellen Sie außerdem sicher, dass Sie die Ressource aus der richtigen Assembly lesen (wenn mehrere Assemblys verwendet werden). Es ist allzu einfach, die Ressourcen aus der aktuell ausgeführten Assembly und nicht aus einer Assembly zu beziehen, auf die verwiesen wird.
BEARBEITEN - .NET Core In
diesem SO-Beitrag finden Sie Details zum Einbetten mit .NET Core.
Das Abrufen der Manifestinformationen sieht ähnlich aus. Verwenden Sie
this.GetType().GetTypeInfo().Assembly.GetManifestResourceNames()
diese Option, um das Manifest von der Assembly abzurufen, in der der Code ausgeführt wird.Ich habe noch nicht herausgefunden, wie man das Äquivalent zu
Assembly.GetExecutingAssembly()
.NET Core macht! Wenn jemand weiß - bitte lassen Sie es mich wissen und ich werde diese Antwort aktualisieren.quelle
Bei einem ähnlichen Problem wurde zuerst überprüft, ob die Datei in Ihrem Projekt enthalten ist. Gehen Sie dann zu den Eigenschaften und setzen Sie die Erstellungsaktion dieser Datei auf Eingebettete Ressource. das hat bei mir funktioniert.
quelle
DefatultNameSpace.Infrastructure.Help.txt
. Standard-Namespace auf Ihrer Projekteigenschaftenseite undInfrastructure
wäre der Ordner, in dem Sie sich befindenDie Eigenschaft "Build Action" der eingebetteten Datei sollte als "Embedded Resource" festgelegt werden, damit die unten angegebene Zeile ordnungsgemäß ausgeführt wird:
Klicken Sie mit der rechten Maustaste auf die Datei, klicken Sie auf die Eigenschaft und legen Sie die Eigenschaft "Build Action" als "Embedded Resource" fest:
quelle
Hier ist die Ursache für meinen Nullwert.
http://adrianmejia.com/blog/2011/07/18/cs-getmanifestresourcestream-gotcha/
Die
GetManifestResourceStream
Methode wird immer zurückgegeben,NULL
wenn die Eigenschaft "Erstellte Aktion" der Ressource nicht auf "Eingebettete Ressource" festgelegt ist.Nachdem Sie diese Eigenschaft mit allen erforderlichen Dateien festgelegt haben, wird
assembly.GetManifestResourceStream
stattdessen der richtige Stream zurückgegebenNULL
.quelle
Nur eine Warnung.
Ich konnte nicht auf meine Datei als eingebettete Ressource zugreifen, obwohl ich angegeben habe, dass dies der Fall ist und obwohl diese Build Action-Eigenschaft vorhanden ist. Ich habe viel Zeit damit verschwendet, meinen Kopf zu schlagen. Ich habe eine csharp-Codedatei eingebettet, an deren Namen (xxx.cs.txt) .txt angehängt ist. Aus irgendeinem Grund sehen die Methoden GetManifestResourceNames () und GetManifestResourceStream () keine Datei mit .cs im Namen.
Ich habe es einfach in xxx.txt umbenannt und alles war in Ordnung.
Seltsam.
quelle
Resource
aber nichtEmbedded Resource
, was es noch seltsamer macht ... Wenn Sie es.cs.
aus dem Namen entfernen , funktioniert es. Argh.Ich hatte das gleiche Problem, dank Jay fand ich, dass es Bindestriche im Verzeichnisnamen waren.
ProjectName.ResourceFolder.Sub-Directory
wird,ProjectName.ResourceFolder.Sub_Directory
wenn Sie auf den Ressourcenstrom verweisen.quelle
In meinem Fall bestand das Problem darin, dass sich der Code, der nach der Ressource suchte, in einem anderen Projekt befand als die Ressource selbst.
Sie können nur auf Ressourcen zugreifen, die sich in demselben Projekt befinden, in dem sich der Code befindet. Ich dachte, ich könnte alle meine Ressourcen in das Webseitenprojekt einfügen, aber ich brauche auch Bilder im E-Mail-Projekt.
Hoffe das hilft jemandem in der gleichen Situation wie ich.
Ich finde wirklich nützliche Anrufe
Assembly.GetExecutingAssembly().GetManifestResourceNames();
.quelle
Wenn es anderen hilft, stellen Sie sicher, dass die
Assembly.GetExecutingAssembly()
Leitung von derselben Assembly aufgerufen wird, in die Ressourcen eingebettet sind.quelle
Eine einfache und optimierte Lösung besteht darin, diese Basisklasse zu haben :
Wenn Sie dann eine Ressource hinzufügen, erstellen Sie eine C # -Klasse für Leser im selben Ordner:
wo die Leserklasse MyResource.cs sehr einfach ist:
Jede Ressource verfügt also über eine "Schatten" -Klasse, die weiß, wie man sie richtig liest.
So lesen Sie die Ressource in Ihrem Code:
Vergessen Sie nicht, wie in anderen Antworten vorgeschlagen, "Eingebettete Ressource" in der Eigenschaft "Aktion erstellen" der Ressourcendatei festzulegen.
Der Vorteil dieser einheitlichen Lösung ist
quelle
quelle
Sie müssen Ihre Lösung entladen. Bearbeiten Sie dann das Projekt. Suchen Sie Ihren Ordner und ändern Sie ihn wie folgt:
quelle
Obwohl OP GetManifestResourceStream dazu gebracht hat, NULL von Ressourcen in derselben Assembly zurückzugeben, wurde in einigen Antworten darauf hingewiesen, dass Ressourcen in einem anderen Projekt oder einer anderen Assembly nicht abgerufen werden können und eine gute Ursache dafür sind, dass GetManifestResourceStream NULL zurückgibt.
Dies gilt zumindest seit 2011 nicht mehr; Wie ich in einigen Kommentaren an anderer Stelle erwähnt habe, machen Assembly.LoadFrom () oder typeof den Trick und als Ergebnis können Sie auf Ressourcen zugreifen, die sich in einem anderen Projekt befinden.
Ich habe hier ein mäßig komplexes Beispiel zu veranschaulichen; Das ist mein Testaufbau:
Weg zu einem anderen Projekt:
Hier aufgenommen:
Und auf Form1.cs von WinFormFramework spezifiziere ich mit
so wie das:
Und das Ergebnis wird im Textfeld angezeigt:
Ich habe mehrere Stunden damit verbracht, es richtig zu machen. Dafür musste ich bei Immediate Window viel verwenden:
Hoffe es hilft jemandem
quelle
Möglicherweise müssen Sie den Pfad zu Ihrer txt-Datei im
GetManifestResourceStream
Parameter angeben , oder Sie können versuchen, die txt-Datei im selben Verzeichnis wie Ihre ausführbare Datei zu speichern. Hoffentlich hilft das!quelle