Related
I have created a 3D game in unity using a asset and I need help changing the save feature so I can save the game in a Sqlite database, any tutorials or videos that could help?
This is the script that is provided to save the game and to load it, im not exactly sure where this is saving to but it seems to save somewhere locally.
using System;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Collections;
using System.Collections.Generic;
using System.Threading.Tasks;
using Newtonsoft.Json.Linq;
using ThunderWire.JsonManager;
using ThunderWire.Helpers;
using HFPS.Prefs;
using UnityEngine;
[Serializable]
public class SaveableDataPair
{
public enum DataBlockType { ISaveable, Attribute }
public DataBlockType BlockType = DataBlockType.ISaveable;
public string BlockKey;
public MonoBehaviour Instance;
public string[] FieldData;
public SaveableDataPair(DataBlockType type, string key, MonoBehaviour instance, string[] fileds)
{
BlockType = type;
BlockKey = key;
Instance = instance;
FieldData = fileds;
}
}
/// <summary>
/// Main script for Save/Load System
/// </summary>
public class SaveGameHandler : Singleton<SaveGameHandler> {
public SaveLoadScriptable SaveLoadSettings;
[Tooltip("Serialize player data between scenes.")]
public bool dataBetweenScenes;
[Tooltip("Not necessary, if you does not want Fade when scene starts or switch, leave this blank.")]
public UIFadePanel fadeControl;
public SaveableDataPair[] saveableDataPairs;
private ItemSwitcher switcher;
private Inventory inventory;
private ObjectiveManager objectives;
private GameObject player;
[HideInInspector]
public string lastSave;
void Start()
{
inventory = GetComponent<Inventory>();
objectives = GetComponent<ObjectiveManager>();
player = GetComponent<HFPS_GameManager>().Player;
switcher = player.GetComponentInChildren<ScriptManager>().GetScript<ItemSwitcher>();
JsonManager.Settings(SaveLoadSettings, true);
if (saveableDataPairs.Any(pair => pair.Instance == null))
{
Debug.LogError("[SaveGameHandler] Some of Saveable Instances are missing or it's destroyed. Please select Setup SaveGame again from the Tools menu!");
return;
}
if (Prefs.Exist(Prefs.LOAD_STATE))
{
int loadstate = Prefs.Game_LoadState();
if(loadstate == 0)
{
DeleteNextLvlData();
}
else if (loadstate == 1 && Prefs.Exist(Prefs.LOAD_SAVE_NAME))
{
string filename = Prefs.Game_SaveName();
if (File.Exists(JsonManager.GetFilePath(FilePath.GameSavesPath) + filename))
{
JsonManager.DeserializeData(filename);
string loadScene = (string)JsonManager.Json()["scene"];
lastSave = filename;
if (UnityEngine.SceneManagement.SceneManager.GetActiveScene().name == loadScene)
{
LoadSavedSceneData(true);
}
}
else
{
Debug.Log("<color=yellow>[SaveGameHandler]</color> Could not find load file: " + filename);
Prefs.Game_LoadState(0);
}
}
else if(loadstate == 2 && Prefs.Exist(Prefs.LOAD_SAVE_NAME) && dataBetweenScenes)
{
JsonManager.ClearArray();
Prefs.Game_SaveName("_NextSceneData.sav");
if (File.Exists(JsonManager.GetFilePath(FilePath.GameDataPath) + "_NextSceneData.sav"))
{
JsonManager.DeserializeData(FilePath.GameDataPath, "_NextSceneData.sav");
LoadSavedSceneData(false);
}
}
}
}
void DeleteNextLvlData()
{
if (File.Exists(JsonManager.GetFilePath(FilePath.GameDataPath) + "_NextSceneData.sav"))
{
File.Delete(JsonManager.GetFilePath(FilePath.GameDataPath) + "_NextSceneData.sav");
}
}
/* SAVE GAME SECTION */
public void SaveGame(bool allData)
{
JsonManager.ClearArray();
Dictionary<string, object> playerData = new Dictionary<string, object>();
Dictionary<string, object> slotData = new Dictionary<string, object>();
Dictionary<string, object> shortcutData = new Dictionary<string, object>();
Dictionary<string, object> objectivesData = new Dictionary<string, object>();
/* PLAYER PAIRS */
if (allData)
{
JsonManager.AddPair("scene", UnityEngine.SceneManagement.SceneManager.GetActiveScene().name);
JsonManager.AddPair("dateTime", DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss"));
playerData.Add("playerPosition", player.transform.position);
playerData.Add("cameraRotation", player.GetComponentInChildren<MouseLook>().GetRotation());
}
playerData.Add("playerHealth", player.GetComponent<HealthManager>().Health);
/* END PLAYER PAIRS */
/* ITEMSWITCHER PAIRS */
Dictionary<string, object> switcherData = new Dictionary<string, object>
{
{ "switcherActiveItem", switcher.currentItem },
{ "switcherLightObject", switcher.currentLightObject },
{ "switcherWeaponItem", switcher.weaponItem }
};
foreach (var Item in switcher.ItemList)
{
Dictionary<string, object> ItemInstances = new Dictionary<string, object>();
foreach (var Instance in Item.GetComponents<MonoBehaviour>().Where(x => typeof(ISaveableArmsItem).IsAssignableFrom(x.GetType())).ToArray())
{
ItemInstances.Add(Instance.GetType().Name.Replace(" ", "_"), (Instance as ISaveableArmsItem).OnSave());
switcherData.Add("switcher_item_" + Item.name.ToLower().Replace(" ", "_"), ItemInstances);
}
}
/* END ITEMSWITCHER PAIRS */
/* INVENTORY PAIRS */
foreach (var slot in inventory.Slots)
{
if (slot.GetComponent<InventorySlot>().itemData != null)
{
InventoryItemData itemData = slot.GetComponent<InventorySlot>().itemData;
Dictionary<string, object> itemDataArray = new Dictionary<string, object>
{
{ "slotID", itemData.slotID },
{ "itemID", itemData.item.ID },
{ "itemAmount", itemData.m_amount },
{ "itemData", itemData.customData }
};
slotData.Add("inv_slot_" + inventory.Slots.IndexOf(slot), itemDataArray);
}
else
{
slotData.Add("inv_slot_" + inventory.Slots.IndexOf(slot), "null");
}
}
Dictionary<string, object> inventoryData = new Dictionary<string, object>
{
{ "inv_slots_count", inventory.Slots.Count },
{ "slotsData", slotData }
};
/* INVENTORY SHORTCUTS PAIRS */
if (inventory.Shortcuts.Count > 0)
{
Dictionary<string, object> shortcutsData = new Dictionary<string, object>();
foreach (var shortcut in inventory.Shortcuts)
{
Dictionary<string, object> shortcutsDataPairs = new Dictionary<string, object>
{
{ "itemID", shortcut.item.ID },
{ "shortcutKey", shortcut.shortcutKey.ToString() }
};
shortcutsData.Add("shortcut_" + shortcut.slot, shortcutsDataPairs);
}
inventoryData.Add("shortcutsData", shortcutsData);
}
/* INVENTORY FIXED CONTAINER PAIRS */
if (inventory.FixedContainerData.Count > 0)
{
inventoryData.Add("fixedContainerData", inventory.GetFixedContainerData());
}
/* END INVENTORY PAIRS */
/* OBJECTIVE PAIRS */
if (objectives.objectiveCache.Count > 0)
{
foreach (var obj in objectives.objectiveCache)
{
Dictionary<string, object> objectiveData = new Dictionary<string, object>
{
{ "toComplete", obj.toComplete },
{ "isCompleted", obj.isCompleted }
};
objectivesData.Add(obj.identifier.ToString(), objectiveData);
}
}
/* END OBJECTIVE PAIRS */
//Add data pairs to serialization buffer
JsonManager.AddPair("playerData", playerData);
JsonManager.AddPair("itemSwitcherData", switcherData);
JsonManager.AddPair("inventoryData", inventoryData);
JsonManager.AddPair("objectivesData", objectivesData);
//Add all saveables
if (allData && saveableDataPairs.Length > 0)
{
foreach (var Pair in saveableDataPairs)
{
if(Pair.BlockType == SaveableDataPair.DataBlockType.ISaveable)
{
var data = (Pair.Instance as ISaveable).OnSave();
if (data != null)
{
JsonManager.AddPair(Pair.BlockKey, data);
}
}
else if (Pair.BlockType == SaveableDataPair.DataBlockType.Attribute)
{
Dictionary<string, object> attributeFieldPairs = new Dictionary<string, object>();
if (Pair.FieldData.Length > 0)
{
foreach (var Field in Pair.FieldData)
{
FieldInfo fieldInfo = Pair.Instance.GetType().GetField(Field);
if (fieldInfo.FieldType == typeof(Color) || fieldInfo.FieldType == typeof(KeyCode))
{
if (fieldInfo.FieldType == typeof(Color))
{
attributeFieldPairs.Add(GetAttributeKey(fieldInfo), string.Format("#{0}", ColorUtility.ToHtmlStringRGBA((Color)Pair.Instance.GetType().InvokeMember(Field, BindingFlags.GetField, null, Pair.Instance, null))));
}
else
{
attributeFieldPairs.Add(GetAttributeKey(fieldInfo), Pair.Instance.GetType().InvokeMember(Field, BindingFlags.GetField, null, Pair.Instance, null).ToString());
}
}
else
{
attributeFieldPairs.Add(GetAttributeKey(fieldInfo), Pair.Instance.GetType().InvokeMember(Field, BindingFlags.GetField, null, Pair.Instance, null));
}
}
}
else
{
Debug.LogError("Empty Fields Data: " + Pair.BlockKey);
}
JsonManager.AddPair(Pair.BlockKey, attributeFieldPairs);
}
}
}
//Serialize all pairs from buffer
SerializeSaveData(!allData);
}
/* LOAD SECTION */
void LoadSavedSceneData(bool allData)
{
if (allData)
{
var posToken = JsonManager.Json()["playerData"]["playerPosition"];
player.transform.position = posToken.ToObject<Vector3>();
var rotToken = JsonManager.Json()["playerData"]["cameraRotation"];
player.GetComponentInChildren<MouseLook>().SetRotation(rotToken.ToObject<Vector2>());
}
var healthToken = JsonManager.Json()["playerData"]["playerHealth"];
player.GetComponent<HealthManager>().Health = (float)healthToken;
switcher.currentLightObject = (int)JsonManager.Json()["itemSwitcherData"]["switcherLightObject"];
switcher.weaponItem = (int)JsonManager.Json()["itemSwitcherData"]["switcherWeaponItem"];
//Deserialize ItemSwitcher Item Data
foreach (var Item in switcher.ItemList)
{
JToken ItemToken = JsonManager.Json()["itemSwitcherData"]["switcher_item_" + Item.name.ToLower().Replace(" ", "_")];
foreach (var Instance in Item.GetComponents<MonoBehaviour>().Where(x => typeof(ISaveableArmsItem).IsAssignableFrom(x.GetType())).ToArray())
{
(Instance as ISaveableArmsItem).OnLoad(ItemToken[Instance.GetType().Name.Replace(" ", "_")]);
}
}
//Deserialize ItemSwitcher ActiveItem
int switchID = (int)JsonManager.Json()["itemSwitcherData"]["switcherActiveItem"];
if (switchID != -1)
{
switcher.ActivateItem(switchID);
}
//Deserialize Inventory Data
StartCoroutine(DeserializeInventory(JsonManager.Json()["inventoryData"]));
//Deserialize Objectives
if (JsonManager.HasKey("objectivesData"))
{
Dictionary<int, Dictionary<string, string>> objectivesData = JsonManager.Json<Dictionary<int, Dictionary<string, string>>>(JsonManager.Json()["objectivesData"].ToString());
foreach (var obj in objectivesData)
{
objectives.AddObjectiveModel(new ObjectiveModel(obj.Key, int.Parse(obj.Value["toComplete"]), bool.Parse(obj.Value["isCompleted"])));
}
}
//Deserialize saveables
if (allData)
{
foreach (var Pair in saveableDataPairs)
{
JToken token = JsonManager.Json()[Pair.BlockKey];
if (token == null) continue;
if (Pair.BlockType == SaveableDataPair.DataBlockType.ISaveable)
{
if (Pair.Instance.GetType() == typeof(SaveObject) && (Pair.Instance as SaveObject).saveType == SaveObject.SaveType.ObjectActive)
{
bool enabled = token["obj_enabled"].ToObject<bool>();
Pair.Instance.gameObject.SetActive(enabled);
}
else
{
(Pair.Instance as ISaveable).OnLoad(token);
}
}
else if (Pair.BlockType == SaveableDataPair.DataBlockType.Attribute)
{
foreach (var Field in Pair.FieldData)
{
SetValue(Pair.Instance, Pair.Instance.GetType().GetField(Field), JsonManager.Json()[Pair.BlockKey][GetAttributeKey(Pair.Instance.GetType().GetField(Field))]);
}
}
}
}
}
/* LOAD SECTION INVENTORY */
private IEnumerator DeserializeInventory(JToken token)
{
yield return new WaitUntil(() => inventory.Slots.Count > 0);
int slotsCount = (int)token["inv_slots_count"];
int neededSlots = slotsCount - inventory.Slots.Count;
if(neededSlots != 0)
{
inventory.ExpandSlots(neededSlots);
}
for (int i = 0; i < inventory.Slots.Count; i++)
{
JToken slotToken = token["slotsData"]["inv_slot_" + i];
string slotString = slotToken.ToString();
if (slotString != "null")
{
inventory.AddItemToSlot((int)slotToken["slotID"], (int)slotToken["itemID"], (int)slotToken["itemAmount"], slotToken["itemData"].ToObject<CustomItemData>());
}
}
//Deserialize Shortcuts
if (token["shortcutsData"] != null && token["shortcutsData"].HasValues)
{
Dictionary<string, Dictionary<string, string>> shortcutsData = token["shortcutsData"].ToObject<Dictionary<string, Dictionary<string, string>>>();
foreach (var shortcut in shortcutsData)
{
int slot = int.Parse(shortcut.Key.Split('_')[1]);
inventory.ShortcutBind(int.Parse(shortcut.Value["itemID"]), slot, (KeyCode)Enum.Parse(typeof(KeyCode), shortcut.Value["shortcutKey"]));
}
}
//Deserialize FixedContainer
if (token["fixedContainerData"] != null && token["fixedContainerData"].HasValues)
{
var fixedContainerData = token["fixedContainerData"].ToObject<Dictionary<int, JToken>>();
foreach (var item in fixedContainerData)
{
inventory.FixedContainerData.Add(new ContainerItemData(inventory.GetItem(item.Key), (int)item.Value["item_amount"], item.Value["item_custom"].ToObject<CustomItemData>()));
}
}
}
string GetAttributeKey(FieldInfo Field)
{
SaveableField saveableAttr = Field.GetCustomAttributes(typeof(SaveableField), false).Cast<SaveableField>().SingleOrDefault();
if (string.IsNullOrEmpty(saveableAttr.CustomKey))
{
return Field.Name.Replace(" ", string.Empty);
}
else
{
return saveableAttr.CustomKey;
}
}
void SetValue(object instance, FieldInfo fInfo, JToken token)
{
Type type = fInfo.FieldType;
string value = token.ToString();
if (type == typeof(string)) fInfo.SetValue(instance, value);
if (type == typeof(int)) fInfo.SetValue(instance, int.Parse(value));
if (type == typeof(uint)) fInfo.SetValue(instance, uint.Parse(value));
if (type == typeof(long)) fInfo.SetValue(instance, long.Parse(value));
if (type == typeof(ulong)) fInfo.SetValue(instance, ulong.Parse(value));
if (type == typeof(float)) fInfo.SetValue(instance, float.Parse(value));
if (type == typeof(double)) fInfo.SetValue(instance, double.Parse(value));
if (type == typeof(bool)) fInfo.SetValue(instance, bool.Parse(value));
if (type == typeof(char)) fInfo.SetValue(instance, char.Parse(value));
if (type == typeof(short)) fInfo.SetValue(instance, short.Parse(value));
if (type == typeof(byte)) fInfo.SetValue(instance, byte.Parse(value));
if (type == typeof(Vector2)) fInfo.SetValue(instance, token.ToObject(type));
if (type == typeof(Vector3)) fInfo.SetValue(instance, token.ToObject(type));
if (type == typeof(Vector4)) fInfo.SetValue(instance, token.ToObject(type));
if (type == typeof(Quaternion)) fInfo.SetValue(instance, token.ToObject(type));
if (type == typeof(KeyCode)) fInfo.SetValue(instance, Parser.Convert<KeyCode>(value));
if (type == typeof(Color)) fInfo.SetValue(instance, Parser.Convert<Color>(value));
}
public void SaveNextSceneData(string scene)
{
Prefs.Game_LoadState(2);
Prefs.Game_LevelName(scene);
JsonManager.ClearArray();
SaveGame(false);
}
async void SerializeSaveData(bool betweenScenes)
{
string filepath = JsonManager.GetFilePath(FilePath.GameSavesPath);
GetComponent<HFPS_GameManager>().ShowSaveNotification();
if (!betweenScenes)
{
if (Directory.Exists(filepath))
{
DirectoryInfo di = new DirectoryInfo(filepath);
FileInfo[] fi = di.GetFiles("Save?.sav");
if (fi.Length > 0)
{
string SaveName = "Save" + fi.Length;
lastSave = SaveName + ".sav";
FileStream file = new FileStream(JsonManager.GetCurrentPath() + SaveName + ".sav", FileMode.OpenOrCreate);
await Task.Run(() => JsonManager.SerializeJsonDataAsync(file));
}
else
{
lastSave = "Save0.sav";
FileStream file = new FileStream(JsonManager.GetCurrentPath() + "Save0.sav", FileMode.OpenOrCreate);
await Task.Run(() => JsonManager.SerializeJsonDataAsync(file));
}
}
else
{
Directory.CreateDirectory(JsonManager.GetCurrentPath());
lastSave = "Save0.sav";
FileStream file = new FileStream(JsonManager.GetCurrentPath() + "Save0.sav", FileMode.OpenOrCreate);
await Task.Run(() => JsonManager.SerializeJsonDataAsync(file));
}
Prefs.Game_SaveName(lastSave);
DeleteNextLvlData();
}
else
{
DeleteNextLvlData();
FileStream file = new FileStream(JsonManager.GetFilePath(FilePath.GameDataPath) + "_NextSceneData.sav", FileMode.OpenOrCreate);
await Task.Run(() => JsonManager.SerializeJsonDataAsync(file, true));
}
}
}
Firstly, please research your structure. You have created a game based on an FPS kit, yes? This means that you have a working game, and save features are typically applied with XML or similar formats.
I recommend utilising C# (Unity's native tongue) to implement something like the MySQL Connector for .NET/Mono and translate the elements. I'm not sure if the kit you used has the features baked in, but if you have access to the source (.cs) then you can see where it is saving, and possibly create a DB structure.
What I would look at are the following components:
Table Structure
What are you storing?
The most common components are Inventory items (ammo, life, stamina, consumables, etc.). To store these, perhaps use a loading system to identify each inventory item by a code (like Bethesda's Hex Cell IDs).
How are you storing it? How much data is needed?
Normalisation
Always avoid duplicate values
Always reference things where possible instead of creating a new value (change the value once, change it everywhere)
There's a lot to think about, but before jumping into copying and pasting code, please read up on proper database procedures - it'll help you out a lot :)
Some reading material:
https://medium.com/#rizasif92/sqlite-and-unity-how-to-do-it-right-31991712190
http://findnerd.com/list/view/How-to-save-data-in-SQLite-in-Unity3d/6357/
https://www.essentialsql.com/get-ready-to-learn-sql-database-normalization-explained-in-simple-english/
Best of luck!
I'm trying to read the mime type in GWT client side in order to validate a file before upload it. To do this I use JSNI to read the file header using HTML5 filereader API. However my problem is that GWT does not wait for the result of the reading and continue the code execution. The side effect is that my boolean is not set yet and my condition goes wrong. Is there any mechanism like promise implemented in GWT?
Any help on this would be much appreciated!
UploadImageButtonWidget.java
private boolean isMimeTypeValid = false;
private String mimeType = null;
public native boolean isValid(Element element)/*-{
var widget = this;
var files = element.files;
var reader = new FileReader();
var CountdownLatch = function (limit){
this.limit = limit;
this.count = 0;
this.waitBlock = function (){};
};
CountdownLatch.prototype.countDown = function (){
this.count = this.count + 1;
if(this.limit <= this.count){
return this.waitBlock();
}
};
CountdownLatch.prototype.await = function(callback){
this.waitBlock = callback;
};
var barrier = new CountdownLatch(1);
reader.readAsArrayBuffer(files[0]);
reader.onloadend = function(e) {
var arr = (new Uint8Array(e.target.result)).subarray(0, 4);
var header = "";
for (var i = 0; i < arr.length; i++) {
header += arr[i].toString(16);
}
widget.#com.portal.client.widgets.base.UploadImageButtonWidget::setMimeType(Ljava/lang/String;)(header);
barrier.countDown();
}
return barrier.await(function(){
return widget.#com.portal.client.widgets.base.UploadImageButtonWidget::isMimeTypeValid();
});
}-*/
public void setMimeType(String headerString) {
boolean mimeValid = true;
if (headerString.equalsIgnoreCase(PNG_HEADER)) {
mimeType = PNG_MIMETYPE;
} else if (headerString.equalsIgnoreCase(GIF_HEADER)) {
mimeType = GIF_MIMETYPE;
} else if (headerString.equalsIgnoreCase(JPG_HEADER1) || headerString.equalsIgnoreCase(JPG_HEADER2) || headerString.equalsIgnoreCase(JPG_HEADER3)) {
mimeType = JPG_MIMETYPE;
} else {
mimeValid = false;
setValidationError(i18n.uploadErrorNotImageBasedOnMimeType());
fileChooser.getElement().setPropertyJSO("files", null);
setErrorStatus();
}
setMimeTypeValid(mimeValid);
}
public boolean isMimeTypeValid() {
GWT.log("mimeType" + mimeType);
GWT.log("isMimetypeValid" + String.valueOf(isMimeTypeValid));
return mimeType != null;
}
in the activity:
public void validateAndUpload() {
UploadImageButtonWidget uploadImageButtonWidget = view.getUpload();
if (uploadImageButtonWidget.isValid()) {
GWT.log("mime ok: will be uploaded");
uploadImage();
} else {
GWT.log("mime not ok: will not be uploaded");
}
}
We have a requirement that is we need to access onedirve through asp.net/C# and need to get the latest uploaded file..?
Please help me how to solve this type of requirement..?
i tried the following code..
i used following namespaces. but didn't work
using Microsoft.Live.Web.Samples.ConnectAppUserWithMSAccount.Filters;
using Microsoft.Live.Web.Samples.ConnectAppUserWithMSAccount.Models;
private LiveAuthClient MSAuthClient
{
get
{
if (this.liveAuthClient == null)
{
IDictionary<int, string> secretMap = new Dictionary<int, string>();
secretMap.Add(ClientSecretKey, ClientSecret);
this.liveAuthClient = new LiveAuthClient(ClientId, secretMap, null, this);
}
return this.liveAuthClient;
}
}
private MSAccountStatus MSAccountStatus
{
get
{
if (this.msAccountStatus == Controllers.MSAccountStatus.None)
{
using (UsersContext db = new UsersContext())
{
MSAccount msAccount = db.MSAccounts.FirstOrDefault(u => u.UserName == this.User.Identity.Name);
this.msAccountStatus = msAccount != null ? MSAccountStatus.Connected : MSAccountStatus.NotConnected;
}
}
if (this.msAccountStatus == MSAccountStatus.Connected)
{
LiveConnectSession session = this.MSAuthClient.Session;
if (session == null || session.Expires < DateTimeOffset.UtcNow)
{
this.msAccountStatus = MSAccountStatus.ConnectedWithError;
}
}
return this.msAccountStatus;
}
}
I am creating Multimedia components using core service and everything is working fine. But when Metadata schema fields are defined on the Multimedia schema using which I am creating my Multimedia components then I am getting following error:-
Unable to find http://www.tridion.com/ContentManager/5.0/DefaultMultimediaSchema:Metadata.
This message is displayed when I have given Default Multimedia schema's TCM ID for Multimedia component. As metadata fields are saved in Tridion Database so I first have to retrieve these fields from broker or what is the best solution for this, please suggest. Below is the sample code. Please modify it if someone have any idea for providing default value for metadatafields and how to retrieve them (with/without querying broker DB):-
public static string UploadMultiMediaComponent(string folderUri, string title, string schemaID)
{
core_service.ServiceReference1.SessionAwareCoreService2010Client client = new SessionAwareCoreService2010Client();
client.ClientCredentials.Windows.ClientCredential.UserName = "myUserName";
client.ClientCredentials.Windows.ClientCredential.Password = "myPassword"; client.Open();
ComponentData multimediaComponent = (ComponentData)client.GetDefaultData(
ItemType.Component, folderUri);
multimediaComponent.Title = title;
multimediaComponent.ComponentType = ComponentType.Multimedia;
multimediaComponent.Schema.IdRef =schemaID;
//multimediaComponent.Metadata = "";
StreamUpload2010Client streamClient = new StreamUpload2010Client();
FileStream objfilestream = new FileStream(#"\My Documents\images.jpg",
FileMode.Open, FileAccess.Read);
string tempLocation = streamClient.UploadBinaryContent("images.jpg",
objfilestream);
BinaryContentData binaryContent = new BinaryContentData();
binaryContent.UploadFromFile = tempLocation;
binaryContent.Filename = "images.jpg";
binaryContent.MultimediaType = new LinkToMultimediaTypeData()
{
// for jpg file
IdRef = "tcm:0-2-65544"
};
multimediaComponent.BinaryContent = binaryContent;
IdentifiableObjectData savedComponent = client.Save(multimediaComponent,
new ReadOptions());
client.CheckIn(savedComponent.Id, null);
streamClient.Close();
client.Close();
Console.WriteLine(savedComponent.Id);
//}
}
I don't know why your code not working but following code is working for me
public static ComponentData GenerateMultiMediaComponent(TridionGeneration tridionGeneration, XmlData newsArticle, string componentName)
{
try
{
Dictionary<string, object> dicTridion = Common.GetTridionObject(tridionGeneration.client, ItemType.Component, tridionGeneration.Settings.ComponentFolderUri, componentName);
int objectCount = (int)dicTridion["count"];
SchemaFieldsData schemaFields = tridionGeneration.client.ReadSchemaFields(tridionGeneration.Settings.SchemaUri, true, new ReadOptions());
ComponentData componentData = (ComponentData)tridionGeneration.client.GetDefaultData(ItemType.Component, tridionGeneration.Settings.ComponentFolderUri);
if (schemaFields.Fields != null)
{
var fields = Fields.ForContentOf(schemaFields);
Helper.FillSchemaFields(tridionGeneration, fields);
componentData.Content = fields.ToString();
}
if (schemaFields.MetadataFields != null)
{
var metafields = Fields.ForMetadataOf(schemaFields, componentData);
Helper.FillSchemaFields(tridionGeneration, metafields);
componentData.Metadata = metafields.ToString();
}
componentData.Title = (objectCount == 0) ? componentName : componentName + " " + (objectCount + 1).ToString();
componentData.ComponentType = ComponentType.Multimedia;
StreamUpload2010Client streamClient = new StreamUpload2010Client();
FileStream objfilestream = new FileStream(#"[IMAGE_PATH]", FileMode.Open, FileAccess.Read);
string tempLocation = streamClient.UploadBinaryContent("images.jpg", objfilestream);
BinaryContentData binaryContent = new BinaryContentData();
binaryContent.UploadFromFile = tempLocation;
binaryContent.Filename = "[IMAGE_NAME]";
componentData.BinaryContent = binaryContent;
binaryContent.MultimediaType = new LinkToMultimediaTypeData()
{
IdRef = "tcm:0-2-65544"
};
componentData = (ComponentData)tridionGeneration.client.Create(componentData, new ReadOptions());
return componentData;
}
catch (Exception ex)
{
return null;
}
}
Here is the Helper class:
public static class Helper
{
public static void FillSchemaFields(TridionGeneration tridionGeneration, Fields fields)
{
List<XmlData> data = XmlHelper.xmlData;
var ofield = fields.GetEnumerator();
while (ofield.MoveNext())
{
Field f = ofield.Current;
FillFieldValue(tridionGeneration, fields, f, data[0]);
}
}
private static void FillFieldValue(TridionGeneration tridionGeneration, Fields fields, Field f, XmlData data)
{
if (f.Type == typeof(MultimediaLinkFieldDefinitionData))
{
fields[f.Name].Value = tridionGeneration.Settings.DefaultImageUri;
}
else if (f.Type != typeof(EmbeddedSchemaFieldDefinitionData))
{
foreach (XmlData fieldvalue in data.Attributes)
{
if (f.Type == typeof(DateFieldDefinitionData))
{
if (fieldvalue.text.ToLower() == f.Name.ToLower())
{
fields[f.Name].Value = Convert.ToDateTime(fieldvalue.value).ToString("yyyy-MM-ddTHH:mm:ss");
}
else
{
string val = FindSchemaValue(tridionGeneration, fieldvalue.Attributes, f.Name);
if (!string.IsNullOrEmpty(val))
{
fields[f.Name].Value = Convert.ToDateTime(val).ToString("yyyy-MM-ddTHH:mm:ss");
}
}
}
else
{
if (fieldvalue.text.ToLower() == f.Name.ToLower())
{
fields[f.Name].Value = System.Net.WebUtility.HtmlEncode(fieldvalue.value);
}
else
{
string val = FindSchemaValue(tridionGeneration, fieldvalue.Attributes, f.Name);
if (!string.IsNullOrEmpty(val))
{
fields[f.Name].Value = System.Net.WebUtility.HtmlEncode(val);
}
}
}
}
}
else
{
Fields fs = f.GetSubFields();
var ofield = fs.GetEnumerator();
while (ofield.MoveNext())
{
Field ff = ofield.Current;
FillFieldValue(tridionGeneration, fs, ff, data);
}
}
}
private static string FindSchemaValue(TridionGeneration tridionGeneration, List<XmlData> data, string fieldname)
{
foreach (XmlData fieldvalue in data)
{
if (fieldvalue.text.ToLower() == fieldname.ToLower())
{
return fieldvalue.value;
}
else
{
FindSchemaValue(tridionGeneration, fieldvalue.Attributes, fieldname);
}
}
return "";
}
}
and the Fields class:
public class Fields
{
private ItemFieldDefinitionData[] definitions;
private XmlNamespaceManager namespaceManager;
private XmlElement root; // the root element under which these fields live
// at any point EITHER data OR parent has a value
private SchemaFieldsData data; // the schema fields data as retrieved from the core service
private Fields parent; // the parent fields (so we're an embedded schema), where we can find the data
public Fields(SchemaFieldsData _data, ItemFieldDefinitionData[] _definitions, string _content = null, string _rootElementName = null)
{
data = _data;
definitions = _definitions;
var content = new XmlDocument();
if (!string.IsNullOrEmpty(_content))
{
content.LoadXml(_content);
}
else
{
content.AppendChild(content.CreateElement(string.IsNullOrEmpty(_rootElementName) ? _data.RootElementName : _rootElementName, _data.NamespaceUri));
}
root = content.DocumentElement;
namespaceManager = new XmlNamespaceManager(content.NameTable);
namespaceManager.AddNamespace("custom", _data.NamespaceUri);
}
public Fields(Fields _parent, ItemFieldDefinitionData[] _definitions, XmlElement _root)
{
definitions = _definitions;
parent = _parent;
root = _root;
}
public static Fields ForContentOf(SchemaFieldsData _data)
{
return new Fields(_data, _data.Fields);
}
public static Fields ForContentOf(SchemaFieldsData _data, ComponentData _component)
{
return new Fields(_data, _data.Fields, _component.Content);
}
public static Fields ForMetadataOf(SchemaFieldsData _data, RepositoryLocalObjectData _item)
{
return new Fields(_data, _data.MetadataFields, _item.Metadata, "Metadata");
}
public string NamespaceUri
{
get { return data != null ? data.NamespaceUri : parent.NamespaceUri; }
}
public XmlNamespaceManager NamespaceManager
{
get { return parent != null ? parent.namespaceManager : namespaceManager; }
}
internal IEnumerable<XmlElement> GetFieldElements(ItemFieldDefinitionData definition)
{
return root.SelectNodes("custom:" + definition.Name, NamespaceManager).OfType<XmlElement>();
}
internal XmlElement AddFieldElement(ItemFieldDefinitionData definition)
{
var newElement = root.OwnerDocument.CreateElement(definition.Name, NamespaceUri);
XmlNodeList nodes = root.SelectNodes("custom:" + definition.Name, NamespaceManager);
XmlElement referenceElement = null;
if (nodes.Count > 0)
{
referenceElement = (XmlElement)nodes[nodes.Count - 1];
}
else
{
// this is the first value for this field, find its position in the XML based on the field order in the schema
bool foundUs = false;
for (int i = definitions.Length - 1; i >= 0; i--)
{
if (!foundUs)
{
if (definitions[i].Name == definition.Name)
{
foundUs = true;
}
}
else
{
var values = GetFieldElements(definitions[i]);
if (values.Count() > 0)
{
referenceElement = values.Last();
break; // from for loop
}
}
} // for every definition in reverse order
} // no existing values found
root.InsertAfter(newElement, referenceElement); // if referenceElement is null, will insert as first child
return newElement;
}
public IEnumerator<Field> GetEnumerator()
{
return (IEnumerator<Field>)new FieldEnumerator(this, definitions);
}
public Field this[string _name]
{
get
{
var definition = definitions.First<ItemFieldDefinitionData>(ifdd => ifdd.Name == _name);
if (definition == null) throw new ArgumentOutOfRangeException("Unknown field '" + _name + "'");
return new Field(this, definition);
}
}
public override string ToString()
{
return root.OuterXml;
}
}
public class FieldEnumerator : IEnumerator<Field>
{
private Fields fields;
private ItemFieldDefinitionData[] definitions;
// Enumerators are positioned before the first element until the first MoveNext() call
int position = -1;
public FieldEnumerator(Fields _fields, ItemFieldDefinitionData[] _definitions)
{
fields = _fields;
definitions = _definitions;
}
public bool MoveNext()
{
position++;
return (position < definitions.Length);
}
public void Reset()
{
position = -1;
}
object IEnumerator.Current
{
get
{
return Current;
}
}
public Field Current
{
get
{
try
{
return new Field(fields, definitions[position]);
}
catch (IndexOutOfRangeException)
{
throw new InvalidOperationException();
}
}
}
public void Dispose()
{
}
}
public class Field
{
private Fields fields;
private ItemFieldDefinitionData definition;
public Field(Fields _fields, ItemFieldDefinitionData _definition)
{
fields = _fields;
definition = _definition;
}
public string Name
{
get { return definition.Name; }
}
public Type Type
{
get { return definition.GetType(); }
}
public string Value
{
get
{
return Values.Count > 0 ? Values[0] : null;
}
set
{
if (Values.Count == 0) fields.AddFieldElement(definition);
Values[0] = value;
}
}
public ValueCollection Values
{
get
{
return new ValueCollection(fields, definition);
}
}
public void AddValue(string value = null)
{
XmlElement newElement = fields.AddFieldElement(definition);
if (value != null) newElement.InnerText = value;
}
public void RemoveValue(string value)
{
var elements = fields.GetFieldElements(definition);
foreach (var element in elements)
{
if (element.InnerText == value)
{
element.ParentNode.RemoveChild(element);
}
}
}
public void RemoveValue(int i)
{
var elements = fields.GetFieldElements(definition).ToArray();
elements[i].ParentNode.RemoveChild(elements[i]);
}
public IEnumerable<Fields> SubFields
{
get
{
var embeddedFieldDefinition = definition as EmbeddedSchemaFieldDefinitionData;
if (embeddedFieldDefinition != null)
{
var elements = fields.GetFieldElements(definition);
foreach (var element in elements)
{
yield return new Fields(fields, embeddedFieldDefinition.EmbeddedFields, (XmlElement)element);
}
}
}
}
public Fields GetSubFields(int i = 0)
{
var embeddedFieldDefinition = definition as EmbeddedSchemaFieldDefinitionData;
if (embeddedFieldDefinition != null)
{
var elements = fields.GetFieldElements(definition);
if (i == 0 && !elements.Any())
{
// you can always set the first value of any field without calling AddValue, so same applies to embedded fields
AddValue();
elements = fields.GetFieldElements(definition);
}
return new Fields(fields, embeddedFieldDefinition.EmbeddedFields, elements.ToArray()[i]);
}
else
{
throw new InvalidOperationException("You can only GetSubField on an EmbeddedSchemaField");
}
}
// The subfield with the given name of this field
public Field this[string name]
{
get { return GetSubFields()[name]; }
}
// The subfields of the given value of this field
public Fields this[int i]
{
get { return GetSubFields(i); }
}
}
Can you try this?
multimediaComponent.Metadata = "<Metadata/>";
I'm customizing the default workflow of build process template using TFS 2010 Team Build. There is an activity named FindMatchingFiles allows to search for specific files with a pattern defined in MatchPattern property. It works if I only specify one file extension. Example:
String.Format("{0}\\**\\\*.msi", SourcesDirectory)
But I would like to include *.exe as well. Trying following pattern but it doesn't work:
String.Format("{0}\\**\\\*.(msi|exe)", SourcesDirectory)
Anyone could show me how to correct it?
You can use String.Format("{0}\**\*.msi;{0}\**\*.exe", SourcesDirectory)
The FindMatchingFiles activity's MatchPattern property uses the
Syntax that is supported by the searchPattern argument of the Directory.GetFiles(String, String) method.
That means that you can't combine multiple extensions. You'll need to call the FindMatchingFiles activity twice. You can then combine the results of those two calls when you use them (i.e. if your results are msiFiles and exeFiles, you can use msiFiles.Concat(exeFiles) as the input to a ForEach).
However, as you can see with #antwoord's answer, the activity does actually seem to accept a semi-colon delimited list of patterns, unlike Directory.GetFiles.
FindMatchingFiles has some strange search pattern. Here is the code (decompiled using ILSpy) so you can test your search patterns without having to kick off a new build.
It contains a hardcoded root dir at the following location (Z:)
List<string> matchingDirectories = GetMatchingDirectories(#"Z:", matchPattern.Substring(0, num), 0);
Code:
using System;
using System.Collections.Generic;
using System.IO;
namespace DirectoryGetFiles
{
//// Use the FindMatchingFiles activity to find files. Specify the search criteria in the MatchPattern (String) property.
//// In this property, you can specify an argument that includes the following elements:
//// Syntax that is supported by the searchPattern argument of the Directory GetFiles(String, String) method.
////
//// ** to specify a recursive search. For example:
//// To search the sources directory for text files, you could specify something that resembles the following
//// value for the MatchPattern property: String.Format("{0}\**\*.txt", SourcesDirectory).
////
//// To search the sources directory for text files in one or more subdirectories that are called txtfiles,
//// you could specify something that resembles the following value for the MatchPattern property:
//// String.Format("{0}\**\txtfiles\*.txt", SourcesDirectory).
class Program
{
static void Main(string[] args)
{
string searchPattern = #"_PublishedWebsites\Web\Scripts\jasmine-specs**\*.js";
var results = Execute(searchPattern);
foreach (var i in results)
{
Console.WriteLine("found: {0}", i);
}
Console.WriteLine("Done...");
Console.ReadLine();
}
private static IEnumerable<string> Execute(string pattern)
{
string text = pattern;
text = text.Replace(";;", "\0");
var hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase);
string[] array = text.Split(new char[]
{
';'
}, StringSplitOptions.RemoveEmptyEntries);
for (int i = 0; i < array.Length; i++)
{
string text2 = array[i];
string text3 = text2.Replace("\0", ";");
if (IsValidPattern(text3))
{
List<string> list = ComputeMatchingPaths(text3);
if (list.Count > 0)
{
using (List<string>.Enumerator enumerator = list.GetEnumerator())
{
while (enumerator.MoveNext())
{
string current = enumerator.Current;
hashSet.Add(current);
}
goto IL_15C;
}
}
////Message = ActivitiesResources.Format("NoMatchesForSearchPattern", new object[]
}
else
{
//// Message = ActivitiesResources.Format("InvalidSearchPattern", new object[]
}
IL_15C: ;
}
return hashSet;//.OrderBy((string x) => x, FileSpec.TopDownComparer);
}
private static bool IsValidPattern(string pattern)
{
string text = "**" + Path.DirectorySeparatorChar;
int num = pattern.IndexOf(text, StringComparison.Ordinal);
return (num < 0 || (pattern.IndexOf(text, num + text.Length, StringComparison.OrdinalIgnoreCase) <= 0 && pattern.IndexOf(Path.DirectorySeparatorChar, num + text.Length) <= 0)) && pattern[pattern.Length - 1] != Path.DirectorySeparatorChar;
}
private static List<string> ComputeMatchingPaths(string matchPattern)
{
List<string> list = new List<string>();
string text = "**" + Path.DirectorySeparatorChar;
int num = matchPattern.IndexOf(text, 0, StringComparison.OrdinalIgnoreCase);
if (num >= 0)
{
List<string> matchingDirectories = GetMatchingDirectories(#"Z:", matchPattern.Substring(0, num), 0);
string searchPattern = matchPattern.Substring(num + text.Length);
using (List<string>.Enumerator enumerator = matchingDirectories.GetEnumerator())
{
while (enumerator.MoveNext())
{
string current = enumerator.Current;
list.AddRange(Directory.GetFiles(current, searchPattern, SearchOption.AllDirectories));
}
return list;
}
}
int num2 = matchPattern.LastIndexOf(Path.DirectorySeparatorChar);
if (num2 >= 0)
{
List<string> matchingDirectories2 = GetMatchingDirectories(string.Empty, matchPattern.Substring(0, num2 + 1), 0);
string searchPattern2 = matchPattern.Substring(num2 + 1);
using (List<string>.Enumerator enumerator2 = matchingDirectories2.GetEnumerator())
{
while (enumerator2.MoveNext())
{
string current2 = enumerator2.Current;
try
{
list.AddRange(Directory.GetFiles(current2, searchPattern2, SearchOption.TopDirectoryOnly));
}
catch
{
}
}
return list;
}
}
try
{
list.AddRange(Directory.GetFiles(Directory.GetCurrentDirectory(), matchPattern, SearchOption.TopDirectoryOnly));
}
catch
{
}
return list;
}
private static List<string> GetMatchingDirectories(string rootDir, string pattern, int level)
{
if (level > 129)
{
return new List<string>();
}
List<string> list = new List<string>();
int num = pattern.IndexOf('*');
if (num >= 0)
{
int num2 = pattern.Substring(0, num).LastIndexOf(Path.DirectorySeparatorChar);
string text = (num2 >= 0) ? Path.Combine(rootDir, pattern.Substring(0, num2 + 1)) : rootDir;
if (text.Equals(string.Empty))
{
text = Directory.GetCurrentDirectory();
}
int num3 = pattern.IndexOf(Path.DirectorySeparatorChar, num);
if (num3 < 0)
{
num3 = pattern.Length;
}
string searchPattern = pattern.Substring(num2 + 1, num3 - num2 - 1);
try
{
string[] directories = Directory.GetDirectories(text, searchPattern, SearchOption.TopDirectoryOnly);
if (num3 < pattern.Length - 1)
{
string pattern2 = pattern.Substring(num3 + 1);
string[] array = directories;
for (int i = 0; i < array.Length; i++)
{
string rootDir2 = array[i];
list.AddRange(GetMatchingDirectories(rootDir2, pattern2, level + 1));
}
}
else
{
list.AddRange(directories);
}
return list;
}
catch
{
return list;
}
}
string text2 = Path.Combine(rootDir, pattern);
if (text2.Equals(string.Empty))
{
list.Add(Directory.GetCurrentDirectory());
}
else
{
if (Directory.Exists(text2))
{
list.Add(Path.GetFullPath(text2));
}
}
return list;
}
}
}